Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using OUTPUT after INSERT to get value of identity column into a (non-table value) variable

Given the following simple test table:

CREATE TABLE dbo.Test
(
  Id bigint IDENTITY(1,1) NOT NULL,
  Name varchar(50) NULL
)

I would like to get the value of the identity column into a scalar variable after the INSERT using the OUTPUT clause, but this does not work:

DECLARE @InsertedId BIGINT;

INSERT INTO Test(Name) 
  OUTPUT @InsertedId=inserted.Id
  VALUES ('Michael')

-- Display resulting id for debugging
SELECT @InsertedId;
-- ...

I know I can easily do this using SCOPE_IDENTITY() after the INSERT, but is it possible to do it as part of the INSERT statement using the OUTPUT clause without resorting to a table variable?

Update, another contrived attempt that is also not legal:

-- Return the id as a result set
INSERT INTO Test(Name) 
OUTPUT inserted.Id AS TheId
VALUES ('Michael')

-- But you can't use the result set as a derived table...
SELECT TheId FROM
(
  INSERT INTO Test(Name) 
  OUTPUT inserted.Id AS TheId
  VALUES ('Michael')
)

-- ..., or you would be able to do this
SELECT TOP 1 @InsertedId=TheId
FROM
(
  INSERT INTO Test(Name) 
  OUTPUT inserted.Id AS TheId
  VALUES ('Michael')
)
like image 518
Michael Goldshteyn Avatar asked Jun 02 '11 22:06

Michael Goldshteyn


People also ask

How do I get the identity column value after insert?

Once we insert a row in a table, the @@IDENTITY function column gives the IDENTITY value generated by the statement. If we run any query that did not generate IDENTITY values, we get NULL value in the output. The SQL @@IDENTITY runs under the scope of the current session.

How do I get identity ID after insert?

@@IDENTITY returns the id of the last thing that was inserted by your client's connection to the database. IDENT_CURRENT returns the last ID that was inserted by anyone. If some other app happens to insert another row at an unforunate time, you'll get the ID of that row instead of your one.

How can I get data after insert in SQL?

If you want to add data to your SQL table, then you can use the INSERT statement. Here is the basic syntax for adding rows to your SQL table: INSERT INTO table_name (column1, column2, column3,etc) VALUES (value1, value2, value3, etc); The second line of code is where you will add the values for the rows.

How do I get the last inserted identity column value in SQL Server?

@@IDENTITY, SCOPE_IDENTITY, and IDENT_CURRENT are similar functions because they all return the last value inserted into the IDENTITY column of a table. @@IDENTITY and SCOPE_IDENTITY return the last identity value generated in any table in the current session.


2 Answers

Remember the value of the output clause is that it can return more than one record and more than one field. So you can output both the natural key and the identity for a set of data so you can also use set theory to insert multiple records into child tables. Output is very powerful and it will pay to get used to using it.

There currently is a bug in scope_identity() (see link: http://connect.microsoft.com/SQLServer/feedback/details/328811/scope-identity-sometimes-returns-incorrect-value) that Microsoft does not intend to fix. That should give you a clue as to whether you should be using output for new development even if it is a bit cludgier for single records.

like image 171
HLGEM Avatar answered Oct 18 '22 21:10

HLGEM


No, this isn't possible. An OUTPUT clause can only output into a table / table variable, or be used to identify columns for composable DML (which doesn't help). SCOPE_IDENTITY() all the way, Michael.

like image 45
Will A Avatar answered Oct 18 '22 22:10

Will A