Nodejs Потоковые обещания пишут только первое - PullRequest
0 голосов
/ 20 февраля 2020

Я пытаюсь создать поток, который записывает в несколько файлов, используя генератор asyn c.

Использование обещаний сокращения выполняется последовательно, поэтому желаемый результат:

$ wc -l *
42 f1.csv
98 f2.csv
78 f3.csv

но я получаю следующий результат:

$ wc -l *
42 f1.csv // only the first one is good
0  f2.csv // nothing in
0  f3.csv // same

AsyncGenerator () - это поиск в ElasticSearch Scroll ( Do c). Я посылаю ему разные запросы на каждое обещание.

const { Readable } = require('stream');
const fs = require('fs');
const util = require('util');
const stream = require('stream');
const pipeline = util.promisify(stream.pipeline);

async function* Query(params) {

    var response = await ESClient.search(params);

    while (true) {
        const sourceHits = response.hits.hits;

        if (sourceHits.length === 0) {
            break;
        }

        for (const hit of sourceHits) {
            yield hit;
        }

        if (!response._scroll_id) {
            break;
        }

        response = await ESClient.scroll({
            scrollId: response._scroll_id,
            scroll: params.scroll
        });
    }
}

async function* AsyncGenerator() {

        const params = {
            index: 'apache-logs',
            scroll: '5s',
            _source: ["foo"],
            size: 2048,
            body: { query } // ElasticSearch DSL Query
        };

        for await (const res of Query(params)) {
            yield res;
        }
    }

async function WriteToFile(file) {

        return new Promise(async (resolve, reject) => {
            const input = Readable.from(AsyncGenerator());
            const output = fs.createWriteStream(file + '.csv');

            await pipeline(
                input,
                json2csv,
                output
            );
            resolve();   
        });
}

const lists = ["f1", "f2", "f3"];

const last = lists.reduce(async (previous, next) => {
            await previous;
            return WriteToFile(next);
}, Promise.resolve());

last.then(_ => { 
    console.log("DONE");  
}).catch((e) => {
    console.log(e);
});

(Lorem ipsum lalalaalalal (sry stackoverflow просит предоставить более подробную информацию, но у меня нет lol))

1 Ответ

0 голосов
/ 21 февраля 2020

Привет, я не уверен, потому что мои знакомые бедны в NodeJs. Я думаю, что вы только один раз вызываете функцию, которая создает ваш .csv

const lists = ["f1", "f2", "f3"];

const last = lists.reduce(async (previous, next) => {
            await previous;
            return WriteToFile(next);
}, Promise.resolve());
...