प्रतिनिधि इंटरव्यू विषय

डेटा इंटरव्यू: PostgreSQL 18 में वैकल्पिक कुंजियों (optional keys) के लिए आप NULLS NOT DISTINCT का उपयोग कैसे करेंगे?

डेटाकठिन
Offer.cc संपादकीय टीमप्रकाशित अपडेट किया गया

प्रश्न

एक orders टेबल प्रति टेनेंट एक वैकल्पिक बाहरी संदर्भ (external reference) की अनुमति देती है: प्रति टेनेंट अधिकतम एक पंक्ति में NULL हो सकता है। ऐतिहासिक डुप्लिकेट, समवर्ती राइट्स और रोलबैक को संभालते हुए आप इसे PostgreSQL 18 में कैसे लागू करेंगे?

प्रॉम्प्ट और संदर्भ

एक orders टेबल प्रति टेनेंट एक वैकल्पिक बाहरी संदर्भ (external reference) की अनुमति देती है: प्रति टेनेंट अधिकतम एक पंक्ति में NULL हो सकता है। ऐतिहासिक डुप्लिकेट, समवर्ती राइट्स और रोलबैक को संभालते हुए आप इसे PostgreSQL 18 में कैसे लागू करेंगे?

PostgreSQL का डिफ़ॉल्ट यूनिक इंडेक्स NULL मानों को भिन्न (distinct) मानता है, इसलिए कई NULL आपस में टकराते नहीं हैं। PostgreSQL 18 में NULLS NOT DISTINCT जोड़ा गया है, जिससे NULL मान विशिष्टता (uniqueness) में भाग लेते हैं। यह प्रश्न रेस-प्रोन (race-prone) बिज़नेस चेक को एप्लिकेशन कोड में ले जाने के बजाय कंस्ट्रेंट डिज़ाइन, माइग्रेशन सुरक्षा और कंकरेंसी सिमेंटिक्स का परीक्षण करता है।

साक्षात्कारकर्ता क्या जांच रहा है

  • क्या आप डिफ़ॉल्ट NULL विशिष्टता बनाम NULLS NOT DISTINCT को सटीक रूप से समझाते हैं।
  • क्या आप जानते हैं कि यह विकल्प साधारण तुलनाओं पर नहीं, बल्कि यूनिक B-tree इंडेक्स या यूनिक कंस्ट्रेंट्स पर लागू होता है।
  • क्या आप पहले ऐतिहासिक डुप्लिकेट NULL और गैर-NULL संयोजनों को खोजते और हल करते हैं।
  • क्या आप एक ऑनलाइन माइग्रेशन, लॉक योजना, समवर्ती-राइट व्यवहार और रोलबैक डिज़ाइन करते हैं।
  • क्या ORM, रेप्लिकेशन, पार्टिशनिंग और डाउनस्ट्रीम अनुबंध संगत रहते हैं।

पहले स्पष्ट करने योग्य प्रश्न

  • क्या दायरा (scope) पूरी टेबल है, या प्रति टेनेंट, क्षेत्र (region) या सक्रिय स्थिति (active state) के लिए एक नियम है?
  • क्या NULL का अर्थ अनिर्धारित (unassigned), अज्ञात (unknown), या एक जानबूझकर साझा किया गया संदर्भ है?
  • क्या ऐतिहासिक पंक्तियों में कई NULL, खाली स्ट्रिंग्स, केस वेरिएंट या सॉफ्ट-डिलीट की गई कुंजियाँ शामिल हैं?
  • राइट दर, लॉक बजट और माइग्रेशन विंडो क्या हैं?
  • क्या एप्लिकेशन, ORM, CDC और रिपोर्ट्स यह मानकर चलते हैं कि NULL दोहराया जा सकता है?

तीस-सेकंड का उत्तर

“मैं NULL के अर्थ और दायरे को स्पष्ट करूँगा, फिर ऐतिहासिक डुप्लिकेट्स का ऑडिट करूँगा। टेनेंट-स्कोप वाले नियम के लिए, मैं टेनेंट और संदर्भ को NULLS NOT DISTINCT के साथ एक कंपोजिट यूनिक की (composite unique key) में रखूँगा; यह विकल्प NULL को उस कुंजी की विशिष्टता में भाग लेने की अनुमति देता है लेकिन SQL की थ्री-वैल्यूड तुलना को नहीं बदलता है और न ही कॉलम को NOT NULL बनाता है। मैं ऐतिहासिक विवादों को साफ़ या तय करूँगा, इंडेक्स से पहले विवाद-हैंडलिंग डिप्लॉय करूँगा, इसे लॉक और लेटेंसी योजना के साथ बनाऊँगा, और ORM व CDC व्यवहार का परीक्षण करूँगा। डेटाबेस समवर्ती अंतिम प्राधिकारी बन जाता है; यदि बिज़नेस सिमेंटिक्स गलत हैं, तो मैं एक रेस-प्रोन प्री-चेक पर निर्भर रहने के बजाय कंस्ट्रेंट और एप्लिकेशन नीति को रोलबैक कर दूँगा।”

