dd-trace 6.9.0 → 6.11.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/README.md +0 -17
- package/ci/vitest-no-worker-init-setup.mjs +112 -10
- package/index.d.ts +150 -3
- package/initialize.mjs +28 -17
- package/openfeature.js +2 -2
- package/package.json +14 -10
- package/packages/datadog-esbuild/index.js +0 -34
- package/packages/datadog-instrumentations/src/anthropic.js +210 -15
- package/packages/datadog-instrumentations/src/aws-sdk.js +9 -1
- package/packages/datadog-instrumentations/src/browser-bunyan.js +11 -0
- package/packages/datadog-instrumentations/src/bunyan.js +3 -16
- package/packages/datadog-instrumentations/src/confluentinc-kafka-javascript.js +111 -6
- package/packages/datadog-instrumentations/src/cucumber.js +26 -11
- package/packages/datadog-instrumentations/src/cypress-config.js +182 -16
- package/packages/datadog-instrumentations/src/cypress-legacy-finalizers.js +30 -0
- package/packages/datadog-instrumentations/src/cypress.js +2 -0
- package/packages/datadog-instrumentations/src/fastify.js +2 -0
- package/packages/datadog-instrumentations/src/helpers/bunyan.js +22 -0
- package/packages/datadog-instrumentations/src/helpers/hooks.js +2 -1
- package/packages/datadog-instrumentations/src/helpers/pool-acquire.js +634 -0
- package/packages/datadog-instrumentations/src/helpers/register.js +10 -8
- package/packages/datadog-instrumentations/src/helpers/rewriter/index.js +2 -1
- package/packages/datadog-instrumentations/src/helpers/rewriter/instrumentations/webdriverio.js +81 -0
- package/packages/datadog-instrumentations/src/helpers/rewriter/targets.json +1 -0
- package/packages/datadog-instrumentations/src/helpers/rewriter/transforms.js +83 -1
- package/packages/datadog-instrumentations/src/jest.js +26 -18
- package/packages/datadog-instrumentations/src/mariadb.js +278 -21
- package/packages/datadog-instrumentations/src/mocha/main.js +540 -56
- package/packages/datadog-instrumentations/src/mocha/utils.js +132 -25
- package/packages/datadog-instrumentations/src/mysql.js +45 -15
- package/packages/datadog-instrumentations/src/mysql2.js +119 -18
- package/packages/datadog-instrumentations/src/path-to-regexp.js +67 -1
- package/packages/datadog-instrumentations/src/pg.js +116 -92
- package/packages/datadog-instrumentations/src/playwright-reporter.js +99 -0
- package/packages/datadog-instrumentations/src/playwright.js +149 -2
- package/packages/datadog-instrumentations/src/router.js +2 -0
- package/packages/datadog-instrumentations/src/vitest-main-no-worker-init.js +43 -4
- package/packages/datadog-instrumentations/src/vitest-main.js +180 -20
- package/packages/datadog-instrumentations/src/vitest-util.js +64 -5
- package/packages/datadog-instrumentations/src/vitest-worker.js +150 -25
- package/packages/datadog-instrumentations/src/webdriverio.js +31 -17
- package/packages/datadog-plugin-aws-durable-execution-sdk-js/src/trace-checkpoint.js +12 -6
- package/packages/datadog-plugin-aws-sdk/src/base.js +1 -0
- package/packages/datadog-plugin-aws-sdk/src/services/eventbridge.js +163 -44
- package/packages/datadog-plugin-aws-sdk/src/services/kinesis.js +4 -13
- package/packages/datadog-plugin-aws-sdk/src/services/sqs.js +1 -5
- package/packages/datadog-plugin-azure-functions/src/index.js +1 -1
- package/packages/datadog-plugin-browser-bunyan/src/index.js +9 -0
- package/packages/datadog-plugin-bunyan/src/index.js +5 -8
- package/packages/datadog-plugin-cucumber/src/index.js +11 -0
- package/packages/datadog-plugin-cypress/src/after-run.js +5 -1
- package/packages/datadog-plugin-cypress/src/after-spec.js +5 -1
- package/packages/datadog-plugin-cypress/src/cypress-plugin.js +82 -30
- package/packages/datadog-plugin-cypress/src/finalization.js +76 -0
- package/packages/datadog-plugin-cypress/src/index.js +12 -6
- package/packages/datadog-plugin-cypress/src/plugin.js +16 -3
- package/packages/datadog-plugin-dd-trace-api/src/index.js +4 -0
- package/packages/datadog-plugin-electron/src/index.js +2 -0
- package/packages/datadog-plugin-fs/src/index.js +1 -1
- package/packages/datadog-plugin-google-cloud-pubsub/src/producer.js +31 -17
- package/packages/datadog-plugin-jest/src/index.js +11 -4
- package/packages/datadog-plugin-kafkajs/src/batch-consumer.js +2 -3
- package/packages/datadog-plugin-kafkajs/src/consumer.js +2 -3
- package/packages/datadog-plugin-kafkajs/src/producer.js +3 -2
- package/packages/datadog-plugin-kafkajs/src/utils.js +65 -7
- package/packages/datadog-plugin-mocha/src/index.js +606 -40
- package/packages/datadog-plugin-mysql/src/index.js +37 -0
- package/packages/datadog-plugin-nats/src/index.js +1 -1
- package/packages/datadog-plugin-next/src/index.js +1 -19
- package/packages/datadog-plugin-openai/src/tracing.js +41 -30
- package/packages/datadog-plugin-openai-agents/src/integration.js +279 -69
- package/packages/datadog-plugin-openai-agents/src/processor.js +16 -4
- package/packages/datadog-plugin-pg/src/index.js +1 -0
- package/packages/datadog-plugin-playwright/src/index.js +42 -13
- package/packages/datadog-plugin-vitest/src/index.js +14 -20
- package/packages/datadog-plugin-ws/src/util.js +2 -1
- package/packages/datadog-webpack/index.js +0 -11
- package/packages/dd-trace/index.js +0 -1
- package/packages/dd-trace/src/agent/info.js +6 -5
- package/packages/dd-trace/src/aiguard/client.js +100 -1
- package/packages/dd-trace/src/aiguard/errors.js +41 -0
- package/packages/dd-trace/src/aiguard/evaluation.js +357 -0
- package/packages/dd-trace/src/aiguard/integrations/anthropic.js +70 -0
- package/packages/dd-trace/src/aiguard/integrations/index.js +4 -0
- package/packages/dd-trace/src/aiguard/messages/anthropic.js +423 -0
- package/packages/dd-trace/src/aiguard/messages/openai.js +1 -24
- package/packages/dd-trace/src/aiguard/messages/utils.js +28 -0
- package/packages/dd-trace/src/aiguard/messages/vercel-ai.js +1 -11
- package/packages/dd-trace/src/aiguard/sdk.js +22 -278
- package/packages/dd-trace/src/appsec/api_security/normalized-route.js +453 -0
- package/packages/dd-trace/src/appsec/handlers/http-request.js +13 -0
- package/packages/dd-trace/src/appsec/iast/taint-tracking/rewriter.js +9 -12
- package/packages/dd-trace/src/carrier.js +356 -0
- package/packages/dd-trace/src/ci-visibility/dynamic-instrumentation/worker/index.js +1 -0
- package/packages/dd-trace/src/ci-visibility/exporters/agent-proxy/index.js +27 -3
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/coverage-writer.js +22 -6
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/di-logs-writer.js +21 -5
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/request-tracker.js +164 -0
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/writer.js +22 -6
- package/packages/dd-trace/src/ci-visibility/exporters/ci-visibility-exporter.js +365 -32
- package/packages/dd-trace/src/ci-visibility/exporters/request.js +201 -0
- package/packages/dd-trace/src/ci-visibility/exporters/test-worker/index.js +5 -3
- package/packages/dd-trace/src/ci-visibility/exporters/test-worker/writer.js +9 -5
- package/packages/dd-trace/src/ci-visibility/intelligent-test-runner/get-skippable-suites.js +2 -1
- package/packages/dd-trace/src/ci-visibility/requests/rate-limit.js +39 -0
- package/packages/dd-trace/src/ci-visibility/requests/request.js +3 -6
- package/packages/dd-trace/src/ci-visibility/requests/upload-test-screenshot.js +6 -2
- package/packages/dd-trace/src/config/generated-config-types.d.ts +7 -0
- package/packages/dd-trace/src/config/index.js +13 -2
- package/packages/dd-trace/src/config/major-overrides.js +7 -0
- package/packages/dd-trace/src/config/supported-configurations.json +24 -0
- package/packages/dd-trace/src/datastreams/context.js +6 -1
- package/packages/dd-trace/src/datastreams/index.js +2 -0
- package/packages/dd-trace/src/datastreams/manager.js +14 -3
- package/packages/dd-trace/src/datastreams/pathway.js +23 -22
- package/packages/dd-trace/src/datastreams/processor.js +16 -13
- package/packages/dd-trace/src/datastreams/size.js +5 -0
- package/packages/dd-trace/src/debugger/devtools_client/index.js +3 -2
- package/packages/dd-trace/src/exporters/agent/writer.js +49 -9
- package/packages/dd-trace/src/exporters/common/buffering-exporter.js +6 -4
- package/packages/dd-trace/src/exporters/common/writer.js +11 -6
- package/packages/dd-trace/src/llmobs/constants/tags.js +5 -0
- package/packages/dd-trace/src/llmobs/experiments/client.js +163 -5
- package/packages/dd-trace/src/llmobs/experiments/dataset.js +241 -87
- package/packages/dd-trace/src/llmobs/experiments/experiment.js +280 -20
- package/packages/dd-trace/src/llmobs/experiments/index.js +58 -59
- package/packages/dd-trace/src/llmobs/experiments/noop.js +71 -3
- package/packages/dd-trace/src/llmobs/experiments/result.js +1 -0
- package/packages/dd-trace/src/llmobs/experiments/util.js +41 -5
- package/packages/dd-trace/src/llmobs/index.js +34 -2
- package/packages/dd-trace/src/llmobs/plugins/ai/util.js +12 -3
- package/packages/dd-trace/src/llmobs/plugins/base.js +4 -2
- package/packages/dd-trace/src/llmobs/span_processor.js +16 -0
- package/packages/dd-trace/src/llmobs/tagger.js +96 -0
- package/packages/dd-trace/src/llmobs/util.js +78 -0
- package/packages/dd-trace/src/noop/proxy.js +3 -4
- package/packages/dd-trace/src/openfeature/flagging_provider.js +18 -2
- package/packages/dd-trace/src/openfeature/remote_config.js +1 -1
- package/packages/dd-trace/src/opentelemetry/context_manager.js +7 -7
- package/packages/dd-trace/src/opentelemetry/logs/batch_log_processor.js +2 -1
- package/packages/dd-trace/src/opentelemetry/logs/logger.js +67 -11
- package/packages/dd-trace/src/opentelemetry/logs/otlp_transformer.js +14 -3
- package/packages/dd-trace/src/opentelemetry/metrics/index.js +25 -12
- package/packages/dd-trace/src/opentelemetry/metrics/otlp_span_stats_exporter.js +2 -5
- package/packages/dd-trace/src/opentelemetry/metrics/otlp_span_stats_transformer.js +96 -43
- package/packages/dd-trace/src/opentracing/propagation/text_map.js +126 -120
- package/packages/dd-trace/src/opentracing/propagation/text_map_dsm.js +4 -8
- package/packages/dd-trace/src/opentracing/tracer.js +5 -2
- package/packages/dd-trace/src/otel-thread-ctx.js +387 -0
- package/packages/dd-trace/src/plugin_manager.js +5 -3
- package/packages/dd-trace/src/plugins/ci_plugin.js +6 -1
- package/packages/dd-trace/src/plugins/index.js +1 -0
- package/packages/{datadog-plugin-jest/src/util.js → dd-trace/src/plugins/util/jest.js} +5 -65
- package/packages/dd-trace/src/plugins/util/test.js +93 -14
- package/packages/dd-trace/src/plugins/util/web.js +56 -2
- package/packages/dd-trace/src/profiling/profiler.js +1 -1
- package/packages/dd-trace/src/profiling/profilers/space.js +1 -3
- package/packages/dd-trace/src/profiling/profilers/wall.js +37 -90
- package/packages/dd-trace/src/profiling/webspan-utils.js +45 -0
- package/packages/dd-trace/src/proxy.js +38 -29
- package/packages/dd-trace/src/ritm.js +9 -2
- package/packages/dd-trace/src/serverless.js +37 -0
- package/packages/dd-trace/src/span_format.js +1 -0
- package/packages/dd-trace/src/span_stats.js +30 -3
- package/packages/dd-trace/src/storage-channels.js +86 -0
- package/packages/dd-trace/src/tracer.js +9 -2
- package/packages/dd-trace/src/tracer_metadata.js +14 -1
- package/packages/dd-trace/src/web-tags-cache.js +132 -0
- package/vendor/dist/@datadog/openfeature-node-server/LICENSE +201 -0
- package/vendor/dist/@datadog/openfeature-node-server/index.js +1 -0
- package/packages/datadog-instrumentations/src/helpers/optional-peer-bundler.js +0 -65
- package/packages/datadog-webpack/src/optional-peer-loader.js +0 -17
- package/packages/dd-trace/src/feature-registry.js +0 -29
- package/packages/dd-trace/src/openfeature/register.js +0 -35
- package/packages/dd-trace/src/openfeature/require-provider.js +0 -18
|
@@ -127,7 +127,7 @@ class TestWorkerCiVisibilityExporter {
|
|
|
127
127
|
}
|
|
128
128
|
|
|
129
129
|
/**
|
|
130
|
-
* @param {() => void} [onDone]
|
|
130
|
+
* @param {(error?: Error) => void} [onDone]
|
|
131
131
|
*/
|
|
132
132
|
flush (onDone) {
|
|
133
133
|
if (!onDone) {
|
|
@@ -141,9 +141,11 @@ class TestWorkerCiVisibilityExporter {
|
|
|
141
141
|
}
|
|
142
142
|
|
|
143
143
|
let pendingWriters = this._telemetryWriter ? 4 : 3
|
|
144
|
-
|
|
144
|
+
let flushError
|
|
145
|
+
const onWriterFlushed = (error) => {
|
|
146
|
+
flushError ||= error
|
|
145
147
|
pendingWriters--
|
|
146
|
-
if (pendingWriters === 0) onDone()
|
|
148
|
+
if (pendingWriters === 0) onDone(flushError)
|
|
147
149
|
}
|
|
148
150
|
|
|
149
151
|
this._writer.flush(onWriterFlushed)
|
|
@@ -21,7 +21,7 @@ class Writer {
|
|
|
21
21
|
}
|
|
22
22
|
|
|
23
23
|
/**
|
|
24
|
-
* @param {() => void} [onDone]
|
|
24
|
+
* @param {(error?: Error) => void} [onDone]
|
|
25
25
|
*/
|
|
26
26
|
flush (onDone) {
|
|
27
27
|
const count = this._encoder.count()
|
|
@@ -69,8 +69,9 @@ class Writer {
|
|
|
69
69
|
|
|
70
70
|
// child_process workers (jest default, cucumber)
|
|
71
71
|
if (process.send) {
|
|
72
|
-
process.send(payload, () => {
|
|
73
|
-
|
|
72
|
+
process.send(payload, (error) => {
|
|
73
|
+
if (error) log.error('Error sending message to parent process', error)
|
|
74
|
+
onDone(error)
|
|
74
75
|
})
|
|
75
76
|
return
|
|
76
77
|
}
|
|
@@ -82,9 +83,12 @@ class Writer {
|
|
|
82
83
|
parentPort.postMessage(payload)
|
|
83
84
|
} catch (error) {
|
|
84
85
|
log.error('Error posting message to parent port', error)
|
|
85
|
-
|
|
86
|
-
|
|
86
|
+
onDone(error)
|
|
87
|
+
return
|
|
87
88
|
}
|
|
89
|
+
// postMessage has no acknowledgement callback. Completion means the
|
|
90
|
+
// message was accepted by the local port, not processed by the parent.
|
|
91
|
+
onDone()
|
|
88
92
|
return
|
|
89
93
|
}
|
|
90
94
|
|
|
@@ -34,10 +34,11 @@ function parseSkippableSuitesResponse (
|
|
|
34
34
|
if (validateRequiredFields) {
|
|
35
35
|
validateSkippableTestsResponse(parsedResponse, { validationMode })
|
|
36
36
|
}
|
|
37
|
-
|
|
37
|
+
let coverage
|
|
38
38
|
const coverageByFilename = parsedResponse.meta?.coverage
|
|
39
39
|
if (coverageByFilename) {
|
|
40
40
|
for (const [filename, bitmap] of Object.entries(coverageByFilename)) {
|
|
41
|
+
coverage ??= {}
|
|
41
42
|
coverage[filename.replaceAll('\\', '/')] = bitmap
|
|
42
43
|
}
|
|
43
44
|
}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const EPOCH_SECONDS_THRESHOLD = 1_000_000_000
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Returns the delay requested by a Test Optimization intake rate-limit response.
|
|
7
|
+
*
|
|
8
|
+
* @param {import('node:http').IncomingHttpHeaders} [headers]
|
|
9
|
+
* @returns {number}
|
|
10
|
+
*/
|
|
11
|
+
function getRateLimitResetDelay (headers) {
|
|
12
|
+
let retryAfter = headers?.['retry-after']
|
|
13
|
+
if (Array.isArray(retryAfter)) retryAfter = retryAfter[0]
|
|
14
|
+
if (typeof retryAfter === 'string' && retryAfter.trim() !== '') {
|
|
15
|
+
const delaySeconds = Number(retryAfter)
|
|
16
|
+
if (Number.isFinite(delaySeconds)) {
|
|
17
|
+
if (delaySeconds >= 0) return delaySeconds * 1000
|
|
18
|
+
} else {
|
|
19
|
+
const resetTimestamp = Date.parse(retryAfter)
|
|
20
|
+
if (Number.isFinite(resetTimestamp)) return Math.max(0, resetTimestamp - Date.now())
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
let reset = headers?.['x-ratelimit-reset']
|
|
25
|
+
if (Array.isArray(reset)) reset = reset[0]
|
|
26
|
+
if (typeof reset !== 'string' || reset.trim() === '') return NaN
|
|
27
|
+
|
|
28
|
+
const resetSeconds = Number(reset)
|
|
29
|
+
if (!Number.isFinite(resetSeconds) || resetSeconds < 0) return NaN
|
|
30
|
+
|
|
31
|
+
// Datadog defines this header as delay seconds. Preserve compatibility with
|
|
32
|
+
// realistic Unix timestamps without confusing ordinary durations with epochs.
|
|
33
|
+
if (resetSeconds >= EPOCH_SECONDS_THRESHOLD) {
|
|
34
|
+
return Math.max(0, resetSeconds * 1000 - Date.now())
|
|
35
|
+
}
|
|
36
|
+
return resetSeconds * 1000
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
module.exports = { getRateLimitResetDelay }
|
|
@@ -13,12 +13,13 @@ const {
|
|
|
13
13
|
singleJitteredDelay,
|
|
14
14
|
} = require('../../exporters/common/retry')
|
|
15
15
|
const { parseUrl } = require('../../exporters/common/url')
|
|
16
|
+
const { getRateLimitResetDelay } = require('./rate-limit')
|
|
16
17
|
|
|
17
18
|
const legacyStorage = storage('legacy')
|
|
18
19
|
|
|
19
20
|
/**
|
|
20
21
|
* Simplified HTTP request for test optimization (library config). Uses common HTTP agents.
|
|
21
|
-
* Retries: 429 (with X-
|
|
22
|
+
* Retries: 429 (with Retry-After or X-RateLimit-Reset, max 30s wait),
|
|
22
23
|
* >=500 and transient network errors (5–7.5s delay with jitter). Max one retry.
|
|
23
24
|
* Destroys connections on errors to prevent reuse of bad connections. Preserves
|
|
24
25
|
* original status code across retries for telemetry.
|
|
@@ -98,11 +99,7 @@ function request (data, options, callback) {
|
|
|
98
99
|
}
|
|
99
100
|
|
|
100
101
|
if (res.statusCode === 429 && !hasRetried) {
|
|
101
|
-
const
|
|
102
|
-
const resetTs = (resetHeader === null || resetHeader === undefined)
|
|
103
|
-
? NaN
|
|
104
|
-
: Number.parseInt(resetHeader, 10)
|
|
105
|
-
const waitMs = Number.isFinite(resetTs) ? Math.max(0, resetTs * 1000 - Date.now()) : NaN
|
|
102
|
+
const waitMs = getRateLimitResetDelay(res.headers)
|
|
106
103
|
|
|
107
104
|
if (Number.isFinite(waitMs) && waitMs <= RATE_LIMIT_MAX_WAIT_MS) {
|
|
108
105
|
hasRetried = true
|
|
@@ -4,8 +4,8 @@ const { readFileSync } = require('node:fs')
|
|
|
4
4
|
const { extname } = require('node:path')
|
|
5
5
|
|
|
6
6
|
const getConfig = require('../../config')
|
|
7
|
-
const request = require('../../exporters/common/request')
|
|
8
7
|
const log = require('../../log')
|
|
8
|
+
const request = require('../exporters/request')
|
|
9
9
|
|
|
10
10
|
const UPLOAD_TIMEOUT_MS = 30_000
|
|
11
11
|
const TEST_SCREENSHOT_ENDPOINT_PREFIX = '/api/v2/ci/test-runs/'
|
|
@@ -74,10 +74,12 @@ function toIdempotencyQueryValue (idempotencyKey) {
|
|
|
74
74
|
* @param {URL} options.url - The base URL for the screenshot upload
|
|
75
75
|
* @param {boolean} [options.isEvpProxy] - Whether to upload through the Agent's evp_proxy
|
|
76
76
|
* @param {string} [options.evpProxyPrefix] - The evp_proxy path prefix (e.g. '/evp_proxy/v4')
|
|
77
|
+
* @param {number} [options.deadline] - Absolute finalization deadline in epoch milliseconds
|
|
78
|
+
* @param {AbortSignal} [options.signal] - Signal used to cancel the upload
|
|
77
79
|
* @param {Function} callback - Callback function (err)
|
|
78
80
|
*/
|
|
79
81
|
function uploadTestScreenshot (
|
|
80
|
-
{ filePath, traceId, idempotencyKey, capturedAtMs, url, isEvpProxy, evpProxyPrefix },
|
|
82
|
+
{ filePath, traceId, idempotencyKey, capturedAtMs, url, isEvpProxy, evpProxyPrefix, deadline, signal },
|
|
81
83
|
callback
|
|
82
84
|
) {
|
|
83
85
|
const { DD_API_KEY } = getConfig()
|
|
@@ -125,6 +127,8 @@ function uploadTestScreenshot (
|
|
|
125
127
|
path: `${basePath}?${query}`,
|
|
126
128
|
timeout: UPLOAD_TIMEOUT_MS,
|
|
127
129
|
url,
|
|
130
|
+
deadline,
|
|
131
|
+
signal,
|
|
128
132
|
}
|
|
129
133
|
|
|
130
134
|
if (isEvpProxy) {
|
|
@@ -209,6 +209,7 @@ export interface GeneratedConfig {
|
|
|
209
209
|
DD_TRACE_BEAUTIFUL_LOGS: boolean;
|
|
210
210
|
DD_TRACE_BLUEBIRD_ENABLED: boolean;
|
|
211
211
|
DD_TRACE_BODY_PARSER_ENABLED: boolean;
|
|
212
|
+
DD_TRACE_BROWSER_BUNYAN_ENABLED: boolean;
|
|
212
213
|
DD_TRACE_BSON_ENABLED: boolean;
|
|
213
214
|
DD_TRACE_BULLMQ_ENABLED: boolean;
|
|
214
215
|
DD_TRACE_BUNYAN_ENABLED: boolean;
|
|
@@ -272,6 +273,7 @@ export interface GeneratedConfig {
|
|
|
272
273
|
DD_TRACE_HAPI_HAPI_ENABLED: boolean;
|
|
273
274
|
DD_TRACE_HONO_ENABLED: boolean;
|
|
274
275
|
DD_TRACE_HTTP_ENABLED: boolean;
|
|
276
|
+
DD_TRACE_HTTP_SERVER_ERROR_STATUSES: string;
|
|
275
277
|
DD_TRACE_HTTP2_ENABLED: boolean;
|
|
276
278
|
DD_TRACE_HTTPS_ENABLED: boolean;
|
|
277
279
|
DD_TRACE_IOREDIS_ENABLED: boolean;
|
|
@@ -339,6 +341,7 @@ export interface GeneratedConfig {
|
|
|
339
341
|
DD_TRACE_OPENSEARCH_PROJECT_OPENSEARCH_ENABLED: boolean;
|
|
340
342
|
DD_TRACE_OPENTELEMETRY_SDK_TRACE_NODE_ENABLED: boolean;
|
|
341
343
|
DD_TRACE_ORACLEDB_ENABLED: boolean;
|
|
344
|
+
DD_TRACE_OTEL_CTX_ENABLED: boolean;
|
|
342
345
|
DD_TRACE_OTEL_ENABLED: boolean;
|
|
343
346
|
DD_TRACE_OTEL_SEMANTICS_ENABLED: boolean;
|
|
344
347
|
DD_TRACE_PASSPORT_ENABLED: boolean;
|
|
@@ -727,6 +730,7 @@ export interface GeneratedEnvVarConfig {
|
|
|
727
730
|
DD_HEAP_SNAPSHOT_COUNT: number;
|
|
728
731
|
DD_HEAP_SNAPSHOT_DESTINATION: string;
|
|
729
732
|
DD_HEAP_SNAPSHOT_INTERVAL: number;
|
|
733
|
+
DD_HTTP_SERVER_ERROR_STATUSES: string;
|
|
730
734
|
DD_IAST_DB_ROWS_TO_TAINT: number;
|
|
731
735
|
DD_IAST_DEDUPLICATION_ENABLED: boolean;
|
|
732
736
|
DD_IAST_ENABLED: boolean;
|
|
@@ -892,6 +896,7 @@ export interface GeneratedEnvVarConfig {
|
|
|
892
896
|
DD_TRACE_BEAUTIFUL_LOGS: boolean;
|
|
893
897
|
DD_TRACE_BLUEBIRD_ENABLED: boolean;
|
|
894
898
|
DD_TRACE_BODY_PARSER_ENABLED: boolean;
|
|
899
|
+
DD_TRACE_BROWSER_BUNYAN_ENABLED: boolean;
|
|
895
900
|
DD_TRACE_BSON_ENABLED: boolean;
|
|
896
901
|
DD_TRACE_BULLMQ_ENABLED: boolean;
|
|
897
902
|
DD_TRACE_BUNYAN_ENABLED: boolean;
|
|
@@ -966,6 +971,7 @@ export interface GeneratedEnvVarConfig {
|
|
|
966
971
|
DD_TRACE_HEADER_TAGS: string[];
|
|
967
972
|
DD_TRACE_HONO_ENABLED: boolean;
|
|
968
973
|
DD_TRACE_HTTP_ENABLED: boolean;
|
|
974
|
+
DD_TRACE_HTTP_SERVER_ERROR_STATUSES: string;
|
|
969
975
|
DD_TRACE_HTTP2_ENABLED: boolean;
|
|
970
976
|
DD_TRACE_HTTPS_ENABLED: boolean;
|
|
971
977
|
DD_TRACE_INFERRED_PROXY_SERVICES_ENABLED: boolean;
|
|
@@ -1037,6 +1043,7 @@ export interface GeneratedEnvVarConfig {
|
|
|
1037
1043
|
DD_TRACE_OPENSEARCH_PROJECT_OPENSEARCH_ENABLED: boolean;
|
|
1038
1044
|
DD_TRACE_OPENTELEMETRY_SDK_TRACE_NODE_ENABLED: boolean;
|
|
1039
1045
|
DD_TRACE_ORACLEDB_ENABLED: boolean;
|
|
1046
|
+
DD_TRACE_OTEL_CTX_ENABLED: boolean;
|
|
1040
1047
|
DD_TRACE_OTEL_ENABLED: boolean;
|
|
1041
1048
|
DD_TRACE_OTEL_SEMANTICS_ENABLED: boolean;
|
|
1042
1049
|
DD_TRACE_PARTIAL_FLUSH_MIN_SPANS: number;
|
|
@@ -15,6 +15,7 @@ const { isTrue } = require('../util')
|
|
|
15
15
|
const telemetry = require('../telemetry')
|
|
16
16
|
const telemetryMetrics = require('../telemetry/metrics')
|
|
17
17
|
const {
|
|
18
|
+
getServerlessPlatformTags,
|
|
18
19
|
IS_SERVERLESS,
|
|
19
20
|
getIsGCPFunction,
|
|
20
21
|
getIsAzureFunction,
|
|
@@ -477,9 +478,13 @@ class Config extends ConfigBase {
|
|
|
477
478
|
|
|
478
479
|
// Apply the OTel sampler when the user opted into OTel traces or explicitly set the sampler.
|
|
479
480
|
// OTEL_TRACES_SAMPLER has `default: parentbased_always_on` (per OTel spec), so opt-in users
|
|
480
|
-
// that don't set the sampler still get parent-based sampling.
|
|
481
|
+
// that don't set the sampler still get parent-based sampling. Electron exporter spans go over
|
|
482
|
+
// the Electron SDK's IPC bridge rather than OTLP (see opentracing/tracer.js), so an
|
|
483
|
+
// OTEL_TRACES_EXPORTER=otlp set for an unrelated telemetry pipeline shouldn't also override
|
|
484
|
+
// dd-trace's own sampling policy in that case.
|
|
481
485
|
if (!trackedConfigOrigins.has('sampleRate') &&
|
|
482
|
-
(trackedConfigOrigins.has('OTEL_TRACES_SAMPLER') ||
|
|
486
|
+
(trackedConfigOrigins.has('OTEL_TRACES_SAMPLER') ||
|
|
487
|
+
(this.OTEL_TRACES_EXPORTER === 'otlp' && this.experimental.exporter !== 'electron'))) {
|
|
483
488
|
setAndTrack(this, 'sampleRate',
|
|
484
489
|
getFromOtelSamplerMap(this.OTEL_TRACES_SAMPLER, this.OTEL_TRACES_SAMPLER_ARG))
|
|
485
490
|
}
|
|
@@ -597,6 +602,12 @@ class Config extends ConfigBase {
|
|
|
597
602
|
this.tags.version = this.version
|
|
598
603
|
}
|
|
599
604
|
this.tags['runtime-id'] = RUNTIME_ID
|
|
605
|
+
const platformTags = getServerlessPlatformTags()
|
|
606
|
+
if (platformTags) {
|
|
607
|
+
for (let i = 0; i < platformTags.length; i += 2) {
|
|
608
|
+
this.tags[platformTags[i]] ??= platformTags[i + 1]
|
|
609
|
+
}
|
|
610
|
+
}
|
|
600
611
|
|
|
601
612
|
if (IS_SERVERLESS) {
|
|
602
613
|
setAndTrack(this, 'telemetry.DD_INSTRUMENTATION_TELEMETRY_ENABLED', false)
|
|
@@ -58,6 +58,13 @@ function applyMajorOverrides (supportedConfigurations, majorVersion) {
|
|
|
58
58
|
delete supportedConfigurations.DD_TRACE_EXPERIMENTAL_RUNTIME_ID_ENABLED
|
|
59
59
|
// eslint-disable-next-line eslint-rules/eslint-env-aliases
|
|
60
60
|
dropAlias(supportedConfigurations.DD_RUNTIME_METRICS_RUNTIME_ID_ENABLED, 'DD_TRACE_EXPERIMENTAL_RUNTIME_ID_ENABLED')
|
|
61
|
+
|
|
62
|
+
if (majorVersion >= 7) {
|
|
63
|
+
// The Electron plugin moved to the Electron SDK and is opt-in (disabled by default) from v7 on,
|
|
64
|
+
// while remaining enabled by default on earlier majors (see ElectronPlugin.optIn).
|
|
65
|
+
const electronEntry = supportedConfigurations.DD_TRACE_ELECTRON_ENABLED?.[0]
|
|
66
|
+
if (electronEntry) electronEntry.default = 'false'
|
|
67
|
+
}
|
|
61
68
|
}
|
|
62
69
|
|
|
63
70
|
/**
|
|
@@ -2452,6 +2452,13 @@
|
|
|
2452
2452
|
"default": "true"
|
|
2453
2453
|
}
|
|
2454
2454
|
],
|
|
2455
|
+
"DD_TRACE_BROWSER_BUNYAN_ENABLED": [
|
|
2456
|
+
{
|
|
2457
|
+
"implementation": "A",
|
|
2458
|
+
"type": "boolean",
|
|
2459
|
+
"default": "true"
|
|
2460
|
+
}
|
|
2461
|
+
],
|
|
2455
2462
|
"DD_TRACE_BSON_ENABLED": [
|
|
2456
2463
|
{
|
|
2457
2464
|
"implementation": "A",
|
|
@@ -2999,6 +3006,16 @@
|
|
|
2999
3006
|
"default": "true"
|
|
3000
3007
|
}
|
|
3001
3008
|
],
|
|
3009
|
+
"DD_TRACE_HTTP_SERVER_ERROR_STATUSES": [
|
|
3010
|
+
{
|
|
3011
|
+
"implementation": "A",
|
|
3012
|
+
"type": "string",
|
|
3013
|
+
"default": "500-599",
|
|
3014
|
+
"aliases": [
|
|
3015
|
+
"DD_HTTP_SERVER_ERROR_STATUSES"
|
|
3016
|
+
]
|
|
3017
|
+
}
|
|
3018
|
+
],
|
|
3002
3019
|
"DD_TRACE_INFERRED_PROXY_SERVICES_ENABLED": [
|
|
3003
3020
|
{
|
|
3004
3021
|
"implementation": "A",
|
|
@@ -3508,6 +3525,13 @@
|
|
|
3508
3525
|
"default": "false"
|
|
3509
3526
|
}
|
|
3510
3527
|
],
|
|
3528
|
+
"DD_TRACE_OTEL_CTX_ENABLED": [
|
|
3529
|
+
{
|
|
3530
|
+
"implementation": "A",
|
|
3531
|
+
"type": "boolean",
|
|
3532
|
+
"default": "false"
|
|
3533
|
+
}
|
|
3534
|
+
],
|
|
3511
3535
|
"DD_TRACE_PARTIAL_FLUSH_MIN_SPANS": [
|
|
3512
3536
|
{
|
|
3513
3537
|
"implementation": "B",
|
|
@@ -13,7 +13,12 @@ function getDataStreamsContext () {
|
|
|
13
13
|
function setDataStreamsContext (dataStreamsContext) {
|
|
14
14
|
log.debug('Setting new DSM Context: %j.', dataStreamsContext)
|
|
15
15
|
|
|
16
|
-
|
|
16
|
+
// `undefined` clears: a message that carries no context must not inherit the previous message's.
|
|
17
|
+
// The identity check keeps the common no-context case from allocating a store per message.
|
|
18
|
+
const store = legacyStorage.getStore()
|
|
19
|
+
if (store?.dataStreamsContext !== dataStreamsContext) {
|
|
20
|
+
legacyStorage.enterWith({ ...store, dataStreamsContext })
|
|
21
|
+
}
|
|
17
22
|
}
|
|
18
23
|
|
|
19
24
|
module.exports = {
|
|
@@ -5,6 +5,7 @@ const {
|
|
|
5
5
|
getHeadersSize,
|
|
6
6
|
getMessageSize,
|
|
7
7
|
getSizeOrZero,
|
|
8
|
+
PATHWAY_FIELD_BYTES,
|
|
8
9
|
} = require('./size')
|
|
9
10
|
|
|
10
11
|
// This is only needed because DSM code is spread across existing tracing
|
|
@@ -121,6 +122,7 @@ module.exports = {
|
|
|
121
122
|
DataStreamsManager,
|
|
122
123
|
DataStreamsProcessor,
|
|
123
124
|
SchemaBuilder,
|
|
125
|
+
PATHWAY_FIELD_BYTES,
|
|
124
126
|
|
|
125
127
|
// These are small functions so they are exposed directly and not lazy loaded.
|
|
126
128
|
getAmqpMessageSize,
|
|
@@ -8,17 +8,28 @@ class DataStreamsManager {
|
|
|
8
8
|
this._dataStreamsProcessor = processor
|
|
9
9
|
}
|
|
10
10
|
|
|
11
|
-
|
|
11
|
+
/**
|
|
12
|
+
* @param {string[]} edgeTags
|
|
13
|
+
* @param {import('../opentracing/span')|null} span
|
|
14
|
+
* @param {number} [payloadSize]
|
|
15
|
+
* @param {number} [pathwayContextSize] See `DataStreamsProcessor#setCheckpoint`.
|
|
16
|
+
* @returns {object|undefined}
|
|
17
|
+
*/
|
|
18
|
+
setCheckpoint (edgeTags, span, payloadSize = 0, pathwayContextSize) {
|
|
12
19
|
const ctx = this._dataStreamsProcessor.setCheckpoint(
|
|
13
|
-
edgeTags, span, DataStreamsContext.getDataStreamsContext(), payloadSize
|
|
20
|
+
edgeTags, span, DataStreamsContext.getDataStreamsContext(), payloadSize, pathwayContextSize
|
|
14
21
|
)
|
|
15
22
|
DataStreamsContext.setDataStreamsContext(ctx)
|
|
16
23
|
return ctx
|
|
17
24
|
}
|
|
18
25
|
|
|
26
|
+
/**
|
|
27
|
+
* @param {Record<string, string>|undefined} carrier Pass every message's carrier, including the
|
|
28
|
+
* ones without a context: that is what starts a new pathway instead of extending the previous
|
|
29
|
+
* message's.
|
|
30
|
+
*/
|
|
19
31
|
decodeDataStreamsContext (carrier) {
|
|
20
32
|
const ctx = DsmPathwayCodec.decode(carrier)
|
|
21
|
-
// we erase the previous context everytime we decode a new one
|
|
22
33
|
DataStreamsContext.setDataStreamsContext(ctx)
|
|
23
34
|
return ctx
|
|
24
35
|
}
|
|
@@ -5,23 +5,25 @@
|
|
|
5
5
|
// this inconsistency is ok because hashes do not need to be consistent across services
|
|
6
6
|
const crypto = require('crypto')
|
|
7
7
|
const { LRUCache } = require('../../../../vendor/dist/lru-cache')
|
|
8
|
+
const {
|
|
9
|
+
hasDsmBase64,
|
|
10
|
+
hasDsmBinary,
|
|
11
|
+
pickDsm,
|
|
12
|
+
readDsmBase64,
|
|
13
|
+
readDsmBinary,
|
|
14
|
+
writeDsmBase64,
|
|
15
|
+
} = require('../carrier')
|
|
8
16
|
const log = require('../log')
|
|
9
|
-
const pick = require('../../../datadog-core/src/utils/src/pick')
|
|
10
17
|
const { encodeVarintInto, decodeVarint } = require('./encoding')
|
|
11
18
|
|
|
12
19
|
const cache = new LRUCache({ max: 500 })
|
|
13
20
|
|
|
14
|
-
const CONTEXT_PROPAGATION_KEY = 'dd-pathway-ctx'
|
|
15
|
-
const CONTEXT_PROPAGATION_KEY_BASE64 = 'dd-pathway-ctx-base64'
|
|
16
|
-
|
|
17
21
|
const PATHWAY_CONTEXT_BYTES = 20
|
|
18
22
|
|
|
19
23
|
// Reused across `encodePathwayContext` calls; the buffer is fully rewritten before each
|
|
20
24
|
// `Buffer.from(...)` copy-out so callers never observe mutation between checkpoints.
|
|
21
25
|
const pathwayScratch = Buffer.allocUnsafe(PATHWAY_CONTEXT_BYTES)
|
|
22
26
|
|
|
23
|
-
const logKeys = [CONTEXT_PROPAGATION_KEY, CONTEXT_PROPAGATION_KEY_BASE64]
|
|
24
|
-
|
|
25
27
|
function shaHash (checkpointString) {
|
|
26
28
|
// Copy out of the 32-byte digest so the LRU cache doesn't retain it.
|
|
27
29
|
return Buffer.from(crypto.createHash('sha256').update(checkpointString).digest().subarray(0, 8))
|
|
@@ -114,7 +116,7 @@ function decodePathwayContext (pathwayContext) {
|
|
|
114
116
|
}
|
|
115
117
|
|
|
116
118
|
/**
|
|
117
|
-
* @param {string} pathwayContext
|
|
119
|
+
* @param {string | Buffer} pathwayContext
|
|
118
120
|
* @returns {ReturnType<typeof decodePathwayContext>|undefined}
|
|
119
121
|
*/
|
|
120
122
|
function decodePathwayContextBase64 (pathwayContext) {
|
|
@@ -142,10 +144,10 @@ const DsmPathwayCodec = {
|
|
|
142
144
|
encode (dataStreamsContext, carrier) {
|
|
143
145
|
if (!dataStreamsContext || !dataStreamsContext.hash) return
|
|
144
146
|
carrier ??= {}
|
|
145
|
-
carrier
|
|
147
|
+
writeDsmBase64(carrier, encodePathwayContextBase64(dataStreamsContext))
|
|
146
148
|
|
|
147
149
|
// eslint-disable-next-line eslint-rules/eslint-log-printf-style
|
|
148
|
-
log.debug(() => `Injected into DSM carrier: ${JSON.stringify(
|
|
150
|
+
log.debug(() => `Injected into DSM carrier: ${JSON.stringify(pickDsm(carrier))}.`)
|
|
149
151
|
|
|
150
152
|
return carrier
|
|
151
153
|
},
|
|
@@ -155,25 +157,25 @@ const DsmPathwayCodec = {
|
|
|
155
157
|
* @returns {ReturnType<typeof decodePathwayContext>|undefined}
|
|
156
158
|
*/
|
|
157
159
|
decode (carrier) {
|
|
158
|
-
// eslint-disable-next-line eslint-rules/eslint-log-printf-style
|
|
159
|
-
log.debug(() => `Attempting extract from DSM carrier: ${JSON.stringify(pick(carrier, logKeys))}.`)
|
|
160
|
-
|
|
161
160
|
if (carrier == null) return
|
|
162
161
|
|
|
162
|
+
// eslint-disable-next-line eslint-rules/eslint-log-printf-style
|
|
163
|
+
log.debug(() => `Attempting extract from DSM carrier: ${JSON.stringify(pickDsm(carrier))}.`)
|
|
164
|
+
|
|
163
165
|
let ctx
|
|
164
|
-
if (
|
|
166
|
+
if (hasDsmBase64(carrier)) {
|
|
165
167
|
// decode v2 encoding of base64
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
168
|
+
const encoded = readDsmBase64(carrier)
|
|
169
|
+
if (encoded !== undefined) ctx = decodePathwayContextBase64(encoded)
|
|
170
|
+
} else if (hasDsmBinary(carrier)) {
|
|
171
|
+
const encoded = readDsmBinary(carrier)
|
|
172
|
+
if (Buffer.isBuffer(encoded)) {
|
|
169
173
|
// decode v1 encoding
|
|
170
|
-
ctx = decodePathwayContext(
|
|
171
|
-
} catch {
|
|
172
|
-
// pass
|
|
174
|
+
ctx = decodePathwayContext(encoded)
|
|
173
175
|
}
|
|
174
176
|
// cover case where base64 context was received under wrong key
|
|
175
|
-
if (!ctx &&
|
|
176
|
-
ctx = decodePathwayContextBase64(
|
|
177
|
+
if (!ctx && encoded !== undefined) {
|
|
178
|
+
ctx = decodePathwayContextBase64(encoded)
|
|
177
179
|
}
|
|
178
180
|
}
|
|
179
181
|
|
|
@@ -182,7 +184,6 @@ const DsmPathwayCodec = {
|
|
|
182
184
|
}
|
|
183
185
|
|
|
184
186
|
module.exports = {
|
|
185
|
-
CONTEXT_PROPAGATION_KEY_BASE64,
|
|
186
187
|
computePathwayHash: computeHash,
|
|
187
188
|
encodePathwayContext,
|
|
188
189
|
decodePathwayContext,
|
|
@@ -8,21 +8,14 @@ const { PATHWAY_HASH, DSM_TRANSACTION_ID, DSM_TRANSACTION_CHECKPOINT } = require
|
|
|
8
8
|
const log = require('../log')
|
|
9
9
|
const processTags = require('../process-tags')
|
|
10
10
|
const propagationHash = require('../propagation-hash')
|
|
11
|
-
const {
|
|
11
|
+
const { computePathwayHash } = require('./pathway')
|
|
12
12
|
const { DataStreamsWriter } = require('./writer')
|
|
13
|
-
const { getAmqpMessageSize, getHeadersSize, getMessageSize, getSizeOrZero } = require('./size')
|
|
13
|
+
const { getAmqpMessageSize, getHeadersSize, getMessageSize, getSizeOrZero, PATHWAY_FIELD_BYTES } = require('./size')
|
|
14
14
|
const { SchemaBuilder } = require('./schemas/schema_builder')
|
|
15
15
|
const { SchemaSampler } = require('./schemas/schema_sampler')
|
|
16
16
|
|
|
17
17
|
const ENTRY_PARENT_HASH = Buffer.from('0000000000000000', 'hex')
|
|
18
18
|
|
|
19
|
-
// A direction:out checkpoint estimates the size cost of the header the
|
|
20
|
-
// producer plugin will inject. The pathway context is always 20 binary
|
|
21
|
-
// bytes, encoded as 28 base64 chars; together with the header key and
|
|
22
|
-
// JSON framing (matching the prior `JSON.stringify({key: value})` byte
|
|
23
|
-
// count minus 1), this is a fixed value.
|
|
24
|
-
const PATHWAY_HEADER_BYTES = CONTEXT_PROPAGATION_KEY_BASE64.length + 28 + 6
|
|
25
|
-
|
|
26
19
|
class StatsPoint {
|
|
27
20
|
constructor (hash, parentHash, edgeTags) {
|
|
28
21
|
this.hash = hash.readBigUInt64LE()
|
|
@@ -289,10 +282,19 @@ class DataStreamsProcessor {
|
|
|
289
282
|
if (this.flushInterval === 0) this.onInterval()
|
|
290
283
|
}
|
|
291
284
|
|
|
292
|
-
|
|
285
|
+
/**
|
|
286
|
+
* @param {string[]} edgeTags Direction tag first.
|
|
287
|
+
* @param {import('../opentracing/span')|null} span
|
|
288
|
+
* @param {object|null|undefined} ctx Parent pathway context.
|
|
289
|
+
* @param {number} [payloadSize] Bytes the caller built, before any propagation context.
|
|
290
|
+
* @param {number} [pathwayContextSize] Bytes the pathway context adds to an outbound payload.
|
|
291
|
+
* Most producers size their payload before this call hands them the context to inject, so they
|
|
292
|
+
* cannot measure it and take the default estimate. Pass `0` to report the payload alone.
|
|
293
|
+
* @returns {object|undefined}
|
|
294
|
+
*/
|
|
295
|
+
setCheckpoint (edgeTags, span, ctx, payloadSize = 0, pathwayContextSize = PATHWAY_FIELD_BYTES) {
|
|
293
296
|
if (!this.enabled) return
|
|
294
297
|
const nowNs = Date.now() * 1e6
|
|
295
|
-
// Callers must place the direction tag at index 0.
|
|
296
298
|
const direction = edgeTags[0]
|
|
297
299
|
let pathwayStartNs = nowNs
|
|
298
300
|
let edgeStartNs = nowNs
|
|
@@ -337,14 +339,15 @@ class DataStreamsProcessor {
|
|
|
337
339
|
const pathwayLatencyNs = nowNs - pathwayStartNs
|
|
338
340
|
const dataStreamsContext = {
|
|
339
341
|
hash,
|
|
340
|
-
|
|
342
|
+
// start the next hop's edge clock here so edge latency stays per-hop
|
|
343
|
+
edgeStartNs: nowNs,
|
|
341
344
|
pathwayStartNs,
|
|
342
345
|
previousDirection: direction,
|
|
343
346
|
closestOppositeDirectionHash,
|
|
344
347
|
closestOppositeDirectionEdgeStart,
|
|
345
348
|
}
|
|
346
349
|
if (direction === 'direction:out') {
|
|
347
|
-
payloadSize +=
|
|
350
|
+
payloadSize += pathwayContextSize
|
|
348
351
|
}
|
|
349
352
|
const checkpoint = {
|
|
350
353
|
currentTimestamp: nowNs,
|
|
@@ -2,6 +2,10 @@
|
|
|
2
2
|
|
|
3
3
|
const { types } = require('util')
|
|
4
4
|
|
|
5
|
+
// Byte cost of the `,"dd-pathway-ctx-base64":"<28 chars>"` field a producer adds to a JSON carrier.
|
|
6
|
+
// A literal so eager `size` consumers don't pull in `./pathway`; `pathway.spec.js` pins it there.
|
|
7
|
+
const PATHWAY_FIELD_BYTES = 55
|
|
8
|
+
|
|
5
9
|
function getSizeOrZero (obj) {
|
|
6
10
|
if (typeof obj === 'string') {
|
|
7
11
|
return Buffer.byteLength(obj, 'utf8')
|
|
@@ -54,4 +58,5 @@ module.exports = {
|
|
|
54
58
|
getHeadersSize,
|
|
55
59
|
getSizeOrZero,
|
|
56
60
|
getAmqpMessageSize,
|
|
61
|
+
PATHWAY_FIELD_BYTES,
|
|
57
62
|
}
|
|
@@ -23,7 +23,6 @@ require('./remote_config')
|
|
|
23
23
|
|
|
24
24
|
/** @typedef {import('node:inspector').Debugger.EvaluateOnCallFrameReturnType} EvaluateOnCallFrameResult */
|
|
25
25
|
|
|
26
|
-
// Expression to run on a call frame of the paused thread to get its active trace and span id.
|
|
27
26
|
const templateExpressionSetupCode = `
|
|
28
27
|
const $dd_inspect = global.require('node:util').inspect;
|
|
29
28
|
const $dd_segmentInspectOptions = {
|
|
@@ -34,8 +33,10 @@ const templateExpressionSetupCode = `
|
|
|
34
33
|
breakLength: Infinity
|
|
35
34
|
};
|
|
36
35
|
`
|
|
36
|
+
|
|
37
|
+
// Expression to run on a call frame of the paused thread to get its active trace and span id.
|
|
37
38
|
const getDDTagsExpression = `(() => {
|
|
38
|
-
const context =
|
|
39
|
+
const context = globalThis._ddtrace.scope().active()?.context();
|
|
39
40
|
return { trace_id: context?.toTraceId(), span_id: context?.toSpanId() }
|
|
40
41
|
})()`
|
|
41
42
|
|