परीक्षण सेटअप
आप बाधा नाम मानते हैं test_def_abc_id_fkey
, पोस्टग्रेज 11 या पुराने में आपके सेटअप के परिणामस्वरूप होने वाला डिफ़ॉल्ट नाम। हालांकि, ध्यान देने योग्य बात यह है कि पोस्टग्रेज 12 के लिए डिफ़ॉल्ट नामों में सुधार किया गया है, जहां एक ही सेटअप का परिणाम test_def_abc_id_abc_id2_fkey
होता है। . पोस्टग्रेज 12 के लिए रिलीज नोट:ए>
देखें:
db<>fiddle यहां
तो चलिए स्पष्ट नाम का उपयोग करते हैं test_def_abc_fkey
FK बाधा के लिए भ्रम से बचने के लिए:
CREATE TABLE test_abc (
pk int PRIMARY KEY
, id int NOT NULL
, id2 int NOT NULL
);
CREATE UNIQUE INDEX test_abc_ids ON test_abc(id,id2);
CREATE TABLE test_def (
id int PRIMARY KEY
, abc_id int
, abc_id2 int
, CONSTRAINT test_def_abc_fkey -- !
FOREIGN KEY (abc_id,abc_id2) REFERENCES test_abc(id,id2)
);
और वह Postgres 9.5 - Postgres 12 में काम करता है।
पोस्टग्रेज 9.3 में भी।
(मैं एक वास्तविक बाधा . के गलत प्रभाव में था की आवश्यकता होगी।)
जवाब
जानकारी स्कीमा को क्वेरी करने से आपका अवलोकन:
SELECT *
FROM information_schema.referential_constraints
WHERE constraint_name = 'test_def_abc_fkey'; -- unequivocal name
हमें एक पंक्ति मिलती है, लेकिन तीन फ़ील्ड unique_constraint_catalog
, unique_constraint_schema
और unique_constraint_name
हैं NULL
.
स्पष्टीकरण सरल लगता है। वे कॉलम वर्णन करते हैं, जैसा कि मैनुअल कहता है:
लेकिन कोई UNIQUE<नहीं है /कोड> बाधा
, बस एक UNIQUE
अनुक्रमणिका
. एक अद्वितीय
एक UNIQUE
. का उपयोग करके बाधा को लागू किया जाता है पोस्टग्रेज में index. बाधाओं को SQL मानक द्वारा परिभाषित किया गया है, अनुक्रमणिका कार्यान्वयन विवरण हैं। आपके द्वारा खोजे गए जैसे मतभेद हैं। संबंधित:
वास्तविक UNIQUE
. के साथ एक ही परीक्षण बाधा अपेक्षित के रूप में डेटा दिखाता है:
db<>fiddle यहां
तो यह समझ में आता है। खासकर जब से सूचना स्कीमा SQL मानक समिति द्वारा भी परिभाषित किया गया है और अनुक्रमणिका मानकीकृत नहीं हैं, केवल बाधाएं हैं। (सूचना स्कीमा दृश्यों में कोई अनुक्रमणिका जानकारी नहीं है।)
सब साफ़? बिलकुल नहीं।
हालांकि
एक और जानकारी स्कीमा दृश्य है key_column_usage
. इसका अंतिम स्तंभ इस प्रकार वर्णित है:
बोल्ड मेरा जोर। यहां, सूचकांक . में स्तंभ की क्रमिक स्थिति वैसे भी सूचीबद्ध है:
SELECT *
FROM information_schema.key_column_usage
WHERE constraint_name = 'test_def_abc_fkey';
देखें:
db<>fiddle यहां
असंगत लगता है।
क्या बुरा है, मैनुअल
दावा करता है कि एक वास्तविक प्राथमिक कुंजी
या अद्वितीय
विदेशी कुंजी
के निर्माण के लिए बाधा की आवश्यकता होगी बाधा:
एक दस्तावेज़ीकरण बग प्रतीत होता है ? अगर कोई यह नहीं बता सकता कि मैं यहाँ कहाँ गलत हो रहा हूँ, तो मैं एक बग रिपोर्ट दर्ज करूँगा।
संबंधित:
समाधान
पोस्टग्रेज में, सिस्टम कैटलॉग सत्य का वास्तविक स्रोत है। देखें:
तो आप कुछ इस तरह का उपयोग कर सकते हैं (जैसे मैंने fiddle में भी जोड़ा है। ऊपर):
SELECT c.conname
, c.conrelid::regclass AS fk_table, k1.fk_columns
, c.confrelid::regclass AS ref_table, k2.ref_key_columns
FROM pg_catalog.pg_constraint c
LEFT JOIN LATERAL (
SELECT ARRAY (
SELECT a.attname
FROM pg_catalog.pg_attribute a
, unnest(c.conkey) WITH ORDINALITY AS k(attnum, ord)
WHERE a.attrelid = c.conrelid
AND a.attnum = k.attnum
ORDER BY k.ord
) AS fk_columns
) k1 ON true
LEFT JOIN LATERAL (
SELECT ARRAY (
SELECT a.attname
FROM pg_catalog.pg_attribute a
, unnest(c.confkey) WITH ORDINALITY AS k(attnum, ord)
WHERE a.attrelid = c.confrelid
AND a.attnum = k.attnum
ORDER BY k.ord
) AS ref_key_columns
) k2 ON true
WHERE conname = 'test_def_abc_fkey';
रिटर्न:
conname | fk_table | fk_columns | ref_table | ref_key_columns :---------------- | :------- | :--------------- | :-------- | :-------------- test_def_abc_fkey | test_def | {abc_id,abc_id2} | test_abc | {id,id2}
संबंधित:
- तालिका, फ़ील्ड और स्कीमा नाम का उपयोग करके संदर्भित तालिका का नाम ढूंढें
- संदर्भित फ़ील्ड ढूंढें( s) विदेशी कुंजी बाधा का
- मैं उन तालिकाओं को कैसे ढूंढ सकता हूं जो किसी विदेशी कुंजी के माध्यम से किसी विशेष पंक्ति का संदर्भ देती हैं?