أحاول الحصول على قيمة المفتاح مرة أخرى بعد عبارة INSERT. مثال: لدي جدول به اسم السمات ومعرفها. معرف هو قيمة ولدت.
INSERT INTO table (name) VALUES('bob');
الآن أريد الحصول على معرف مرة أخرى في نفس الخطوة. كيف يتم ذلك؟
نحن نستخدم Microsoft SQL Server 2008.
لا حاجة ل SELECT منفصلة ...
INSERT INTO table (name)
OUTPUT Inserted.ID
VALUES('bob');
يعمل هذا مع أعمدة غير الهوية (مثل GUID) أيضًا
استخدم SCOPE_IDENTITY()
للحصول على قيمة المعرف الجديد
INSERT INTO table (name) VALUES('bob');
SELECT SCOPE_IDENTITY()
INSERT INTO files (title) VALUES ('whatever');
SELECT * FROM files WHERE id = SCOPE_IDENTITY();
هو الرهان الأكثر أمانًا نظرًا لوجود مشكلة معروفة في تعارض جملة OUTPUT على الجداول مع المشغلات. يجعل هذا الأمر غير موثوق به تمامًا كما لو لم يكن لجدولك حاليًا أي مشغلات - حيث يقوم شخص بإضافة واحد أسفل السطر إلى تعطيل طلبك. قنبلة الوقت نوع من السلوك.
راجع مقالة msdn للحصول على شرح أعمق:
ينفذ Entity Framework شيئًا مشابهًا لإجابة gbn:
DECLARE @generated_keys table([Id] uniqueidentifier)
INSERT INTO Customers(FirstName)
OUTPUT inserted.CustomerID INTO @generated_keys
VALUES('bob');
SELECT t.[CustomerID]
FROM @generated_keys AS g
JOIN dbo.Customers AS t
ON g.Id = t.CustomerID
WHERE @@ROWCOUNT > 0
يتم تخزين نتائج الإخراج في متغير جدول مؤقت ، ثم يتم تحديدها مرة أخرى إلى العميل. يجب أن تكون على بينة من مسكتك:
يمكن للإدراج إدراج أكثر من صف واحد ، بحيث يمكن للمتغير أن يحتفظ بأكثر من صف واحد ، بحيث يمكنك إرجاع أكثر من واحد
ID
ليس لدي أي فكرة عن سبب انضمام EF إلى الطاولة المؤقتة إلى الطاولة الحقيقية (تحت أي ظروف لن يتطابق الاثنان).
ولكن هذا ما يفعله EF.
SQL Server 2008 أو الأحدث فقط. إذا كان عام 2005 فأنت بعيد الحظ.
IDENTITY هي وظيفة نظام تقوم بإرجاع قيمة الهوية الأخيرة المدرجة.
يمكنك استخدام range_identity لتحديد معرف الصف الذي قمت بإدراجه للتو في متغير ثم فقط حدد أي أعمدة تريد من هذا الجدول حيث id = الهوية التي حصلت عليها من scope_identity
انظر هنا للحصول على معلومات MSDN http://msdn.Microsoft.com/en-us/library/ms190315.aspx
الحل الأفضل والأكثر استخدامًا يستخدم SCOPE_IDENTITY. فقط عليك الحصول على هوية النطاق بعد كل إدخال وحفظه في متغير لأنه يمكنك استدعاء اثنين إدراج في نفس النطاق. قد تكون هويةidentity وغير أنها تعمل ولكنها ليست مجالًا آمنًا. يمكن أن يكون لديك مشاكل في تطبيق كبير
declare @duplicataId int
select @duplicataId = (SELECT SCOPE_IDENTITY())
مزيد من التفاصيل هنا مستندات Microsoft
يمكنك إلحاق عبارة تحديد ببيان الإدراج. عدد صحيح myInt = إدراج في table1 (FName) القيم ('فريد') ؛ حدد Scope_Identity () ؛ هذا سيعود قيمة الهوية عند تنفيذ المتسلق.
هذه هي الطريقة التي استخدم بها OUTPUT INSERTED ، عند الإدراج في جدول يستخدم المعرّف كعمود هوية في SQL Server:
'myConn is the ADO connection, RS a recordset and ID an integer
Set RS=myConn.Execute("INSERT INTO M2_VOTELIST(PRODUCER_ID,TITLE,TIMEU) OUTPUT INSERTED.ID VALUES ('Gator','Test',GETDATE())")
ID=RS(0)