पायथन एक शक्तिशाली और लचीली प्रोग्रामिंग भाषा है जिसका उपयोग दुनिया भर के लाखों डेवलपर्स अपने एप्लिकेशन बनाने के लिए करते हैं। यह कोई आश्चर्य की बात नहीं है कि पायथन डेवलपर्स आमतौर पर अपनी लचीली प्रकृति और स्कीमा आवश्यकताओं की कमी के कारण अपने परिनियोजन के लिए सबसे लोकप्रिय NoSQL डेटाबेस MongoDB होस्टिंग का लाभ उठाते हैं।
तो, पायथन के साथ MongoDB का उपयोग करने का सबसे अच्छा तरीका क्या है? PyMongo एक पायथन वितरण है जिसमें MongoDB और अनुशंसित Python MongoDB ड्राइवर के साथ काम करने के लिए उपकरण शामिल हैं। यह काफी परिपक्व ड्राइवर है जो डेटाबेस के साथ अधिकांश सामान्य संचालन का समर्थन करता है।
उत्पादन में तैनात करते समय, MongoDB प्रतिकृति सेट कॉन्फ़िगरेशन में सेटअप करने की अत्यधिक अनुशंसा की जाती है ताकि उच्च उपलब्धता के लिए आपका डेटा भौगोलिक रूप से वितरित किया जा सके। यह भी अनुशंसा की जाती है कि क्लाइंट-डेटाबेस ट्रैफ़िक को एन्क्रिप्ट करने के लिए SSL कनेक्शन सक्षम किए जाएं। हम उत्पादन उपयोग के मामलों के लिए योग्य बनाने के लिए या जब हमारे ग्राहक हमसे सलाह मांगते हैं, तो हम अक्सर विभिन्न MongoDB ड्राइवरों की विफलता विशेषताओं का परीक्षण करते हैं। इस पोस्ट में, हम आपको दिखाते हैं कि PyMongo का उपयोग करके स्व-हस्ताक्षरित प्रमाणपत्रों के साथ कॉन्फ़िगर किए गए SSL-सक्षम MongoDB प्रतिकृति सेट से कैसे कनेक्ट करें, और अपने कोड में MongoDB विफलता व्यवहार का परीक्षण कैसे करें।
स्व-हस्ताक्षरित प्रमाणपत्रों का उपयोग करके MongoDB SSL से कनेक्ट करना
पहला कदम यह सुनिश्चित करना है कि PyMongo के सही संस्करण और इसकी निर्भरताएं स्थापित हैं। यह मार्गदर्शिका निर्भरताओं को छांटने में आपकी सहायता करती है, और ड्राइवर संगतता मैट्रिक्स यहां पाया जा सकता है।
mongo_client.MongoClient हमारे लिए रुचिकर पैरामीटर ssl . हैं और ss_ca_cert . एक एसएसएल-सक्षम मोंगोडीबी एंडपॉइंट से कनेक्ट करने के लिए जो एक स्व-हस्ताक्षरित प्रमाणपत्र का उपयोग करता है, ssl सत्य . पर सेट होना चाहिए और ss_ca_cert CA प्रमाणपत्र फ़ाइल को इंगित करना चाहिए।
यदि आप एक स्केलग्रिड ग्राहक हैं, तो आप अपने MongoDB क्लस्टर के लिए CA प्रमाणपत्र फ़ाइल को यहां दिखाए गए स्केलग्रिड कंसोल से डाउनलोड कर सकते हैं:
तो, एक कनेक्शन स्निपेट ऐसा दिखेगा:
>>> import pymongo >>> MONGO_URI = 'mongodb://rwuser:@SG-example-0.servers.mongodirector.com:27017,SG-example-1.servers.mongodirector.com:27017,SG-example-2.servers.mongodirector.com:27017/admin?replicaSet=RS-example&ssl=true' >>> client = pymongo.MongoClient(MONGO_URI, ssl = True, ssl_ca_certs = '') >>> print("Databases - " + str(client.list_database_names())) Databases - ['admin', 'local', 'test'] >>> client.close() >>>
यदि आप अपने स्वयं के हस्ताक्षरित प्रमाणपत्रों का उपयोग कर रहे हैं जहां होस्टनाम सत्यापन विफल हो सकता है, तो आपको ssl_match_hostname<भी सेट करना होगा /टीटी> गलत . के लिए पैरामीटर . जैसा कि ड्राइवर दस्तावेज़ कहता है, यह अनुशंसित नहीं है क्योंकि यह कनेक्शन को मैन-इन-द-बीच हमलों के लिए अतिसंवेदनशील बनाता है।
विफलता व्यवहार का परीक्षण
MongoDB परिनियोजन के साथ, विफलताओं को प्रमुख घटना नहीं माना जाता है क्योंकि वे पारंपरिक डेटाबेस प्रबंधन प्रणालियों के साथ थे। हालांकि अधिकांश MongoDB ड्राइवर इस घटना को सारगर्भित करने का प्रयास करते हैं, डेवलपर्स को इस तरह के व्यवहार के लिए अपने अनुप्रयोगों को समझना और डिज़ाइन करना चाहिए, क्योंकि अनुप्रयोगों को क्षणिक नेटवर्क त्रुटियों की अपेक्षा करनी चाहिए और त्रुटियों को दूर करने से पहले पुनः प्रयास करना चाहिए।
आप अपने कार्यभार के चलने के दौरान विफलताओं को प्रेरित करके अपने अनुप्रयोगों के लचीलेपन का परीक्षण कर सकते हैं। फेलओवर को प्रेरित करने का सबसे आसान तरीका rs.stepDown() कमांड चलाना है:
RS-example-0:PRIMARY> rs.stepDown() 2019-04-18T19:44:42.257+0530 E QUERY [thread1] Error: error doing query: failed: network error while attempting to run command 'replSetStepDown' on host 'SG-example-1.servers.mongodirector.com:27017' : DB.prototype.runCommand@src/mongo/shell/db.js:168:1 DB.prototype.adminCommand@src/mongo/shell/db.js:185:1 rs.stepDown@src/mongo/shell/utils.js:1305:12 @(shell):1:1 2019-04-18T19:44:42.261+0530 I NETWORK [thread1] trying reconnect to SG-example-1.servers.mongodirector.com:27017 (X.X.X.X) failed 2019-04-18T19:44:43.267+0530 I NETWORK [thread1] reconnect SG-example-1.servers.mongodirector.com:27017 (X.X.X.X) ok RS-example-0:SECONDARY>
एक सरल 'सतत' लेखक ऐप लिखकर ड्राइवरों के व्यवहार का परीक्षण करना मुझे पसंद है। यह सरल कोड होगा जो उपयोगकर्ता द्वारा बाधित किए जाने तक डेटाबेस को लिखता रहता है, और ड्राइवर और डेटाबेस व्यवहार को समझने में हमारी सहायता करने के लिए सभी अपवादों को प्रिंट करेगा। मैं यह सुनिश्चित करने के लिए लिखे गए डेटा का भी ट्रैक रखता हूं कि परीक्षण में कोई रिपोर्ट नहीं किया गया डेटा हानि नहीं है। यहां परीक्षण कोड का प्रासंगिक भाग दिया गया है जिसका उपयोग हम अपने MongoDB विफलता व्यवहार का परीक्षण करने के लिए करेंगे:
import logging import traceback ... import pymongo ... logger = logging.getLogger("test") MONGO_URI = 'mongodb://rwuser:@SG-example-0.servers.mongodirector.com:48273,SG-example-1.servers.mongodirector.com:27017,SG-example-2.servers.mongodirector.com:27017/admin?replicaSet=RS-example-0&ssl=true' try: logger.info("Attempting to connect...") client = pymongo.MongoClient(MONGO_URI, ssl = True, ssl_ca_certs = 'path-to-cacert.pem') db = client['test'] collection = db['test'] i = 0 while True: try: text = ''.join(random.choices(string.ascii_uppercase + string.digits, k = 3)) doc = { "idx": i, "date" : datetime.utcnow(), "text" : text} i += 1 id = collection.insert_one(doc).inserted_id logger.info("Record inserted - id: " + str(id)) sleep(3) except pymongo.errors.ConnectionFailure as e: logger.error("ConnectionFailure seen: " + str(e)) traceback.print_exc(file = sys.stdout) logger.info("Retrying...") logger.info("Done...") except Exception as e: logger.error("Exception seen: " + str(e)) traceback.print_exc(file = sys.stdout) finally: client.close()
जिस तरह की प्रविष्टियां यह लिखती हैं, वे इस तरह दिखती हैं:
RS-example-0:PRIMARY> db.test.find() { "_id" : ObjectId("5cb6d6269ece140f18d05438"), "idx" : 0, "date" : ISODate("2019-04-17T07:30:46.533Z"), "text" : "400" } { "_id" : ObjectId("5cb6d6299ece140f18d05439"), "idx" : 1, "date" : ISODate("2019-04-17T07:30:49.755Z"), "text" : "X63" } { "_id" : ObjectId("5cb6d62c9ece140f18d0543a"), "idx" : 2, "date" : ISODate("2019-04-17T07:30:52.976Z"), "text" : "5BX" } { "_id" : ObjectId("5cb6d6329ece140f18d0543c"), "idx" : 4, "date" : ISODate("2019-04-17T07:30:58.001Z"), "text" : "TGQ" } { "_id" : ObjectId("5cb6d63f9ece140f18d0543d"), "idx" : 5, "date" : ISODate("2019-04-17T07:31:11.417Z"), "text" : "ZWA" } { "_id" : ObjectId("5cb6d6429ece140f18d0543e"), "idx" : 6, "date" : ISODate("2019-04-17T07:31:14.654Z"), "text" : "WSR" } ..
कनेक्शन विफलता अपवाद को संभालना
ध्यान दें कि हम सभी नेटवर्क-संबंधित मुद्दों से निपटने के लिए कनेक्शन विफलता अपवाद को पकड़ते हैं जो हमें विफलताओं के कारण सामना करना पड़ सकता है - हम अपवाद को प्रिंट करते हैं और डेटाबेस को लिखने का प्रयास जारी रखते हैं। ड्राइवर दस्तावेज़ीकरण अनुशंसा करता है कि:
<ब्लॉकक्वॉट>यदि नेटवर्क त्रुटि के कारण कोई कार्रवाई विफल हो जाती है, तो ConnectionFailure उठाया जाता है और क्लाइंट पृष्ठभूमि में फिर से जुड़ जाता है। एप्लिकेशन कोड को इस अपवाद को संभालना चाहिए (यह मानते हुए कि ऑपरेशन विफल हो गया है) और फिर निष्पादित करना जारी रखना चाहिए।
चलिए इसे चलाते हैं और इसे निष्पादित करते समय डेटाबेस फेलओवर करते हैं। यहाँ क्या होता है:
04/17/2019 12:49:17 PM INFO Attempting to connect... 04/17/2019 12:49:20 PM INFO Record inserted - id: 5cb6d3789ece145a2408cbc7 04/17/2019 12:49:23 PM INFO Record inserted - id: 5cb6d37b9ece145a2408cbc8 04/17/2019 12:49:27 PM INFO Record inserted - id: 5cb6d37e9ece145a2408cbc9 04/17/2019 12:49:30 PM ERROR PyMongoError seen: connection closed Traceback (most recent call last): id = collection.insert_one(doc).inserted_id File "C:\Users\Random\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pymongo\collection.py", line 693, in insert_one session=session), ... File "C:\Users\Random\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pymongo\network.py", line 173, in receive_message _receive_data_on_socket(sock, 16)) File "C:\Users\Random\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pymongo\network.py", line 238, in _receive_data_on_socket raise AutoReconnect("connection closed") pymongo.errors.AutoReconnect: connection closed 04/17/2019 12:49:30 PM INFO Retrying... 04/17/2019 12:49:42 PM INFO Record inserted - id: 5cb6d3829ece145a2408cbcb 04/17/2019 12:49:45 PM INFO Record inserted - id: 5cb6d3919ece145a2408cbcc 04/17/2019 12:49:49 PM INFO Record inserted - id: 5cb6d3949ece145a2408cbcd 04/17/2019 12:49:52 PM INFO Record inserted - id: 5cb6d3989ece145a2408cbce
ध्यान दें कि ड्राइवर को नई टोपोलॉजी को समझने, नए प्राइमरी से जुड़ने और लिखना जारी रखने में लगभग 12 सेकंड का समय लगता है। उठाया गया अपवाद त्रुटियां . है <टीटी>। स्वतः पुनः कनेक्ट करें जो ConnectionFailure . का उपवर्ग है ।
PyMongo Tutorial:टेस्टिंग MongoDB फेलओवर आपके पायथन ऐप में ट्वीट करने के लिए क्लिक करें
आप कुछ और रन बनाकर देख सकते हैं कि अन्य अपवाद क्या हैं। उदाहरण के लिए, यहां एक और अपवाद ट्रेस है जिसका मुझे सामना करना पड़ा:
id = collection.insert_one(doc).inserted_id File "C:\Users\Random\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pymongo\collection.py", line 693, in insert_one session=session), ... File "C:\Users\Randome\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pymongo\network.py", line 150, in command parse_write_concern_error=parse_write_concern_error) File "C:\Users\Random\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pymongo\helpers.py", line 132, in _check_command_response raise NotMasterError(errmsg, response) pymongo.errors.NotMasterError: not master
यह अपवाद ConnectionFailure का एक उपवर्ग भी है।
'फिर से कोशिश करें' पैरामीटर
MongoDB फेलओवर व्यवहार का परीक्षण करने के लिए एक अन्य क्षेत्र यह देखना होगा कि अन्य पैरामीटर विविधताएं परिणामों को कैसे प्रभावित करती हैं। एक पैरामीटर जो प्रासंगिक है वह है 'पुन:प्रयास करें ':
<ब्लॉकक्वॉट>retryWrites:(बूलियन) क्या इस MongoClient के भीतर निष्पादित समर्थित लेखन कार्यों को MongoDB 3.6+ पर नेटवर्क त्रुटि के बाद एक बार पुनः प्रयास किया जाएगा। डिफ़ॉल्ट से गलत.
आइए देखें कि यह पैरामीटर फेलओवर के साथ कैसे काम करता है। कोड में किया गया एकमात्र परिवर्तन है:
client = pymongo.MongoClient(MONGO_URI, ssl = True, ssl_ca_certs = 'path-to-cacert.pem', retryWrites = True)
चलिए इसे अभी चलाते हैं, और फिर डेटाबेस सिस्टम फेलओवर करते हैं:
04/18/2019 08:49:30 PM INFO Attempting to connect... 04/18/2019 08:49:35 PM INFO Record inserted - id: 5cb895869ece146554010c77 04/18/2019 08:49:38 PM INFO Record inserted - id: 5cb8958a9ece146554010c78 04/18/2019 08:49:41 PM INFO Record inserted - id: 5cb8958d9ece146554010c79 04/18/2019 08:49:44 PM INFO Record inserted - id: 5cb895909ece146554010c7a 04/18/2019 08:49:48 PM INFO Record inserted - id: 5cb895939ece146554010c7b <<< Failover around this time 04/18/2019 08:50:04 PM INFO Record inserted - id: 5cb895979ece146554010c7c 04/18/2019 08:50:07 PM INFO Record inserted - id: 5cb895a79ece146554010c7d 04/18/2019 08:50:10 PM INFO Record inserted - id: 5cb895aa9ece146554010c7e 04/18/2019 08:50:14 PM INFO Record inserted - id: 5cb895ad9ece146554010c7f ...
ध्यान दें कि कैसे फेलओवर के बाद इंसर्ट में लगभग 12 सेकंड लगते हैं, लेकिन retryWrites के रूप में सफलतापूर्वक पूरा हो जाता है पैरामीटर सुनिश्चित करता है कि विफल लेखन का पुन:प्रयास किया गया है। याद रखें कि इस पैरामीटर को सेट करने से आप ConnectionFailure को संभालने से बच नहीं सकते हैं अपवाद - आपको पढ़ने और अन्य कार्यों के बारे में चिंता करने की ज़रूरत है जिनके व्यवहार इस पैरामीटर से प्रभावित नहीं होते हैं। यह समर्थित संचालन के लिए भी पूरी तरह से समस्या का समाधान नहीं करता है - कभी-कभी विफलताओं को पूरा होने में अधिक समय लग सकता है और पुन:प्रयास करें अकेले ही काफी नहीं होगा।
नेटवर्क टाइमआउट मान कॉन्फ़िगर करना
rs.stepDown() एक त्वरित विफलता उत्पन्न करता है, क्योंकि प्रतिकृति सेट प्राथमिक को द्वितीयक बनने के लिए निर्देशित किया जाता है, और माध्यमिक नए प्राथमिक को निर्धारित करने के लिए चुनाव करते हैं। उत्पादन परिनियोजन में, नेटवर्क लोड, विभाजन, और ऐसी अन्य समस्याएं प्राथमिक सर्वर की अनुपलब्धता का पता लगाने में देरी करती हैं, इस प्रकार, आपके विफलता समय को लम्बा खींचती हैं। आप अक्सर PyMongo त्रुटियों जैसे errors.ServerSelectionTimeoutError में भी भाग लेंगे , errors.NetworkTimeout, आदि नेटवर्क समस्याओं और विफलताओं के दौरान।
यदि यह बहुत बार होता है, तो आपको टाइमआउट पैरामीटर को बदलना होगा। संबंधित MongoClient टाइमआउट पैरामीटर serverSelectionTimeoutMS . हैं , connectTimeoutMS, और socketTimeoutMS . इनमें से serverSelectionTimeoutMS . के लिए बड़े मान का चयन करना अक्सर विफलताओं के दौरान त्रुटियों से निपटने में मदद करता है:
<ब्लॉकक्वॉट>serverSelectionTimeoutMS:(पूर्णांक) नियंत्रित करता है कि डेटाबेस ऑपरेशन करने के लिए ड्राइवर कितनी देर तक (मिलीसेकंड में) उपलब्ध, उपयुक्त सर्वर को खोजने के लिए प्रतीक्षा करेगा; जबकि यह प्रतीक्षा कर रहा है, एकाधिक सर्वर निगरानी संचालन किए जा सकते हैं, प्रत्येक कनेक्टटाइमआउटएमएस द्वारा नियंत्रित किया जाता है। 30000 (30 सेकंड) के लिए डिफ़ॉल्ट।
अपने Python एप्लिकेशन में MongoDB का उपयोग करने के लिए तैयार हैं? यह देखने के लिए कि आप केवल 5 आसान चरणों में कैसे उठ सकते हैं और कैसे चल सकते हैं, यह देखने के लिए हमारा Python और MongoDB के साथ आरंभ करना लेख देखें। स्केलग्रिड एकमात्र MongoDB DBaaS प्रदाता है जो आपको आपके इंस्टेंस तक पूर्ण SSH एक्सेस देता है ताकि आप अपने Python सर्वर को उसी मशीन पर चला सकें जिस पर आपका MongoDB सर्वर है। समर्पित सर्वर, उच्च उपलब्धता और आपदा रिकवरी के साथ AWS, Azure, या DigitalOcean पर अपने MongoDB क्लाउड परिनियोजन को स्वचालित करें ताकि आप अपने Python एप्लिकेशन को विकसित करने पर ध्यान केंद्रित कर सकें।