stream: use new AsyncResource instead of bind

The bind method uses ObjectDefineProperty that shows up
in flamegraphs. This changes it to avoid the utility.

Signed-off-by: Matteo Collina <hello@matteocollina.com>
PR-URL: https://github.com/nodejs/node/pull/59867
Reviewed-By: Robert Nagy <ronagy@icloud.com>
Reviewed-By: Ruben Bridgewater <ruben@bridgewater.de>
Reviewed-By: Rafael Gonzaga <rafael.nunu@hotmail.com>
Reviewed-By: James M Snell <jasnell@gmail.com>
Reviewed-By: Luigi Pinca <luigipinca@gmail.com>
Reviewed-By: Stephen Belanger <admin@stephenbelanger.com>
This commit is contained in:
Matteo Collina authored and Antoine du Hamel committed 2025-10-07 17:29:37 +02:00
1 parent 6d24b88fbc
commit ba00875f01
1 file changed
+12 -3
+12 -3
View File
@@ -45,7 +45,7 @@ const {
} = require('internal/streams/utils');
// Lazy load
let AsyncLocalStorage;
let AsyncResource;
let addAbortListener;
function isRequest(stream) {
@@ -54,6 +54,14 @@ function isRequest(stream) {
const nop = () => {};
function bindAsyncResource(fn, type) {
AsyncResource ??= require('async_hooks').AsyncResource;
const resource = new AsyncResource(type);
return function(...args) {
return resource.runInAsyncScope(fn, this, ...args);
};
}
function eos(stream, options, callback) {
if (arguments.length === 2) {
callback = options;
@@ -66,8 +74,9 @@ function eos(stream, options, callback) {
validateFunction(callback, 'callback');
validateAbortSignal(options.signal, 'options.signal');
AsyncLocalStorage ??= require('async_hooks').AsyncLocalStorage;
callback = once(AsyncLocalStorage.bind(callback));
// Avoid AsyncResource.bind() because it calls ObjectDefineProperties which
// is a bottleneck here.
callback = once(bindAsyncResource(callback, 'STREAM_END_OF_STREAM'));
if (isReadableStream(stream) || isWritableStream(stream)) {
return eosWeb(stream, options, callback);