Biegniemy SQL Server 2012 SP1 x64 (11.0.3000.0)SQL Server: dowolna automatycznego przyrostu z klucza podstawowego
Mam poniższej tabeli z polem InvoiceId
jako autoinkrementacja, klucz podstawowy:
CREATE TABLE Orders(
InvoiceId bigint IDENTITY(1001,1) NOT FOR REPLICATION,
OrderId varchar(8) NOT NULL,
... -- other fields removed for brevity
CONSTRAINT [PK_ORDERS] PRIMARY KEY CLUSTERED (InvoiceId)
ON [PRIMARY],
)
Nowe wiersze dodaje chociaż prosty sposób przechowywane jak następuje:
SET XACT_ABORT ON
SET NOCOUNT ON
BEGIN TRANSACTION
INSERT INTO Orders(
OrderId,
... -- other fields removed for brevity
)
VALUES (
@orderId,
...
)
SELECT @newRowId = SCOPE_IDENTITY()
COMMIT TRANSACTION
powyższy sproc zwraca nowo utworzony rząd-ID (Orders.InvoiceId
) do dzwoniącego.
Kod działał idealnie, z [InvoiceId]
zaczynając od 1001 i zwiększając o 1 dla każdego kolejnego wkładu.
Nasi użytkownicy wstawili około 130 wierszy. [InvoiceId]
był o 1130, a następnie przy następnym wstawieniu jego wartość przeskoczyła do !
Oto zrzut danych:
Jestem zaskoczony, co się stało tutaj. Dlaczego licznik autodostatków nagle pomija prawie 10 000 punktów?
Używamy wartości [InvoiceId]
do generowania kodów kreskowych, więc wolimy, aby wartość pozostała w określonym zakresie, najlepiej w ciągłej serii.
Przeanalizowałem dokumentację T-SQL, ale nie znalazłem nic związanego z moim problemem. Czy jest to normalne zachowanie (dowolna populacja) pola tożsamości?
UPDATE Dzięki Martingowi & Aron, znalazłem obejście. Oto official response od Microsoft:
W SQL Server 2012 realizacja mienia tożsamość został zmieniony w celu dostosowania inwestycji do innych funkcji. W poprzednich wersjach SQL Server śledzenie generowania tożsamości opierało się na rekordach dziennika transakcji dla każdej wygenerowanej wartości tożsamości. W SQL Server 2012 generujemy wartości tożsamości w partiach i rejestrujemy tylko maksymalną wartość partii. Zmniejsza to ilość i częstotliwość informacji zapisywanych w dzienniku transakcji, poprawiając skalowalność wstawiania .
Jeśli wymagają tego samego semantykę generacji tożsamość jako poprzednia wersje SQL Server są dwie opcje:
• Korzystanie śladowej flaga 272 o spowoduje zapis dziennika mają być generowane dla każdego generowanego tożsamości wartość. Wydajność generowania tożsamości może zostać zakłócona przez włączenie tej flagi śledzenia.
• wykorzystać sekwencję generatora z ustawienie pamięcią podręczną (http://msdn.microsoft.com/en-us/library/ff878091.aspx) o tej spowoduje zapis dziennika jest generowany dla każdego wygenerowanego wartości sekwencji . Należy pamiętać, że wydajność generowania wartości sekwencji może mieć wartość , która ma wpływ na użycie opcji NO CACHE.
Przykład:
CREATE SEQUENCE s1 AS INT START WITH 1 NO CACHE;
CREATE TABLE t1 (Id INT PRIMARY KEY DEFAULT NEXT VALUE FOR s1, col INT NOT NULL);
'IDENTITY' nigdy nie gwarantowane przyległe ale nie jest to znany problem w 2012 roku, gdzie może nagle wyskoczyć pozostawiając duże luki po ponownym uruchomieniu usługi. –
Dzięki @MartinSmith! To wydaje się być problemem w moim przypadku. Pamiętam restartowanie maszyny db przed skokiem tożsamości! Jak mogę tego uniknąć? – masroore
Nie można tego uniknąć, ponieważ nie gwarantowano zgodności, ale istnieje flaga śledzenia, którą można ustawić, aby uzyskać wolniejsze (zarejestrowane) zachowanie w wersji 2008 lub można użyć sekwencji o mniejszym rozmiarze pamięci podręcznej. Zobacz [dyskusja tutaj] (https://connect.microsoft.com/SQLServer/feedback/details/739013/failover-lub-restart-results-in-reseed-of-identity) –