节点流 - 将多个转换流输出到单个PassThrough流

时间:2017-06-09 19:53:07

标签: javascript node.js node-streams

我经常需要下载/解析一堆Json数据,大约1000~1.000.000行。

每个请求的块大小限制为5000.所以我想在当时触发一堆请求,通过它自己的Transfomer流输出每个输出来过滤掉键/值,然后写入一个将其输出写入数据库的 组合 流。

但是每次尝试它都不起作用,或者由于许多事件监听器被设置而产生错误。如果我理解了最后一根管道,那么这似乎是正确的。始终是链中的下一个参考。

这是一些代码(很多次改变了,所以没什么意义)。

问题是:将多个流连接到一个是不好的做法?谷歌也没有展示很多相关内容。

谢谢!

brokerApi / getCandles.js

// The 'combined output' stream
let passStream = new Stream.PassThrough();

countChunks.forEach(chunk => {
    let arr = [];
    let leftOver = '';
    let startFound = false;
    let lastPiece = false;
    let firstByte = false;
    let now = Date.now();

    let transformStream = this._client

        // Returns PassThrough stream
        .getCandles(instrument, chunk.from, chunk.until, timeFrame, chunk.count)
        .on('error', err => console.error(err) || passStream.emit('error', err))
        .on('end', () => {
            if (++finished === countChunks.length)
                passStream.end();
        })
        .pipe(passStream);

    transformStream._transform = function(data, type, done) {
        /** Treansform to typedArray **/

        this.push(/** Taansformed value **/)
    }
});

额外 - '消费的其他文件'流(写入DB)

DataLayer.js

    brokerApi.getCandles(instrument, timeFrame, from, until, count)
            .on('data', async (buf: NodeBuffer) => {
                this._dataLayer.write(instrument, timeFrame, buf);

                if (from && until) {
                    await this._mapper.update(instrument, timeFrame, from, until, buf.length / (10 * Float64Array.BYTES_PER_ELEMENT));
                } else {
                    if (buf.length) {
                        if (!from)
                            from = buf.readDoubleLE(0);

                        if (!until) {
                            until = buf.readDoubleLE(buf.length - (10 * Float64Array.BYTES_PER_ELEMENT));
                            console.log('UNTIL TUNIL', until);
                        }

                        if (from && until)
                            await this._mapper.update(instrument, timeFrame, from, until, buf.length / (10 * Float64Array.BYTES_PER_ELEMENT));
                    }
                }

            })
            .on('end', () => {
                winston.info(`Cache: Fetching ${instrument} took ${Date.now() - now} ms`);
                resolve()
            })
            .on('error', reject)

1 个答案:

答案 0 :(得分:1)

查看来自highlandjs的信息流助手,例如(未经测试的伪代码):

function getCandle(candle) {...}

_(chunks).map(getCandle).parallel(5000).pipe(...)