0% found this document useful (0 votes)
134 views

How To Insert An Auto - Increment Key Into SQL Server Table - Stack Overflow

The document is a discussion on Stack Overflow about how to insert an auto-increment key into a SQL Server table. The discussion includes: 1) Suggesting using an identity column for the primary key if possible to let the database automatically generate incrementing values. 2) If an identity column cannot be used, providing a method to manually select the max existing primary key value, increment it by 1, and insert it along with other column values in a single atomic statement to prevent duplicate keys. 3) Advising that the best long term solution is to alter the table structure to make the primary key column an identity column if possible.

Uploaded by

csalas71
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
134 views

How To Insert An Auto - Increment Key Into SQL Server Table - Stack Overflow

The document is a discussion on Stack Overflow about how to insert an auto-increment key into a SQL Server table. The discussion includes: 1) Suggesting using an identity column for the primary key if possible to let the database automatically generate incrementing values. 2) If an identity column cannot be used, providing a method to manually select the max existing primary key value, increment it by 1, and insert it along with other column values in a single atomic statement to prevent duplicate keys. 3) Advising that the best long term solution is to alter the table structure to make the primary key column an identity column if possible.

Uploaded by

csalas71
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 4

5/11/2019 How to insert an auto_increment key into SQL Server table - Stack Overflow

We now integrate with Microsoft Teams, helping you to connect your internal knowledge base with your
chat. Learn more.

How to insert an auto_increment key into SQL Server table


Asked 6 years, 10 months ago Active 3 years, 3 months ago Viewed 67k times

I want to insert rows into a table that has a unique, non auto-incremented primary key.

Is there a native SQL function to evaluate the last key and increment it or do I have to do it in two
9 steps:

key = select max(primary.key) + 1

INSERT INTO dbo.TABLE (primary.key, field1, fiels2) VALUES (KEY, value1, value2)
4

sql sql-server

edited Dec 21 '12 at 18:02 asked Dec 21 '12 at 17:41


marc_s Ruben Teixeira
610k 139 1169 269 2 6 15
1300

3 Do you mean you have an IDENTITY column on the table? If so, what precise problem are you having that is
not discussed in the documentation or the many questions on this site about using them? In a comment below
you mention an error but you haven't said exactly what it is. Ideally, please show your CREATE TABLE script,
your INSERT statement, and the resulting error message. – Pondlife Dec 21 '12 at 17:50

This thread have solved my all headache and code is compiling back. Why ppl does downvoted this? –
sandun dhammika Mar 22 '14 at 14:20

4 Answers

Judging by you comments throughout, you have a primary key on the table that is not an identity
column.
13 If your version of SQL Server is SQL 2012 you should look into sequences:
http://msdn.microsoft.com/en-us/library/ff878091.aspx

