Skip to content

Commit 1374e7a

Browse files
Qardclaude
andcommitted
fix: Chain natively for Promise instances, side-chain for subclasses/thenables
Mirror the behaviour of Node.js core diagnostics_channel tracePromise: - Native Promise (promise.constructor === Promise): chain via .then() and return the chained promise. Safe because there is no subclass API to preserve and the native .then() returns a native Promise. - Promise subclass or other thenable: side-chain .then() purely for the asyncStart/asyncEnd event callbacks, then return the original promise unchanged. This preserves any subclass-specific methods on the return value (e.g. Anthropic SDK's APIPromise.withResponse()). Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
1 parent bb5e08b commit 1374e7a

1 file changed

Lines changed: 24 additions & 1 deletion

File tree

lib/transforms.js

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -391,9 +391,32 @@ function wrapPromise (state, node) {
391391
try {
392392
let promise = __apm$traced();
393393
if (typeof promise?.then !== 'function') {
394-
__apm$ctx.result = promise;
394+
__apm$ctx.result = promise;
395395
return promise;
396396
}
397+
// Mirror Node.js core diagnostics_channel behaviour: for native Promise
398+
// instances, chain normally (safe since there is no subclass API to
399+
// preserve). For Promise subclasses and other thenables, side-chain the
400+
// callbacks for event publishing and return the original so that any
401+
// subclass-specific methods (e.g. APIPromise.withResponse()) remain
402+
// accessible to the caller.
403+
if (promise instanceof Promise && promise.constructor === Promise) {
404+
return promise.then(
405+
result => {
406+
__apm$ctx.result = result;
407+
${channelVariable}.asyncStart.publish(__apm$ctx);
408+
${channelVariable}.asyncEnd.publish(__apm$ctx);
409+
return result;
410+
},
411+
err => {
412+
__apm$ctx.error = err;
413+
${channelVariable}.error.publish(__apm$ctx);
414+
${channelVariable}.asyncStart.publish(__apm$ctx);
415+
${channelVariable}.asyncEnd.publish(__apm$ctx);
416+
throw err;
417+
}
418+
);
419+
}
397420
promise.then(
398421
result => {
399422
__apm$ctx.result = result;

0 commit comments

Comments
 (0)