Reputation: 7547
Let's take basic scenario where I want to insert a record during user registration only if no username exists in the database.
My question is will you create 2 separate stored procedures and make 2 calls to the database one for checking whether the username exists or not and 2nd one to actually insert into the database or will you create one stored procedure and write both the queries inside that only?
If you create one stored procedure, then my 2nd question what should you actually return from stored procedure? I normally return hard coded numbers from stored procedures and then check inside code. Is this a good practise?
Upvotes: 1
Views: 605
Reputation: 389
MERGE
statement may be helpful. Let say MERGE
is conditional INSERT
/UPDATE
. In single statement you can INSERT
new user if it does not exist or just UPDATE
it if exists.
As written by other folks: stored procedure is much better then dynamic SQL. Wrap MERGE
into CREATE PROCEDURE
.
In real world, user interaction / workflow in your app / webapp will tell you if you need one or two procedures.
Scenario A)
In scenario A do MERGE
for conditional INSERT
/UPDATE
.
Scenario B)
In scenario B you may check for login existance and then do INSERT
or (better) do INSERT
in TRY .. CATCH
block. You can do RAISERROR
in CATCH
block with useful message / state - so you can report problem with creating account by throwing "exception" from SQL (instead of return param) and catching it in your application code. This logic may be more useful in coding.
Upvotes: 0
Reputation: 70728
You could do something like:
CREATE PROCEDURE AddNewUser
(
@Username VARCHAR(30)
, @Password VARCHAR(30)
, @UserExists BIT OUTPUT
)
AS
-- CHECK IF THE USER EXISTS:
DECLARE @RowCount INT
SELECT @RowCount = COUNT(*)
FROM Users
WHERE Username = @Username
IF (@RowCount > 0)
BEGIN
SET @UserExists = 1
END
ELSE
BEGIN
SET @UserExists = 0
INSERT INTO Users
(Username, [Password])
VALUES
(@Username, @Password)
END
GO
Then in the application you could use the @UserExists parameter, 1 would indicate that the user already exists, 0 would indicate that the user did not exist and has been created.
For good practice you should use stored procedures and not inline SQL as you will be vulnerable to SQL injection attacks.
Upvotes: 1
Reputation: 60190
This operation ultimately needs to be "atomic" - the check cannot be detached from the actual creation or you might run into concurrency issues. While you can handle some of it with transactions and locking accross two or more SPs, the best way IMHO is to use one SP and perform the check at the same time (in the same statement) as the insert occurs.
I'd return a recordset with the full record of the inserted user, and raise an error if there is a name conflict.
Upvotes: 4
Reputation: 9271
I will do one stored procedure that will return the ID of the newly inserted user or -1 if no insert occured
Upvotes: 3