dd-trace 2.12.1 → 3.2.0
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/LICENSE-3rdparty.csv +3 -2
- package/MIGRATING.md +119 -0
- package/ci/init.js +2 -27
- package/ext/formats.js +3 -5
- package/ext/tags.d.ts +2 -1
- package/ext/tags.js +2 -1
- package/index.d.ts +44 -38
- package/package.json +9 -8
- package/packages/datadog-core/src/storage/async_resource.js +19 -1
- package/packages/datadog-core/src/storage/index.js +1 -1
- package/packages/datadog-instrumentations/index.js +1 -52
- package/packages/datadog-instrumentations/src/connect.js +1 -1
- package/packages/datadog-instrumentations/src/crypto.js +30 -0
- package/packages/datadog-instrumentations/src/cucumber.js +15 -0
- package/packages/datadog-instrumentations/src/grpc/client.js +2 -2
- package/packages/datadog-instrumentations/src/grpc/server.js +1 -1
- package/packages/datadog-instrumentations/src/hapi.js +3 -31
- package/packages/datadog-instrumentations/src/helpers/hooks.js +69 -0
- package/packages/datadog-instrumentations/src/helpers/instrument.js +5 -34
- package/packages/datadog-instrumentations/src/helpers/instrumentations.js +7 -0
- package/packages/datadog-instrumentations/src/helpers/register.js +59 -0
- package/packages/datadog-instrumentations/src/http/server.js +1 -1
- package/packages/datadog-instrumentations/src/jest.js +33 -11
- package/packages/datadog-instrumentations/src/koa.js +1 -1
- package/packages/datadog-instrumentations/src/mocha.js +4 -1
- package/packages/datadog-instrumentations/src/net.js +13 -0
- package/packages/datadog-instrumentations/src/pg.js +2 -2
- package/packages/datadog-instrumentations/src/restify.js +27 -5
- package/packages/datadog-instrumentations/src/router.js +1 -1
- package/packages/datadog-plugin-aws-sdk/src/base.js +1 -2
- package/packages/datadog-plugin-aws-sdk/src/services/sqs.js +1 -2
- package/packages/datadog-plugin-cucumber/src/index.js +4 -0
- package/packages/datadog-plugin-grpc/src/client.js +2 -2
- package/packages/datadog-plugin-grpc/src/server.js +2 -2
- package/packages/datadog-plugin-http/src/client.js +1 -1
- package/packages/datadog-plugin-http/src/server.js +1 -1
- package/packages/datadog-plugin-http2/src/client.js +1 -1
- package/packages/datadog-plugin-jest/src/index.js +25 -4
- package/packages/datadog-plugin-mocha/src/index.js +2 -2
- package/packages/datadog-plugin-mongodb-core/src/index.js +32 -8
- package/packages/datadog-plugin-oracledb/src/index.js +12 -4
- package/packages/datadog-plugin-restify/src/index.js +7 -0
- package/packages/dd-trace/index.js +1 -1
- package/packages/dd-trace/src/appsec/iast/analyzers/analyzers.js +3 -0
- package/packages/dd-trace/src/appsec/iast/analyzers/index.js +20 -0
- package/packages/dd-trace/src/appsec/iast/analyzers/vulnerability-analyzer.js +48 -0
- package/packages/dd-trace/src/appsec/iast/analyzers/weak-hash-analyzer.js +24 -0
- package/packages/dd-trace/src/appsec/iast/iast-context.js +50 -0
- package/packages/dd-trace/src/appsec/iast/index.js +59 -0
- package/packages/dd-trace/src/appsec/iast/overhead-controller.js +94 -0
- package/packages/dd-trace/src/appsec/iast/path-line.js +70 -0
- package/packages/dd-trace/src/appsec/iast/vulnerability-reporter.js +113 -0
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/coverage-writer.js +50 -0
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/index.js +53 -8
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/writer.js +23 -24
- package/packages/dd-trace/src/ci-visibility/exporters/git/git_metadata.js +220 -0
- package/packages/dd-trace/src/config.js +97 -10
- package/packages/dd-trace/src/constants.js +9 -1
- package/packages/dd-trace/src/encode/0.4.js +55 -58
- package/packages/dd-trace/src/encode/agentless-ci-visibility.js +13 -34
- package/packages/dd-trace/src/encode/coverage-ci-visibility.js +84 -0
- package/packages/dd-trace/src/encode/span-stats.js +155 -0
- package/packages/dd-trace/src/exporters/agent/index.js +25 -7
- package/packages/dd-trace/src/exporters/agent/writer.js +7 -4
- package/packages/dd-trace/src/{profiling/exporters → exporters/common}/form-data.js +0 -0
- package/packages/dd-trace/src/exporters/common/request.js +69 -39
- package/packages/dd-trace/src/exporters/common/writer.js +16 -6
- package/packages/dd-trace/src/exporters/span-stats/index.js +20 -0
- package/packages/dd-trace/src/exporters/span-stats/writer.js +54 -0
- package/packages/dd-trace/src/format.js +2 -0
- package/packages/dd-trace/src/id.js +16 -13
- package/packages/dd-trace/src/iitm.js +12 -1
- package/packages/dd-trace/src/index.js +10 -0
- package/packages/dd-trace/src/noop/proxy.js +77 -0
- package/packages/dd-trace/src/noop/scope.js +2 -6
- package/packages/dd-trace/src/noop/span.js +12 -12
- package/packages/dd-trace/src/noop/tracer.js +8 -9
- package/packages/dd-trace/src/opentracing/propagation/text_map.js +77 -6
- package/packages/dd-trace/src/opentracing/span.js +63 -49
- package/packages/dd-trace/src/opentracing/span_context.js +1 -5
- package/packages/dd-trace/src/opentracing/tracer.js +32 -37
- package/packages/dd-trace/src/plugin_manager.js +111 -64
- package/packages/dd-trace/src/plugins/index.js +57 -45
- package/packages/dd-trace/src/plugins/log_plugin.js +16 -9
- package/packages/dd-trace/src/plugins/util/ci.js +34 -9
- package/packages/dd-trace/src/plugins/util/git.js +52 -2
- package/packages/dd-trace/src/plugins/util/ip_blocklist.js +25 -0
- package/packages/dd-trace/src/plugins/util/tags.js +4 -1
- package/packages/dd-trace/src/plugins/util/web.js +149 -6
- package/packages/dd-trace/src/priority_sampler.js +36 -1
- package/packages/dd-trace/src/profiling/exporters/agent.js +1 -1
- package/packages/dd-trace/src/profiling/profilers/cpu.js +3 -3
- package/packages/dd-trace/src/proxy.js +21 -90
- package/packages/dd-trace/src/ritm.js +10 -1
- package/packages/dd-trace/src/scope.js +2 -184
- package/packages/dd-trace/src/span_processor.js +7 -1
- package/packages/dd-trace/src/span_stats.js +210 -0
- package/packages/dd-trace/src/startup-log.js +8 -19
- package/packages/dd-trace/src/telemetry/dependencies.js +83 -0
- package/packages/dd-trace/src/{telemetry.js → telemetry/index.js} +11 -79
- package/packages/dd-trace/src/telemetry/send-data.js +35 -0
- package/packages/dd-trace/src/tracer.js +0 -4
- package/scripts/install_plugin_modules.js +17 -26
- package/ci/jest/env.js +0 -39
- package/cypress/plugin.js +0 -5
- package/cypress/support.js +0 -1
- package/packages/datadog-plugin-fs/src/index.js +0 -548
|
@@ -0,0 +1,210 @@
|
|
|
1
|
+
const os = require('os')
|
|
2
|
+
const { version } = require('./pkg')
|
|
3
|
+
const pkg = require('../../../package.json')
|
|
4
|
+
|
|
5
|
+
const { LogCollapsingLowestDenseDDSketch } = require('@datadog/sketches-js')
|
|
6
|
+
const { ORIGIN_KEY, TOP_LEVEL_KEY } = require('./constants')
|
|
7
|
+
const {
|
|
8
|
+
MEASURED,
|
|
9
|
+
HTTP_STATUS_CODE
|
|
10
|
+
} = require('../../../ext/tags')
|
|
11
|
+
|
|
12
|
+
const { SpanStatsExporter } = require('./exporters/span-stats')
|
|
13
|
+
|
|
14
|
+
const {
|
|
15
|
+
DEFAULT_SPAN_NAME,
|
|
16
|
+
DEFAULT_SERVICE_NAME
|
|
17
|
+
} = require('./encode/tags-processors')
|
|
18
|
+
|
|
19
|
+
class SpanAggStats {
|
|
20
|
+
constructor (aggKey) {
|
|
21
|
+
this.aggKey = aggKey
|
|
22
|
+
this.hits = 0
|
|
23
|
+
this.topLevelHits = 0
|
|
24
|
+
this.errors = 0
|
|
25
|
+
this.duration = 0
|
|
26
|
+
this.okDistribution = new LogCollapsingLowestDenseDDSketch(0.00775)
|
|
27
|
+
this.errorDistribution = new LogCollapsingLowestDenseDDSketch(0.00775)
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
record (span) {
|
|
31
|
+
const durationNs = span._duration * 1e6
|
|
32
|
+
this.hits++
|
|
33
|
+
this.duration += durationNs
|
|
34
|
+
|
|
35
|
+
if (span.metrics[TOP_LEVEL_KEY]) {
|
|
36
|
+
this.topLevelHits++
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
if (span.error) {
|
|
40
|
+
this.errors++
|
|
41
|
+
this.errorDistribution.accept(durationNs)
|
|
42
|
+
} else {
|
|
43
|
+
this.okDistribution.accept(durationNs)
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
toJSON () {
|
|
48
|
+
const {
|
|
49
|
+
name,
|
|
50
|
+
service,
|
|
51
|
+
resource,
|
|
52
|
+
type,
|
|
53
|
+
statusCode,
|
|
54
|
+
synthetics
|
|
55
|
+
} = this.aggKey
|
|
56
|
+
|
|
57
|
+
return {
|
|
58
|
+
Name: name,
|
|
59
|
+
Service: service,
|
|
60
|
+
Resource: resource,
|
|
61
|
+
Type: type,
|
|
62
|
+
HTTPStatusCode: statusCode,
|
|
63
|
+
Synthetics: synthetics,
|
|
64
|
+
Hits: this.hits,
|
|
65
|
+
TopLevelHits: this.topLevelHits,
|
|
66
|
+
Errors: this.errors,
|
|
67
|
+
Duration: this.duration,
|
|
68
|
+
OkSummary: this.okDistribution.toProto(),
|
|
69
|
+
ErrorSummary: this.errorDistribution.toProto()
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
class SpanAggKey {
|
|
75
|
+
constructor (span) {
|
|
76
|
+
this.name = span.name || DEFAULT_SPAN_NAME
|
|
77
|
+
this.service = span.service || DEFAULT_SERVICE_NAME
|
|
78
|
+
this.resource = span.resource || ''
|
|
79
|
+
this.type = span.type || ''
|
|
80
|
+
this.statusCode = span.meta[HTTP_STATUS_CODE] || 0
|
|
81
|
+
this.synthetics = span.meta[ORIGIN_KEY] === 'synthetics'
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
toString () {
|
|
85
|
+
return [
|
|
86
|
+
this.name,
|
|
87
|
+
this.service,
|
|
88
|
+
this.resource,
|
|
89
|
+
this.type,
|
|
90
|
+
this.statusCode,
|
|
91
|
+
this.synthetics
|
|
92
|
+
].join(',')
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
class SpanBuckets extends Map {
|
|
97
|
+
forSpan (span) {
|
|
98
|
+
const aggKey = new SpanAggKey(span)
|
|
99
|
+
const key = aggKey.toString()
|
|
100
|
+
|
|
101
|
+
if (!this.has(key)) {
|
|
102
|
+
this.set(key, new SpanAggStats(aggKey))
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
return this.get(key)
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
class TimeBuckets extends Map {
|
|
110
|
+
forTime (time) {
|
|
111
|
+
if (!this.has(time)) {
|
|
112
|
+
this.set(time, new SpanBuckets())
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
return this.get(time)
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
class SpanStatsProcessor {
|
|
120
|
+
constructor ({
|
|
121
|
+
stats: {
|
|
122
|
+
enabled = false,
|
|
123
|
+
interval = 10
|
|
124
|
+
},
|
|
125
|
+
hostname,
|
|
126
|
+
port,
|
|
127
|
+
url,
|
|
128
|
+
env,
|
|
129
|
+
tags
|
|
130
|
+
} = {}) {
|
|
131
|
+
this.exporter = new SpanStatsExporter({
|
|
132
|
+
hostname,
|
|
133
|
+
port,
|
|
134
|
+
tags,
|
|
135
|
+
url
|
|
136
|
+
})
|
|
137
|
+
this.interval = interval
|
|
138
|
+
this.bucketSizeNs = interval * 1e9
|
|
139
|
+
this.buckets = new TimeBuckets()
|
|
140
|
+
this.hostname = os.hostname()
|
|
141
|
+
this.enabled = enabled
|
|
142
|
+
this.env = env
|
|
143
|
+
this.tags = tags || {}
|
|
144
|
+
this.sequence = 0
|
|
145
|
+
|
|
146
|
+
if (enabled) {
|
|
147
|
+
this.timer = setInterval(this.onInterval.bind(this), interval * 1e3)
|
|
148
|
+
this.timer.unref()
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
onInterval () {
|
|
153
|
+
const serialized = this._serializeBuckets()
|
|
154
|
+
if (!serialized) return
|
|
155
|
+
|
|
156
|
+
this.exporter.export({
|
|
157
|
+
Hostname: this.hostname,
|
|
158
|
+
Env: this.env,
|
|
159
|
+
Version: version,
|
|
160
|
+
Stats: serialized,
|
|
161
|
+
Lang: 'javascript',
|
|
162
|
+
TracerVersion: pkg.version,
|
|
163
|
+
RuntimeID: this.tags['runtime-id'],
|
|
164
|
+
Sequence: ++this.sequence
|
|
165
|
+
})
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
onSpanFinished (span) {
|
|
169
|
+
if (!this.enabled) return
|
|
170
|
+
if (!span.metrics[TOP_LEVEL_KEY] && !span.metrics[MEASURED]) return
|
|
171
|
+
|
|
172
|
+
const spanEndNs = span.startTime + span.duration
|
|
173
|
+
const bucketTime = spanEndNs - (spanEndNs % this.bucketSizeNs)
|
|
174
|
+
|
|
175
|
+
this.buckets.forTime(bucketTime)
|
|
176
|
+
.forSpan(span)
|
|
177
|
+
.record(span)
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
_serializeBuckets () {
|
|
181
|
+
const { bucketSizeNs } = this
|
|
182
|
+
const serializedBuckets = []
|
|
183
|
+
|
|
184
|
+
for (const [ timeNs, bucket ] of this.buckets.entries()) {
|
|
185
|
+
const bucketAggStats = []
|
|
186
|
+
|
|
187
|
+
for (const stats of bucket.values()) {
|
|
188
|
+
bucketAggStats.push(stats.toJSON())
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
serializedBuckets.push({
|
|
192
|
+
Start: timeNs,
|
|
193
|
+
Duration: bucketSizeNs,
|
|
194
|
+
Stats: bucketAggStats
|
|
195
|
+
})
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
this.buckets.clear()
|
|
199
|
+
|
|
200
|
+
return serializedBuckets
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
module.exports = {
|
|
205
|
+
SpanAggStats,
|
|
206
|
+
SpanAggKey,
|
|
207
|
+
SpanBuckets,
|
|
208
|
+
TimeBuckets,
|
|
209
|
+
SpanStatsProcessor
|
|
210
|
+
}
|
|
@@ -5,38 +5,27 @@ const mainLogger = require('./log')
|
|
|
5
5
|
const os = require('os')
|
|
6
6
|
const { inspect } = require('util')
|
|
7
7
|
const tracerVersion = require('../../../package.json').version
|
|
8
|
-
const requirePackageJson = require('./require-package-json')
|
|
9
8
|
|
|
10
9
|
const logger = Object.create(mainLogger)
|
|
11
10
|
logger._enabled = true
|
|
12
11
|
|
|
13
12
|
let config
|
|
14
|
-
let
|
|
13
|
+
let pluginManager
|
|
15
14
|
let samplingRules = []
|
|
16
|
-
|
|
17
15
|
let alreadyRan = false
|
|
18
16
|
|
|
19
17
|
function getIntegrationsAndAnalytics () {
|
|
20
18
|
const integrations = new Set()
|
|
21
19
|
const extras = {}
|
|
22
|
-
for (const
|
|
23
|
-
|
|
24
|
-
try {
|
|
25
|
-
const version = requirePackageJson(plugin.name, module).version
|
|
26
|
-
integrations.add(`${plugin.name}@${version}`)
|
|
27
|
-
} catch (e) {
|
|
28
|
-
integrations.add(plugin.name)
|
|
29
|
-
}
|
|
30
|
-
} else {
|
|
31
|
-
integrations.add(plugin.name)
|
|
32
|
-
}
|
|
20
|
+
for (const pluginName in pluginManager._pluginsByName) {
|
|
21
|
+
integrations.add(pluginName)
|
|
33
22
|
}
|
|
34
23
|
extras.integrations_loaded = Array.from(integrations)
|
|
35
24
|
return extras
|
|
36
25
|
}
|
|
37
26
|
|
|
38
27
|
function startupLog ({ agentError } = {}) {
|
|
39
|
-
if (!config || !
|
|
28
|
+
if (!config || !pluginManager) {
|
|
40
29
|
return
|
|
41
30
|
}
|
|
42
31
|
|
|
@@ -106,7 +95,7 @@ function startupLog ({ agentError } = {}) {
|
|
|
106
95
|
}
|
|
107
96
|
|
|
108
97
|
config = undefined
|
|
109
|
-
|
|
98
|
+
pluginManager = undefined
|
|
110
99
|
samplingRules = undefined
|
|
111
100
|
}
|
|
112
101
|
|
|
@@ -114,8 +103,8 @@ function setStartupLogConfig (aConfig) {
|
|
|
114
103
|
config = aConfig
|
|
115
104
|
}
|
|
116
105
|
|
|
117
|
-
function
|
|
118
|
-
|
|
106
|
+
function setStartupLogPluginManager (thePluginManager) {
|
|
107
|
+
pluginManager = thePluginManager
|
|
119
108
|
}
|
|
120
109
|
|
|
121
110
|
function setSamplingRules (theRules) {
|
|
@@ -125,6 +114,6 @@ function setSamplingRules (theRules) {
|
|
|
125
114
|
module.exports = {
|
|
126
115
|
startupLog,
|
|
127
116
|
setStartupLogConfig,
|
|
128
|
-
|
|
117
|
+
setStartupLogPluginManager,
|
|
129
118
|
setSamplingRules
|
|
130
119
|
}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const path = require('path')
|
|
4
|
+
const parse = require('module-details-from-path')
|
|
5
|
+
const requirePackageJson = require('../require-package-json')
|
|
6
|
+
const { sendData } = require('./send-data')
|
|
7
|
+
const dc = require('diagnostics_channel')
|
|
8
|
+
const { fileURLToPath } = require('url')
|
|
9
|
+
|
|
10
|
+
const savedDependencies = []
|
|
11
|
+
const detectedDependencyNames = new Set()
|
|
12
|
+
const FILE_URI_START = `file://`
|
|
13
|
+
const moduleLoadStartChannel = dc.channel('dd-trace:moduleLoadStart')
|
|
14
|
+
|
|
15
|
+
let immediate, config, application, host
|
|
16
|
+
|
|
17
|
+
function waitAndSend (config, application, host) {
|
|
18
|
+
if (!immediate) {
|
|
19
|
+
immediate = setImmediate(() => {
|
|
20
|
+
immediate = null
|
|
21
|
+
if (savedDependencies.length > 0) {
|
|
22
|
+
const dependencies = savedDependencies.splice(0, 1000)
|
|
23
|
+
sendData(config, application, host, 'app-dependencies-loaded', { dependencies })
|
|
24
|
+
if (savedDependencies.length > 0) {
|
|
25
|
+
waitAndSend(config, application, host)
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
})
|
|
29
|
+
immediate.unref()
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
function onModuleLoad (data) {
|
|
34
|
+
if (data) {
|
|
35
|
+
let filename = data.filename
|
|
36
|
+
if (filename && filename.startsWith(FILE_URI_START)) {
|
|
37
|
+
try {
|
|
38
|
+
filename = fileURLToPath(filename)
|
|
39
|
+
} catch (e) {
|
|
40
|
+
// cannot transform url to path
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
const parseResult = filename && parse(filename)
|
|
44
|
+
const request = data.request || (parseResult && parseResult.name)
|
|
45
|
+
if (filename && request && isDependency(filename, request) && !detectedDependencyNames.has(request)) {
|
|
46
|
+
detectedDependencyNames.add(request)
|
|
47
|
+
if (parseResult) {
|
|
48
|
+
const { name, basedir } = parseResult
|
|
49
|
+
if (basedir) {
|
|
50
|
+
try {
|
|
51
|
+
const { version } = requirePackageJson(basedir, module)
|
|
52
|
+
savedDependencies.push({ name, version })
|
|
53
|
+
waitAndSend(config, application, host)
|
|
54
|
+
} catch (e) {
|
|
55
|
+
// can not read the package.json, do nothing
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
function start (_config, _application, _host) {
|
|
63
|
+
config = _config
|
|
64
|
+
application = _application
|
|
65
|
+
host = _host
|
|
66
|
+
moduleLoadStartChannel.subscribe(onModuleLoad)
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
function isDependency (filename, request) {
|
|
70
|
+
return request.indexOf(`.${path.sep}`) !== 0 && request.indexOf(path.sep) !== 0
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
function stop () {
|
|
74
|
+
config = null
|
|
75
|
+
application = null
|
|
76
|
+
host = null
|
|
77
|
+
detectedDependencyNames.clear()
|
|
78
|
+
savedDependencies.splice(0, savedDependencies.length)
|
|
79
|
+
if (moduleLoadStartChannel.hasSubscribers) {
|
|
80
|
+
moduleLoadStartChannel.unsubscribe(onModuleLoad)
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
module.exports = { start, stop }
|
|
@@ -1,18 +1,14 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
|
-
const tracerVersion = require('
|
|
4
|
-
const
|
|
5
|
-
const containerId = require('./exporters/common/docker').id()
|
|
6
|
-
const requirePackageJson = require('./require-package-json')
|
|
7
|
-
const path = require('path')
|
|
3
|
+
const tracerVersion = require('../../../../package.json').version
|
|
4
|
+
const containerId = require('../exporters/common/docker').id()
|
|
8
5
|
const os = require('os')
|
|
9
|
-
const
|
|
6
|
+
const dependencies = require('./dependencies')
|
|
7
|
+
const { sendData } = require('./send-data')
|
|
10
8
|
|
|
11
9
|
let config
|
|
12
|
-
let instrumenter
|
|
13
10
|
let pluginManager
|
|
14
11
|
|
|
15
|
-
let seqId = 0
|
|
16
12
|
let application
|
|
17
13
|
let host
|
|
18
14
|
let interval
|
|
@@ -20,17 +16,6 @@ const sentIntegrations = new Set()
|
|
|
20
16
|
|
|
21
17
|
function getIntegrations () {
|
|
22
18
|
const newIntegrations = []
|
|
23
|
-
for (const plugin of instrumenter._instrumented.keys()) {
|
|
24
|
-
if (sentIntegrations.has(plugin.name)) {
|
|
25
|
-
continue
|
|
26
|
-
}
|
|
27
|
-
newIntegrations.push({
|
|
28
|
-
name: plugin.name,
|
|
29
|
-
enabled: true,
|
|
30
|
-
auto_enabled: true
|
|
31
|
-
})
|
|
32
|
-
sentIntegrations.add(plugin.name)
|
|
33
|
-
}
|
|
34
19
|
for (const pluginName in pluginManager._pluginsByName) {
|
|
35
20
|
if (sentIntegrations.has(pluginName)) {
|
|
36
21
|
continue
|
|
@@ -45,27 +30,6 @@ function getIntegrations () {
|
|
|
45
30
|
return newIntegrations
|
|
46
31
|
}
|
|
47
32
|
|
|
48
|
-
function getDependencies () {
|
|
49
|
-
const deps = []
|
|
50
|
-
const { dependencies } = pkg
|
|
51
|
-
if (!dependencies) {
|
|
52
|
-
return deps
|
|
53
|
-
}
|
|
54
|
-
const rootDir = pkg.findRoot()
|
|
55
|
-
for (const [name, version] of Object.entries(dependencies)) {
|
|
56
|
-
const dep = { name }
|
|
57
|
-
try {
|
|
58
|
-
dep.version = requirePackageJson(
|
|
59
|
-
path.join(rootDir, 'node_modules', name.replace('/', path.sep))
|
|
60
|
-
).version
|
|
61
|
-
} catch (e) {
|
|
62
|
-
dep.version = version
|
|
63
|
-
}
|
|
64
|
-
deps.push(dep)
|
|
65
|
-
}
|
|
66
|
-
return deps
|
|
67
|
-
}
|
|
68
|
-
|
|
69
33
|
function flatten (input, result = [], prefix = [], traversedObjects = null) {
|
|
70
34
|
traversedObjects = traversedObjects || new WeakSet()
|
|
71
35
|
if (traversedObjects.has(input)) {
|
|
@@ -85,7 +49,7 @@ function flatten (input, result = [], prefix = [], traversedObjects = null) {
|
|
|
85
49
|
function appStarted () {
|
|
86
50
|
return {
|
|
87
51
|
integrations: getIntegrations(),
|
|
88
|
-
dependencies:
|
|
52
|
+
dependencies: [],
|
|
89
53
|
configuration: flatten(config),
|
|
90
54
|
additional_payload: []
|
|
91
55
|
}
|
|
@@ -93,7 +57,7 @@ function appStarted () {
|
|
|
93
57
|
|
|
94
58
|
function onBeforeExit () {
|
|
95
59
|
process.removeListener('beforeExit', onBeforeExit)
|
|
96
|
-
sendData('app-closing')
|
|
60
|
+
sendData(config, application, host, 'app-closing')
|
|
97
61
|
}
|
|
98
62
|
|
|
99
63
|
function createAppObject () {
|
|
@@ -114,49 +78,17 @@ function createHostObject () {
|
|
|
114
78
|
}
|
|
115
79
|
}
|
|
116
80
|
|
|
117
|
-
function
|
|
118
|
-
const {
|
|
119
|
-
hostname,
|
|
120
|
-
port
|
|
121
|
-
} = config
|
|
122
|
-
const options = {
|
|
123
|
-
hostname,
|
|
124
|
-
port,
|
|
125
|
-
method: 'POST',
|
|
126
|
-
path: '/telemetry/proxy/api/v2/apmtelemetry',
|
|
127
|
-
headers: {
|
|
128
|
-
'content-type': 'application/json',
|
|
129
|
-
'dd-telemetry-api-version': 'v1',
|
|
130
|
-
'dd-telemetry-request-type': reqType
|
|
131
|
-
}
|
|
132
|
-
}
|
|
133
|
-
const data = JSON.stringify({
|
|
134
|
-
api_version: 'v1',
|
|
135
|
-
request_type: reqType,
|
|
136
|
-
tracer_time: Math.floor(Date.now() / 1000),
|
|
137
|
-
runtime_id: config.tags['runtime-id'],
|
|
138
|
-
seq_id: ++seqId,
|
|
139
|
-
payload,
|
|
140
|
-
application,
|
|
141
|
-
host
|
|
142
|
-
})
|
|
143
|
-
|
|
144
|
-
request(data, options, true, () => {
|
|
145
|
-
// ignore errors
|
|
146
|
-
})
|
|
147
|
-
}
|
|
148
|
-
|
|
149
|
-
function start (aConfig, theInstrumenter, thePluginManager) {
|
|
81
|
+
function start (aConfig, thePluginManager) {
|
|
150
82
|
if (!aConfig.telemetryEnabled) {
|
|
151
83
|
return
|
|
152
84
|
}
|
|
153
85
|
config = aConfig
|
|
154
|
-
instrumenter = theInstrumenter
|
|
155
86
|
pluginManager = thePluginManager
|
|
156
87
|
application = createAppObject()
|
|
157
88
|
host = createHostObject()
|
|
158
|
-
|
|
159
|
-
|
|
89
|
+
dependencies.start(config, application, host)
|
|
90
|
+
sendData(config, application, host, 'app-started', appStarted())
|
|
91
|
+
interval = setInterval(() => sendData(config, application, host, 'app-heartbeat'), 60000)
|
|
160
92
|
interval.unref()
|
|
161
93
|
process.on('beforeExit', onBeforeExit)
|
|
162
94
|
}
|
|
@@ -177,7 +109,7 @@ function updateIntegrations () {
|
|
|
177
109
|
if (integrations.length === 0) {
|
|
178
110
|
return
|
|
179
111
|
}
|
|
180
|
-
sendData('app-integrations-change', { integrations })
|
|
112
|
+
sendData(config, application, host, 'app-integrations-change', { integrations })
|
|
181
113
|
}
|
|
182
114
|
|
|
183
115
|
module.exports = {
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
const request = require('../exporters/common/request')
|
|
2
|
+
let seqId = 0
|
|
3
|
+
function sendData (config, application, host, reqType, payload = {}) {
|
|
4
|
+
const {
|
|
5
|
+
hostname,
|
|
6
|
+
port
|
|
7
|
+
} = config
|
|
8
|
+
const options = {
|
|
9
|
+
hostname,
|
|
10
|
+
port,
|
|
11
|
+
method: 'POST',
|
|
12
|
+
path: '/telemetry/proxy/api/v2/apmtelemetry',
|
|
13
|
+
headers: {
|
|
14
|
+
'content-type': 'application/json',
|
|
15
|
+
'dd-telemetry-api-version': 'v1',
|
|
16
|
+
'dd-telemetry-request-type': reqType
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
const data = JSON.stringify({
|
|
20
|
+
api_version: 'v1',
|
|
21
|
+
request_type: reqType,
|
|
22
|
+
tracer_time: Math.floor(Date.now() / 1000),
|
|
23
|
+
runtime_id: config.tags['runtime-id'],
|
|
24
|
+
seq_id: ++seqId,
|
|
25
|
+
payload,
|
|
26
|
+
application,
|
|
27
|
+
host
|
|
28
|
+
})
|
|
29
|
+
|
|
30
|
+
request(data, options, () => {
|
|
31
|
+
// ignore errors
|
|
32
|
+
})
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
module.exports = { sendData }
|
|
@@ -7,8 +7,6 @@ const semver = require('semver')
|
|
|
7
7
|
const proxyquire = require('proxyquire')
|
|
8
8
|
const exec = require('./helpers/exec')
|
|
9
9
|
const childProcess = require('child_process')
|
|
10
|
-
const plugins = require('../packages/dd-trace/src/plugins')
|
|
11
|
-
const Plugin = require('../packages/dd-trace/src/plugins/plugin')
|
|
12
10
|
const externals = require('../packages/dd-trace/test/plugins/externals')
|
|
13
11
|
|
|
14
12
|
const requirePackageJsonPath = require.resolve('../packages/dd-trace/src/require-package-json')
|
|
@@ -16,6 +14,9 @@ const requirePackageJsonPath = require.resolve('../packages/dd-trace/src/require
|
|
|
16
14
|
const workspaces = new Set()
|
|
17
15
|
const versionLists = {}
|
|
18
16
|
const deps = {}
|
|
17
|
+
const names = []
|
|
18
|
+
const filter = process.env.hasOwnProperty('PLUGINS') && process.env.PLUGINS.split('|')
|
|
19
|
+
|
|
19
20
|
Object.keys(externals).forEach(external => externals[external].forEach(thing => {
|
|
20
21
|
if (thing.dep) {
|
|
21
22
|
if (!deps[external]) {
|
|
@@ -29,7 +30,10 @@ fs.readdirSync(path.join(__dirname, '../packages/datadog-instrumentations/src'))
|
|
|
29
30
|
.filter(file => file.endsWith('js'))
|
|
30
31
|
.forEach(file => {
|
|
31
32
|
file = file.replace('.js', '')
|
|
32
|
-
|
|
33
|
+
|
|
34
|
+
if (!filter || filter.includes(file)) {
|
|
35
|
+
names.push(file)
|
|
36
|
+
}
|
|
33
37
|
})
|
|
34
38
|
|
|
35
39
|
run()
|
|
@@ -42,32 +46,19 @@ async function run () {
|
|
|
42
46
|
}
|
|
43
47
|
|
|
44
48
|
async function assertVersions () {
|
|
45
|
-
let filter = []
|
|
46
|
-
let names = Object.keys(plugins)
|
|
47
|
-
|
|
48
|
-
if (process.env.hasOwnProperty('PLUGINS')) {
|
|
49
|
-
filter = process.env.PLUGINS.split('|')
|
|
50
|
-
names = names.filter(name => ~filter.indexOf(name))
|
|
51
|
-
}
|
|
52
|
-
|
|
53
49
|
const internals = names
|
|
54
50
|
.map(key => {
|
|
55
|
-
const
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
} catch (e) {
|
|
64
|
-
loadInstFile(`${name}.js`, instrumentations)
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
return instrumentations
|
|
68
|
-
} else {
|
|
69
|
-
return plugin
|
|
51
|
+
const instrumentations = []
|
|
52
|
+
const name = key
|
|
53
|
+
|
|
54
|
+
try {
|
|
55
|
+
loadInstFile(`${name}/server.js`, instrumentations)
|
|
56
|
+
loadInstFile(`${name}/client.js`, instrumentations)
|
|
57
|
+
} catch (e) {
|
|
58
|
+
loadInstFile(`${name}.js`, instrumentations)
|
|
70
59
|
}
|
|
60
|
+
|
|
61
|
+
return instrumentations
|
|
71
62
|
})
|
|
72
63
|
.reduce((prev, next) => prev.concat(next), [])
|
|
73
64
|
|
package/ci/jest/env.js
DELETED
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
/* eslint-disable no-console */
|
|
2
|
-
|
|
3
|
-
const tracer = require('../../packages/dd-trace')
|
|
4
|
-
const { ORIGIN_KEY } = require('../../packages/dd-trace/src/constants')
|
|
5
|
-
|
|
6
|
-
const options = {
|
|
7
|
-
startupLogs: false,
|
|
8
|
-
tags: {
|
|
9
|
-
[ORIGIN_KEY]: 'ciapp-test'
|
|
10
|
-
}
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
const isAgentlessEnabled = process.env.DD_CIVISIBILITY_AGENTLESS_ENABLED &&
|
|
14
|
-
process.env.DD_CIVISIBILITY_AGENTLESS_ENABLED !== 'false' &&
|
|
15
|
-
process.env.DD_CIVISIBILITY_AGENTLESS_ENABLED !== '0'
|
|
16
|
-
|
|
17
|
-
if (isAgentlessEnabled) {
|
|
18
|
-
if (process.env.DATADOG_API_KEY || process.env.DD_API_KEY) {
|
|
19
|
-
tracer.init({
|
|
20
|
-
...options,
|
|
21
|
-
experimental: {
|
|
22
|
-
exporter: 'datadog'
|
|
23
|
-
}
|
|
24
|
-
})
|
|
25
|
-
} else {
|
|
26
|
-
console.error(`DD_CIVISIBILITY_AGENTLESS_ENABLED is set, \
|
|
27
|
-
but neither DD_API_KEY nor DATADOG_API_KEY are set in your environment, \
|
|
28
|
-
so dd-trace will not be initialized.`)
|
|
29
|
-
}
|
|
30
|
-
} else {
|
|
31
|
-
tracer.init({
|
|
32
|
-
...options,
|
|
33
|
-
flushInterval: 400000
|
|
34
|
-
})
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
tracer.use('fs', false)
|
|
38
|
-
|
|
39
|
-
module.exports = tracer
|
package/cypress/plugin.js
DELETED
package/cypress/support.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
require('../packages/datadog-plugin-cypress/src/support')
|