1'use strict'; 2 3const { 4 ArrayIsArray, 5 Set, 6 Symbol, 7} = primordials; 8 9const { hasTracing } = internalBinding('config'); 10const kHandle = Symbol('handle'); 11const kEnabled = Symbol('enabled'); 12const kCategories = Symbol('categories'); 13 14const kMaxTracingCount = 10; 15 16const { 17 ERR_TRACE_EVENTS_CATEGORY_REQUIRED, 18 ERR_TRACE_EVENTS_UNAVAILABLE, 19 ERR_INVALID_ARG_TYPE 20} = require('internal/errors').codes; 21 22const { ownsProcessState } = require('internal/worker'); 23if (!hasTracing || !ownsProcessState) 24 throw new ERR_TRACE_EVENTS_UNAVAILABLE(); 25 26const { CategorySet, getEnabledCategories } = internalBinding('trace_events'); 27const { customInspectSymbol } = require('internal/util'); 28const { format } = require('internal/util/inspect'); 29 30const enabledTracingObjects = new Set(); 31 32class Tracing { 33 constructor(categories) { 34 this[kHandle] = new CategorySet(categories); 35 this[kCategories] = categories; 36 this[kEnabled] = false; 37 } 38 39 enable() { 40 if (!this[kEnabled]) { 41 this[kEnabled] = true; 42 this[kHandle].enable(); 43 enabledTracingObjects.add(this); 44 if (enabledTracingObjects.size > kMaxTracingCount) { 45 process.emitWarning( 46 'Possible trace_events memory leak detected. There are more than ' + 47 `${kMaxTracingCount} enabled Tracing objects.` 48 ); 49 } 50 } 51 } 52 53 disable() { 54 if (this[kEnabled]) { 55 this[kEnabled] = false; 56 this[kHandle].disable(); 57 enabledTracingObjects.delete(this); 58 } 59 } 60 61 get enabled() { 62 return this[kEnabled]; 63 } 64 65 get categories() { 66 return this[kCategories].join(','); 67 } 68 69 [customInspectSymbol](depth, opts) { 70 if (typeof depth === 'number' && depth < 0) 71 return this; 72 73 const obj = { 74 enabled: this.enabled, 75 categories: this.categories 76 }; 77 return `Tracing ${format(obj)}`; 78 } 79} 80 81function createTracing(options) { 82 if (typeof options !== 'object' || options === null) 83 throw new ERR_INVALID_ARG_TYPE('options', 'object', options); 84 85 if (!ArrayIsArray(options.categories)) { 86 throw new ERR_INVALID_ARG_TYPE('options.categories', 'string[]', 87 options.categories); 88 } 89 90 if (options.categories.length <= 0) 91 throw new ERR_TRACE_EVENTS_CATEGORY_REQUIRED(); 92 93 return new Tracing(options.categories); 94} 95 96module.exports = { 97 createTracing, 98 getEnabledCategories 99}; 100