ALLOW_SNAPSHOT_ISOLATION और READ_COMMITTED_SNAPSHOT


38

मंच और उदाहरण के अधिकांश ऑनलाइन हमेशा दोनों के लिए सुझाव देते हैं ALLOW_SNAPSHOT_ISOLATIONऔर READ_COMMITTED_SNAPSHOTजब भी किसी को, स्नैपशॉट पूछ रहा है पंक्ति वर्ज़निंग या इसी तरह के सवाल पर करने के लिए सेट।

मुझे लगता है कि दोनों सेटिंग में SNAPSHOT शब्द थोड़ा भ्रमित करते हैं। मुझे लगता है कि, READ_COMMITTED डिफ़ॉल्ट व्यवहार के लिए ताले के बजाय पंक्ति संस्करण का उपयोग करने के लिए डेटाबेस इंजन के लिए, डेटाबेस READ_COMMITTED_SNAPSHOTको किस सेटिंग की परवाह किए बिना चालू किया जाता है ALLOW_SNAPSHOT_ISOLATION

ALLOW_SNAPSHOT_ISOLATIONसेटिंग जब एक सौदा (जैसे सेट लेनदेन अलगाव स्तर स्नैपशॉट) शुरू करने ही स्नैपशॉट अलगाव अनुमति देने के लिए चालू पर सेट है परवाह किए बिना की READ_COMMITTED_SNAPSHOTसेटिंग।

इन दो सेटिंग्स को चालू करने का एकमात्र कारण यह है कि इसके लिए पंक्तिबद्ध संस्करण और स्नैपशॉट अलगाव की आवश्यकता है।

मेरा सवाल यह है कि क्या मेरी समझ किसी तरह से गलत है? और यह कि इन दोनों सेटिंग को हमेशा एक साथ सेट करना होगा (विशेषकर READ COMMITTED पंक्ति संस्करण के लिए)?

जवाबों:


25

आपकी समझ सही है। यह थोड़ा भ्रमित करता है।

किम ट्रिप (SQL सर्वर के प्रोग्रामर और SQLSkills का एक अभिन्न अंग) स्नैपशॉट अलगाव पर MCM वीडियो में कहा गया है कि वास्तव में के माध्यम से चला जाता है । वीडियो में उस हिस्से को पाने के लिए फास्ट फॉरवर्ड 41:45 पर करें जहां वह आपके प्रश्न का उत्तर देती है।

यदि आप उपयोग करते हैं ALLOW_SNAPSHOT_ISOLATIONतो सुनिश्चित करें कि आप SET TRANSACTION ISOLATION LEVEL SNAPSHOTअपने कोड में उपयोग करते हैं, अन्यथा आपको कोई लाभ नहीं मिलेगा।

यदि आप सेट करते हैं SET READ_COMMITTED_SNAPSHOT ON, तो किसी भी कोड को संशोधित करने की आवश्यकता नहीं है। MS SQL सर्वर स्वचालित रूप से उस तालिका के लिए स्नैपशॉट अलगाव लागू करता है।

मैंने यह देखने के लिए परीक्षण नहीं किया है कि यदि आप अपने कोड में अलग-अलग अलगाव स्तर पूछते हैं तो मुझे क्या होगा, मुझे संदेह है कि यह इस विकल्प को अधिलेखित कर देगा लेकिन पहले परीक्षण करें।

स्नैपशॉट अलगाव का उपयोग कर प्रदर्शन ओवरहेड पर एक त्वरित नज़र।

स्नैपशॉट अलगाव के बारे में अच्छा लेख आपके ऐप के अपेक्षित व्यवहार को बदल सकता है । यह दिखाता है कि अपडेट स्टेटमेंट और चुनिंदा स्टेटमेंट कैसे पूरी तरह से अलग और अप्रत्याशित परिणाम दे सकते हैं।


लिंक के लिए धन्यवाद। अन्य बीओएल की तरह, उसने स्वतंत्र रूप से और सामूहिक रूप से इन दो सेटिंग्स पर चर्चा की (यह वह जगह है जहां यह थोड़ा भ्रमित हो जाता है, या शायद मुझे लगता है कि यह अधिक है)। बेहतर समझ पाने के लिए मुझे इसका परीक्षण करना पड़ा।
ट्रैविस

