सरलतम स्थिति में, जब हम एक नई पंक्ति को एक तालिका में डालते हैं (और लेन-देन शुरू होता है), तो यह सभी बाद के लेनदेन के लिए दिखाई देगा। xmax
इस उदाहरण में 0 देखें :
CREATE TABLE vis (
id serial,
is_active boolean
);
INSERT INTO vis (is_active) VALUES (FALSE);
SELECT ctid, xmin, xmax, * FROM vis;
ctid │xmin │ xmax │ id │ is_active
───────┼─────┼──────┼────┼───────────
(0,1) │2699 │ 0 │ 1 │ f
जब हम इसे अपडेट करते हैं (क्योंकि झंडा FALSE
दुर्घटना से सेट हो गया था), यह थोड़ा बदलता है:
UPDATE vis SET is_active = TRUE;
SELECT ctid, xmin, xmax, * FROM vis;
ctid │ xmin │ xmax │ id │ is_active
──────┼──────┼──────┼────┼───────────
(0,2) │ 2700 │ 0 │ 1 │ t
MVCC मॉडल PostgreSQL उपयोगों के अनुसार , एक नई भौतिक पंक्ति लिखी गई थी और पुरानी को अमान्य कर दिया गया था (इसे इससे देखा जा सकता है ctid
)। नया अभी भी सभी बाद के लेनदेन के लिए दिखाई दे रहा है।
अब जब हम वापस रोल करते हैं तो एक दिलचस्प बात होती है UPDATE
:
BEGIN;
UPDATE vis SET is_active = TRUE;
ROLLBACK;
SELECT ctid, xmin, xmax, * FROM vis;
ctid │ xmin │ xmax │ id │ is_active
───────┼──────┼──────┼────┼───────────
(0,2) │ 2700 │ 2702 │ 1 │ t
पंक्ति संस्करण समान रहता है, लेकिन अब xmax
कुछ पर सेट है। इसके बावजूद, बाद के लेनदेन इसे (अन्यथा अपरिवर्तित) पंक्ति देख सकते हैं।
इस बारे में थोड़ा पढ़ने के बाद, आप पंक्ति दृश्यता के बारे में कुछ बातें जान सकते हैं। नहीं है दृश्यता मानचित्र , लेकिन यह केवल पता चलता है कि एक पूरे पेज दिखाई दे रहा है - यह निश्चित रूप से पंक्ति (टपल) स्तर पर काम नहीं करता। फिर कमिट लॉग (उर्फ clog
) है - लेकिन पोस्टग्रेज यह पता लगाने के लिए कि यह कैसे जाना है?
मैंने यह देखने के लिए कि वास्तव में कैसे दृश्यता काम करती है, यह जानने के लिए infomask बिट्स पर एक नज़र डालने का फैसला किया । उन्हें देखने के लिए, सबसे आसान तरीका पेजिन्सपेक्ट एक्सटेंशन का उपयोग करना है । यह जानने के लिए कि कौन से बिट सेट हैं, मैंने उन्हें स्टोर करने के लिए एक टेबल बनाया:
CREATE TABLE infomask (
i_flag text,
i_bits bit(16)
);
INSERT INTO infomask
VALUES
('HEAP_HASNULL', x'0001'::bit(16)),
('HEAP_HASVARWIDTH', x'0002'::bit(16)),
('HEAP_HASEXTERNAL', x'0004'::bit(16)),
('HEAP_HASOID', x'0008'::bit(16)),
('HEAP_XMAX_KEYSHR_LOCK', x'0010'::bit(16)),
('HEAP_COMBOCID', x'0020'::bit(16)),
('HEAP_XMAX_EXCL_LOCK', x'0040'::bit(16)),
('HEAP_XMAX_LOCK_ONLY', x'0080'::bit(16)),
('HEAP_XMIN_COMMITTED', x'0100'::bit(16)),
('HEAP_XMIN_INVALID', x'0200'::bit(16)),
('HEAP_XMAX_COMMITTED', x'0400'::bit(16)),
('HEAP_XMAX_INVALID', x'0800'::bit(16)),
('HEAP_XMAX_IS_MULTI', x'1000'::bit(16)),
('HEAP_UPDATED', x'2000'::bit(16)),
('HEAP_MOVED_OFF', x'4000'::bit(16)),
('HEAP_MOVED_IN', x'8000'::bit(16)),
('HEAP_XACT_MASK', x'FFF0'::bit(16));
फिर जाँच की कि मेरी vis
मेज के अंदर क्या है - ध्यान दें कि pageinspect
ढेर की भौतिक सामग्री को दिखाता है, इसलिए न केवल दिखाई देने वाली पंक्तियाँ वापस आ जाती हैं:
SELECT t_xmin, t_xmax, string_agg(i_flag, ', ') FILTER (WHERE (t_infomask::bit(16) & i_bits)::integer::boolean)
FROM heap_page_items(get_raw_page('vis', 0)),
infomask
GROUP BY t_xmin, t_xmax;
t_xmin │ t_xmax │ string_agg
────────┼────────┼──────────────────────────────────────────────────────
2699 │ 2700 │ HEAP_XMIN_COMMITTED, HEAP_XMAX_COMMITTED
2700 │ 2702 │ HEAP_XMIN_COMMITTED, HEAP_XMAX_INVALID, HEAP_UPDATED
2702 │ 0 │ HEAP_XMIN_INVALID, HEAP_XMAX_INVALID, HEAP_UPDATED
जो मैं ऊपर से समझता हूं वह यह है कि पहला संस्करण 2699 के लेन-देन के साथ जीवन में आया, फिर 2700 पर नए संस्करण द्वारा सफलतापूर्वक प्रतिस्थापित किया गया।
फिर अगले एक, जो 2700 से जीवित था, UPDATE
2702 में लुढ़का हुआ वापस प्रयास किया गया था, जिसे देखा गया था । HEAP_XMAX_INVALID
।
अंतिम वाला वास्तव में कभी पैदा नहीं हुआ था, जैसा कि दिखाया गया है HEAP_XMIN_INVALID
।
इसलिए, ऊपर से अनुमान लगाने पर, पहला और आखिरी मामला स्पष्ट है - वे 2703 या उच्चतर लेनदेन करने के लिए अब दिखाई नहीं दे रहे हैं।
दूसरे को कहीं और देखना पड़ता है - मुझे लगता है कि यह कमिट लॉग है, उर्फ clog
।
आगे के मुद्दों को जटिल बनाने के लिए, UPDATE
निम्नलिखित में परिणाम:
t_xmin │ t_xmax │ string_agg
────────┼────────┼────────────────────────────────────────────────────
2699 │ 2700 │ HEAP_XMIN_COMMITTED, HEAP_XMAX_COMMITTED
2702 │ 0 │ HEAP_XMIN_INVALID, HEAP_XMAX_INVALID, HEAP_UPDATED
2703 │ 0 │ HEAP_XMAX_INVALID, HEAP_UPDATED
2700 │ 2703 │ HEAP_XMIN_COMMITTED, HEAP_UPDATED
यहां मुझे पहले से ही दो उम्मीदवार दिखाई दे रहे हैं जो दिखाई दे सकते हैं। तो, अंत में, यहाँ मेरे सवाल हैं:
- क्या मेरी धारणा है कि
clog
इन मामलों में दृश्यता निर्धारित करने के लिए देखने के लिए जगह है? - कौन से झंडे (या झंडे का संयोजन) सिस्टम को यात्रा करने के लिए कहते हैं
clog
? - क्या यह जांचने का कोई तरीका है कि अंदर क्या है
clog
?clog
Postgres के पुराने संस्करणों में भ्रष्टाचार के बारे में उल्लेख है और एक संकेत है कि कोई मैन्युअल रूप से एक नकली फ़ाइल बना सकता है। जानकारी का यह टुकड़ा इसके साथ बहुत मदद करेगा।