In other versions you either need to recreate the table using the IDENTITY property
By using our site, you acknowledge that you have read and understand our Cookie Policy, Privacy Policy, and our
(http://msdn.microsoft.com/en-us/library/aa933196(v=sql.80).aspx) for the primary key column or
Terms ofuse
Service. step approach.
a two

https://stackoverflow.com/questions/13994736/how-to-insert-an-auto-increment-key-into-sql-server-table 1/4
5/11/2019 How to insert an auto_increment key into SQL Server table - Stack Overflow

If you go with the two step approach you need to make sure that concurrently running inserts won't
end up using the same new value. The easiest way to do that is this is by combining the select and
the insert into one value and using the serializable table hint:

CREATE TABLE dbo.Tbl1(id INT PRIMARY KEY, val1 INT, val2 INT)

INSERT INTO dbo.Tbl1(id, val1, val2)


VALUES((SELECT ISNULL(MAX(id)+1,0) FROM dbo.Tbl1 WITH(SERIALIZABLE, UPDLOCK)), 42, 47);

SELECT * FROM dbo.Tbl1;

edited Dec 21 '12 at 22:27 answered Dec 21 '12 at 18:03


Sebastian Meine
9,488 20 29

THANK YOU!!! Now there's a solution, it´s not a function but I can manage with a sub-querie, better then a two
step procedure. Thanks. – Ruben Teixeira Dec 21 '12 at 18:18

1 SERIALIZABLE is equivalent to HOLDLOCK and is a good start but is not enough. Your query can still fail with
high concurrency. You must add UPDLOCK, TABLOCKX . The parts of a query are executed over time, and locks
are acquired over time--so the INSERT comes after the SELECT . Two clients can SELECT at the same time
with fully compatible read locks, then the second one be blocked while the first one converts to an UPDLOCK
for its INSERT , then the second one has the old value once the block is over. You need the SELECT to block
all readers! – ErikE Dec 21 '12 at 20:34

1 Ultimately, this SELECT max() + 1 pattern is not best practice and cannot be recommended. Identity columns
exist for precisely this reason. Use them. – ErikE Dec 21 '12 at 20:35

@ErikE, you are right, I forgot the UPDLOCK. I did update the answer. - However, a TABLOCKX is not
required. We only need to stop the same query from reading, not any query. Then we only need to make sure
that any insert is using this pattern. Concurrent inserts not following this pattern will be blocked by the
SERIALIZABLE query hint and eventually fail. - While it is not the best solution, it is a usable one. Sometimes
IDENTITY columns are just not an option. – Sebastian Meine Dec 21 '12 at 22:27

2 If the sync procedure inserts one record at a time you can use the same pattern. If you need to be able to
insert several rows in a single insert statement, you can stil use this pattern if you combine it with the
ROW_NUMBER() function. Important is that the SELECT max() +1 uses both SERIALIZABLE and UPDLOCK
on all(!) inserts to this table. If that select is not a sub-select as in my example you also need to wrap it
together with the insert in a transaction (If this happens in a procedure read this first:sqlity.net/en/585/how-to-
rollback-in-procedures) – Sebastian Meine Dec 22 '12 at 17:09

Since it's auto-generated, simply don't provide it:

21 INSERT INTO bo.TABLE (field1, fiels2) VALUES (value1, value2)

Update: that will work if your column is an IDENTITY column.

To provide explicit values to an identity column, you have to do this:

set identity_insert bo.TABLE on

INSERT
By using our site,INTO bo.TABLE (primary_key,
you acknowledge field1,
that you have fiels2)
read and VALUES
understand our((SELECT ISNULL(MAX(id)
Cookie Policy + 1,, and our
, Privacy Policy
0) FROM bo.Table), value1, value2)
Terms of Service.

https://stackoverflow.com/questions/13994736/how-to-insert-an-auto-increment-key-into-sql-server-table 2/4
5/11/2019 How to insert an auto_increment key into SQL Server table - Stack Overflow

set identity_insert bo.TABLE off

But there's no compelling reason for doing it this way.

edited Dec 21 '12 at 20:48 answered Dec 21 '12 at 17:43


Jordão
47.4k 11 98 127

I've tried it, throws a constraint error, I have to provide the value. – Ruben Teixeira Dec 21 '12 at 17:46

1 Please post the error.... and your table definition. – Jordão Dec 21 '12 at 17:46

Violation of PRIMARY KEY constraint 'pk_bo'. Cannot insert duplicate key in object 'dbo.bo'. The duplicate key
value is (921, 0, 2012). – Ruben Teixeira Dec 21 '12 at 17:53

1 Looks like your auto-incremented field is not part of the primary key. Can you post the table definition and your
insert statements? – Jordão Dec 21 '12 at 17:59

1 @RubenTeixeira: any table can only ever have one primary key .... – marc_s Dec 21 '12 at 18:02

In my opinion the best answer is to fix your table so that the PK column is an identity column.
(Please see my comments on the answer from Sebastian Meine about why your currently selected
4 answer is not best.) The only way to make an existing PK become an identity column is by swapping
out the table. Roughly:

BEGIN TRAN;
-- Rename all constraints in original table
EXEC sp_rename 'dbo.YourOriginalTable.PK_ConstraintName', 'PKConstraint_Backup';
EXEC sp_rename 'dbo.YourOriginalTable.OtherConstraintName',
'OtherConstraintName_Backup';
CREATE TABLE dbo.WorkTable (
YourPKColumn int identity(1, 1) NOT NULL -- your PK converted to identity
CONSTRAINT PK_YourOriginalTableConstraintName PRIMARY KEY CLUSTERED,
AllOtherColumns -- all your other columns exactly as in the original table
);

SET IDENTITY_INSERT dbo.WorkTable ON;


INSERT dbo.WorkTable (YourPKColumn, AllOtherColumns)
SELECT YourPKColumn, AllOtherColumns
FROM dbo.YourOriginalTable WITH (TABLOCKX, HOLDLOCK);

SET IDENTITY_INSERT dbo.WorkTable OFF;

-- Drop all FK constraints from other tables pointing to your table


ALTER TABLE dbo.TableWithFK_1
DROP CONSTRAINT FK_TableWithFK_1_YourOriginalTableSomethingID;

-- Swap out the tables


EXEC sp_rename 'dbo.YourOriginalTable', 'YourOriginalTableBackup';
EXEC sp_rename 'dbo.WorkTable', 'YourOriginalTable';

-- If you didn't add them in the WorkTable creation,


-- add all other removed or needed constraints creation
ALTER TABLE dbo.YourOriginalTable
By using our site, you acknowledge that you have read and understand our Cookie Policy, Privacy Policy, and our
ADD CONSTRAINT OriginalConstraint (OriginalConstraintColumns);
Terms of Service
-- Add .back FK constraints from other tables to this one.
COMMIT TRAN;
https://stackoverflow.com/questions/13994736/how-to-insert-an-auto-increment-key-into-sql-server-table 3/4
5/11/2019 How to insert an auto_increment key into SQL Server table - Stack Overflow

You now have a table that has an identity column with a clustered PK on it. You can insert to it no
problem. No more concurrency issues and silly SELECT Max() + 1 junk that is so easy to get wrong.

edited May 12 '14 at 21:53 answered Dec 21 '12 at 20:42


ErikE
35.5k 14 124 167

+1 of course if this is an active system you'll want to do this in an explicit transaction. Otherwise there is danger
of getting some data into YourOriginalTable after the INSERT but before the renames. – Aaron Bertrand
Dec 21 '12 at 21:33

Thank you Aaron that is a good catch. Fixed (I think). – ErikE Dec 21 '12 at 21:34

Sorry It´s not my Db, I can't make any changes, it was design to work with a ERP application. Just need to do
the procedure explained in the question, thank you anyway. – Ruben Teixeira Dec 22 '12 at 13:08

create table if not exists Emp ( eid int(10) not null primary key auto_increment, name varchar(45) not
null, age int(5) default 20, salary int(5) ) insert into emp values(102,'Ranjan',21,450000);
0 Then try below sql query . It will automaticaly increment the eid to next number .

insert into emp (name,salary) values( 'Lisma',118500);

select * from emp;

answered Jul 18 '16 at 20:02


PyDevSRS
957 7 15

By using our site, you acknowledge that you have read and understand our Cookie Policy, Privacy Policy, and our
Terms of Service.

https://stackoverflow.com/questions/13994736/how-to-insert-an-auto-increment-key-into-sql-server-table 4/4

You might also like