appdynamics 24.10.0 → 25.5.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +0 -1
- package/appdynamics_version.json +3 -3
- package/lib/core/agent.js +18 -12
- package/lib/core/opentelemetry-tracer.js +3 -2
- package/lib/libagent/libagent-connector.js +33 -0
- package/lib/libagent/transaction-sender.js +30 -3
- package/lib/probes/apollo-entry-probe.js +8 -4
- package/lib/probes/cassandra-probe.js +4 -0
- package/lib/probes/cluster-probe.js +4 -0
- package/lib/probes/couchbase-probe.js +12 -3
- package/lib/probes/disk-probe.js +4 -0
- package/lib/probes/dynamodb-probe.js +4 -0
- package/lib/probes/express-probe.js +4 -0
- package/lib/probes/http-common.js +29 -5
- package/lib/probes/http-entry-probe.js +4 -3
- package/lib/probes/http-exit-probe.js +110 -9
- package/lib/probes/http-probe.js +11 -3
- package/lib/probes/http2-entry-probe.js +1 -1
- package/lib/probes/ioredis-probe.js +4 -0
- package/lib/probes/memcached-probe.js +4 -0
- package/lib/probes/mongodb-probe.js +14 -10
- package/lib/probes/mssql-probe.js +4 -0
- package/lib/probes/mysql-probe.js +4 -0
- package/lib/probes/net-probe.js +4 -0
- package/lib/probes/nsolid-probe.js +4 -0
- package/lib/probes/pg-probe.js +4 -0
- package/lib/probes/process-probe.js +4 -0
- package/lib/probes/redis-probe.js +5 -0
- package/lib/probes/socket.io-probe.js +4 -0
- package/lib/probes/tedious-probe.js +4 -0
- package/lib/probes/winston-probe.js +5 -0
- package/lib/profiler/profiler.js +55 -0
- package/lib/transactions/cookie-util.js +1 -1
- package/lib/v8/cpu-profiler.js +4 -0
- package/lib/v8/gc-stats.js +2 -0
- package/lib/v8/heap-profiler.js +4 -0
- package/package.json +9 -15
- package/packageBck.json +9 -15
package/README.md
CHANGED
package/appdynamics_version.json
CHANGED
package/lib/core/agent.js
CHANGED
|
@@ -55,7 +55,7 @@ function Agent() {
|
|
|
55
55
|
this.initialized = false;
|
|
56
56
|
this.version = agentVersion.version;
|
|
57
57
|
this.compatibilityVersion = agentVersion.compatibilityVersion;
|
|
58
|
-
this.nextId =
|
|
58
|
+
this.nextId = parseInt(crypto.randomBytes(4).toString('hex'), 16) % 1e6;
|
|
59
59
|
this.appdNative = undefined;
|
|
60
60
|
this.meta = [];
|
|
61
61
|
|
|
@@ -124,8 +124,7 @@ Agent.prototype.recursiveMkDir = function (dir) {
|
|
|
124
124
|
var dirsToMake = [];
|
|
125
125
|
var currDir = path.normalize(dir);
|
|
126
126
|
var parentDir = path.dirname(currDir);
|
|
127
|
-
|
|
128
|
-
while (controlVar) {
|
|
127
|
+
while (currDir !== parentDir) {
|
|
129
128
|
if (fs.existsSync(currDir))
|
|
130
129
|
break;
|
|
131
130
|
dirsToMake.push(currDir);
|
|
@@ -229,17 +228,25 @@ Agent.prototype.init = function (opts) {
|
|
|
229
228
|
|
|
230
229
|
self.backendConnector = new LibAgent(this);
|
|
231
230
|
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
231
|
+
// agent_deployment_mode = 'appd' || 'dual' || 'hybrid'
|
|
232
|
+
let agent_deployment_mode = opts.agent_deployment_mode || process.env.agent_deployment_mode;
|
|
233
|
+
if(agent_deployment_mode == 'dual' || opts.openTelemetry && opts.openTelemetry.enabled) {
|
|
234
|
+
const url = require('url');
|
|
235
|
+
let collectorEndpoint = process.env.OTEL_EXPORTER_OTLP_ENDPOINT || "http://localhost:4318";
|
|
236
|
+
let collectorEndpointUrl = url.parse(collectorEndpoint);
|
|
237
|
+
self.opts.dualModeConfig = {
|
|
238
|
+
collectorHost: collectorEndpointUrl.hostname,
|
|
239
|
+
collectorPort: collectorEndpointUrl.port,
|
|
240
|
+
};
|
|
241
|
+
try {
|
|
242
|
+
const { start } = require('@splunk/otel');
|
|
243
|
+
start();
|
|
244
|
+
}
|
|
245
|
+
catch (err) {
|
|
246
|
+
self.logger.error('AppDynamics dual mode could not be started ' + err);
|
|
238
247
|
}
|
|
239
|
-
self.tracer = self.TracerProvider.getTracer('appdynamics-tracer');
|
|
240
248
|
}
|
|
241
249
|
|
|
242
|
-
|
|
243
250
|
self.libagentConnector.subscribeToIsEnabled((isEnabled) => setMetadataFile(self, isEnabled));
|
|
244
251
|
|
|
245
252
|
self.precompiled = opts.precompiled === undefined || opts.precompiled;
|
|
@@ -734,4 +741,3 @@ exports = module.exports = new AppDynamics();
|
|
|
734
741
|
|
|
735
742
|
// export for testing
|
|
736
743
|
exports._setMetadataFile = setMetadataFile;
|
|
737
|
-
|
|
@@ -17,7 +17,8 @@ module.exports = TracerProvider;
|
|
|
17
17
|
function TracerProvider(logger) {
|
|
18
18
|
this.host = 'localhost';
|
|
19
19
|
this.port = '4318';
|
|
20
|
-
this.url =
|
|
20
|
+
this.url = process.env.OTEL_EXPORTER_OTLP_ENDPOINT ? process.env.OTEL_EXPORTER_OTLP_ENDPOINT + '/v1/traces'
|
|
21
|
+
: `http://${this.host}:${this.port}/v1/traces`;
|
|
21
22
|
this.ot_api = opentelemetry_api;
|
|
22
23
|
this.ROOT_CONTEXT = ROOT_CONTEXT;
|
|
23
24
|
this.logger = logger;
|
|
@@ -42,7 +43,7 @@ TracerProvider.prototype.register = function(config) {
|
|
|
42
43
|
[SemanticResourceAttributes.SERVICE_NAMESPACE]: config.applicationName,
|
|
43
44
|
[SemanticResourceAttributes.CONTAINER_ID]: ""
|
|
44
45
|
};
|
|
45
|
-
|
|
46
|
+
|
|
46
47
|
const mergedResource = new Resource(configResourceAttributes)
|
|
47
48
|
.merge(envResource)
|
|
48
49
|
.merge(processResource)
|
|
@@ -174,6 +174,12 @@ LibagentConnector.prototype.init = function () {
|
|
|
174
174
|
|
|
175
175
|
self.agent.transactionSender.isEnabled = true;
|
|
176
176
|
});
|
|
177
|
+
|
|
178
|
+
self.libagent.delegate.on('sepDropped', function (guid) {
|
|
179
|
+
var profiler = self.agent.profiler;
|
|
180
|
+
profiler.sepDropped(guid);
|
|
181
|
+
});
|
|
182
|
+
|
|
177
183
|
self.libagent.delegate.on('transactionDropped', function (guid) {
|
|
178
184
|
var profiler = self.agent.profiler;
|
|
179
185
|
profiler.transactionDropped(guid);
|
|
@@ -229,6 +235,33 @@ LibagentConnector.prototype.stopBusinessTransaction = function (transaction) {
|
|
|
229
235
|
self.libagent.stopBusinessTransaction(transaction.btGuid);
|
|
230
236
|
};
|
|
231
237
|
|
|
238
|
+
LibagentConnector.prototype.startServiceEndpoint = function (entryPointType, request) {
|
|
239
|
+
var self = this;
|
|
240
|
+
return self.libagent.startServiceEndpoint(entryPointType, request);
|
|
241
|
+
};
|
|
242
|
+
|
|
243
|
+
LibagentConnector.prototype.stopServiceEndpoint = function (sep) {
|
|
244
|
+
var self = this;
|
|
245
|
+
|
|
246
|
+
if(!self.agent.profiler.isValidSepThreadId(sep.threadId)) {
|
|
247
|
+
return;
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
if (sep.error) {
|
|
251
|
+
var name = self.protobufModel.extractErrorName(sep.error);
|
|
252
|
+
if (!name) {
|
|
253
|
+
name = "";
|
|
254
|
+
}
|
|
255
|
+
var message = self.protobufModel.extractErrorMessage(sep.error);
|
|
256
|
+
if (!message) {
|
|
257
|
+
message = "";
|
|
258
|
+
}
|
|
259
|
+
|
|
260
|
+
self.libagent.addErrorToEndpoint(sep.sepGuid, name, message);
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
self.libagent.stopServiceEndpoint(sep.sepGuid);
|
|
264
|
+
};
|
|
232
265
|
|
|
233
266
|
LibagentConnector.prototype.startExitCall = function (transaction, exitCall) {
|
|
234
267
|
var self = this;
|
|
@@ -22,6 +22,29 @@ TransactionSender.prototype.init = function() {
|
|
|
22
22
|
self.isEnabled = true;
|
|
23
23
|
});
|
|
24
24
|
|
|
25
|
+
self.agent.on("serviceEndpointStart", function(sep, req) {
|
|
26
|
+
if (!self.isEnabled) {
|
|
27
|
+
self.agent.logger.warn('serviceEndpointStart sent without enabled sender');
|
|
28
|
+
return;
|
|
29
|
+
}
|
|
30
|
+
var sepData = libagentConnector.startServiceEndpoint('NODEJS_WEB', utility.createBtNamingWrapper(req));
|
|
31
|
+
|
|
32
|
+
if (sepData === undefined || sepData.isExcluded) {
|
|
33
|
+
sep.skip = true;
|
|
34
|
+
return;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
sep.skip = false;
|
|
38
|
+
sep.name = sepData.name;
|
|
39
|
+
sep.sepGuid = sepData.sepGuid;
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
self.agent.on("serviceEndpointStop", function(sep) {
|
|
43
|
+
if (!self.isEnabled || sep.skip) {
|
|
44
|
+
return;
|
|
45
|
+
}
|
|
46
|
+
libagentConnector.stopServiceEndpoint(sep);
|
|
47
|
+
});
|
|
25
48
|
|
|
26
49
|
self.agent.on("transactionStarted", function(transaction, req) {
|
|
27
50
|
if (!self.isEnabled) {
|
|
@@ -47,15 +70,15 @@ TransactionSender.prototype.init = function() {
|
|
|
47
70
|
if('singularityheader' in req.headers) {
|
|
48
71
|
corrHeader = req.headers.singularityheader || "";
|
|
49
72
|
} else if(self.agent.tracer && transaction.baggageCorrHeader) {
|
|
50
|
-
/*
|
|
51
|
-
* 1: We append the doNotResolveSubHeader when the upstream is a pure OT service to
|
|
73
|
+
/*
|
|
74
|
+
* 1: We append the doNotResolveSubHeader when the upstream is a pure OT service to
|
|
52
75
|
* prevent resolution to the preceding APPD service
|
|
53
76
|
2: The noTxDetectHeader is treated specially by libagent, so do not append the doNotResolveSubHeader
|
|
54
77
|
in this case
|
|
55
78
|
*/
|
|
56
79
|
const noTxDetectHeader = self.agent.correlation.DISABLE_TRANSACTION_DETECTION + '=true';
|
|
57
80
|
const doNotResolveSubHeader = self.agent.correlation.DONOTRESOLVE + '=true';
|
|
58
|
-
corrHeader = transaction.baggageCorrHeader != noTxDetectHeader ? transaction.baggageCorrHeader + '*' +
|
|
81
|
+
corrHeader = transaction.baggageCorrHeader != noTxDetectHeader ? transaction.baggageCorrHeader + '*' +
|
|
59
82
|
doNotResolveSubHeader : transaction.baggageCorrHeader;
|
|
60
83
|
self.agent.logger.debug(`Using Singularity Header from Opentelemetry Baggage ${corrHeader}`);
|
|
61
84
|
}
|
|
@@ -79,6 +102,7 @@ TransactionSender.prototype.init = function() {
|
|
|
79
102
|
transaction.eumEnabled = txData.eumEnabled;
|
|
80
103
|
transaction.isHttpRequest = isHttpRequest;
|
|
81
104
|
|
|
105
|
+
self.agent.logger.debug('Started Txn with TxnGuid: ' + transaction.guid + ' id: ' + transaction.id);
|
|
82
106
|
if (libagentConnector.isSnapshotRequired(transaction)) {
|
|
83
107
|
libagentConnector.emit("autoProcessSnapshot");
|
|
84
108
|
}
|
|
@@ -99,6 +123,7 @@ TransactionSender.prototype.init = function() {
|
|
|
99
123
|
}
|
|
100
124
|
}
|
|
101
125
|
|
|
126
|
+
self.agent.logger.debug('Stopped Txn with TxnGuid: ' + transaction.guid + ' id: ' + transaction.id);
|
|
102
127
|
libagentConnector.stopBusinessTransaction(transaction);
|
|
103
128
|
});
|
|
104
129
|
|
|
@@ -108,6 +133,7 @@ TransactionSender.prototype.init = function() {
|
|
|
108
133
|
return;
|
|
109
134
|
}
|
|
110
135
|
|
|
136
|
+
self.agent.logger.debug('Started Exitcall with TxnGuid: ' + transaction.guid + ' id: ' + transaction.id);
|
|
111
137
|
libagentConnector.startExitCall(transaction, exitCall);
|
|
112
138
|
});
|
|
113
139
|
|
|
@@ -117,6 +143,7 @@ TransactionSender.prototype.init = function() {
|
|
|
117
143
|
return;
|
|
118
144
|
}
|
|
119
145
|
|
|
146
|
+
self.agent.logger.debug('Stopped Exitcall with TxnGuid: ' + transaction.guid + ' id: ' + transaction.id);
|
|
120
147
|
libagentConnector.stopExitCall(exitCall, error);
|
|
121
148
|
});
|
|
122
149
|
};
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/*
|
|
2
|
-
This is for apollo-server entry probe
|
|
2
|
+
This is for apollo-server entry probe
|
|
3
3
|
*/
|
|
4
4
|
|
|
5
5
|
let HttpCommon = require("./http-common");
|
|
@@ -16,6 +16,10 @@ ApolloEntryProbe.prototype.attach = function (obj, moduleName) {
|
|
|
16
16
|
|
|
17
17
|
let self = this;
|
|
18
18
|
|
|
19
|
+
if(process.env.APPDYNAMICS_APOLLO_PROBE_DISABLE == true || process.env.APPDYNAMICS_APOLLO_PROBE_DISABLE == 'true') {
|
|
20
|
+
return;
|
|
21
|
+
}
|
|
22
|
+
|
|
19
23
|
if(moduleName == 'apollo-server') {
|
|
20
24
|
self.agent.proxy.before(
|
|
21
25
|
obj.ApolloServer.prototype,
|
|
@@ -29,7 +33,7 @@ ApolloEntryProbe.prototype.attach = function (obj, moduleName) {
|
|
|
29
33
|
|
|
30
34
|
overriddenObject.ApolloServer = proxyApolloServer(self, originalObject);
|
|
31
35
|
return overriddenObject;
|
|
32
|
-
|
|
36
|
+
|
|
33
37
|
} else if(moduleName === '@apollo/server/express4') {
|
|
34
38
|
const originalObject = obj;
|
|
35
39
|
const overriddenObject = {};
|
|
@@ -40,7 +44,7 @@ ApolloEntryProbe.prototype.attach = function (obj, moduleName) {
|
|
|
40
44
|
} else if(moduleName === '@apollo/server/standalone'){
|
|
41
45
|
const originalObject = obj;
|
|
42
46
|
const overriddenObject = {};
|
|
43
|
-
|
|
47
|
+
|
|
44
48
|
overriddenObject.startStandaloneServer = proxyStartStandaloneServer(self, originalObject);
|
|
45
49
|
overriddenObject.__proto__ = originalObject;
|
|
46
50
|
return overriddenObject;
|
|
@@ -106,7 +110,7 @@ function appDynamicsApolloServerPlugin(self) {
|
|
|
106
110
|
}
|
|
107
111
|
requestContext.contextValue.gqlReq.graphqlop = requestContext.operationName;
|
|
108
112
|
requestContext.contextValue.gqlReq.transactionStarted = true;
|
|
109
|
-
|
|
113
|
+
|
|
110
114
|
HttpCommon.startTransactionHandler(
|
|
111
115
|
requestContext.contextValue.gqlReq,
|
|
112
116
|
requestContext.contextValue.gqlRes,
|
|
@@ -20,6 +20,10 @@ CassandraProbe.prototype.attach = function(obj) {
|
|
|
20
20
|
var proxy = self.agent.proxy;
|
|
21
21
|
var profiler = self.agent.profiler;
|
|
22
22
|
|
|
23
|
+
if(process.env.APPDYNAMICS_CASSANDRA_PROBE_DISABLE == true || process.env.APPDYNAMICS_CASSANDRA_PROBE_DISABLE == 'true') {
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
|
|
23
27
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
24
28
|
obj.__appdynamicsProbeAttached__ = true;
|
|
25
29
|
self.agent.on('destroy', function() {
|
|
@@ -20,6 +20,10 @@ exports.ClusterProbe = ClusterProbe;
|
|
|
20
20
|
ClusterProbe.prototype.attach = function(obj) {
|
|
21
21
|
var self = this;
|
|
22
22
|
|
|
23
|
+
if(process.env.APPDYNAMICS_CLUSTER_PROBE_DISABLE == true || process.env.APPDYNAMICS_CLUSTER_PROBE_DISABLE == 'true') {
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
|
|
23
27
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
24
28
|
obj.__appdynamicsProbeAttached__ = true;
|
|
25
29
|
self.agent.on('destroy', function() {
|
|
@@ -18,6 +18,10 @@ exports.CouchBaseProbe = CouchBaseProbe;
|
|
|
18
18
|
CouchBaseProbe.prototype.attach = function(obj) {
|
|
19
19
|
var self = this;
|
|
20
20
|
|
|
21
|
+
if(process.env.APPDYNAMICS_COUCHBASE_PROBE_DISABLE == true || process.env.APPDYNAMICS_COUCHBASE_PROBE_DISABLE == 'true') {
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
|
|
21
25
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
22
26
|
obj.__appdynamicsProbeAttached__ = true;
|
|
23
27
|
self.agent.on('destroy', function() {
|
|
@@ -49,12 +53,15 @@ CouchBaseProbe.prototype.attach = function(obj) {
|
|
|
49
53
|
function(obj, args, locals) {
|
|
50
54
|
locals.time = self.agent.profiler.time();
|
|
51
55
|
locals.methodHasCb = proxy.callback(args, -1, function() {}, null, self.agent.thread.current());
|
|
52
|
-
|
|
56
|
+
|
|
53
57
|
var bucketName, addresses;
|
|
54
58
|
var couchBaseBucket = obj._scope._bucket; // ???
|
|
55
59
|
bucketName = couchBaseBucket.name;
|
|
56
60
|
addresses = couchBaseBucket._cluster._connStr || '';
|
|
57
|
-
|
|
61
|
+
|
|
62
|
+
var matches = addresses.match(/^(?:https?:\/\/)?([^/?]+)/);
|
|
63
|
+
var domain = matches ? matches[1] : '';
|
|
64
|
+
addresses = domain.split(',');
|
|
58
65
|
|
|
59
66
|
var command = cmd;
|
|
60
67
|
var commandArgs = args;
|
|
@@ -74,7 +81,9 @@ CouchBaseProbe.prototype.attach = function(obj) {
|
|
|
74
81
|
var addresses;
|
|
75
82
|
var bucketName = Object.keys(obj._conns);
|
|
76
83
|
addresses = obj._connStr || '';
|
|
77
|
-
|
|
84
|
+
var matches = addresses.match(/^(?:https?:\/\/)?([^/?]+)/);
|
|
85
|
+
var domain = matches ? matches[1] : '';
|
|
86
|
+
addresses = domain.split(',');
|
|
78
87
|
|
|
79
88
|
var command = 'query';
|
|
80
89
|
var commandArgs = args;
|
package/lib/probes/disk-probe.js
CHANGED
|
@@ -18,6 +18,10 @@ exports.DiskProbe = DiskProbe;
|
|
|
18
18
|
DiskProbe.prototype.attach = function(obj) {
|
|
19
19
|
var self = this;
|
|
20
20
|
|
|
21
|
+
if(process.env.APPDYNAMICS_DISK_PROBE_DISABLE == true || process.env.APPDYNAMICS_DISK_PROBE_DISABLE == 'true') {
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
|
|
21
25
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
22
26
|
obj.__appdynamicsProbeAttached__ = true;
|
|
23
27
|
self.agent.on('destroy', function() {
|
|
@@ -16,6 +16,10 @@ exports.DynamoDbProbe = DynamoDbProbe;
|
|
|
16
16
|
DynamoDbProbe.prototype.attach = function(obj) {
|
|
17
17
|
var self = this;
|
|
18
18
|
|
|
19
|
+
if(process.env.APPDYNAMICS_DYNAMODB_PROBE_DISABLE == true || process.env.APPDYNAMICS_DYNAMODB_PROBE_DISABLE == 'true') {
|
|
20
|
+
return;
|
|
21
|
+
}
|
|
22
|
+
|
|
19
23
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
20
24
|
obj.__appdynamicsProbeAttached__ = true;
|
|
21
25
|
self.agent.on('destroy', function() {
|
|
@@ -28,6 +28,10 @@ ExpressProbe.prototype.attach = function(obj) {
|
|
|
28
28
|
var self = this,
|
|
29
29
|
proxy = self.agent.proxy;
|
|
30
30
|
|
|
31
|
+
if(process.env.APPDYNAMICS_EXPRESS_PROBE_DISABLE == true || process.env.APPDYNAMICS_EXPRESS_PROBE_DISABLE == 'true') {
|
|
32
|
+
return;
|
|
33
|
+
}
|
|
34
|
+
|
|
31
35
|
if(obj.__appdynamicsProbeAttached__) {
|
|
32
36
|
return obj.__appdynamicsWrapperFn;
|
|
33
37
|
}
|
|
@@ -10,6 +10,7 @@ module.exports.getHttpStatusCodeConfig = getHttpStatusCodeConfig;
|
|
|
10
10
|
module.exports.generateError = generateError;
|
|
11
11
|
module.exports.getHttpExitCallError = getHttpExitCallError;
|
|
12
12
|
module.exports.finalizeTransaction = finalizeTransaction;
|
|
13
|
+
module.exports.finalizeRequest = finalizeRequest;
|
|
13
14
|
module.exports.startTransactionHandler = startTransactionHandler;
|
|
14
15
|
|
|
15
16
|
|
|
@@ -66,10 +67,30 @@ function getHttpExitCallError(statusCode, stack, locals) {
|
|
|
66
67
|
return error;
|
|
67
68
|
}
|
|
68
69
|
|
|
69
|
-
|
|
70
|
-
function finalizeTransaction (err, profiler, time, transaction, req, res, span) {
|
|
70
|
+
function finalizeRequest(err, profiler, time, transaction, req, res, span, sep) {
|
|
71
71
|
if (!time.done()) return;
|
|
72
|
+
finalizeTransaction(err, profiler, time, transaction, req, res, span);
|
|
73
|
+
finalizeServiceEndpoint(err, profiler, time, sep, res);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
function finalizeServiceEndpoint (err, profiler, time, sep, res) {
|
|
77
|
+
if(!sep) return;
|
|
78
|
+
sep.error = sep.error || res.error || err;
|
|
79
|
+
sep.statusCode = sep.statusCode ||
|
|
80
|
+
(sep.error && sep.error.statusCode) ||
|
|
81
|
+
(res && res.statusCode) ||
|
|
82
|
+
500;
|
|
83
|
+
sep.stackTrace = sep.stackTrace || profiler.formatStackTrace(sep.error);
|
|
84
|
+
|
|
85
|
+
var error = generateError(sep.error, sep.statusCode);
|
|
86
|
+
if (error) {
|
|
87
|
+
sep.error = error;
|
|
88
|
+
}
|
|
89
|
+
profiler.endServiceEndpoint(time, sep);
|
|
90
|
+
}
|
|
91
|
+
|
|
72
92
|
|
|
93
|
+
function finalizeTransaction (err, profiler, time, transaction, req, res, span) {
|
|
73
94
|
transaction.error = transaction.error || res.error || err;
|
|
74
95
|
transaction.statusCode = transaction.statusCode ||
|
|
75
96
|
(transaction.error && transaction.error.statusCode) ||
|
|
@@ -108,7 +129,7 @@ function startTransactionHandler(req, res, agent, isHTTPs, tracer, ot_api) {
|
|
|
108
129
|
var span = undefined;
|
|
109
130
|
var baggageCorrHeader = undefined;
|
|
110
131
|
var otContext = undefined;
|
|
111
|
-
|
|
132
|
+
|
|
112
133
|
if (tracer) {
|
|
113
134
|
otContext = ot_api.propagation.extract(agent.TracerProvider.ot_api.ROOT_CONTEXT, req.headers);
|
|
114
135
|
var baggage = ot_api.propagation.getBaggage(otContext);
|
|
@@ -151,10 +172,13 @@ function startTransactionHandler(req, res, agent, isHTTPs, tracer, ot_api) {
|
|
|
151
172
|
});
|
|
152
173
|
}
|
|
153
174
|
|
|
175
|
+
var serviceEndpoint = profiler.startServiceEndpoint(time, req, 'NODEJS_WEB');
|
|
176
|
+
|
|
154
177
|
proxy.after(res, "end", function () {
|
|
155
|
-
|
|
178
|
+
finalizeRequest(null, profiler, time, transaction, req, res, span, serviceEndpoint);
|
|
156
179
|
transaction = null;
|
|
180
|
+
serviceEndpoint = null;
|
|
157
181
|
});
|
|
158
182
|
|
|
159
|
-
return { transaction, span, otContext };
|
|
183
|
+
return { transaction, span, otContext, serviceEndpoint };
|
|
160
184
|
}
|
|
@@ -115,7 +115,7 @@ HttpEntryProbe.prototype.__createRequestHandler = function (callback, isHTTPs) {
|
|
|
115
115
|
|
|
116
116
|
self.agent.metricsManager.addMetric(self.agent.metricsManager.HTTP_INCOMING_COUNT, 1);
|
|
117
117
|
|
|
118
|
-
let { transaction, span, otContext } = HttpCommon.startTransactionHandler(req, res, self.agent, isHTTPs, self.tracer, self.ot_api);
|
|
118
|
+
let { transaction, span, otContext, serviceEndpoint } = HttpCommon.startTransactionHandler(req, res, self.agent, isHTTPs, self.tracer, self.ot_api);
|
|
119
119
|
|
|
120
120
|
var threadId = transaction.threadId;
|
|
121
121
|
self.agent.context.run(() => {
|
|
@@ -127,7 +127,8 @@ HttpEntryProbe.prototype.__createRequestHandler = function (callback, isHTTPs) {
|
|
|
127
127
|
let threadProxyWrappedCb = self.agent.proxy.wrapWithThreadProxyIfEnabled(callback);
|
|
128
128
|
return invokeOriginal(threadProxyWrappedCb, this, arguments, self.ot_api, span, otContext, req, res);
|
|
129
129
|
} catch (e) {
|
|
130
|
-
HttpCommon.
|
|
130
|
+
HttpCommon.finalizeRequest(e, profiler, time, transaction, req, res, span, serviceEndpoint);
|
|
131
|
+
serviceEndpoint = null;
|
|
131
132
|
transaction = null;
|
|
132
133
|
throw e;
|
|
133
134
|
} finally {
|
|
@@ -140,6 +141,6 @@ HttpEntryProbe.prototype.__createRequestHandler = function (callback, isHTTPs) {
|
|
|
140
141
|
// This is needed as Express attaches a bunch of extra properties and
|
|
141
142
|
// functionality, which may need to be accessed by other modules down stream.
|
|
142
143
|
handler.__proto__ = callback;
|
|
143
|
-
|
|
144
|
+
|
|
144
145
|
return handler;
|
|
145
146
|
};
|
|
@@ -42,6 +42,10 @@ HttpExitProbe.prototype.attach = function (obj, moduleName) {
|
|
|
42
42
|
obj = obj.globalAgent;
|
|
43
43
|
}
|
|
44
44
|
|
|
45
|
+
if (typeof global.fetch === 'function' && !global.fetch.__appdynamicsProxyInfo__) {
|
|
46
|
+
self.instrumentFetch();
|
|
47
|
+
}
|
|
48
|
+
|
|
45
49
|
function clientCallback(locals) {
|
|
46
50
|
if (!locals.time.done()) return;
|
|
47
51
|
|
|
@@ -70,7 +74,7 @@ HttpExitProbe.prototype.attach = function (obj, moduleName) {
|
|
|
70
74
|
|
|
71
75
|
var [input, options] = args;
|
|
72
76
|
|
|
73
|
-
if (typeof(input) != 'string' && !(input instanceof url.URL)) {
|
|
77
|
+
if (typeof (input) != 'string' && !(input instanceof url.URL)) {
|
|
74
78
|
options = input;
|
|
75
79
|
input = null;
|
|
76
80
|
} else if (!options) {
|
|
@@ -78,7 +82,7 @@ HttpExitProbe.prototype.attach = function (obj, moduleName) {
|
|
|
78
82
|
args[1] = options;
|
|
79
83
|
}
|
|
80
84
|
|
|
81
|
-
if(typeof(options) == 'function') {
|
|
85
|
+
if (typeof (options) == 'function') {
|
|
82
86
|
args[2] = options;
|
|
83
87
|
options = {};
|
|
84
88
|
args[1] = options;
|
|
@@ -110,15 +114,17 @@ HttpExitProbe.prototype.attach = function (obj, moduleName) {
|
|
|
110
114
|
}
|
|
111
115
|
|
|
112
116
|
var isOtPath = self.agent.TracerProvider && locals.opts.hostname == self.agent.TracerProvider.host
|
|
113
|
-
|
|
117
|
+
&& locals.opts.port == self.agent.TracerProvider.port;
|
|
118
|
+
var isDualMode = self.agent.opts.dualModeConfig && self.agent.opts.dualModeConfig.collectorHost == locals.opts.hostname;
|
|
114
119
|
var isDynamoDBReq = options.headers && options.headers['X-Amz-Target'] && options.headers['X-Amz-Target'].indexOf('DynamoDB') > -1;
|
|
115
|
-
if (options.appdIgnore || isDynamoDBReq || isRepeatForHttps || isOtPath) {
|
|
120
|
+
if (options.appdIgnore || isDynamoDBReq || isRepeatForHttps || isOtPath || isDualMode) {
|
|
116
121
|
// (ignore internal HTTP calls, e.g. to Analytics Agent, DynamoDB calls)
|
|
117
122
|
self.agent.logger.debug('Skipping HTTP exit call for the transaction.' +
|
|
118
123
|
'AppdIgnore is: ' + options.appdIgnore + ' ' +
|
|
119
124
|
'DynamoDB call is:' + isDynamoDBReq + ' ' +
|
|
120
125
|
'HTTPS call is:' + isRepeatForHttps + ' ' +
|
|
121
|
-
'isOtPath is :' + isOtPath
|
|
126
|
+
'isOtPath is :' + isOtPath + ' ' +
|
|
127
|
+
'isDualMode is :' + isDualMode);
|
|
122
128
|
} else {
|
|
123
129
|
self.agent.logger.debug('Gatheing HTTP exit call information.');
|
|
124
130
|
var threadId = self.agent.thread.current();
|
|
@@ -144,8 +150,8 @@ HttpExitProbe.prototype.attach = function (obj, moduleName) {
|
|
|
144
150
|
var span = {};
|
|
145
151
|
if (self.tracer) {
|
|
146
152
|
const currentSpan = self.ot_api.trace.getSpan(self.ot_api.context.active());
|
|
147
|
-
if(currentSpan) {
|
|
148
|
-
var method = locals.opts.method ? locals.opts.method
|
|
153
|
+
if (currentSpan) {
|
|
154
|
+
var method = locals.opts.method ? locals.opts.method : 'GET';
|
|
149
155
|
span = self.tracer.startSpan(method + ' ' + path, {
|
|
150
156
|
kind: self.ot_api.SpanKind.CLIENT,
|
|
151
157
|
attributes: HttpOTUtils.getOutgoingRequestAttributes(locals.opts, args[0].headers)
|
|
@@ -211,7 +217,7 @@ HttpExitProbe.prototype.attach = function (obj, moduleName) {
|
|
|
211
217
|
function (obj, args, ret, locals) {
|
|
212
218
|
var [input, options] = args;
|
|
213
219
|
|
|
214
|
-
if (typeof(input) != 'string' && !(input instanceof url.URL)) {
|
|
220
|
+
if (typeof (input) != 'string' && !(input instanceof url.URL)) {
|
|
215
221
|
options = input;
|
|
216
222
|
input = null;
|
|
217
223
|
}
|
|
@@ -245,7 +251,7 @@ HttpExitProbe.prototype.attach = function (obj, moduleName) {
|
|
|
245
251
|
var ot_context = self.ot_api.context.active();
|
|
246
252
|
if (correlationHeaderValue) {
|
|
247
253
|
var baggage = self.ot_api.propagation.getBaggage(ot_context) || {};
|
|
248
|
-
baggage[self.agent.correlation.HEADER_NAME] = {value: correlationHeaderValue};
|
|
254
|
+
baggage[self.agent.correlation.HEADER_NAME] = { value: correlationHeaderValue };
|
|
249
255
|
ot_context = self.ot_api.propagation.setBaggage(ot_context, self.ot_api.propagation.createBaggage(baggage));
|
|
250
256
|
}
|
|
251
257
|
|
|
@@ -321,3 +327,98 @@ HttpExitProbe.prototype.setHttpDefaults = function (locals, spec, opts, protocol
|
|
|
321
327
|
|| ((protocol === 'https') ? 443 : 80);
|
|
322
328
|
locals.opts.path = locals.opts.path || '/';
|
|
323
329
|
};
|
|
330
|
+
|
|
331
|
+
|
|
332
|
+
HttpExitProbe.prototype.instrumentFetch = function () {
|
|
333
|
+
const self = this;
|
|
334
|
+
|
|
335
|
+
const profiler = self.agent.profiler;
|
|
336
|
+
const proxy = self.agent.proxy;
|
|
337
|
+
|
|
338
|
+
proxy.around(
|
|
339
|
+
global,
|
|
340
|
+
['fetch'],
|
|
341
|
+
function beforeFetch(_, args, locals) {
|
|
342
|
+
let [input, options = {}] = args;
|
|
343
|
+
const parsedUrl = typeof input === 'string' ? new url.URL(input) : input instanceof url.URL ? input : new url.URL(input.url);
|
|
344
|
+
const method = (options.method || 'GET').toUpperCase();
|
|
345
|
+
|
|
346
|
+
self.setHttpDefaults(locals, parsedUrl, args[1], parsedUrl.protocol === 'https:' ? 'https' : 'http');
|
|
347
|
+
|
|
348
|
+
locals.time = profiler.time();
|
|
349
|
+
|
|
350
|
+
self.agent.logger.debug('Instrumenting fetch request for endpoint: ' +
|
|
351
|
+
`${method} ${parsedUrl.hostname}:${parsedUrl.port || (parsedUrl.protocol === 'https:' ? 443 : 80)}${parsedUrl.pathname}`);
|
|
352
|
+
self.agent.metricsManager.addMetric(self.agent.metricsManager.HTTP_OUTGOING_COUNT, 1);
|
|
353
|
+
|
|
354
|
+
locals.exitCall = profiler.createExitCall(locals.time, {
|
|
355
|
+
exitType: 'EXIT_HTTP',
|
|
356
|
+
supportedProperties: {
|
|
357
|
+
'HOST': locals.opts.hostname,
|
|
358
|
+
'PORT': locals.opts.port,
|
|
359
|
+
'URL': locals.opts.path,
|
|
360
|
+
},
|
|
361
|
+
stackTrace: profiler.stackTrace(),
|
|
362
|
+
group: method,
|
|
363
|
+
method,
|
|
364
|
+
command: `${locals.opts.hostname}:${locals.opts.port}${locals.opts.path}`,
|
|
365
|
+
category: ['POST', 'PUT'].includes(method) ? 'write' : 'read',
|
|
366
|
+
protocol: parsedUrl.protocol,
|
|
367
|
+
});
|
|
368
|
+
|
|
369
|
+
if (!locals.exitCall) return;
|
|
370
|
+
|
|
371
|
+
Error.captureStackTrace(locals.exitCall);
|
|
372
|
+
|
|
373
|
+
let correlationHeaderValue = undefined;
|
|
374
|
+
if (locals.exitCall) {
|
|
375
|
+
correlationHeaderValue = self.agent.backendConnector.getCorrelationHeader(locals.exitCall);
|
|
376
|
+
}
|
|
377
|
+
|
|
378
|
+
if ((typeof options === 'object' && options.headers == undefined)) {
|
|
379
|
+
options.headers = {};
|
|
380
|
+
}
|
|
381
|
+
|
|
382
|
+
if (correlationHeaderValue) {
|
|
383
|
+
args[1].headers = Object.assign(args[1].headers, {
|
|
384
|
+
[self.agent.correlation.HEADER_NAME]: correlationHeaderValue
|
|
385
|
+
});
|
|
386
|
+
}
|
|
387
|
+
|
|
388
|
+
return args;
|
|
389
|
+
},
|
|
390
|
+
function afterFetch(_, args, response, locals) {
|
|
391
|
+
if (!response || !response.data) {
|
|
392
|
+
return;
|
|
393
|
+
}
|
|
394
|
+
|
|
395
|
+
const res = response.data;
|
|
396
|
+
locals.res = res;
|
|
397
|
+
|
|
398
|
+
if (res.status < 200 || res.status >= 400) {
|
|
399
|
+
locals.error = new Error(`HTTP error! Status: ${res.status} - ${res.statusText}`);
|
|
400
|
+
}
|
|
401
|
+
self.finalizeClientCallback(profiler, locals);
|
|
402
|
+
return;
|
|
403
|
+
}
|
|
404
|
+
);
|
|
405
|
+
};
|
|
406
|
+
|
|
407
|
+
//replace the original function with this in the next commit after 24.12 release
|
|
408
|
+
HttpExitProbe.prototype.finalizeClientCallback = function (profiler, locals) {
|
|
409
|
+
if (!locals.time.done()) return;
|
|
410
|
+
|
|
411
|
+
var exitCall = locals.exitCall;
|
|
412
|
+
var error = locals.error;
|
|
413
|
+
|
|
414
|
+
if (exitCall) {
|
|
415
|
+
if (locals.res) {
|
|
416
|
+
exitCall.responseHeaders = locals.res.headers;
|
|
417
|
+
exitCall.statusCode = ~~locals.res.status || ~~locals.res.statusCode;
|
|
418
|
+
if ((!error) && ((exitCall.statusCode < 200) || (exitCall.statusCode >= 400))) {
|
|
419
|
+
error = HttpCommon.getHttpExitCallError(exitCall.statusCode, exitCall.stack, locals);
|
|
420
|
+
}
|
|
421
|
+
}
|
|
422
|
+
profiler.addExitCall(locals.time, exitCall, error);
|
|
423
|
+
}
|
|
424
|
+
};
|
package/lib/probes/http-probe.js
CHANGED
|
@@ -33,6 +33,10 @@ HttpProbe.prototype.attach = function (obj, moduleName) {
|
|
|
33
33
|
var self = this;
|
|
34
34
|
var proxy = this.agent.proxy;
|
|
35
35
|
|
|
36
|
+
if(process.env.APPDYNAMICS_HTTP_PROBE_DISABLE == 'true' || process.env.APPDYNAMICS_HTTP_PROBE_DISABLE == true) {
|
|
37
|
+
return;
|
|
38
|
+
}
|
|
39
|
+
|
|
36
40
|
if (obj.__appdynamicsProbeAttached__) return;
|
|
37
41
|
obj.__appdynamicsProbeAttached__ = true;
|
|
38
42
|
|
|
@@ -47,7 +51,7 @@ HttpProbe.prototype.attach = function (obj, moduleName) {
|
|
|
47
51
|
}
|
|
48
52
|
});
|
|
49
53
|
}
|
|
50
|
-
|
|
54
|
+
|
|
51
55
|
if (moduleName === 'express-graphql') {
|
|
52
56
|
if (self.agent.opts.enableGraphQL) {
|
|
53
57
|
this.entryProbe.enableGraphQL(obj);
|
|
@@ -77,7 +81,11 @@ HttpProbe.prototype.attach = function (obj, moduleName) {
|
|
|
77
81
|
this.entryProbe.enableGraphQLHttp(obj);
|
|
78
82
|
}
|
|
79
83
|
} else {
|
|
80
|
-
|
|
81
|
-
|
|
84
|
+
if(process.env.APPDYNAMICS_HTTP_ENTRY_PROBE_DISABLE != 'true' && process.env.APPDYNAMICS_HTTP_ENTRY_PROBE_DISABLE != true) {
|
|
85
|
+
this.entryProbe.attach(obj, moduleName);
|
|
86
|
+
}
|
|
87
|
+
if(process.env.APPDYNAMICS_HTTP_EXIT_PROBE_DISABLE != 'true' && process.env.APPDYNAMICS_HTTP_EXIT_PROBE_DISABLE != true) {
|
|
88
|
+
this.exitProbe.attach(obj, moduleName);
|
|
89
|
+
}
|
|
82
90
|
}
|
|
83
91
|
};
|
|
@@ -69,7 +69,7 @@ function buildEumCookie(agent, transaction, responseHeaders, request)
|
|
|
69
69
|
{
|
|
70
70
|
var response = {headers: responseHeaders,
|
|
71
71
|
setHeader: function(key, value) { this.headers[key] = value; },
|
|
72
|
-
getHeader: function(key) { this.headers[key]; }};
|
|
72
|
+
getHeader: function(key) { return this.headers[key]; }};
|
|
73
73
|
var eumCookie = agent.eum.newEumCookie(transaction, request, response, request.headers[":scheme"] == 'https');
|
|
74
74
|
eumCookie.build();
|
|
75
75
|
}
|
|
@@ -33,6 +33,10 @@ exports.IoredisProbe = IoredisProbe;
|
|
|
33
33
|
IoredisProbe.prototype.attach = function(obj) {
|
|
34
34
|
var self = this;
|
|
35
35
|
|
|
36
|
+
if(process.env.APPDYNAMICS_IOREDIS_PROBE_DISABLE == true || process.env.APPDYNAMICS_IOREDIS_PROBE_DISABLE == 'true') {
|
|
37
|
+
return;
|
|
38
|
+
}
|
|
39
|
+
|
|
36
40
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
37
41
|
obj.__appdynamicsProbeAttached__ = true;
|
|
38
42
|
self.agent.on('destroy', function() {
|
|
@@ -47,6 +47,10 @@ exports.MemcachedProbe = MemcachedProbe;
|
|
|
47
47
|
MemcachedProbe.prototype.attach = function(obj) {
|
|
48
48
|
var self = this;
|
|
49
49
|
|
|
50
|
+
if(process.env.APPDYNAMICS_MEMCACHED_PROBE_DISABLE == true || process.env.APPDYNAMICS_MEMCACHED_PROBE_DISABLE == 'true') {
|
|
51
|
+
return;
|
|
52
|
+
}
|
|
53
|
+
|
|
50
54
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
51
55
|
obj.__appdynamicsProbeAttached__ = true;
|
|
52
56
|
self.agent.on('destroy', function() {
|
|
@@ -21,6 +21,10 @@ MongodbProbe.prototype.attach = function (obj) {
|
|
|
21
21
|
var profiler = self.agent.profiler;
|
|
22
22
|
var mongoObj = obj;
|
|
23
23
|
|
|
24
|
+
if(process.env.APPDYNAMICS_MONGODB_PROBE_DISABLE == true || process.env.APPDYNAMICS_MONGODB_PROBE_DISABLE == 'true') {
|
|
25
|
+
return;
|
|
26
|
+
}
|
|
27
|
+
|
|
24
28
|
if (obj.__appdynamicsProbeAttached__) return;
|
|
25
29
|
obj.__appdynamicsProbeAttached__ = true;
|
|
26
30
|
|
|
@@ -148,7 +152,7 @@ MongodbProbe.prototype.attach = function (obj) {
|
|
|
148
152
|
});
|
|
149
153
|
|
|
150
154
|
supportedCommands.forEach(function (command) {
|
|
151
|
-
proxy.before(obj.Collection.prototype, command, withAPMBeforeHandler);
|
|
155
|
+
proxy.before(obj.Collection.prototype, command, withAPMBeforeHandler);
|
|
152
156
|
proxy.before(obj.Server.prototype, command, withAPMBeforeHandler);
|
|
153
157
|
proxy.before(obj.ReplSet.prototype, command, withAPMBeforeHandler);
|
|
154
158
|
});
|
|
@@ -283,7 +287,7 @@ MongodbProbe.prototype.attach = function (obj) {
|
|
|
283
287
|
proxy.before(obj.MongoClient.prototype, 'connect', function(obj){
|
|
284
288
|
obj.monitorCommands = true;
|
|
285
289
|
var newServerPool;
|
|
286
|
-
var newOpQueue =
|
|
290
|
+
var newOpQueue = new Map();
|
|
287
291
|
var newApmCollectionEvents = ['create', 'drop'];
|
|
288
292
|
var newCollectionCommandMap = {
|
|
289
293
|
'create': 'createCollection',
|
|
@@ -306,13 +310,13 @@ MongodbProbe.prototype.attach = function (obj) {
|
|
|
306
310
|
newServerPool = [event.address];
|
|
307
311
|
}
|
|
308
312
|
if (newServerPool) {
|
|
309
|
-
if (!newOpQueue
|
|
310
|
-
newOpQueue
|
|
313
|
+
if (!newOpQueue.has(requestId)) {
|
|
314
|
+
newOpQueue.set(requestId, {
|
|
311
315
|
time: profiler.time(),
|
|
312
316
|
serverPool: newServerPool
|
|
313
|
-
};
|
|
317
|
+
});
|
|
314
318
|
}
|
|
315
|
-
newRequest = newOpQueue
|
|
319
|
+
newRequest = newOpQueue.get(requestId);
|
|
316
320
|
newCommandQuery = event.command.filter;
|
|
317
321
|
if (event.command.filter && Object.prototype.toString.call(event.command.filter) == "[object Object]") {
|
|
318
322
|
newCommandQuery = utility.filterSensitiveDataFromObject(utility.deepCopy(event.command.filter));
|
|
@@ -334,18 +338,18 @@ MongodbProbe.prototype.attach = function (obj) {
|
|
|
334
338
|
});
|
|
335
339
|
|
|
336
340
|
obj.on('commandSucceeded', function (event) {
|
|
337
|
-
var requestId = event.requestId, newRequest = newOpQueue
|
|
341
|
+
var requestId = event.requestId, newRequest = newOpQueue.get(requestId);
|
|
338
342
|
if (newRequest) {
|
|
339
343
|
self.addExitCall(newRequest.time, newRequest.exitCall);
|
|
340
|
-
newOpQueue
|
|
344
|
+
newOpQueue.delete(requestId);
|
|
341
345
|
}
|
|
342
346
|
});
|
|
343
347
|
|
|
344
348
|
obj.on('commandFailed', function (event) {
|
|
345
|
-
var requestId = event.requestId, newRequest = newOpQueue
|
|
349
|
+
var requestId = event.requestId, newRequest = newOpQueue.get(requestId);
|
|
346
350
|
if (newRequest) {
|
|
347
351
|
self.addExitCall(event.time, event.exitCall, event.failure);
|
|
348
|
-
newOpQueue
|
|
352
|
+
newOpQueue.delete(requestId);
|
|
349
353
|
}
|
|
350
354
|
});
|
|
351
355
|
});
|
|
@@ -18,6 +18,10 @@ MssqlProbe.prototype.attach = function(obj) {
|
|
|
18
18
|
var proxy = self.agent.proxy;
|
|
19
19
|
var profiler = self.agent.profiler;
|
|
20
20
|
|
|
21
|
+
if(process.env.APPDYNAMICS_MSSQL_PROBE_DISABLE == true || process.env.APPDYNAMICS_MSSQL_PROBE_DISABLE == 'true') {
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
|
|
21
25
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
22
26
|
obj.__appdynamicsProbeAttached__ = true;
|
|
23
27
|
self.agent.on('destroy', function() {
|
|
@@ -102,6 +102,10 @@ MysqlProbe.prototype.attach = function(obj, name) {
|
|
|
102
102
|
var cmds = ['createClient', 'createConnection', 'createPool'];
|
|
103
103
|
var mysqlConnection;
|
|
104
104
|
|
|
105
|
+
if(process.env.APPDYNAMICS_MYSQL_PROBE_DISABLE == true || process.env.APPDYNAMICS_MYSQL_PROBE_DISABLE == 'true') {
|
|
106
|
+
return;
|
|
107
|
+
}
|
|
108
|
+
|
|
105
109
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
106
110
|
obj.__appdynamicsProbeAttached__ = true;
|
|
107
111
|
self.agent.on('destroy', function() {
|
package/lib/probes/net-probe.js
CHANGED
|
@@ -19,6 +19,10 @@ exports.NetProbe = NetProbe;
|
|
|
19
19
|
NetProbe.prototype.attach = function(obj) {
|
|
20
20
|
var self = this;
|
|
21
21
|
|
|
22
|
+
if(process.env.APPDYNAMICS_NET_PROBE_DISABLE == true || process.env.APPDYNAMICS_NET_PROBE_DISABLE == 'true') {
|
|
23
|
+
return;
|
|
24
|
+
}
|
|
25
|
+
|
|
22
26
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
23
27
|
obj.__appdynamicsProbeAttached__ = true;
|
|
24
28
|
self.agent.on('destroy', function() {
|
|
@@ -20,6 +20,10 @@ NSolidProbe.prototype.attach = function(obj) {
|
|
|
20
20
|
var agent = self.agent;
|
|
21
21
|
self.nsolid = obj;
|
|
22
22
|
|
|
23
|
+
if(process.env.APPDYNAMICS_NSOLID_PROBE_DISABLE == true || process.env.APPDYNAMICS_NSOLID_PROBE_DISABLE == 'true') {
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
|
|
23
27
|
if (!agent.nsolidEnabled) return;
|
|
24
28
|
|
|
25
29
|
if(obj.__appdynamicsProbeAttached__) return;
|
package/lib/probes/pg-probe.js
CHANGED
|
@@ -18,6 +18,10 @@ exports.PgProbe = PgProbe;
|
|
|
18
18
|
PgProbe.prototype.attach = function(obj) {
|
|
19
19
|
var self = this;
|
|
20
20
|
|
|
21
|
+
if(process.env.APPDYNAMICS_PG_PROBE_DISABLE == true || process.env.APPDYNAMICS_PG_PROBE_DISABLE == 'true') {
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
|
|
21
25
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
22
26
|
obj.__appdynamicsProbeAttached__ = true;
|
|
23
27
|
self.agent.on('destroy', function() {
|
|
@@ -17,6 +17,10 @@ ProcessProbe.prototype.attach = function(obj) {
|
|
|
17
17
|
var proxy = this.agent.proxy;
|
|
18
18
|
var thread = this.agent.thread;
|
|
19
19
|
|
|
20
|
+
if(process.env.APPDYNAMICS_PROCESS_PROBE_DISABLE == true || process.env.APPDYNAMICS_PROCESS_PROBE_DISABLE == 'true') {
|
|
21
|
+
return;
|
|
22
|
+
}
|
|
23
|
+
|
|
20
24
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
21
25
|
obj.__appdynamicsProbeAttached__ = true;
|
|
22
26
|
this.agent.on('destroy', function() {
|
|
@@ -46,6 +46,11 @@ function proxyAttachCommands(self, originalObject) {
|
|
|
46
46
|
|
|
47
47
|
RedisProbe.prototype.attachRelative = function(mod, args, obj) {
|
|
48
48
|
var self = this;
|
|
49
|
+
|
|
50
|
+
if(process.env.APPDYNAMICS_REDIS_PROBE_DISABLE == true || process.env.APPDYNAMICS_REDIS_PROBE_DISABLE == 'true') {
|
|
51
|
+
return;
|
|
52
|
+
}
|
|
53
|
+
|
|
49
54
|
if (args[0] == '../commander') {
|
|
50
55
|
var parentMod = mod.filename.split('@');
|
|
51
56
|
if (parentMod.length < 2
|
|
@@ -20,6 +20,10 @@ SocketioProbe.prototype.attach = function(obj) {
|
|
|
20
20
|
var self = this;
|
|
21
21
|
var socketIOServer;
|
|
22
22
|
|
|
23
|
+
if(process.env.APPDYNAMICS_SOCKETIO_PROBE_DISABLE == true || process.env.APPDYNAMICS_SOCKETIO_PROBE_DISABLE == 'true') {
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
|
|
23
27
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
24
28
|
obj.__appdynamicsProbeAttached__ = true;
|
|
25
29
|
self.agent.on('destroy', function() {
|
|
@@ -11,6 +11,10 @@ TediousProbe.prototype.attach = function (obj) {
|
|
|
11
11
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
12
12
|
obj.__appdynamicsProbeAttached__ = true;
|
|
13
13
|
|
|
14
|
+
if(process.env.APPDYNAMICS_TEDIOUS_PROBE_DISABLE == true || process.env.APPDYNAMICS_TEDIOUS_PROBE_DISABLE == 'true') {
|
|
15
|
+
return;
|
|
16
|
+
}
|
|
17
|
+
|
|
14
18
|
let self = this;
|
|
15
19
|
self.agent.on('destroy', function() {
|
|
16
20
|
if(obj.__appdynamicsProbeAttached__) {
|
|
@@ -8,6 +8,11 @@ function WinstonProbe(agent) {
|
|
|
8
8
|
WinstonProbe.prototype.init = function () {};
|
|
9
9
|
|
|
10
10
|
WinstonProbe.prototype.attach = function (obj) {
|
|
11
|
+
|
|
12
|
+
if(process.env.APPDYNAMICS_WINSTON_PROBE_DISABLE == true || process.env.APPDYNAMICS_WINSTON_PROBE_DISABLE == 'true') {
|
|
13
|
+
return;
|
|
14
|
+
}
|
|
15
|
+
|
|
11
16
|
if(obj.__appdynamicsProbeAttached__) return;
|
|
12
17
|
obj.__appdynamicsProbeAttached__ = true;
|
|
13
18
|
let self = this;
|
package/lib/profiler/profiler.js
CHANGED
|
@@ -19,6 +19,7 @@ function Profiler(agent) {
|
|
|
19
19
|
this.agent = agent;
|
|
20
20
|
|
|
21
21
|
this.transactions = {};
|
|
22
|
+
this.serviceEndpoints = {};
|
|
22
23
|
this.stackTraceFilter = /appdynamics/;
|
|
23
24
|
}
|
|
24
25
|
exports.Profiler = Profiler;
|
|
@@ -83,6 +84,43 @@ Profiler.prototype.formatStackTrace = function (err) {
|
|
|
83
84
|
return undefined;
|
|
84
85
|
};
|
|
85
86
|
|
|
87
|
+
Profiler.prototype.startServiceEndpoint = function(time, req, entryType) {
|
|
88
|
+
var self = this;
|
|
89
|
+
var sep = {};
|
|
90
|
+
sep.time = time;
|
|
91
|
+
sep.id = time.id;
|
|
92
|
+
sep.threadId = time.threadId;
|
|
93
|
+
sep.entryType = entryType;
|
|
94
|
+
|
|
95
|
+
self.serviceEndpoints[time.threadId] = sep;
|
|
96
|
+
|
|
97
|
+
try {
|
|
98
|
+
self.agent.emit('serviceEndpointStart', sep, req);
|
|
99
|
+
} catch (err) {
|
|
100
|
+
self.agent.logger.warn(err);
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
return sep;
|
|
104
|
+
};
|
|
105
|
+
|
|
106
|
+
Profiler.prototype.endServiceEndpoint = function (time, sep) {
|
|
107
|
+
var self = this;
|
|
108
|
+
|
|
109
|
+
if (sep.isFinished) {
|
|
110
|
+
return;
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
sep.isFinished = true;
|
|
114
|
+
sep.ms = time.ms;
|
|
115
|
+
|
|
116
|
+
try {
|
|
117
|
+
self.agent.emit('serviceEndpointStop', sep);
|
|
118
|
+
} catch (err) {
|
|
119
|
+
self.agent.logger.warn(err);
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
delete self.serviceEndpoints[time.threadId];
|
|
123
|
+
};
|
|
86
124
|
|
|
87
125
|
Profiler.prototype.startTransaction = function(time, req, entryType, baggageCorrHeader) {
|
|
88
126
|
var self = this;
|
|
@@ -184,6 +222,11 @@ Profiler.prototype.isValidThreadId = function(threadId) {
|
|
|
184
222
|
return (threadId && self.transactions[threadId]);
|
|
185
223
|
};
|
|
186
224
|
|
|
225
|
+
Profiler.prototype.isValidSepThreadId = function(threadId) {
|
|
226
|
+
var self = this;
|
|
227
|
+
return (threadId && self.serviceEndpoints[threadId]);
|
|
228
|
+
};
|
|
229
|
+
|
|
187
230
|
Profiler.prototype._endTransaction = function (time, transaction) {
|
|
188
231
|
var self = this;
|
|
189
232
|
|
|
@@ -217,6 +260,18 @@ Profiler.prototype.transactionDropped = function (guid) {
|
|
|
217
260
|
}
|
|
218
261
|
};
|
|
219
262
|
|
|
263
|
+
Profiler.prototype.sepDropped = function (guid) {
|
|
264
|
+
var self = this;
|
|
265
|
+
|
|
266
|
+
for (var threadId in self.serviceEndpoints) {
|
|
267
|
+
if (self.serviceEndpoints[threadId].sepGuid === guid) {
|
|
268
|
+
self.agent.logger.info('SEP ' + self.serviceEndpoints[threadId].id + ' dropped');
|
|
269
|
+
delete self.serviceEndpoints[threadId];
|
|
270
|
+
break;
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
};
|
|
274
|
+
|
|
220
275
|
Profiler.prototype.__getNextSequenceInfo = function (transaction) {
|
|
221
276
|
var self = this;
|
|
222
277
|
transaction.exitCallCounter++;
|
package/lib/v8/cpu-profiler.js
CHANGED
|
@@ -47,6 +47,10 @@ CpuProfiler.prototype.onAgentDestroy = function () {
|
|
|
47
47
|
CpuProfiler.prototype.startCpuProfiler = function(seconds, callback, threadId) {
|
|
48
48
|
var self = this;
|
|
49
49
|
|
|
50
|
+
if(process.env.APPDYNAMICS_CPU_PROFILER_DISABLED == 'true' || process.env.APPDYNAMICS_CPU_PROFILER_DISABLED == true) {
|
|
51
|
+
return callback("CPU Profiling Disabled.");
|
|
52
|
+
}
|
|
53
|
+
|
|
50
54
|
if(!self.agent.appdNative) {
|
|
51
55
|
return callback("V8 tools are not loaded.");
|
|
52
56
|
}
|
package/lib/v8/gc-stats.js
CHANGED
|
@@ -15,6 +15,8 @@ exports.GCStats = GCStats;
|
|
|
15
15
|
|
|
16
16
|
GCStats.prototype.init = function() {
|
|
17
17
|
/* istanbul ignore next */
|
|
18
|
+
if(process.env.APPDYNAMICS_GC_STATS_DISABLED == 'true' || process.env.APPDYNAMICS_GC_STATS_DISABLED == true) return;
|
|
19
|
+
|
|
18
20
|
if (!this.agent.appdNative) return;
|
|
19
21
|
|
|
20
22
|
var mm = this.agent.metricsManager;
|
package/lib/v8/heap-profiler.js
CHANGED
|
@@ -32,6 +32,10 @@ HeapProfiler.prototype.isObjectTrackingSupported = function() {
|
|
|
32
32
|
HeapProfiler.prototype.trackAllocations = function(duration, callback) {
|
|
33
33
|
var self = this;
|
|
34
34
|
|
|
35
|
+
if(process.env.APPDYNAMICS_HEAP_PROFILER_DISABLED == 'true' || process.env.APPDYNAMICS_HEAP_PROFILER_DISABLED == true) {
|
|
36
|
+
return callback("Heap Profiling Disabled.");
|
|
37
|
+
}
|
|
38
|
+
|
|
35
39
|
if(!self.agent.appdNative) {
|
|
36
40
|
return callback("V8 tools are not loaded.");
|
|
37
41
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "appdynamics",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "25.5.7",
|
|
4
4
|
"description": "Performance Profiler and Monitor",
|
|
5
5
|
"author": "AppDynamics, Inc.",
|
|
6
6
|
"homepage": "https://www.appdynamics.com",
|
|
@@ -34,26 +34,20 @@
|
|
|
34
34
|
"n": "^6.8.0"
|
|
35
35
|
},
|
|
36
36
|
"dependencies": {
|
|
37
|
-
"@opentelemetry/api": "
|
|
38
|
-
"@opentelemetry/
|
|
39
|
-
"@opentelemetry/
|
|
40
|
-
"@opentelemetry/
|
|
41
|
-
"@opentelemetry/
|
|
42
|
-
"@opentelemetry/exporter-logs-otlp-proto": "^0.45.1",
|
|
43
|
-
"@opentelemetry/exporter-trace-otlp-proto": "^0.36.1",
|
|
44
|
-
"@opentelemetry/resources": "~1.10.1",
|
|
45
|
-
"@opentelemetry/sdk-logs": "^0.45.1",
|
|
46
|
-
"@opentelemetry/sdk-trace-base": "~1.10.1",
|
|
47
|
-
"@opentelemetry/semantic-conventions": "~1.10.1",
|
|
37
|
+
"@opentelemetry/api": "^1.8.0",
|
|
38
|
+
"@opentelemetry/core": "^1.3.0",
|
|
39
|
+
"@opentelemetry/exporter-logs-otlp-http": "^0.57.0",
|
|
40
|
+
"@opentelemetry/exporter-logs-otlp-proto": "^0.57.0",
|
|
41
|
+
"@opentelemetry/api-logs": "^0.57.0",
|
|
48
42
|
"@yarnpkg/lockfile": "^1.1.0",
|
|
49
43
|
"body-parser": "^1.20.3",
|
|
50
44
|
"cls-hooked": "4.2.2",
|
|
51
45
|
"https-proxy-agent": "^5.0.1",
|
|
52
46
|
"uuid": "^8.3.2",
|
|
53
47
|
"y18n": "^5.0.8",
|
|
54
|
-
"appdynamics-libagent-napi": "https://cdn.appdynamics.com/packages/nodejs/
|
|
55
|
-
"appdynamics-native": "https://cdn.appdynamics.com/packages/nodejs/
|
|
56
|
-
"appdynamics-protobuf": "https://cdn.appdynamics.com/packages/nodejs/
|
|
48
|
+
"appdynamics-libagent-napi": "https://cdn.appdynamics.com/packages/nodejs/25.5.7.0/appdynamics-libagent-napi-node.tgz",
|
|
49
|
+
"appdynamics-native": "https://cdn.appdynamics.com/packages/nodejs/25.5.7.0/appdynamics-native-node.tgz",
|
|
50
|
+
"appdynamics-protobuf": "https://cdn.appdynamics.com/packages/nodejs/25.5.7.0/appdynamics-protobuf-node.tgz"
|
|
57
51
|
},
|
|
58
52
|
"overrides": {
|
|
59
53
|
"semver": "7.5.4"
|
package/packageBck.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "appdynamics",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "25.5.7",
|
|
4
4
|
"description": "Performance Profiler and Monitor",
|
|
5
5
|
"author": "AppDynamics, Inc.",
|
|
6
6
|
"homepage": "https://www.appdynamics.com",
|
|
@@ -34,26 +34,20 @@
|
|
|
34
34
|
"n": "^6.8.0"
|
|
35
35
|
},
|
|
36
36
|
"dependencies": {
|
|
37
|
-
"@opentelemetry/api": "
|
|
38
|
-
"@opentelemetry/
|
|
39
|
-
"@opentelemetry/
|
|
40
|
-
"@opentelemetry/
|
|
41
|
-
"@opentelemetry/
|
|
42
|
-
"@opentelemetry/exporter-logs-otlp-proto": "^0.45.1",
|
|
43
|
-
"@opentelemetry/exporter-trace-otlp-proto": "^0.36.1",
|
|
44
|
-
"@opentelemetry/resources": "~1.10.1",
|
|
45
|
-
"@opentelemetry/sdk-logs": "^0.45.1",
|
|
46
|
-
"@opentelemetry/sdk-trace-base": "~1.10.1",
|
|
47
|
-
"@opentelemetry/semantic-conventions": "~1.10.1",
|
|
37
|
+
"@opentelemetry/api": "^1.8.0",
|
|
38
|
+
"@opentelemetry/core": "^1.3.0",
|
|
39
|
+
"@opentelemetry/exporter-logs-otlp-http": "^0.57.0",
|
|
40
|
+
"@opentelemetry/exporter-logs-otlp-proto": "^0.57.0",
|
|
41
|
+
"@opentelemetry/api-logs": "^0.57.0",
|
|
48
42
|
"@yarnpkg/lockfile": "^1.1.0",
|
|
49
43
|
"body-parser": "^1.20.3",
|
|
50
44
|
"cls-hooked": "4.2.2",
|
|
51
45
|
"https-proxy-agent": "^5.0.1",
|
|
52
46
|
"uuid": "^8.3.2",
|
|
53
47
|
"y18n": "^5.0.8",
|
|
54
|
-
"appdynamics-libagent-napi": "https://cdn.appdynamics.com/packages/nodejs/
|
|
55
|
-
"appdynamics-native": "https://cdn.appdynamics.com/packages/nodejs/
|
|
56
|
-
"appdynamics-protobuf": "https://cdn.appdynamics.com/packages/nodejs/
|
|
48
|
+
"appdynamics-libagent-napi": "https://cdn.appdynamics.com/packages/nodejs/25.5.7.0/appdynamics-libagent-napi-node.tgz",
|
|
49
|
+
"appdynamics-native": "https://cdn.appdynamics.com/packages/nodejs/25.5.7.0/appdynamics-native-node.tgz",
|
|
50
|
+
"appdynamics-protobuf": "https://cdn.appdynamics.com/packages/nodejs/25.5.7.0/appdynamics-protobuf-node.tgz"
|
|
57
51
|
},
|
|
58
52
|
"overrides": {
|
|
59
53
|
"semver": "7.5.4"
|