Получить асинхронный результат в массиве async.filter () nodejs - PullRequest
0 голосов
/ 17 марта 2019

Необходимо проанализировать некоторые XML-файлы из массива mass со значениями file_path.Попробуйте использовать async, fs, xml2js.При использовании одной строки file_path все работает отлично.Но когда я использую aync.filter() с массивом, я не могу понять, как я могу return result из xml.parseString()

const fs = require('fs');
const xml2js = require('xml2js');
const async = require('async');

var mass=['/file1.xml','/fil2.xml','/file3.xml',...]

async.filter(mass, async function(file_path, callback){
    if(fs.statSync(file_path)['size']>0){
        fs.readFileSync(file_path, 'utf8', function(err, data) {        
            xml.parseString(data, function (err, result) {
               console.log(Object.keys(result)[0]);
               return result; //need get this result to results array
            })
        }) 
    }
}, function(err, results) {
    console.log(results)
});

Кто может понять, как это работает и что мне нужно изменить в моем коде.Большое спасибо!

1 Ответ

0 голосов
/ 17 марта 2019

Вы пытаетесь отобразить и отфильтровать одновременно.Поскольку условие фильтра доступно синхронно, используйте для этого метод массива filter, а затем передайте его в async.map.

Затем вы должны вызвать функцию обратного вызова, которую async.map предоставляет вам, передав ей результат.Поэтому не возвращайте его, а вызывайте обратный вызов.

Метод readFileSync не принимает обратный вызов, как его асинхронный аналог.Он просто возвращает данные.

Кроме того, отбросьте ключевое слово async, поскольку вы вообще не используете ключевое слово await.

async.map(mass.filter((file_path) => fs.statSync(file_path).size > 0), 
    function(file_path, callback){
        var data = fs.readFileSync(file_path, 'utf8');
        xml.parseString(data, function (err, result) {
           console.log(Object.keys(result)[0]);
           callback(null, result);
        }) 
    }, function(err, results) {
        console.log(results)
    }); 

Однако следует отметить, чтопоскольку Node теперь поставляется с Promise API и даже с расширением async/await, модуль async стал гораздо менее интересным.Рассмотрите возможность использования обещаний.

const promises = mass.filter(file_path => {
    return fs.statSync(file_path).size > 0
}).map(function(file_path) {
    return new Promise(resolve => {
        const data = fs.readFileSync(file_path, 'utf8');
        xml.parseString(data, function (err, result) {
            console.log(Object.keys(result)[0]);
            resolve(result);
        });
    }); 
});
Promise.all(promises).then(results => {
    console.log(results);
}); 
...