क्वेरी के धीमे चलने की समस्या को हल करने के लिए, क्वेरी की व्याख्या करें सुविधा का इस्तेमाल करें. इससे आपको क्वेरी के एक्ज़ीक्यूशन प्लान और रनटाइम एक्ज़ीक्यूशन प्रोफ़ाइल के बारे में जानकारी मिलेगी. यहां दिए गए सेक्शन में, क्वेरी की परफ़ॉर्मेंस को ऑप्टिमाइज़ करने के तरीके बताए गए हैं. ये तरीके, एक्ज़ीक्यूशन प्रोफ़ाइल के हिसाब से अलग-अलग हो सकते हैं:
नतीजों की संख्या सीमित करना
यह पता लगाने के लिए कि क्वेरी से कई दस्तावेज़ तो नहीं मिल रहे हैं, एक्ज़ीक्यूशन ट्री में मौजूद 'वापस लाए गए रिकॉर्ड' फ़ील्ड का इस्तेमाल करें. $limit क्लॉज़ का इस्तेमाल करके, खोज के नतीजों में दिखने वाले दस्तावेज़ों की संख्या को सीमित करें. इससे नेटवर्क पर क्लाइंट को नतीजे भेजते समय, नतीजे के सीरियलाइज़ किए गए बाइट साइज़ को कम किया जाता है. अगर Limit नोड से पहले MajorSort नोड आता है, तो क्वेरी इंजन Limit और MajorSort नोड को एक साथ जोड़ सकता है. साथ ही, पूरी तरह से इन-मेमोरी मटीरियलाइज़ेशन और सॉर्ट को TopN सॉर्ट से बदल सकता है. इससे क्वेरी के लिए मेमोरी की ज़रूरत कम हो जाती है.
नतीजे के तौर पर मिले दस्तावेज़ के साइज़ की सीमा तय करना
ज़रूरी न होने वाले फ़ील्ड फ़ेच करने से बचने के लिए, $project क्लॉज़ का इस्तेमाल करके, जवाब के तौर पर मिले दस्तावेज़ के साइज़ को सीमित करें. इससे, इंटरमीडिएट नतीजों को प्रोसेस करने की कंप्यूट और मेमोरी की लागत कम करने में मदद मिलती है. साथ ही, नेटवर्क पर क्लाइंट को नतीजे वापस भेजने पर, नतीजों के क्रम से लगाए गए बाइट साइज़ को कम करने में मदद मिलती है. जिन मामलों में क्वेरी में शामिल सभी फ़ील्ड, सामान्य इंडेक्स (मल्टीकी नहीं) से कवर किए जाते हैं उनमें क्वेरी को इंडेक्स स्कैन से पूरी तरह कवर किया जा सकता है. इससे प्राइमरी स्टोरेज से दस्तावेज़ों को फ़ेच करने की ज़रूरत नहीं पड़ती.
इंडेक्स का इस्तेमाल करना
इंडेक्स सेट अप करने और उन्हें ऑप्टिमाइज़ करने के लिए, यहां दिए गए निर्देशों का पालन करें.
यह पता लगाना कि क्वेरी किसी इंडेक्स का इस्तेमाल कर रही है या नहीं
यह पता लगाया जा सकता है कि क्वेरी किसी इंडेक्स का इस्तेमाल कर रही है या नहीं. इसके लिए, आपको एक्ज़ीक्यूशन ट्री में मौजूद लीफ़ नोड की जांच करनी होगी. अगर एक्ज़ीक्यूशन ट्री का लीफ़ नोड, TableScan नोड है, तो इसका मतलब है कि क्वेरी किसी इंडेक्स का इस्तेमाल नहीं कर रही है. साथ ही, प्राइमरी स्टोरेज से दस्तावेज़ स्कैन कर रही है. अगर किसी इंडेक्स का इस्तेमाल किया जा रहा है, तो एक्ज़ीक्यूशन ट्री का लीफ़ नोड, इंडेक्स का आईडी और इंडेक्स फ़ील्ड दिखाएगा.
यह पता लगाना कि इस्तेमाल किए गए इंडेक्स को ऑप्टिमाइज़ किया जा सकता है या नहीं
कोई इंडेक्स, क्वेरी के लिए तब फ़ायदेमंद होता है, जब वह उन दस्तावेज़ों की संख्या को कम कर सकता है जिन्हें क्वेरी इंजन को प्राइमरी स्टोरेज से फ़ेच करना होता है. इसके अलावा, अगर इंडेक्स के फ़ील्ड का क्रम, क्वेरी की क्रम से लगाने की ज़रूरत को पूरा कर सकता है, तब भी इंडेक्स फ़ायदेमंद होता है.
अगर किसी क्वेरी के लिए इंडेक्स का इस्तेमाल किया जाता है, लेकिन क्वेरी इंजन अब भी कई दस्तावेज़ों को फ़ेच और खारिज कर रहा है, तो इसका मतलब है कि इंडेक्स का इस्तेमाल करके क्वेरी प्रेडिकेट को पूरा नहीं किया जा रहा है. इसकी पहचान, स्कैन नोड से की जाती है. यह नोड कई रिकॉर्ड दिखाता है. इसके बाद, फ़िल्टर नोड कुछ रिकॉर्ड दिखाता है. ज़्यादा सही इंडेक्स बनाने के लिए, इंडेक्स बनाना लेख पढ़ें.
अगर किसी क्वेरी के लिए, एक से ज़्यादा कुंजियों वाले इंडेक्स का इस्तेमाल नहीं किया जाता है, लेकिन क्वेरी इंजन अब भी नतीजे के सेट को मेमोरी में फिर से क्रम में लगा रहा है, तो यह इस बात का संकेत है कि इस्तेमाल किए गए इंडेक्स का इस्तेमाल, क्वेरी की क्रम से लगाने की ज़रूरत को पूरा करने के लिए नहीं किया जा सकता. इसकी पहचान, क्वेरी के एक्ज़ीक्यूशन ट्री में मौजूद MajorSort नोड से होती है. ज़्यादा काम का इंडेक्स बनाने के लिए, अगला सेक्शन देखें.
$lookup क्वेरी को ऑप्टिमाइज़ करना
$lookup कलेक्शन में इंडेक्स जोड़कर, $lookup क्वेरी को ऑप्टिमाइज़ किया जा सकता है. इससे ऑपरेशन को पूरे कलेक्शन को स्कैन किए बिना, मैच करने वाले दस्तावेज़ों को आसानी से ढूंढने में मदद मिलती है.from
$lookup का पेमेंट localField और foreignField से किया गया
अगर $lookup स्टेज में localField और foreignField विकल्पों का इस्तेमाल किया जा रहा है, तो from कलेक्शन में मौजूद foreignField पर इंडेक्स बनाएं.
नेस्ट की गई पाइपलाइन वाली $lookup
अगर $match चरणों के साथ $lookup चरण में pipeline विकल्प का इस्तेमाल किया जा रहा है, तो फ़ुल कलेक्शन स्कैन से बचने के लिए, फ़ॉरेन कलेक्शन में शामिल फ़ील्ड पर इंडेक्स बनाएं:
- फ़िल्टर सिमैंटिक्स (उदाहरण के लिए,
{$match: {a: true}}) वाले$matchचरणों के लिए, फ़ॉरेन कलेक्शन (a) में शामिल फ़ील्ड पर इंडेक्स बनाएं. $matchस्टेज के लिए, एग्रीगेशन सिमैंटिक का इस्तेमाल करके किसी फ़ील्ड की तुलना किसी कॉन्स्टेंट वैल्यू (उदाहरण के लिए,{$match: {$expr: {$gt: [a, 10]}}}) याletमें तय किए गए फ़ील्ड और वैरिएबल के बीच समानता की तुलना (eqयाin) से की जाती है. उदाहरण के लिए,{$match: {$expr: {$eq: [a, "$$a"]}}}. ऐसे में, फ़ॉरेन कलेक्शन में शामिल फ़ील्ड पर इंडेक्स बनाएं. ध्यान दें कि मल्टीकी इंडेक्स का इस्तेमाल प्लानिंग में नहीं किया जाएगा.
इंडेक्स बनाना
इंडेक्स बनाने के लिए, इंडेक्स मैनेजमेंट से जुड़े दस्तावेज़ पढ़ें. यह पक्का करने के लिए कि आपकी क्वेरी इंडेक्स का इस्तेमाल कर सकती है, रेगुलर (मल्टीकी नहीं) इंडेक्स बनाएं. साथ ही, फ़ील्ड को इस क्रम में रखें:
- ऐसे सभी फ़ील्ड जिनका इस्तेमाल समानता ऑपरेटर में किया जाएगा. क्वेरी में फ़ील्ड के फिर से इस्तेमाल होने की संभावना को बढ़ाने के लिए, क्वेरी में इक्वलिटी ऑपरेटर में फ़ील्ड के दिखने की संख्या के घटते क्रम में फ़ील्ड को क्रम से लगाएं.
- वे सभी फ़ील्ड जिनके आधार पर डेटा को क्रम से लगाया जाएगा (एक ही क्रम में).
- ऐसे फ़ील्ड जिनका इस्तेमाल रेंज या असमानता वाले ऑपरेटर में किया जाएगा. इन्हें क्वेरी की शर्त के हिसाब से घटते क्रम में रखा जाएगा.
- ऐसे फ़ील्ड जिन्हें इंडेक्स में क्वेरी के हिस्से के तौर पर दिखाया जाएगा. इंडेक्स में ऐसे फ़ील्ड शामिल करने से, इंडेक्स को क्वेरी को कवर करने और प्राइमरी स्टोरेज से दस्तावेज़ को फ़ेच करने से बचने की अनुमति मिलती है.
ऐसी क्वेरी के लिए मल्टीकी इंडेक्स बनाएं जिनमें ऐरे फ़ील्ड को फ़िल्टर और क्रम से लगाना शामिल हो.
क्वेरी के सुझाव का इस्तेमाल करना
अगर आपने क्वेरी के लिए ज़्यादा सही इंडेक्स बनाया है, लेकिन क्वेरी इंजन उस इंडेक्स का इस्तेमाल नहीं कर रहा है, तो क्वेरी हिंट का इस्तेमाल करके, क्वेरी इंजन की इंडेक्स प्राथमिकता को बदला जा सकता है.
Query Explain की मदद से की गई क्वेरी के आउटपुट के बारे में ज़्यादा जानने के लिए, क्वेरी एक्ज़ीक्यूशन रेफ़रंस देखें.