簡體   English   中英

節點讀取流:什么時候進行流傳輸?

[英]Node read stream: when does the streaming happen?

這是一個代碼示例,與您可以從網上獲得的文檔或文檔沒有太大不同:

var fs = require('fs');
var r = fs.createReadStream(process.argv[2], { encoding: 'utf8' });
r.on('data', function (chunk) {
    console.log("chunk: >>>" + chunk + "<<<");
});
r.on('end', function () {
    console.log("This is the end");
});

令我感到困惑的是:什么時候觸發事件的流媒體發生? 顯然,不是直接在讀取流的構造上進行的,因為這將在到達on s之前完成,並且事件監聽代碼將永遠不會執行(這是完美的)。

我擔心的:有一個理論的機會,如果事件被錯過on來電時為時已晚?

答案是否定的,在節點0.10.x和更高版本中是不可能的。 創建流時,它會暫停,因此無法dataend事件。 添加data偵聽器(但不添加end偵聽器)時,流將自動恢復。

還值得一提的是,在當前“滴答”結束之前不會發生任何IO,因此即使在同一滴答中附加data偵聽器也總是安全的,即使對於較早的節點版本也是如此。 例如:

stream.resume();
stream.on('data', ...); // <- same tick, same javascript invocation = safe

stream.resume();
setImmediate(function () {
  stream.on('data', ...); // <- different tick, different javascript invocation = unsafe
});

這聽起來可能令人困惑,但是在process.nextTick回調中添加偵聽器也是安全的,因為它實際上是在CURRENT滴答之后立即在任何IO回調之前進行調用(這種情況確實很糟糕)。

想到這一點的最簡單方法是,您提供的所有代碼都被阻止,因此,如vkurchatkin所解釋的那樣,直到當前滴答結束為止,流上才能發生任何活動。 只有當當前滴答聲的JavaScript執行完成時,流IO才能開始。

var fs = require('fs');
var r = fs.createReadStream(process.argv[2], { encoding: 'utf8' });
// Stream created in paused state, JS code is blocking IO

// We're still in the current tick so no IO could have occured since the above lines
r.on('data', function (chunk) {
  console.log("chunk: >>>" + chunk + "<<<");
});

// We're still in the current tick so no IO could have occured since the above lines
r.on('end', function () {
  console.log("This is the end");
});

// We've left the current tick so the internal IO code will now execute and call the bound events if necessary

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM