कैसे async के साथ फ़ाइल पढ़ने के लिए / ठीक से प्रतीक्षा करें?


120

मैं यह पता नहीं लगा सकता कि कैसे async/ awaitकाम करता है। मैं इसे थोड़ा समझता हूं लेकिन मैं इसे काम नहीं कर सकता।

function loadMonoCounter() {
    fs.readFileSync("monolitic.txt", "binary", async function(err, data) {
       return await new Buffer( data);
  });
}

module.exports.read = function() {
  console.log(loadMonoCounter());
};

मुझे पता है कि मैं उपयोग कर सकता हूं readFileSync, लेकिन अगर मैं करता हूं, तो मुझे पता है कि मैं कभी नहीं समझूंगा async/ awaitऔर मैं सिर्फ इस मुद्दे को दफन कर दूंगा।

लक्ष्य: कॉल करें loadMonoCounter()और किसी फ़ाइल की सामग्री लौटाएँ।

उस फ़ाइल को हर बार incrementMonoCounter()(हर पेज लोड) कहा जाता है। फ़ाइल में बाइनरी में एक डंप होता है और इसे एसएसडी पर संग्रहीत किया जाता है।

कोई फर्क नहीं पड़ता कि मैं क्या करता हूं, मुझे एक त्रुटि मिलती है या undefinedकंसोल में।


जवाबों:


165

उपयोग करने के लिए await/ asyncआपको वादे वापस करने की विधियों की आवश्यकता है। मुख्य API फ़ंक्शंस ऐसा नहीं करते हैं जैसे रैपर के बिना promisify:

const fs = require('fs');
const util = require('util');

// Convert fs.readFile into Promise version of same    
const readFile = util.promisify(fs.readFile);

function getStuff() {
  return readFile('test');
}

// Can't use `await` outside of an async function so you need to chain
// with then()
getStuff().then(data => {
  console.log(data);
})

नोट के रूप में, readFileSyncकॉलबैक नहीं लेता है, यह डेटा लौटाता है या अपवाद फेंकता है। आपको वह मान नहीं मिल रहा है जो आप चाहते हैं क्योंकि उस फ़ंक्शन को जो आप आपूर्ति करते हैं उसे अनदेखा कर दिया जाता है और आप वास्तविक रिटर्न मान पर कब्जा नहीं कर रहे हैं।


3
धन्यवाद, मुझे नहीं पता था कि मुझे कोर एपीआई को लपेटने की आवश्यकता है। आप कमाल के है।
जेरेमी डिजायर

4
कोर एपीआई आधुनिक प्रोमिस विनिर्देश और async/ के गोद लेने से पहले की तारीखें रखता है await, इसलिए यह एक आवश्यक कदम है। अच्छी खबर promisifyयह है कि यह बिना किसी गड़बड़ के काम करता है।
tadman

1
यह सामान्य रूप से FS के साथ async-wait का लाभ उठाने में सक्षम नहीं होने की गड़बड़ी को संभालता है। इसके लिए शुक्रिया! आपने मुझे एक टन बचाया! इसका कोई जवाब नहीं है कि वास्तव में यह आपकी तरह संबोधित करता है।
जेकॉब्ब्सन

3
इसके अलावा इंतजार थोड़े बेमानी है क्योंकि यह बांधा जा सकता है। केवल यदि आप स्पष्ट रूप से उदाहरण में प्रतीक्षा करना चाहते हैं, तो आप कर सकते हैं const file = await readFile...; return file;
बिगकाहुनाबर्गर

1
@ शेजीन जब तक नोड कोर एपीआई वादों पर खरा नहीं उतरता है, जो इस बिंदु पर संभावना नहीं है, तो हाँ। एनपीएम रैपर हैं जो इसे आपके लिए करते हैं, हालांकि।
tadman 20

150

चूंकि Node v11.0.0 fs वाद मूल रूप से बिना उपलब्ध हैं promisify:

const fs = require('fs').promises;
async function loadMonoCounter() {
    const data = await fs.readFile("monolitic.txt", "binary");
    return new Buffer(data);
}

4
कोई अतिरिक्त काम नहीं, स्वच्छ और सरल - यह बेहतर जवाब होना चाहिए
एडम बुबेला

2
21-अक्टूबर
-2019 तक

16
import { promises as fs } from "fs";यदि आप आयात सिंटैक्स का उपयोग करना चाहते हैं।
tr3online

21

यह @ जोएल के उत्तर का टाइपस्क्रिप्ट संस्करण है। यह नोड 11.0 के बाद प्रयोग करने योग्य है:

import { promises as fs } from 'fs';

async function loadMonoCounter() {
    const data = await fs.readFile('monolitic.txt', 'binary');
    return Buffer.from(data);
}

18

आप आसानी से readFile कमांड को इस तरह के वादे के साथ लपेट सकते हैं:

async function readFile(path) {
    return new Promise((resolve, reject) => {
      fs.readFile(path, 'utf8', function (err, data) {
        if (err) {
          reject(err);
        }
        resolve(data);
      });
    });
  }

फिर उपयोग करें:

await readFile("path/to/file");

Async फ़ंक्शन के अंदर उपयोग नहीं किया गया है?
विकासभाट

@VikasBhat हाँ, ऊपर दी गई लाइन का उपयोग किसी अन्य async फ़ंक्शन के अंदर किया जाएगा क्योंकि कल्पना को ऐसा करने की आवश्यकता होती है।
व्हॉटशॉटड

8

fs.promisesNode v11.0.0 के बाद से आप मूल रूप से उपलब्ध का उपयोग कर सकते हैं

import fs from 'fs';

const readFile = async filePath => {
  try {
    const data = await fs.promises.readFile(filePath, 'utf8')
    return data
  }
  catch(err) {
    console.log(err)
  }
}

यदि आप केवल वादों का उपयोग करना चाहते हैं, तो आप कुछ ऐसा कर सकते हैंconst fs = require('fs').promises
nathanfranke

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.