4
यह एक महान जवाब है और मैं केवल कुछ चीजों को स्पष्ट करना चाहूंगा। सबसे पहले, यदि आप वीडियो को स्कैन कर रहे हैं, तो 23:18 के साथ-साथ 41:45 पर शुरू करें। प्रारंभिक समय और अधिक विस्तार जोड़ता है। यद्यपि किम मूल प्रश्न के उत्तर का उल्लेख करता है, फिर भी दोनों का उपयोग करते हुए कोड को संशोधित करने की आवश्यकता है। Read_Committed_Snapshot कथन-स्तर अलगाव है, दूसरे शब्दों में वर्तमान में चल रहे कथन पर ही लागू होता है। Allow_Snapshot_Isolation लेन-देन-स्तर अलगाव है, शुरुआती ट्रान और कमिट के बीच सब कुछ। उन्हें अलग से लगाया जा सकता है, लेकिन प्रति पंक्ति 14-बाइट ओवरहेड स्थापित किया जाता है।
Delux

स्थापित किए जा रहे 14 बाइट ओवरहेड पर अतिरिक्त विवरण जोड़ने के लिए धन्यवाद। किम वीडियो में इसके माध्यम से जाता है, लेकिन इसके बहुत उपयोगी होने के साथ-साथ पाठ में भी है।
अली रज़ेगी

15

ठीक है, घर वापस गए और परीक्षण किया। यहाँ अवलोकन है।

CREATE DATABASE TEST;
GO
CREATE TABLE TABLE1
(
    ID tinyint,
    Details varchar(10)
);
GO
INSERT INTO TABLE1
VALUES (1, 'Original');
GO

SELECT
    name,
    snapshot_isolation_state_desc,
    is_read_committed_snapshot_on
FROM sys.databases
WHERE name = 'TEST';
GO

दोनों सेटिंग्स के साथ पहला परीक्षण बंद होने की पुष्टि की।

प्रश्न 1

USE TEST;

BEGIN TRAN
UPDATE TABLE1
SET Details = 'Update'
WHERE ID = 1;

--COMMIT;
--ROLLBACK;
GO

प्रश्न २

USE TEST;

SELECT ID, Details
FROM TABLE1
WHERE ID = 1;
GO

इस परीक्षण में, क्वेरी 2 के लिए 1 से कमिट करने की प्रतीक्षा की जा रही है, dm_tran_locks DMV से पता चलता है कि क्वेरी 1 द्वारा किए गए TABLE1 पर अनन्य लॉक है।

USE TEST;

SELECT
    DB_NAME(tl.resource_database_id) AS DBName,
    resource_type,
    OBJECT_NAME(resource_associated_entity_id) AS tbl_name,
    request_mode,
    request_status,
    request_session_id
FROM sys.dm_tran_locks tl
WHERE 
    resource_database_id = db_id('TEST')
    AND resource_type = 'OBJECT'

दूसरा परीक्षण , पिछला लेन-देन रोलबैक करें, READ_COMMITTED_SNAPSHOT को सेट करें लेकिन ALLOW_SNAPSHOT_ISOLATION को छोड़ दें।

ALTER DATABASE TEST
SET READ_COMMITTED_SNAPSHOT ON
WITH ROLLBACK IMMEDIATE;
GO

क्वेरी 1 चलाएं, और क्वेरी 2 चलाएं। DMV क्वेरी 1 इनक एक्सक्लूसिव लॉक दिखाती है, लेकिन क्वेरी 2 बिना रिटर्न के 'मूल' के साथ विवरण देता है। ऐसा प्रतीत होता है कि READ_COMMITTED पंक्ति संस्करण की जगह है।

जोड़ना SET TRANSACTION ISOLATION LEVEL SNAPSHOT;क्वेरी 1 और क्वेरी 2, और रन क्वेरी 1 या क्वेरी 2 रिटर्न त्रुटि पर - स्नैपशॉट अलगाव लेन-देन तक पहुँचने डेटाबेस 'टेस्ट' विफल स्नैपशॉट अलगाव इस डेटाबेस में अनुमति नहीं है क्योंकि। स्नैपशॉट अलगाव की अनुमति देने के लिए ALTER DATABASE का उपयोग करें।

