簡體   English   中英

從SQL插入語句中獲取新的uniqueidentifier的最佳方法,同時仍然確定插入的成功或失敗?

[英]Best way to obtain new uniqueidentifier from an SQL insert statement while still determining success or failure of insertion?

我開始使用uniqueidentifier,並且遇到了意外問題。

首先,在我通常使用SCOPE_IDENTITY()的地方,使用uniqueidentifier不再可能,即使在概念上由於默認(newid()或newsequentialid()的結果,它仍包含自動生成的id值) )約束。

我決定在INSERT語句中使用OUTPUT子句將UUID輸出到表變量。 現在,我考慮了一下,考慮到這是實現同一件事甚至更多的更清晰,更強大的方法(例如,為所有插入的行獲得清晰且直接的訪問多個自動生成的列的方式),OUTPUT子句使SCOPE_IDENTITY過時。

但是,通過使用OUTPUT,我現在想知道這如何影響通常在插入之后進行的@@ rowcount測試。 @@ rowcount是否將反映主語句中插入的行數或output子句中插入表變量的行數?

您可能會認為這沒有什么不同(即,兩種方式的計數都應該相同),但是確實有區別,因為文檔說OUTPUT子句將返回值並填充表,即使insert語句失敗也是如此。 。

具有OUTPUT子句的UPDATE,INSERT或DELETE語句將向客戶端返回行,即使該語句遇到錯誤並回滾也是如此。 如果在運行該語句時發生任何錯誤,則不應使用該結果。

它確實提到了@@ rowcount特別是始終僅在使用OUTPUT時始終反映最外面的語句,但它提到這是嵌套查詢的上下文。 由於在我的情況下OUTPUT子句是最外層語句的一部分,因此不清楚如果insert語句失敗,@@ rowcount是否將報告插入到輸出表中的行數。

    declare @new_uuid TABLE (ID uniqueidentifier);
    insert into Users (ID, PersonID, Username, Password, Notes, Enabled)
    output INSERTED.UUID into @new_uuid
        values (@id, @personid, @username, @password, @notes, @enabled )
    if (@@rowcount <> 1) goto fail; --does this reflect rows inserted into Users or @new_uuid?  What if the insert fails, and rows are still output to @new_uuid?

我已經通過以下TSQL代碼實驗性地測試了此行為:

create function NEWOBJECTID() returns int as begin return 1 / 0; end --function that would typically perform work to create a new object id, but intentionally throws an error instead
go

declare @uuidtable table (UUID uniqueidentifier);

insert into Users (ID)
output INSERTED.UUID into @uuidtable --UUID column has default constraint of (newid())
values (dbo.NEWOBJECTID()); --value to insert will throw an error

print @@rowcount; --called immediately after statement to see how it was affected by the failure
select * from @idtable; --see if anything was output into the table variable

該語句的結果是@@ rowcount返回零,並且@uuidtable變量中存在零行,但是請繼續閱讀,因為此結果會引起誤解。

首先,這使我相信,由於未插入任何行,因此不會發生輸出。 這是錯誤的,簡單的修改就可以證明這一點。

insert into Users (ID)
output INSERTED.UUID into @uuidtable --UUID column has default constraint of (newid())
values
(1), --value to insert should succeed
(2), --value to insert should succeed
(dbo.NEWOBJECTID()); --value to insert will throw an error

這次運行時,@@ rowcount仍為零; 但是,有兩個帶有兩個新的uniqueidentifiers的行已輸出到@uuidtable中。

這表明@@ rowcount反映了最終插入的行數,該數目為零,這是因為盡管成功插入了前兩個值並將OUTPUT插入@uuidtable,但由於錯誤,該語句作為一個整體回滾了。

由於在OUTPUT表中插入了兩行,但是由於語句失敗而最終插入了零行,並且@@ rowcount報告為零,這證明它反映了插入語句本身插入的行數,而不是數目。插入到OUTPUT表中的行數。 這也證實了文檔中所說的內容,即使整個語句失敗,行也將是OUTPUT。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM