[英]Pause readable stream when piped to writable stream
I have a readable stream that I would like to pause.我有一个我想暂停的可读流。 It is piped to a writable stream.
它通过管道传输到可写流。 My code looks like this
我的代码看起来像这样
const { get } = require('https');
const { createWriteStream };
const writableStream = createWriteStream(SOME_PATH);
get(SOME_URL, (res) => {
res.pipe(writableStream);
setTimeout(() => {
res.pause();
}, 2000);
setTimeout(() => {
res.resume();
}, 4000);
});
This works well on Mac.这在 Mac 上运行良好。 But for some reason, on Windows while downloading from an
https
URL, this doesn't pause.但出于某种原因,在 Windows 上从
https
URL 下载时,这不会暂停。
I think this is because my readable stream is piped to a writable stream and the writable stream is asking for more data, which resumes the stream.我认为这是因为我的可读流通过管道传输到可写流,而可写流要求更多数据,从而恢复流。 If I unpipe, this will solve the issue.
如果我取消管道,这将解决问题。 Here is my code when I unpipe
这是我取消管道时的代码
const writableStream = createWriteStream(SOME_PATH);
get(SOME_URL, (res) => {
res.pipe(writableStream);
setTimeout(() => {
res.unpipe(writableStream);
res.pause();
}, 2000);
setTimeout(() => {
res.pipe(writableStream);
res.resume();
}, 4000);
});
This actually causes my download to pause.这实际上导致我的下载暂停。 But this creates a new issue.
但这会产生一个新问题。 After calling
res.unpipe()
, I still get data events.调用
res.unpipe()
,我仍然收到数据事件。 This means that the few milliseconds in between calling res.unpipe()
and res.pause()
, some of my data is sent to the res
pipe, but not written to writableStream
pipe.这意味着在调用
res.unpipe()
和res.pause()
之间的几毫秒内,我的一些数据被发送到res
管道,但没有写入writableStream
管道。 This ends with my downloaded file getting corrupted.这以我下载的文件损坏而告终。
Is there any way to fix this problem?有没有办法解决这个问题? I'm not married to the idea of unpiping, it's just the only solution I could come up with.
我并没有接受取消管道的想法,这只是我能想出的唯一解决方案。
I was thinking about storing the data the res
gets when not piped to writableStream
and manually passing it to writableStream
when they pipe again.我正在考虑存储未通过管道传输到
writableStream
时res
获得的数据,并在它们再次通过管道传输时手动将其传递给writableStream
。 Is that even possible?这甚至可能吗? If not, are there other ways I can go about pausing a stream when piped to a readable stream?
如果没有,是否有其他方法可以在通过管道传输到可读流时暂停流?
I figured it out.我想到了。 I'm not sure why this solution works, but it works for me.
我不确定为什么这个解决方案有效,但它对我有用。 Instead of unpiping before I paused, I created a listener for
pause
and unpipe there.我没有在暂停之前取消管道,而是在那里创建了一个用于
pause
和取消管道的侦听器。 In addition, I also set res.readableFlowing
to false manually.此外,我还手动将
res.readableFlowing
设置为 false。 With these two additions, I was able to pause and resume without the download file breaking.通过这两个添加,我能够在不破坏下载文件的情况下暂停和恢复。 Here's the implementation
这是实现
let isPaused = false;
const writableStream = createWriteStream(SOME_PATH);
get(SOME_URL, (res) => {
res.pipe(writableStream);
setTimeout(() => {
isPaused = true;
res.pause();
}, 2000);
setTimeout(() => {
isPaused = false;
res.pipe(writableStream);
res.resume();
}, 4000);
res.on('pause', () => {
// Add this flag because pause event gets called many times, and we only
// want this code to happen when we call it manually
if (isPaused) {
res.unPipe(writableStream);
res.readableFlowing = false;
}
});
});
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.