diff --git a/doc/api/async_context.md b/doc/api/async_context.md index 1194a313f45553..065aafd22181a6 100644 --- a/doc/api/async_context.md +++ b/doc/api/async_context.md @@ -446,6 +446,10 @@ added: - v14.8.0 - v12.19.0 changes: + - version: REPLACEME + pr-url: https://github.com/nodejs/node/pull/42177 + description: Changed the default when `thisArg` is undefined to use `this` + from the caller. - version: v16.0.0 pr-url: https://github.com/nodejs/node/pull/36782 description: Added optional thisArg. @@ -468,6 +472,10 @@ added: - v14.8.0 - v12.19.0 changes: + - version: REPLACEME + pr-url: https://github.com/nodejs/node/pull/42177 + description: Changed the default when `thisArg` is undefined to use `this` + from the caller. - version: v16.0.0 pr-url: https://github.com/nodejs/node/pull/36782 description: Added optional thisArg. diff --git a/lib/async_hooks.js b/lib/async_hooks.js index af5a37b749d94b..6cc2052474d9c2 100644 --- a/lib/async_hooks.js +++ b/lib/async_hooks.js @@ -5,6 +5,7 @@ const { ArrayPrototypeIndexOf, ArrayPrototypePush, ArrayPrototypeSplice, + ArrayPrototypeUnshift, FunctionPrototypeBind, NumberIsSafeInteger, ObjectDefineProperties, @@ -223,15 +224,19 @@ class AsyncResource { return this[trigger_async_id_symbol]; } - bind(fn, thisArg = this) { + bind(fn, thisArg) { validateFunction(fn, 'fn'); - const ret = - FunctionPrototypeBind( - this.runInAsyncScope, - this, - fn, - thisArg); - ObjectDefineProperties(ret, { + let bound; + if (thisArg === undefined) { + const resource = this; + bound = function(...args) { + ArrayPrototypeUnshift(args, fn, this); + return ReflectApply(resource.runInAsyncScope, resource, args); + }; + } else { + bound = FunctionPrototypeBind(this.runInAsyncScope, this, fn, thisArg); + } + ObjectDefineProperties(bound, { 'length': { configurable: true, enumerable: false, @@ -245,7 +250,7 @@ class AsyncResource { writable: true, } }); - return ret; + return bound; } static bind(fn, type, thisArg) { diff --git a/test/parallel/test-asyncresource-bind.js b/test/parallel/test-asyncresource-bind.js index a9f613d9302edf..29de9bbb0f10bb 100644 --- a/test/parallel/test-asyncresource-bind.js +++ b/test/parallel/test-asyncresource-bind.js @@ -41,7 +41,7 @@ const fn3 = asyncResource.bind(common.mustCall(function() { fn3(); const fn4 = asyncResource.bind(common.mustCall(function() { - assert.strictEqual(this, asyncResource); + assert.strictEqual(this, undefined); })); fn4(); @@ -49,3 +49,8 @@ const fn5 = asyncResource.bind(common.mustCall(function() { assert.strictEqual(this, false); }), false); fn5(); + +const fn6 = asyncResource.bind(common.mustCall(function() { + assert.strictEqual(this, 'test'); +})); +fn6.call('test');