चरण-दर-चरण गहन विश्लेषण

चरण 1: NULL का अर्थ और दायरा स्पष्ट करें

अनिर्धारित मान को अज्ञात मान से अलग करें। यदि NULL का अर्थ अनिर्धारित है, तो एक NULL इच्छित नियम हो सकता है; यदि इसका अर्थ अज्ञात है और दोहराव मान्य हैं, तो विशिष्टता लागू करना गलत है। तय करें कि कंस्ट्रेंट वैश्विक है या टेनेंट, क्षेत्र और सक्रिय स्थिति के आधार पर समूहीकृत है, फिर कंपोजिट-कुंजी क्रम चुनें और तय करें कि क्या आंशिक इंडेक्स (partial index) की आवश्यकता है।

चरण 2: डेटाबेस एक्सप्रेशन चुनें

PostgreSQL 18 यूनिक इंडेक्स पर NULLS NOT DISTINCT का समर्थन करता है। डिफ़ॉल्ट NULLs को असमान मानता है और एकाधिक NULLs की अनुमति देता है। एक यूनिक कंस्ट्रेंट मॉडल को अधिक स्पष्ट बना सकता है, जबकि एक यूनिक B-tree इंडेक्स ऑनलाइन माइग्रेशन के अनुकूल हो सकता है। यह विकल्प केवल विशिष्टता तुलना को बदलता है: WHERE value = NULL अभी भी थ्री-वैल्यूड लॉजिक का पालन करता है, और कॉलम अशक्त (nullable) रह सकता है।

चरण 3: ऐतिहासिक डेटा का ऑडिट और सफ़ाई करें

प्रस्तावित कुंजी द्वारा समूहीकृत करें और कई NULLs, खाली स्ट्रिंग्स, केस वेरिएंट और सॉफ्ट-डिलीट की गई पंक्तियों की गणना करें जो अभी भी एक कुंजी पर काबिज हैं। प्रति विवाद तय करें कि क्या ऑर्डर मर्ज करने हैं, संदर्भ भरना है, एक पंक्ति रखकर बाकियों को माइग्रेट करना है, या किसी अपवाद का दस्तावेज़ीकरण करना है। सफ़ाई को पुन: प्रयोज्य (replayable) और ऑडिट योग्य बनाएं, और इंडेक्स निर्माण द्वारा अनसुलझे विवादों को उजागर करने से पहले इसे शैडो वातावरण में मान्य करें।

चरण 4: ऑनलाइन माइग्रेशन डिज़ाइन करें

पहले यूनिक विवादों के लिए संगत एप्लिकेशन हैंडलिंग रिलीज़ करें, फिर एक नियंत्रित विंडो के दौरान इंडेक्स या कंस्ट्रेंट बनाएं। एक बड़ी टेबल के लिए, समवर्ती निर्माण (concurrent creation), लॉक स्तर, डिस्क स्पेस और राइट लेटेंसी का मूल्यांकन करें; पूरे समय विवादों और लंबे ट्रांजैक्शन पर नज़र रखें। यदि टेनेंट्स को चरणों में माइग्रेट किया जाना चाहिए, तो बैचों में नियम बनाएं और एक पूर्णता वॉटरमार्क रिकॉर्ड करें। डेटाबेस कंस्ट्रेंट और त्रुटि मैपिंग तैयार होने तक पुराने प्री-चेक को बनाए रखें।

चरण 5: कंकरेंसी और डाउनस्ट्रीम अनुबंधों को संभालें

समवर्ती इंसर्ट और अपडेट के लिए यूनिक इंडेक्स अंतिम मध्यस्थ है। एप्लिकेशन का "जांचें फिर डालें" (check then insert) संदेश को बेहतर बना सकता है लेकिन कंस्ट्रेंट की जगह नहीं ले सकता। बिना किसी अंतहीन पुनः प्रयासों के एक यूनिक उल्लंघन को पुनः प्रयास योग्य या उपयोगकर्ता-दृश्यमान व्यावसायिक त्रुटि में मैप करें। CDC, रेप्लिकेशन, ORM स्कीमा, रिपोर्ट्स और कैश में इस धारणा की जांच करें कि NULL दोहराया जा सकता है, फिर अनुबंधों और अलर्ट्स को अपडेट करें।

चरण 6: सत्यापित करें, मॉनिटर करें और रोलबैक करें

