All files / lib/internal inspector_async_hook.js

86.84% Statements 66/76
87.5% Branches 14/16
100% Functions 7/7
86.84% Lines 66/76

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77145x 145x 145x 145x 145x 145x 145x 145x 145x 2x 2x 2x 2x 2x 2x 2x 6x 6x 6x 6x 6x 6x 6x 1x 1x 2x 2x 2x 3x 3x 1x 2x 2x 2x 3x 3x 1x 2x 2x 2x 1x 1x 1x 2x 2x 2x 2x 2x 145x 2x 2x 2x                     2x 2x 2x 2x 145x 3x 3x 3x 3x 145x 145x 145x 145x 145x  
'use strict';
 
let hook;
let config;
 
const {
  SafeSet,
} = primordials;
 
function lazyHookCreation() {
  const inspector = internalBinding('inspector');
  const { createHook } = require('async_hooks');
  config = internalBinding('config');
 
  hook = createHook({
    init(asyncId, type, triggerAsyncId, resource) {
    // It's difficult to tell which tasks will be recurring and which won't,
    // therefore we mark all tasks as recurring. Based on the discussion
    // in https://github.com/nodejs/node/pull/13870#discussion_r124515293,
    // this should be fine as long as we call asyncTaskCanceled() too.
      const recurring = true;
      if (type === 'PROMISE')
        this.promiseIds.add(asyncId);
      else
        inspector.asyncTaskScheduled(type, asyncId, recurring);
    },
 
    before(asyncId) {
      if (this.promiseIds.has(asyncId))
        return;
      inspector.asyncTaskStarted(asyncId);
    },
 
    after(asyncId) {
      if (this.promiseIds.has(asyncId))
        return;
      inspector.asyncTaskFinished(asyncId);
    },
 
    destroy(asyncId) {
      if (this.promiseIds.has(asyncId))
        return this.promiseIds.delete(asyncId);
      inspector.asyncTaskCanceled(asyncId);
    },
  });
 
  hook.promiseIds = new SafeSet();
}
 
function enable() {
  if (hook === undefined) lazyHookCreation();
  if (config.bits < 64) {
    // V8 Inspector stores task ids as (void*) pointers.
    // async_hooks store ids as 64bit numbers.
    // As a result, we cannot reliably translate async_hook ids to V8 async_task
    // ids on 32bit platforms.
    process.emitWarning(
      'Warning: Async stack traces in debugger are not available ' +
      `on ${config.bits}bit platforms. The feature is disabled.`,
      {
        code: 'INSPECTOR_ASYNC_STACK_TRACES_NOT_AVAILABLE',
      });
  } else {
    hook.enable();
  }
}
 
function disable() {
  if (hook === undefined) lazyHookCreation();
  hook.disable();
}
 
module.exports = {
  enable,
  disable
};