2013-06-11 15 views
5

में फ़ाइलों को पारस्परिक रूप से लिखना मेरे पास एक Node.js एप्लिकेशन है जो फ़ाइल में कुछ कॉन्फ़िगरेशन डेटा संग्रहीत करता है। यदि आप कुछ सेटिंग्स बदलते हैं, तो कॉन्फ़िगरेशन फ़ाइल डिस्क पर लिखी जाती है।नोड.जेएस

फिलहाल, मैं एक साधारण fs.writeFile का उपयोग कर रहा हूं।

अब मेरा प्रश्न है: फ़ाइल के दौरान नोड.जेएस क्रैश होने पर क्या होता है? क्या डिस्क पर दूषित फ़ाइल होने का मौका है? या Node.js गारंटी देता है कि फ़ाइल परमाणु तरीके से लिखा गया है, ताकि पुराना या नया संस्करण मान्य हो?

यदि नहीं, तो मैं इस तरह की गारंटी कैसे लागू कर सकता हूं? क्या इसके लिए कोई मॉड्यूल हैं?

उत्तर

7

क्या होता है जब फ़ाइल लिखा जा रहा है जब Node.js क्रैश हो जाता है? डिस्क पर दूषित फ़ाइल होने का मौका है? या Node.js गारंटी देता है कि फ़ाइल एक परमाणु तरीके से लिखा गया है, ताकि पुराना या नया संस्करण मान्य है?

नोड सिस्टम कॉल पर केवल एक (पतला) एसिंक रैपर लागू करता है, इस प्रकार यह लिखने की परमाणुता के बारे में कोई गारंटी नहीं देता है। वास्तव में, fs.writeAll बार-बार fs.write पर कॉल करता है जब तक कि सभी डेटा लिखे नहीं जाते। आप सही हैं कि जब Node.js क्रैश हो जाता है, तो आप दूषित फ़ाइल के साथ समाप्त हो सकते हैं।

यदि नहीं, तो मैं इस तरह की गारंटी कैसे लागू कर सकता हूं? क्या इसके लिए कोई मॉड्यूल हैं?

सबसे सरल समाधान जो मैं साथ आ सकता हूं वह है उदाहरण के लिए एफ़टीपी अपलोड के लिए:

  1. सामग्री को एक अलग नाम से अस्थायी फ़ाइल में सहेजें।
  2. जब सामग्री डिस्क पर लिखी जाती है, तो गंतव्य फ़ाइल में अस्थायी फ़ाइल का नाम बदलें।

man page उस जगह (लिनक्स या OSX की तरह यूनिक्स सिस्टम पर) में Newpath का एक उदाहरण छोड़ने के लिए की गारंटी देता है नाम बदलने कहते हैं।

+0

मैं OSX में इस समस्या को पूरी तरह हल नहीं है कि इस बात की पुष्टि कर सकते हैं, लेकिन यह http://manpages.courier-mta.org/htmlman7/pipe.7.html, PIPE_BUF के अनुसार फ़ाइल भ्रष्टाचार –

6

fs.writeFile, fs मॉड्यूल में अन्य सभी विधियों की तरह मानक पॉज़िक्स कार्यों के आसपास सरल रैपर के रूप में लागू किया गया है (जैसा कि docs में बताया गया है)।

नोडजेस कोड में थोड़ा सा खोदना, कोई देख सकता है कि fs.js, जहां सभी रैपर परिभाषित किए गए हैं, fs.c का उपयोग सभी फाइल सिस्टम कॉल के लिए करता है। अधिक विशेष रूप से, बफर की सामग्री लिखने के लिए write विधि का उपयोग किया जाता है। ऐसा लगता है कि लिखने के लिए POSIX specification स्पष्ट रूप से कहा गया है कि:

परमाणु/गैर-परमाणु: एक लिखने परमाणु है अगर पूरे एक आपरेशन में लिखा राशि किसी अन्य प्रक्रिया से डेटा के साथ interleaved नहीं है। यह तब उपयोगी होता है जब कई लेखक एकल पाठक को डेटा भेजते हैं। अनुप्रयोगों को यह जानने की आवश्यकता है कि पर लिखने का अनुरोध कितना बड़ा हो सकता है। इस अधिकतम को {PIPE_BUF} कहा जाता है। आईईईई स्टडी 1003 की यह मात्रा।1-2001 यह नहीं कहता कि {PIPE_BUF} बाइट्स से अधिक के लिए अनुरोध लिखने परमाणु हैं, लेकिन की आवश्यकता है जो {PIPE_BUF} या कम बाइट्स लिखते हैं, परमाणु होंगे।

तो ऐसा लगता है कि यह लिखना बहुत सुरक्षित है, जब तक बफर का आकार PIPE_BUF से छोटा होता है। यह स्थिर है जो सिस्टम-निर्भर है हालांकि, आपको इसे कहीं और जांचना पड़ सकता है।

+0

की घटनाओं को कम करता है कम से कम 512 बाइट होने की आवश्यकता है, और लिनक्स में 4.096 बाइट्स है। इसे इंगित करने के लिए धन्यवाद, क्योंकि यह वास्तव में अच्छी और रोचक सामग्री है :-) –

2

write-file-atomic आपको जो चाहिए वह करेगा। यह अस्थायी फ़ाइल को लिखता है, फिर नाम बदलें। यह सुरक्षित है।