Question

Most of my databases use IDENTITY columns as primary keys. I am writing a change log/audit trail in the database and want to use the ID BIGINT to keep trap of the changes sequentially.

While BIGINT is pretty big, it will run out of numbers one day and my design will fail to function properly at that point. I have been aware of this problem with my other ID columns and intended to eventually convert to GUIDs/UUIDs as I have used on Postgres in the past.

GUIDs take 16 bytes and BIGINT takes 8. For my current task, I would like to stay with BIGINT for the space savings and the sequencing. Under Postgres, I created a custom sequence with the first two digits as the current year and a fixed number of digits as the sequence within the year. The sequence generator automatically reset the sequence when the year changed.

SQL Server 2008 has no sequence generator. My research has turned up some ideas most of which involve using a table to maintain the sequence number, updating that within a transaction, and then using that to assign to my data in a separate transaction.

I want to write an SP or function that will update the sequence and return me the new value when called from a trigger on the target table before a row is written. There are many ideas but all seem to talk about locking issues and isolation problems.

Does anyone have a suggestion on how to automate this ID assignment, protect the process from assigning duplicates in a concurrent write, and prevent lock latency issues?

Was it helpful?

Solution

The stored procedure is prone to issues like blocking and deadlocks. However, there are ways around that.

For now, why not start the ID off at the bottom of the negative range?

CREATE TABLE FOO
(
ID BIGINT IDENTITY(-9223372036854775808, 1) 
)

That gives you a range from -9,223,372,036,854,775,808 to 9,223,372,036,854,775,807.

Are you really going to eat up 2^63 + 2^63 numbers?

If you are still committed to the other solution, I can give you a piece of working code. However, application locks and Serializable isolation has to be used.

It is still prone to timeouts or blocking depending upon the timeout setting and the server load.

In short, 2012 introduced sequences. That is basically what you want.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top