मैं से संबंधित सभी events
को पुनर्प्राप्त करने के लिए सबसे सरल, सबसे कुशल SQL क्वेरी लिखना चाहता हूं।एसक्यूएल में नेस्टेड रिश्तों के लिए आसानी से और कुशलतापूर्वक पूछताछ कैसे करें?
सेटअप
यहाँ मेरी स्कीमा कैसा दिखता है की एक साधारण प्रतिनिधित्व है:
कुछ बातें गौर करने योग्य
users
memberships
के माध्यम सेteams
से संबंध रखते हैं ।teams
कईcollections
,apps
, औरwebhooks
हो सकते हैं।collections
में कईwebhooks
भी हो सकते हैं।webhooks
या तोteam
याcollection
से संबंधित हो सकता है, लेकिन केवल एक ही।events
किसी भी वस्तु से संबंधित हो सकता है, लेकिन केवल एक ही।
यह एक काफी बुनियादी सेटअप की तरह लगता है कि अधिकांश सास-प्रकार की कंपनियों के पास (जैसे स्लैक या स्ट्रिप) होगा। टीमों द्वारा सब कुछ "स्वामित्व" है, लेकिन उपयोगकर्ता टीमों से संबंधित हैं और इंटरफेस के साथ बातचीत करते हैं।
समस्या
यह देखते हुए कि सेटअप, मैं एक SQL क्वेरी कि हल करती है बनाना चाहते हैं ...
कि घटनाओं से संबंधित हैं (प्रत्यक्ष या परोक्ष) के सभी का पता लगाएं करने के लिए
id
द्वारा दिया गया उपयोगकर्ता।
मैं आसानी से उन प्रश्नों को लिख सकता हूं जो किसी विशिष्ट माध्यम से प्रत्यक्ष या परोक्ष रूप से मिलते हैं। उदाहरण के लिए ...
घटनाओं सीधे एक उपयोगकर्ता से संबंधित
id
से कर रहे हैं के सभी का पता लगाएं।
SELECT *
FROM events
WHERE user_id = ${id}
या ...
घटनाओं परोक्ष रूप से अपनी टीमों के माध्यम से एक उपयोगकर्ता से संबंधित हैं के सभी का पता लगाएं।
SELECT events.*
FROM events
JOIN memberships ON memberships.team_id = events.team_id
WHERE memberships.user_id = ${id}
या यहां तक कि ...
घटनाओं परोक्ष रूप से एक उपयोगकर्ता से संबंधित अपनी टीमों में से किसी संग्रह के माध्यम से कर रहे हैं के सभी का पता लगाएं।
SELECT events.*
FROM events
JOIN collections ON collections.id = events.collection_id
JOIN memberships ON memberships.team_id = collections.team_id
WHERE memberships.user_id = ${id}
Webhooks, एक अधिक जटिल हैं क्योंकि वे दो अलग अलग तरीकों से संबंधित हो सकता है ...
घटनाओं परोक्ष रूप से एक उपयोगकर्ता से संबंधित किसी भी webhooks के माध्यम से कर रहे हैं के सभी का पता लगाएं उनकी टीमों या संग्रहों का।
SELECT *
FROM events
WHERE webhook_id IN (
SELECT webhooks.id
FROM webhooks
JOIN memberships ON memberships.team_id = webhooks.team_id
WHERE memberships.user_id = ${id}
)
OR webhook_id IN (
SELECT webhooks.id
FROM webhooks
JOIN collections ON collections.id = webhooks.collection_id
JOIN memberships ON memberships.team_id = collections.team_id
WHERE memberships.user_id = ${id}
)
लेकिन जैसा कि आप देख सकते हैं, वहाँ के लिए एक उपयोगकर्ता एक घटना जो हुआ उन सभी रास्तों के माध्यम से, से संबंधित होना अलग अलग तरीकों का एक बहुत हैं! तो जब मैं एक प्रश्न है कि सफलतापूर्वक उन से संबंधित घटनाओं के सभी हो जाता है करने के लिए प्रयास करते हैं, यह की तरह लग रही समाप्त होता है ...
SELECT *
FROM events
WHERE user_id = ${id}
OR app_id IN (
SELECT apps.id
FROM apps
JOIN memberships ON memberships.team_id = apps.team_id
WHERE memberships.user_id = ${id}
)
OR collection_id IN (
SELECT collections.id
FROM collections
JOIN memberships ON memberships.team_id = collections.team_id
WHERE memberships.user_id = ${id}
)
OR memberships_id IN (
SELECT id
FROM memberships
WHERE user_id = ${id}
)
OR team_id IN (
SELECT team_id
FROM memberships
WHERE user_id = ${id}
)
OR webhook_id IN (
SELECT webhooks.id
FROM webhooks
JOIN memberships ON memberships.team_id = webhooks.team_id
WHERE memberships.user_id = ${id}
)
OR webhook_id IN (
SELECT webhooks.id
FROM webhooks
JOIN collections ON collections.id = webhooks.collection_id
JOIN memberships ON memberships.team_id = collections.team_id
WHERE memberships.user_id = ${id}
)
प्रश्न
- है कि अंतिम "सभी शामिल" क्वेरी बहुत अक्षम?
- क्या इसे लिखने का एक और अधिक प्रभावी तरीका है?
- क्या इसे लिखने के लिए एक आसान, आसान-पढ़ने-बाद का तरीका है?
आपने यहां 3 अलग-अलग डेटाबेस सिस्टम टैग किए हैं, कृपया केवल एक के साथ चिपके रहें। – DavidG
यह मेरे मित्र का एक अच्छी तरह से लिखित प्रश्न है, और मैं देख सकता हूं कि आपने इसे स्वयं हल करने का प्रयास किया है, यह दर्शाता है कि आपने इसमें काम किया है। –