स्टेजिंग और कैनरी टेनेंट में, एक NULL, दूसरा NULL, समान गैर-NULL मान, भिन्न गैर-NULL मान, अपडेट, डिलीट-और-पुनर्निर्माण, और समवर्ती राइट्स का परीक्षण करें। इंडेक्स निर्माण, लॉक प्रतीक्षा, विवाद दर, एप्लिकेशन त्रुटियों और डाउनस्ट्रीम लेटेंसी की निगरानी करें। यदि सिमेंटिक्स या विवाद दर अस्वीकार्य हैं, तो नए राइट पाथ को रोकें, कंस्ट्रेंट हटाएँ, संगत त्रुटि प्रबंधन पुनर्स्थापित करें, और विश्लेषण के लिए ऑडिट ट्रेल को सुरक्षित रखें।

उच्च-गुणवत्ता वाला नमूना उत्तर

मैं सबसे पहले NULL के अर्थ और दायरे की पुष्टि करूँगा। यदि प्रत्येक टेनेंट में एक वैकल्पिक संदर्भ हो सकता है, तो मैं टेनेंट और संदर्भ को एक कंपोजिट यूनिक की में शामिल करूँगा और PostgreSQL 18 में NULLS NOT DISTINCT का उपयोग करूँगा। यह NULL को उस कुंजी की विशिष्टता में भाग लेने की अनुमति देता है, जबकि साधारण SQL थ्री-वैल्यूड लॉजिक और नलेब्ल कॉलम अपरिवर्तित रहते हैं।

रोलआउट से पहले, मैं कई NULLs, खाली स्ट्रिंग्स, केस वेरिएंट और सॉफ्ट-डिलीट की गई पंक्तियों का ऑडिट करूँगा, यह तय करूँगा कि प्रत्येक विवाद को कैसे मर्ज या भरा जाए, और निर्णय को रिकॉर्ड करूँगा। मैं इंडेक्स बनाने से पहले यूनिक-विवाद हैंडलिंग को डिप्लॉय करूँगा, फिर लॉक्स, स्पेस, लंबे ट्रांजैक्शन और विवादों की निगरानी करूँगा। परीक्षण एक और दो NULLs, समान और भिन्न गैर-NULLs, अपडेट्स, डिलीट-और-पुनर्निर्माण, और कंकरेंसी को कवर करते हैं। डेटाबेस अंतिम प्राधिकारी है, और ORM, CDC, रिपोर्ट्स और कैश को समान अनुबंध अपनाना चाहिए; यदि व्यावसायिक अर्थ गलत साबित होता है, तो मैं कंस्ट्रेंट हटा दूँगा और एप्लिकेशन नीति को रोलबैक कर दूँगा।

सामान्य गलतियाँ

  • यह मानना कि डिफ़ॉल्ट रूप से UNIQUE केवल एक NULL की अनुमति देता है → PostgreSQL NULLs को भिन्न मानता है → स्पष्ट रूप से NULLS NOT DISTINCT का उपयोग करें।
  • इसे NOT NULL के रूप में मानना → यह विकल्प अभी भी एक NULL की अनुमति देता है → लापता-मान के अर्थ को विशिष्टता से अलग करें।
  • केवल एप्लिकेशन प्री-चेक का उपयोग करना → समवर्ती अनुरोधों में अभी भी रेस कंडीशन होती है → डेटाबेस यूनिक इंडेक्स को निर्णय लेने दें।
  • खाली स्ट्रिंग्स और केस वेरिएंट की अनदेखी करना → व्यावसायिक डुप्लिकेट्स NULL विवाद नहीं हो सकते हैं → पहले सामान्यीकरण और सफ़ाई को परिभाषित करें।
  • ऐतिहासिक सफ़ाई के बिना ऑनलाइन निर्माण करना → मौजूदा डुप्लिकेट माइग्रेशन को विफल या ब्लॉक कर सकते हैं → ऑडिट करें, निर्णय लें और लंबे ट्रांजैक्शन की निगरानी करें।
  • केवल डेटाबेस बदलना → ORM, CDC और रिपोर्ट्स अभी भी दोहराए जाने योग्य NULLs मान सकते हैं → डेटा अनुबंध और त्रुटि मैपिंग को अपडेट करें।

फॉलो-अप प्रश्न

क्या NULLS NOT DISTINCT साधारण NULL तुलनाओं को बदलता है?

नहीं। यह केवल यह बदलता है कि क्या NULLs एक यूनिक इंडेक्स में टकराते हैं। WHERE value = NULL अभी भी SQL के थ्री-वैल्यूड लॉजिक का पालन करता है और उसे IS NULL का उपयोग करना चाहिए। क्वेरी सिमेंटिक्स, इंडेक्स सिमेंटिक्स और कॉलम नलेबिलिटी को अलग से समझाया जाना चाहिए।

जब दो NULL पहले से मौजूद हों तो आप बिना डाउनटाइम के माइग्रेट कैसे कर सकते हैं?

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

क्या मल्टी-टेनेंट नियम को कंपोजिट कुंजी का उपयोग करना चाहिए या आंशिक इंडेक्स का?

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

सार्वजनिक स्रोत

संबंधित प्रश्न