तीसरा परीक्षण , पिछला लेनदेन रोलबैक। READ_COMMITTED_SNAPSHOT बंद और ALLOW_SNAPSHOT_ISOLATION सेट करें।

ALTER DATABASE TEST
SET READ_COMMITTED_SNAPSHOT OFF
WITH ROLLBACK IMMEDIATE;
GO

ALTER DATABASE TEST
SET ALLOW_SNAPSHOT_ISOLATION ON;
GO

क्वेरी 1 चलाएं, और फिर क्वेरी 2। DMV क्वेरी द्वारा किए गए अनन्य लॉक दिखाता है। क्वेरी 2 क्वेरी 1 के पूरा होने की प्रतीक्षा कर रहा है। ALLOW_SNAPSHOT_ISOLATION चालू करने से पंक्तिबद्ध संस्करण तैयार करने में सक्षम नहीं होता है।

जोड़ा जा रहा है SET TRANSACTION ISOLATION LEVEL SNAPSHOT;दोनों क्वेरी 1 और क्वेरी 2. चलाएँ क्वेरी 1 करने के लिए और उसके बाद क्वेरी 2. जबकि DMV शो क्वेरी 1 को अपने ऊपर लेना अनन्य ताला, क्वेरी 2 वापसी 'मूल' के साथ विवरण। स्नैपशॉट अलगाव जगह में दिखाई देता है।

परीक्षण के अवलोकन से पता चलता है कि सेटिंग की READ_COMMITTED_SNAPSHOTपरवाह किए बिना READ COMMITTED पंक्ति संस्करण को स्वयं सक्षम / अक्षम करें ALLOW_SNAPSHOT_ISOLATION, और इसके विपरीत।


4

आपकी समझ सही है। मुझे यहाँ से संक्षिप्त, स्वच्छ और सरल परिभाषा पसंद है :

जब READ_COMMITTED_SNAPSHOT डेटाबेस विकल्प चालू होता है, तो रीड प्रतिबद्ध आइसोलेशन स्तर उपयोग वर्जन कोडिंग को सेट करता है।

जब ALLOW_SNAPSHOT_ISOLATION डेटाबेस विकल्प चालू होता है, तो लेनदेन स्नैपशॉट अलगाव स्तर सेट कर सकता है।

एमएस से ही बहुत सी गलतफहमी होने लगती है। उदाहरण के लिए, यहां वे कहते हैं:

यदि आप READ_COMMITTED_SNAPSHOT डेटाबेस विकल्प को ON पर सेट करते हैं, तो डेटाबेस इंजन डेटा की सुरक्षा के लिए ताले का उपयोग करने के बजाय, डिफ़ॉल्ट रूप में पंक्ति संस्करण और स्नैपशॉट अलगाव का उपयोग करता है।

लेकिन उल्लिखित "स्नैपशॉट अलगाव" लेनदेन के व्यवहार के बराबर नहीं है जिसके लिए set transaction isolation level snapshotइसे लागू किया जाता है।

अंतर के रूप में, अच्छी व्याख्या यहाँ है

संभवतः यह बेहतर होगा कि READ_COMMITTED_SNAPSHOT का नाम READ_COMMITTED_ROW_VERSIONING या कुछ इस तरह रखा जाए। :)


0

मुझे Microsoft का यह सारांश पसंद है :

READ_COMMITTED_SNAPSHOT को विकल्प पर सेट करने से डिफ़ॉल्ट READ COMMITTED आइसोलेशन स्तर के अंतर्गत संस्करणित पंक्तियों तक पहुँच की अनुमति मिलती है। यदि READ_COMMITTED_SNAPSHOT विकल्प OFF पर सेट है, तो आपको संस्करण पंक्तियों तक पहुँचने के लिए प्रत्येक सत्र के लिए स्नैपशॉट अलगाव स्तर स्पष्ट रूप से सेट करना होगा।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.