SQL Server อ่านแล้วยอมรับ SNAPSHOT กับ SNAPSHOT


23

ฉันค้นคว้าความแตกต่างระหว่าง SQL Server READ COMMITTED SNAPSHOTและSNAPSHOTระดับการแยกและพบกับทรัพยากรต่อไปนี้:

การเลือกระดับการแยกตามเวอร์ชันของแถว

สำหรับแอปพลิเคชันส่วนใหญ่ขอแนะนำให้อ่านการแยกโดยใช้การกำหนดเวอร์ชันของแถวมากกว่าการแยกสแน็ปช็อตด้วยเหตุผลต่อไปนี้:

  • มันใช้พื้นที่ tempdb น้อยกว่าการแยกสแน็ปช็อต

  • การแยกสแนปชอตมีความเสี่ยงที่จะอัปเดตความขัดแย้งที่ไม่สามารถใช้งานได้กับการอ่านแบบแยกที่มุ่งมั่นโดยใช้การกำหนดเวอร์ชันของแถว เมื่อธุรกรรมที่รันภายใต้การแยกสแน็ปช็อตอ่านข้อมูลที่ถูกแก้ไขโดยธุรกรรมอื่นการอัพเดตโดยธุรกรรมสแน็ปช็อตไปยังข้อมูลเดียวกันทำให้เกิดความขัดแย้งในการอัปเดตและธุรกรรมจะสิ้นสุดและย้อนกลับ นี่ไม่ใช่ปัญหาของการแยกการอ่านโดยใช้การกำหนดเวอร์ชันของแถว

ฉันค่อนข้างใหม่สำหรับหัวข้อเหล่านี้ แต่ดูเหมือนว่าฉันไม่สามารถเข้าใจหัวข้อย่อยทั้งสองจากลิงก์ด้านบน

  1. ทำไมพื้นที่ tempdb จะแตกต่างกันสำหรับโหมดเหล่านี้ มีร้านหนึ่งที่ควบคุมเวอร์ชันย่อยได้มากกว่าร้านอื่นหรือไม่

  2. ทำไมการแยกสแน็ปช็อตจึงมีความเสี่ยงที่จะอัปเดตข้อขัดแย้ง

คำตอบ:


18
  1. READ COMMITTED SNAPSHOTใช้ภาพรวมใหม่หลังจากแต่ละคำสั่ง ซึ่งหมายความว่าเวอร์ชันแถวที่น้อยกว่าจะถูกรักษาไว้ (คำสั่งที่คุณยกมาจากเอกสารนั้นทำให้เข้าใจผิดเล็กน้อยเพราะมันบอกว่ามันเป็นจริงเสมอ - มันจะเป็นจริงในกรณีของการSNAPSHOTทำธุรกรรมนาน) รุ่นแถว Snapshot ถูกสร้างขึ้นในการเขียน ผู้อ่านไม่ได้มีอิทธิพลต่อสิ่งที่ได้รับใส่ลงใน tempdb ผู้เขียนไม่สามารถคาดการณ์ได้ว่าสิ่งใดที่การอ่านจะดำเนินการในอนาคต ผู้อ่านมีอิทธิพลต่อสิ่งที่สามารถกำจัดได้เท่านั้น
  2. เมื่อมีSNAPSHOTการทำธุรกรรมT1เขียนไปแถวนั้นได้รับการแก้ไขโดยการทำธุรกรรมอื่นT2ในเวลาระหว่างการT1เริ่มต้นและT1ความพยายามในการเขียนคำสั่งล้มเหลวด้วยข้อผิดพลาดในการปรับปรุงความขัดแย้ง นี่คือรูปแบบการทำงานพร้อมกันในแง่ดี ด้วยREAD COMMITTED SNAPSHOT T1จะรอT2การปล่อย X-lock ในแถวและดำเนินการตามปกติ

1
สำหรับ # 2 มีความปลอดภัยหรือไม่ที่จะบอกว่า SNAPSHOT ไม่ได้ล็อคการอัปเดตเป็นพิเศษ - เพียงแค่อาศัยเวอร์ชันแถว
John Russell

1
@JohnRussell มันล็อคเฉพาะเพื่อรองรับการย้อนกลับ การเขียนทั้งหมดต้อง X-lock เพื่อให้แน่ใจว่าแถวสามารถเรียกคืนได้ในกรณีที่มีการย้อนกลับ
usr

0

ความแตกต่างระหว่างสแน็ปช็อตและสแน็ปช็อตที่อ่านเพิ่มมีความแตกต่างอีกประการ

  1. snapshot

ในช่วงแรก

SET TRAN ISOLATION LEVEL SNAPSHOT BEGIN TRAN SELECT * จาก TB1 ..... .....

ในช่วงที่สอง

อัปเดต TB1 SET NAME = NAME + 'ทดสอบ' โดยที่ id = 1

ในช่วงแรก

SELECT * จาก TB1 - สิ่งนี้จะส่งคืนชื่อค่าสำหรับ ID = 1 ไม่ใช่ชื่อ + 'test' COMMIT TRAN

ในสแน็ปช็อตที่อ่านแล้วการเลือกแรกในเซสชั่น 1 จะส่งคืนชื่อสำหรับ id = 1 และการเลือกที่สองจะส่งคืนชื่อ + 'ทดสอบ'

ดังนั้นในการแยกสแนปช็อต SQL SERVER จะทำสแน็ปช็อตในตอนเริ่มต้นของธุรกรรมและอ่านจากสแน็ปช็อตนั้นระหว่างการทำธุรกรรมทั้งหมด

ในสแน็ปช็อตที่อ่านเพื่อกำหนดสแน็ปช็อตจะถูกใช้สำหรับทุกคำสั่ง SELECT ในระหว่างการทำธุรกรรม

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.