dd-trace 5.109.0 → 5.111.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 +13 -8
- package/ci/init.js +25 -5
- package/ci/vitest-no-worker-init-setup.mjs +430 -0
- package/ext/tags.js +2 -0
- package/index.d.ts +79 -24
- package/initialize.mjs +5 -6
- package/loader-hook.mjs +154 -47
- package/package.json +20 -16
- package/packages/datadog-esbuild/index.js +26 -0
- package/packages/datadog-esbuild/src/utils.js +46 -3
- package/packages/datadog-instrumentations/src/connect.js +4 -3
- package/packages/datadog-instrumentations/src/fastify.js +4 -12
- package/packages/datadog-instrumentations/src/fs.js +8 -6
- package/packages/datadog-instrumentations/src/graphql.js +26 -484
- package/packages/datadog-instrumentations/src/helpers/check-require-cache.js +81 -8
- package/packages/datadog-instrumentations/src/helpers/instrument.js +27 -2
- package/packages/datadog-instrumentations/src/helpers/optional-peer-bundler.js +65 -0
- package/packages/datadog-instrumentations/src/helpers/register.js +6 -4
- package/packages/datadog-instrumentations/src/helpers/require-optional-peer.js +17 -0
- package/packages/datadog-instrumentations/src/helpers/rewriter/instrumentations/graphql.js +201 -0
- package/packages/datadog-instrumentations/src/helpers/rewriter/instrumentations/index.js +1 -0
- package/packages/datadog-instrumentations/src/helpers/rewriter/loader.mjs +18 -2
- package/packages/datadog-instrumentations/src/koa.js +3 -2
- package/packages/datadog-instrumentations/src/mariadb.js +4 -2
- package/packages/datadog-instrumentations/src/mocha/main.js +3 -3
- package/packages/datadog-instrumentations/src/mongoose.js +14 -2
- package/packages/datadog-instrumentations/src/next.js +10 -10
- package/packages/datadog-instrumentations/src/otel-sdk-trace.js +7 -6
- package/packages/datadog-instrumentations/src/playwright.js +1 -1
- package/packages/datadog-instrumentations/src/restify.js +4 -3
- package/packages/datadog-instrumentations/src/router.js +18 -5
- package/packages/datadog-instrumentations/src/selenium.js +1 -2
- package/packages/datadog-instrumentations/src/tedious.js +28 -0
- package/packages/datadog-instrumentations/src/vitest-main-no-worker-init.js +1293 -0
- package/packages/datadog-instrumentations/src/vitest-main.js +1567 -0
- package/packages/datadog-instrumentations/src/vitest-util.js +249 -0
- package/packages/datadog-instrumentations/src/vitest-worker.js +753 -0
- package/packages/datadog-instrumentations/src/vitest.js +11 -1598
- package/packages/datadog-plugin-avsc/src/schema_iterator.js +2 -2
- package/packages/datadog-plugin-aws-durable-execution-sdk-js/src/client.js +2 -2
- package/packages/datadog-plugin-aws-durable-execution-sdk-js/src/context.js +18 -10
- package/packages/datadog-plugin-aws-durable-execution-sdk-js/src/util.js +47 -11
- package/packages/datadog-plugin-aws-sdk/src/base.js +13 -9
- package/packages/datadog-plugin-aws-sdk/src/services/eventbridge.js +43 -6
- package/packages/datadog-plugin-aws-sdk/src/services/sqs.js +83 -91
- package/packages/datadog-plugin-cucumber/src/index.js +1 -1
- package/packages/datadog-plugin-cypress/src/cypress-plugin.js +19 -5
- package/packages/datadog-plugin-cypress/src/support.js +45 -1
- package/packages/datadog-plugin-express/src/code_origin.js +1 -1
- package/packages/datadog-plugin-fastify/src/code_origin.js +1 -1
- package/packages/datadog-plugin-graphql/src/execute.js +627 -11
- package/packages/datadog-plugin-graphql/src/index.js +20 -8
- package/packages/datadog-plugin-graphql/src/parse.js +24 -4
- package/packages/datadog-plugin-graphql/src/validate.js +16 -5
- package/packages/datadog-plugin-http/src/client.js +8 -3
- package/packages/datadog-plugin-http/src/index.js +6 -8
- package/packages/datadog-plugin-http2/src/client.js +5 -2
- package/packages/datadog-plugin-jest/src/index.js +1 -1
- package/packages/datadog-plugin-mocha/src/index.js +1 -1
- package/packages/datadog-plugin-mysql/src/index.js +7 -2
- package/packages/datadog-plugin-openai/src/services.js +2 -2
- package/packages/datadog-plugin-playwright/src/index.js +1 -1
- package/packages/datadog-plugin-protobufjs/src/schema_iterator.js +2 -2
- package/packages/datadog-plugin-undici/src/index.js +5 -2
- package/packages/datadog-plugin-vitest/src/index.js +76 -64
- package/packages/datadog-shimmer/src/shimmer.js +37 -16
- package/packages/datadog-webpack/index.js +17 -1
- package/packages/datadog-webpack/src/optional-peer-loader.js +17 -0
- package/packages/dd-trace/src/aiguard/sdk.js +15 -3
- package/packages/dd-trace/src/appsec/api_security/index.js +55 -0
- package/packages/dd-trace/src/appsec/api_security/sampler.js +147 -0
- package/packages/dd-trace/src/appsec/channels.js +3 -1
- package/packages/dd-trace/src/appsec/downstream_requests.js +4 -4
- package/packages/dd-trace/src/appsec/graphql.js +5 -5
- package/packages/dd-trace/src/appsec/iast/analyzers/nosql-injection-mongodb-analyzer.js +26 -19
- package/packages/dd-trace/src/appsec/iast/security-controls/index.js +2 -2
- package/packages/dd-trace/src/appsec/iast/telemetry/index.js +2 -1
- package/packages/dd-trace/src/appsec/index.js +20 -7
- package/packages/dd-trace/src/appsec/lambda.js +135 -0
- package/packages/dd-trace/src/appsec/reporter.js +50 -10
- package/packages/dd-trace/src/appsec/telemetry/api_security.js +34 -0
- package/packages/dd-trace/src/appsec/telemetry/index.js +27 -1
- package/packages/dd-trace/src/appsec/waf/index.js +16 -4
- package/packages/dd-trace/src/appsec/waf/waf_context_wrapper.js +4 -4
- package/packages/dd-trace/src/ci-visibility/early-flake-detection/get-known-tests.js +21 -6
- package/packages/dd-trace/src/ci-visibility/exporters/agent-proxy/index.js +2 -2
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/coverage-writer.js +1 -1
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/di-logs-writer.js +1 -1
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/index.js +3 -2
- package/packages/dd-trace/src/ci-visibility/exporters/agentless/writer.js +1 -1
- package/packages/dd-trace/src/ci-visibility/exporters/ci-visibility-exporter.js +55 -13
- package/packages/dd-trace/src/ci-visibility/exporters/git/git_metadata.js +2 -2
- package/packages/dd-trace/src/ci-visibility/exporters/test-worker/writer.js +17 -0
- package/packages/dd-trace/src/ci-visibility/intelligent-test-runner/get-skippable-suites.js +47 -26
- package/packages/dd-trace/src/ci-visibility/log-submission/log-submission-plugin.js +2 -2
- package/packages/dd-trace/src/ci-visibility/requests/get-library-configuration.js +64 -53
- package/packages/dd-trace/src/ci-visibility/requests/request.js +1 -17
- package/packages/dd-trace/src/ci-visibility/requests/upload-coverage-report.js +3 -3
- package/packages/dd-trace/src/ci-visibility/test-management/get-test-management-tests.js +23 -5
- package/packages/dd-trace/src/ci-visibility/test-optimization-http-cache-schema.js +128 -0
- package/packages/dd-trace/src/ci-visibility/test-optimization-http-cache.js +287 -0
- package/packages/dd-trace/src/config/defaults.js +25 -5
- package/packages/dd-trace/src/config/generated-config-types.d.ts +596 -58
- package/packages/dd-trace/src/config/helper.js +134 -33
- package/packages/dd-trace/src/config/index.js +39 -23
- package/packages/dd-trace/src/config/major-overrides.js +4 -2
- package/packages/dd-trace/src/config/parsers.js +19 -1
- package/packages/dd-trace/src/config/remote_config.js +1 -1
- package/packages/dd-trace/src/config/supported-configurations.json +109 -57
- package/packages/dd-trace/src/constants.js +7 -0
- package/packages/dd-trace/src/datastreams/processor.js +11 -3
- package/packages/dd-trace/src/debugger/devtools_client/breakpoints.js +47 -35
- package/packages/dd-trace/src/debugger/devtools_client/index.js +31 -66
- package/packages/dd-trace/src/debugger/devtools_client/probe_sampler.js +83 -0
- package/packages/dd-trace/src/debugger/devtools_client/state.js +1 -0
- package/packages/dd-trace/src/debugger/index.js +5 -0
- package/packages/dd-trace/src/debugger/probe_sampler.js +112 -0
- package/packages/dd-trace/src/debugger/probe_sampler_constants.js +19 -0
- package/packages/dd-trace/src/encode/agentless-ci-visibility.js +77 -26
- package/packages/dd-trace/src/exporters/agent/index.js +1 -1
- package/packages/dd-trace/src/exporters/agentless/writer.js +4 -4
- package/packages/dd-trace/src/exporters/common/request.js +1 -20
- package/packages/dd-trace/src/exporters/common/url.js +34 -0
- package/packages/dd-trace/src/exporters/span-stats/writer.js +1 -3
- package/packages/dd-trace/src/guardrails/index.js +8 -5
- package/packages/dd-trace/src/index.js +6 -4
- package/packages/dd-trace/src/llmobs/constants/tags.js +6 -0
- package/packages/dd-trace/src/llmobs/index.js +17 -6
- package/packages/dd-trace/src/llmobs/plugins/base.js +4 -4
- package/packages/dd-trace/src/llmobs/plugins/genai/util.js +3 -3
- package/packages/dd-trace/src/llmobs/plugins/langchain/index.js +5 -1
- package/packages/dd-trace/src/llmobs/plugins/langgraph/index.js +1 -1
- package/packages/dd-trace/src/llmobs/sdk.js +8 -6
- package/packages/dd-trace/src/llmobs/span_processor.js +5 -1
- package/packages/dd-trace/src/llmobs/tagger.js +58 -3
- package/packages/dd-trace/src/llmobs/telemetry.js +1 -0
- package/packages/dd-trace/src/llmobs/writers/base.js +1 -1
- package/packages/dd-trace/src/log/index.js +18 -20
- package/packages/dd-trace/src/openfeature/flagging_provider.js +2 -7
- package/packages/dd-trace/src/opentelemetry/bridge-span-base.js +5 -4
- package/packages/dd-trace/src/opentelemetry/metrics/index.js +54 -5
- package/packages/dd-trace/src/opentelemetry/metrics/instruments.js +2 -1
- package/packages/dd-trace/src/opentelemetry/metrics/otlp_span_stats_exporter.js +40 -0
- package/packages/dd-trace/src/opentelemetry/metrics/otlp_span_stats_transformer.js +169 -0
- package/packages/dd-trace/src/opentelemetry/metrics/periodic_metric_reader.js +4 -3
- package/packages/dd-trace/src/opentelemetry/metrics/time.js +19 -0
- package/packages/dd-trace/src/opentelemetry/otlp/common.proto +2 -2
- package/packages/dd-trace/src/opentelemetry/otlp/logs.proto +1 -1
- package/packages/dd-trace/src/opentelemetry/otlp/logs_service.proto +1 -1
- package/packages/dd-trace/src/opentelemetry/otlp/metrics.proto +1 -1
- package/packages/dd-trace/src/opentelemetry/otlp/metrics_service.proto +1 -1
- package/packages/dd-trace/src/opentelemetry/otlp/otlp_http_exporter_base.js +44 -38
- package/packages/dd-trace/src/opentelemetry/span-helpers.js +29 -13
- package/packages/dd-trace/src/opentelemetry/span.js +14 -3
- package/packages/dd-trace/src/opentelemetry/span_context.js +1 -0
- package/packages/dd-trace/src/opentelemetry/trace/index.js +6 -1
- package/packages/dd-trace/src/opentelemetry/trace/otlp_http_trace_exporter.js +3 -2
- package/packages/dd-trace/src/opentelemetry/trace/otlp_transformer.js +26 -13
- package/packages/dd-trace/src/opentelemetry/tracer_provider.js +1 -1
- package/packages/dd-trace/src/opentracing/propagation/text_map.js +3 -3
- package/packages/dd-trace/src/opentracing/span_context.js +17 -0
- package/packages/dd-trace/src/opentracing/tracer.js +6 -1
- package/packages/dd-trace/src/plugin_manager.js +14 -8
- package/packages/dd-trace/src/plugins/ci_plugin.js +21 -4
- package/packages/dd-trace/src/plugins/util/http-otel-semantics.js +276 -0
- package/packages/dd-trace/src/plugins/util/llm.js +6 -1
- package/packages/dd-trace/src/plugins/util/test.js +91 -9
- package/packages/dd-trace/src/plugins/util/url.js +68 -1
- package/packages/dd-trace/src/plugins/util/web.js +19 -36
- package/packages/dd-trace/src/priority_sampler.js +1 -13
- package/packages/dd-trace/src/profiling/config.js +129 -198
- package/packages/dd-trace/src/profiling/constants.js +4 -7
- package/packages/dd-trace/src/profiling/exporter_cli.js +10 -10
- package/packages/dd-trace/src/profiling/exporters/agent.js +23 -16
- package/packages/dd-trace/src/profiling/exporters/event_serializer.js +45 -14
- package/packages/dd-trace/src/profiling/exporters/file.js +16 -5
- package/packages/dd-trace/src/profiling/oom.js +71 -0
- package/packages/dd-trace/src/profiling/profiler.js +35 -23
- package/packages/dd-trace/src/profiling/profilers/events.js +14 -7
- package/packages/dd-trace/src/profiling/profilers/space.js +27 -18
- package/packages/dd-trace/src/profiling/profilers/wall.js +35 -25
- package/packages/dd-trace/src/proxy.js +8 -8
- package/packages/dd-trace/src/ritm.js +4 -2
- package/packages/dd-trace/src/serverless.js +1 -2
- package/packages/dd-trace/src/service-naming/schemas/util.js +36 -5
- package/packages/dd-trace/src/service-naming/schemas/v1/web.js +5 -3
- package/packages/dd-trace/src/span_format.js +2 -1
- package/packages/dd-trace/src/span_processor.js +11 -6
- package/packages/dd-trace/src/span_stats.js +96 -78
- package/packages/dd-trace/src/startup-log.js +2 -1
- package/packages/dd-trace/src/telemetry/dependencies.js +1 -1
- package/packages/dd-trace/src/telemetry/endpoints.js +6 -4
- package/packages/dd-trace/src/telemetry/index.js +2 -2
- package/packages/dd-trace/src/telemetry/logs/index.js +1 -1
- package/packages/dd-trace/src/telemetry/send-data.js +20 -18
- package/packages/dd-trace/src/telemetry/session-propagation.js +1 -1
- package/packages/dd-trace/src/telemetry/telemetry.js +9 -9
- package/packages/dd-trace/src/tracer.js +15 -1
- package/packages/dd-trace/src/util.js +14 -0
- package/register.js +58 -1
- package/vendor/dist/@apm-js-collab/code-transformer/index.js +1 -1
- package/vendor/dist/@datadog/sketches-js/index.js +1 -1
- package/vendor/dist/pprof-format/index.js +1 -1
- package/vendor/dist/protobufjs/index.js +1 -1
- package/vendor/dist/protobufjs/minimal/index.js +1 -1
- package/vendor/dist/shell-quote/index.js +1 -1
- package/packages/datadog-plugin-graphql/src/resolve.js +0 -170
- package/packages/dd-trace/src/appsec/api_security_sampler.js +0 -117
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
const { version: ddTraceVersion } = require('../../../../package.json')
|
|
3
|
-
const { ITR_CORRELATION_ID } = require('../../src/plugins/util/test')
|
|
3
|
+
const { ITR_CORRELATION_ID, TEST_LEVELS_METADATA } = require('../../src/plugins/util/test')
|
|
4
4
|
const id = require('../../src/id')
|
|
5
5
|
const {
|
|
6
6
|
distributionMetric,
|
|
@@ -9,10 +9,15 @@ const {
|
|
|
9
9
|
} = require('../ci-visibility/telemetry')
|
|
10
10
|
const { MsgpackChunk } = require('../msgpack')
|
|
11
11
|
const { AgentEncoder } = require('./0.4')
|
|
12
|
-
const {
|
|
12
|
+
const {
|
|
13
|
+
truncateSpanTestOpt,
|
|
14
|
+
normalizeSpan,
|
|
15
|
+
MAX_META_VALUE_LENGTH_TEST_OPTIMIZATION,
|
|
16
|
+
} = require('./tags-processors')
|
|
13
17
|
|
|
14
18
|
const ENCODING_VERSION = 1
|
|
15
19
|
const ALLOWED_CONTENT_TYPES = new Set(['test_session_end', 'test_module_end', 'test_suite_end', 'test'])
|
|
20
|
+
const ALLOWED_METADATA_TARGETS = new Set([...ALLOWED_CONTENT_TYPES, TEST_LEVELS_METADATA])
|
|
16
21
|
|
|
17
22
|
const TEST_SUITE_KEYS_LENGTH = 12
|
|
18
23
|
const TEST_MODULE_KEYS_LENGTH = 11
|
|
@@ -36,6 +41,33 @@ function formatSpan (span) {
|
|
|
36
41
|
}
|
|
37
42
|
}
|
|
38
43
|
|
|
44
|
+
function isAllowedMetadataTarget (target) {
|
|
45
|
+
return ALLOWED_METADATA_TARGETS.has(target)
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
function isEncodableMetadataValue (value) {
|
|
49
|
+
return typeof value === 'string' || typeof value === 'number'
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
function truncateTestLevelMetadataValue (value) {
|
|
53
|
+
if (typeof value !== 'string' || value.length <= MAX_META_VALUE_LENGTH_TEST_OPTIMIZATION) {
|
|
54
|
+
return value
|
|
55
|
+
}
|
|
56
|
+
return `${value.slice(0, MAX_META_VALUE_LENGTH_TEST_OPTIMIZATION)}...`
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
function truncateTestLevelMetadataTags (tags) {
|
|
60
|
+
const truncatedTags = {}
|
|
61
|
+
let hasTags = false
|
|
62
|
+
for (const key of Object.keys(tags)) {
|
|
63
|
+
const value = truncateTestLevelMetadataValue(tags[key])
|
|
64
|
+
if (!isEncodableMetadataValue(value)) continue
|
|
65
|
+
truncatedTags[key] = value
|
|
66
|
+
hasTags = true
|
|
67
|
+
}
|
|
68
|
+
return hasTags ? truncatedTags : undefined
|
|
69
|
+
}
|
|
70
|
+
|
|
39
71
|
class AgentlessCiVisibilityEncoder extends AgentEncoder {
|
|
40
72
|
constructor (writer, { runtimeId, service, env }) {
|
|
41
73
|
super(writer, INTAKE_SOFT_LIMIT)
|
|
@@ -49,6 +81,7 @@ class AgentlessCiVisibilityEncoder extends AgentEncoder {
|
|
|
49
81
|
|
|
50
82
|
this.metadataTags = {}
|
|
51
83
|
this.wildcardMetadataTags = {}
|
|
84
|
+
this.testLevelsMetadataKeys = []
|
|
52
85
|
|
|
53
86
|
this.reset()
|
|
54
87
|
}
|
|
@@ -60,12 +93,39 @@ class AgentlessCiVisibilityEncoder extends AgentEncoder {
|
|
|
60
93
|
...tags['*'],
|
|
61
94
|
}
|
|
62
95
|
}
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
96
|
+
|
|
97
|
+
for (const target of Object.keys(tags)) {
|
|
98
|
+
if (target === '*' || !tags[target] || !isAllowedMetadataTarget(target)) continue
|
|
99
|
+
|
|
100
|
+
const targetTags = target === TEST_LEVELS_METADATA
|
|
101
|
+
? truncateTestLevelMetadataTags(tags[target])
|
|
102
|
+
: tags[target]
|
|
103
|
+
if (!targetTags) continue
|
|
104
|
+
|
|
105
|
+
this.metadataTags[target] = {
|
|
106
|
+
...this.metadataTags[target],
|
|
107
|
+
...targetTags,
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
if (target === TEST_LEVELS_METADATA) {
|
|
111
|
+
this.testLevelsMetadataKeys = Object.keys(this.metadataTags[target])
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
_removeDuplicateTestLevelsMetadata (event) {
|
|
117
|
+
if (!ALLOWED_CONTENT_TYPES.has(event.type)) return
|
|
118
|
+
|
|
119
|
+
const meta = event.content.meta
|
|
120
|
+
if (!meta) return
|
|
121
|
+
|
|
122
|
+
const testLevelsMetadataTags = this.metadataTags[TEST_LEVELS_METADATA]
|
|
123
|
+
const testLevelsMetadataKeys = this.testLevelsMetadataKeys
|
|
124
|
+
|
|
125
|
+
for (let i = 0; i < testLevelsMetadataKeys.length; i++) {
|
|
126
|
+
const key = testLevelsMetadataKeys[i]
|
|
127
|
+
if (meta[key] === testLevelsMetadataTags[key]) {
|
|
128
|
+
delete meta[key]
|
|
69
129
|
}
|
|
70
130
|
}
|
|
71
131
|
}
|
|
@@ -276,7 +336,11 @@ class AgentlessCiVisibilityEncoder extends AgentEncoder {
|
|
|
276
336
|
|
|
277
337
|
this._eventCount += events.length
|
|
278
338
|
|
|
339
|
+
const hasTestLevelsMetadata = this.testLevelsMetadataKeys.length !== 0
|
|
279
340
|
for (const event of events) {
|
|
341
|
+
if (hasTestLevelsMetadata) {
|
|
342
|
+
this._removeDuplicateTestLevelsMetadata(event)
|
|
343
|
+
}
|
|
280
344
|
this._encodeEvent(bytes, event)
|
|
281
345
|
}
|
|
282
346
|
distributionMetric(
|
|
@@ -343,24 +407,11 @@ class AgentlessCiVisibilityEncoder extends AgentEncoder {
|
|
|
343
407
|
this._encodeString(bytes, 'version')
|
|
344
408
|
bytes.writeNumber(payload.version)
|
|
345
409
|
this._encodeString(bytes, 'metadata')
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
this.
|
|
351
|
-
this._encodeMap(bytes, payload.metadata.test)
|
|
352
|
-
}
|
|
353
|
-
if (payload.metadata.test_suite_end) {
|
|
354
|
-
this._encodeString(bytes, 'test_suite_end')
|
|
355
|
-
this._encodeMap(bytes, payload.metadata.test_suite_end)
|
|
356
|
-
}
|
|
357
|
-
if (payload.metadata.test_module_end) {
|
|
358
|
-
this._encodeString(bytes, 'test_module_end')
|
|
359
|
-
this._encodeMap(bytes, payload.metadata.test_module_end)
|
|
360
|
-
}
|
|
361
|
-
if (payload.metadata.test_session_end) {
|
|
362
|
-
this._encodeString(bytes, 'test_session_end')
|
|
363
|
-
this._encodeMap(bytes, payload.metadata.test_session_end)
|
|
410
|
+
const metadataKeys = Object.keys(payload.metadata)
|
|
411
|
+
bytes.writeMapPrefix(metadataKeys.length)
|
|
412
|
+
for (const metadataKey of metadataKeys) {
|
|
413
|
+
this._encodeString(bytes, metadataKey)
|
|
414
|
+
this._encodeMap(bytes, payload.metadata[metadataKey])
|
|
364
415
|
}
|
|
365
416
|
this._encodeString(bytes, 'events')
|
|
366
417
|
this._eventsOffset = bytes.length
|
|
@@ -13,7 +13,7 @@ class AgentExporter {
|
|
|
13
13
|
this._url = config.url
|
|
14
14
|
|
|
15
15
|
const headers = {}
|
|
16
|
-
if (stats.
|
|
16
|
+
if (stats.DD_TRACE_STATS_COMPUTATION_ENABLED || apmTracingEnabled === false) {
|
|
17
17
|
headers['Datadog-Client-Computed-Stats'] = 'yes'
|
|
18
18
|
}
|
|
19
19
|
|
|
@@ -40,7 +40,7 @@ class AgentlessWriter extends BaseWriter {
|
|
|
40
40
|
}
|
|
41
41
|
}
|
|
42
42
|
|
|
43
|
-
if (!getConfig().
|
|
43
|
+
if (!getConfig().DD_API_KEY) {
|
|
44
44
|
this.#apiKeyMissing = true
|
|
45
45
|
log.error('DD_API_KEY is required for agentless trace intake. Set DD_API_KEY. Traces will not be sent.')
|
|
46
46
|
}
|
|
@@ -109,8 +109,8 @@ class AgentlessWriter extends BaseWriter {
|
|
|
109
109
|
return
|
|
110
110
|
}
|
|
111
111
|
|
|
112
|
-
const
|
|
113
|
-
if (!
|
|
112
|
+
const { DD_API_KEY } = getConfig()
|
|
113
|
+
if (!DD_API_KEY) {
|
|
114
114
|
if (!this.#apiKeyMissing) {
|
|
115
115
|
this.#apiKeyMissing = true
|
|
116
116
|
log.error('DD_API_KEY is required for agentless trace intake. Set DD_API_KEY. Traces will not be sent.')
|
|
@@ -126,7 +126,7 @@ class AgentlessWriter extends BaseWriter {
|
|
|
126
126
|
method: 'POST',
|
|
127
127
|
headers: {
|
|
128
128
|
'Content-Type': 'application/json',
|
|
129
|
-
'dd-api-key':
|
|
129
|
+
'dd-api-key': DD_API_KEY,
|
|
130
130
|
'X-Datadog-Trace-Count': String(count),
|
|
131
131
|
'Datadog-Meta-Lang': 'nodejs',
|
|
132
132
|
'Datadog-Meta-Lang-Version': process.version,
|
|
@@ -11,7 +11,7 @@ const zlib = require('zlib')
|
|
|
11
11
|
|
|
12
12
|
const { storage } = require('../../../../datadog-core')
|
|
13
13
|
const log = require('../../log')
|
|
14
|
-
const {
|
|
14
|
+
const { parseUrl } = require('./url')
|
|
15
15
|
const docker = require('./docker')
|
|
16
16
|
const { httpAgent, httpsAgent } = require('./agents')
|
|
17
17
|
const {
|
|
@@ -27,25 +27,6 @@ const maxActiveBufferSize = 1024 * 1024 * 64
|
|
|
27
27
|
|
|
28
28
|
let activeBufferSize = 0
|
|
29
29
|
|
|
30
|
-
/**
|
|
31
|
-
* @param {string|URL|object} urlObjOrString
|
|
32
|
-
* @returns {object}
|
|
33
|
-
*/
|
|
34
|
-
function parseUrl (urlObjOrString) {
|
|
35
|
-
if (urlObjOrString !== null && typeof urlObjOrString === 'object') return urlToHttpOptions(urlObjOrString)
|
|
36
|
-
|
|
37
|
-
const url = urlToHttpOptions(new URL(urlObjOrString))
|
|
38
|
-
|
|
39
|
-
// Special handling if we're using named pipes on Windows
|
|
40
|
-
if (url.protocol === 'unix:' && url.hostname === '.') {
|
|
41
|
-
const udsPath = urlObjOrString.slice(5)
|
|
42
|
-
url.path = udsPath
|
|
43
|
-
url.pathname = udsPath
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
return url
|
|
47
|
-
}
|
|
48
|
-
|
|
49
30
|
/**
|
|
50
31
|
* @param {string} hostname Host as resolved by {@link parseUrl}; IPv6 is unbracketed (`::1`).
|
|
51
32
|
*/
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { urlToHttpOptions } = require('./url-to-http-options-polyfill')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Convert an agent/intake URL into Node http(s) request options.
|
|
7
|
+
*
|
|
8
|
+
* A Windows named pipe (`unix://./pipe/<name>`) parses the `.` as the URL
|
|
9
|
+
* authority, dropping it from the path. Fold it back so the socket path stays
|
|
10
|
+
* `//./pipe/<name>`; otherwise it collapses to `/pipe/<name>` and misses the
|
|
11
|
+
* pipe. Exporters receive `config.url` as a URL object, so this must run for
|
|
12
|
+
* both string and object input.
|
|
13
|
+
*
|
|
14
|
+
* @param {string|URL|object} urlObjOrString
|
|
15
|
+
* @returns {object}
|
|
16
|
+
*/
|
|
17
|
+
function parseUrl (urlObjOrString) {
|
|
18
|
+
// `urlToHttpOptions` returns `pathname` at runtime, but @types/node narrows it
|
|
19
|
+
// to `ClientRequestArgs`, which omits it; cast so the named-pipe fold below can
|
|
20
|
+
// read and rewrite it.
|
|
21
|
+
const url = /** @type {import('node:http').ClientRequestArgs & { pathname: string }} */ (
|
|
22
|
+
urlObjOrString !== null && typeof urlObjOrString === 'object'
|
|
23
|
+
? urlToHttpOptions(urlObjOrString)
|
|
24
|
+
: urlToHttpOptions(new URL(urlObjOrString))
|
|
25
|
+
)
|
|
26
|
+
|
|
27
|
+
if (url.protocol === 'unix:' && url.hostname === '.') {
|
|
28
|
+
url.path = url.pathname = `//.${url.pathname}`
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
return url
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
module.exports = { parseUrl }
|
|
@@ -37,9 +37,7 @@ function makeRequest (data, url, cb) {
|
|
|
37
37
|
'Datadog-Meta-Tracer-Version': pkg.version,
|
|
38
38
|
'Content-Type': 'application/msgpack',
|
|
39
39
|
},
|
|
40
|
-
|
|
41
|
-
hostname: url.hostname,
|
|
42
|
-
port: url.port,
|
|
40
|
+
url,
|
|
43
41
|
}
|
|
44
42
|
|
|
45
43
|
log.debug('Request to the intake: %j', options)
|
|
@@ -14,11 +14,13 @@ function guard (fn) {
|
|
|
14
14
|
var initBailout = false
|
|
15
15
|
var clobberBailout = false
|
|
16
16
|
var forced = isTrue(process.env.DD_INJECT_FORCE)
|
|
17
|
-
var
|
|
18
|
-
var
|
|
17
|
+
var pkg = require('../../../../package.json')
|
|
18
|
+
var engines = pkg.engines
|
|
19
|
+
var versions = engines.node.match(/^>=(\d+)$/)
|
|
19
20
|
var minMajor = versions[1]
|
|
20
|
-
var nextMajor =
|
|
21
|
+
var nextMajor = pkg.nodeMaxMajor
|
|
21
22
|
var version = process.versions.node
|
|
23
|
+
var supportedRange = engines.node + ' <' + nextMajor
|
|
22
24
|
|
|
23
25
|
if (process.env.DD_INJECTION_ENABLED) {
|
|
24
26
|
// If we're running via single-step install, and we're in the app's
|
|
@@ -45,16 +47,17 @@ function guard (fn) {
|
|
|
45
47
|
// should not initialize the tracer.
|
|
46
48
|
if (!clobberBailout && (NODE_MAJOR < minMajor || NODE_MAJOR >= nextMajor)) {
|
|
47
49
|
initBailout = true
|
|
50
|
+
var runtimeInfo = 'Incompatible runtime Node.js ' + version + ', supported runtimes: Node.js ' + supportedRange
|
|
48
51
|
telemetry([
|
|
49
52
|
{ name: 'abort', tags: ['reason:incompatible_runtime'] },
|
|
50
53
|
{ name: 'abort.runtime', tags: [] }
|
|
51
54
|
], undefined, {
|
|
52
55
|
result: 'abort',
|
|
53
56
|
result_class: 'incompatible_runtime',
|
|
54
|
-
result_reason:
|
|
57
|
+
result_reason: runtimeInfo
|
|
55
58
|
})
|
|
56
59
|
log.info('Aborting application instrumentation due to incompatible_runtime.')
|
|
57
|
-
log.info('Found incompatible runtime Node.js %s, Supported runtimes: Node.js %s.', version,
|
|
60
|
+
log.info('Found incompatible runtime Node.js %s, Supported runtimes: Node.js %s.', version, supportedRange)
|
|
58
61
|
if (forced) {
|
|
59
62
|
log.info('DD_INJECT_FORCE enabled, allowing unsupported runtimes and continuing.')
|
|
60
63
|
}
|
|
@@ -1,14 +1,16 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
3
|
const { getValueFromEnvSources } = require('./config/helper')
|
|
4
|
-
const { isFalse } = require('./util')
|
|
5
4
|
|
|
6
5
|
// Global `jest` is only present in Jest workers.
|
|
7
6
|
const inJestWorker = typeof jest !== 'undefined'
|
|
8
7
|
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
8
|
+
// skipDefault: distinguish an unset DD_TRACE_ENABLED (fall back to the OTel signal) from an
|
|
9
|
+
// explicit value; the registered default would otherwise mask the OTEL_TRACES_EXPORTER check.
|
|
10
|
+
const ddTraceEnabled = getValueFromEnvSources('DD_TRACE_ENABLED', true)
|
|
11
|
+
const ddTraceDisabled = ddTraceEnabled === undefined
|
|
12
|
+
? getValueFromEnvSources('OTEL_TRACES_EXPORTER') === 'none'
|
|
13
|
+
: ddTraceEnabled === false
|
|
12
14
|
|
|
13
15
|
module.exports = ddTraceDisabled || inJestWorker
|
|
14
16
|
? require('./noop/proxy')
|
|
@@ -14,6 +14,12 @@ module.exports = {
|
|
|
14
14
|
PROPAGATED_PARENT_ID_KEY: '_dd.p.llmobs_parent_id',
|
|
15
15
|
PROPAGATED_ML_APP_KEY: '_dd.p.llmobs_ml_app',
|
|
16
16
|
PARENT_ID_KEY: '_ml_obs.llmobs_parent_id',
|
|
17
|
+
PROPAGATED_SAMPLE_RATE_KEY: '_dd.p.llmobs_sr',
|
|
18
|
+
PROPAGATED_SAMPLING_DECISION_KEY: '_dd.p.llmobs_sd',
|
|
19
|
+
SAMPLE_RATE: '_ml_obs.sample_rate',
|
|
20
|
+
SAMPLING_DECISION: '_ml_obs.sampling_decision',
|
|
21
|
+
SAMPLING_DECISION_SAMPLED: '1',
|
|
22
|
+
SAMPLING_DECISION_DROPPED: '0',
|
|
17
23
|
TAGS: '_ml_obs.tags',
|
|
18
24
|
NAME: '_ml_obs.name',
|
|
19
25
|
TRACE_ID: '_ml_obs.trace_id',
|
|
@@ -9,6 +9,10 @@ const {
|
|
|
9
9
|
ML_APP,
|
|
10
10
|
PROPAGATED_ML_APP_KEY,
|
|
11
11
|
PROPAGATED_PARENT_ID_KEY,
|
|
12
|
+
SAMPLE_RATE,
|
|
13
|
+
SAMPLING_DECISION,
|
|
14
|
+
PROPAGATED_SAMPLE_RATE_KEY,
|
|
15
|
+
PROPAGATED_SAMPLING_DECISION_KEY,
|
|
12
16
|
} = require('./constants/tags')
|
|
13
17
|
const { storage } = require('./storage')
|
|
14
18
|
const telemetry = require('./telemetry')
|
|
@@ -68,10 +72,10 @@ function enable (config) {
|
|
|
68
72
|
spanFinishCh.subscribe(handleSpanProcess)
|
|
69
73
|
|
|
70
74
|
// distributed tracing for llmobs
|
|
71
|
-
injectCh.subscribe(
|
|
75
|
+
injectCh.subscribe(handleLLMObsInjection)
|
|
72
76
|
|
|
73
77
|
setAgentStrategy(config, useAgentless => {
|
|
74
|
-
if (useAgentless && !(config.
|
|
78
|
+
if (useAgentless && !(config.DD_API_KEY && config.site)) {
|
|
75
79
|
if (DD_MAJOR < 6 || !config?.startupLogs) {
|
|
76
80
|
// eslint-disable-next-line no-console
|
|
77
81
|
console.error(INCOMPATIBLE_INITIALIZATION)
|
|
@@ -92,7 +96,7 @@ function disable () {
|
|
|
92
96
|
if (evalMetricAppendCh.hasSubscribers) evalMetricAppendCh.unsubscribe(handleEvalMetricAppend)
|
|
93
97
|
if (flushCh.hasSubscribers) flushCh.unsubscribe(handleFlush)
|
|
94
98
|
if (spanFinishCh.hasSubscribers) spanFinishCh.unsubscribe(handleSpanProcess)
|
|
95
|
-
if (injectCh.hasSubscribers) injectCh.unsubscribe(
|
|
99
|
+
if (injectCh.hasSubscribers) injectCh.unsubscribe(handleLLMObsInjection)
|
|
96
100
|
if (registerUserSpanProcessorCh.hasSubscribers) registerUserSpanProcessorCh.unsubscribe(handleRegisterProcessor)
|
|
97
101
|
|
|
98
102
|
spanWriter?.destroy()
|
|
@@ -106,8 +110,8 @@ function disable () {
|
|
|
106
110
|
}
|
|
107
111
|
|
|
108
112
|
// since LLMObs traces can extend between services and be the same trace,
|
|
109
|
-
// we need to propagate the parent id and
|
|
110
|
-
function
|
|
113
|
+
// we need to propagate the parent id, mlApp, and sampling rate/decision.
|
|
114
|
+
function handleLLMObsInjection ({ carrier }) {
|
|
111
115
|
// Respect the standard propagator's gate: when trace tag propagation is
|
|
112
116
|
// disabled, don't write `x-datadog-tags` for LLMObs either.
|
|
113
117
|
if (globalTracerConfig.DD_TRACE_X_DATADOG_TAGS_MAX_LENGTH === 0) return
|
|
@@ -122,7 +126,12 @@ function handleLLMObsParentIdInjection ({ carrier }) {
|
|
|
122
126
|
parentContext?._trace?.tags?.[PROPAGATED_ML_APP_KEY] ||
|
|
123
127
|
globalTracerConfig.llmobs.mlApp
|
|
124
128
|
|
|
125
|
-
|
|
129
|
+
const sampleRate =
|
|
130
|
+
mlObsSpanTags?.[SAMPLE_RATE] ?? parentContext?._trace?.tags?.[PROPAGATED_SAMPLE_RATE_KEY]
|
|
131
|
+
const samplingDecision =
|
|
132
|
+
mlObsSpanTags?.[SAMPLING_DECISION] ?? parentContext?._trace?.tags?.[PROPAGATED_SAMPLING_DECISION_KEY]
|
|
133
|
+
|
|
134
|
+
if (!parentId && !mlApp && samplingDecision == null) return
|
|
126
135
|
|
|
127
136
|
// `_injectTags` only writes `x-datadog-tags` when the trace has `_dd.p.*`
|
|
128
137
|
// tags, so it may be undefined here — coalesce before appending.
|
|
@@ -130,6 +139,8 @@ function handleLLMObsParentIdInjection ({ carrier }) {
|
|
|
130
139
|
let tags = existing || ''
|
|
131
140
|
if (parentId) tags += `${tags ? ',' : ''}${PROPAGATED_PARENT_ID_KEY}=${parentId}`
|
|
132
141
|
if (mlApp) tags += `${tags ? ',' : ''}${PROPAGATED_ML_APP_KEY}=${mlApp}`
|
|
142
|
+
if (sampleRate != null) tags += `${tags ? ',' : ''}${PROPAGATED_SAMPLE_RATE_KEY}=${sampleRate}`
|
|
143
|
+
if (samplingDecision != null) tags += `${tags ? ',' : ''}${PROPAGATED_SAMPLING_DECISION_KEY}=${samplingDecision}`
|
|
133
144
|
if (tags !== existing) carrier['x-datadog-tags'] = tags
|
|
134
145
|
}
|
|
135
146
|
|
|
@@ -25,7 +25,7 @@ class LLMObsPlugin extends TracingPlugin {
|
|
|
25
25
|
start (ctx) {
|
|
26
26
|
// even though llmobs span events won't be enqueued if llmobs is disabled
|
|
27
27
|
// we should avoid doing any computations here (these listeners aren't disabled)
|
|
28
|
-
const enabled = this._tracerConfig.llmobs.
|
|
28
|
+
const enabled = this._tracerConfig.llmobs.DD_LLMOBS_ENABLED
|
|
29
29
|
if (!enabled) return
|
|
30
30
|
|
|
31
31
|
const parentStore = llmobsStorage.getStore()
|
|
@@ -52,7 +52,7 @@ class LLMObsPlugin extends TracingPlugin {
|
|
|
52
52
|
}
|
|
53
53
|
|
|
54
54
|
end (ctx) {
|
|
55
|
-
const enabled = this._tracerConfig.llmobs.
|
|
55
|
+
const enabled = this._tracerConfig.llmobs.DD_LLMOBS_ENABLED
|
|
56
56
|
if (!enabled) return
|
|
57
57
|
|
|
58
58
|
// only attempt to restore the context if the current span was an LLMObs span
|
|
@@ -67,7 +67,7 @@ class LLMObsPlugin extends TracingPlugin {
|
|
|
67
67
|
asyncEnd (ctx) {
|
|
68
68
|
// even though llmobs span events won't be enqueued if llmobs is disabled
|
|
69
69
|
// we should avoid doing any computations here (these listeners aren't disabled)
|
|
70
|
-
const enabled = this._tracerConfig.llmobs.
|
|
70
|
+
const enabled = this._tracerConfig.llmobs.DD_LLMOBS_ENABLED
|
|
71
71
|
if (!enabled) return
|
|
72
72
|
|
|
73
73
|
const apmStore = ctx.currentStore
|
|
@@ -85,7 +85,7 @@ class LLMObsPlugin extends TracingPlugin {
|
|
|
85
85
|
|
|
86
86
|
configure (config) {
|
|
87
87
|
// we do not want to enable any LLMObs plugins if it is disabled on the tracer
|
|
88
|
-
const llmobsEnabled = this._tracerConfig.llmobs.
|
|
88
|
+
const llmobsEnabled = this._tracerConfig.llmobs.DD_LLMOBS_ENABLED
|
|
89
89
|
if (llmobsEnabled === false) {
|
|
90
90
|
config = typeof config === 'boolean' ? false : { ...config, enabled: false } // override to false
|
|
91
91
|
}
|
|
@@ -114,7 +114,7 @@ function extractMetrics (response) {
|
|
|
114
114
|
}
|
|
115
115
|
|
|
116
116
|
const totalTokens = tokenUsage.totalTokenCount ||
|
|
117
|
-
|
|
117
|
+
(tokenUsage.promptTokenCount || 0) + (tokenUsage.candidatesTokenCount || 0)
|
|
118
118
|
if (totalTokens) {
|
|
119
119
|
metrics.totalTokens = totalTokens
|
|
120
120
|
}
|
|
@@ -458,8 +458,8 @@ function formatStreamingOutput (response) {
|
|
|
458
458
|
|
|
459
459
|
// Skip special cases in streaming (handle them as non-streaming)
|
|
460
460
|
if (content.parts.some(part => part.functionCall ||
|
|
461
|
-
|
|
462
|
-
|
|
461
|
+
part.executableCode ||
|
|
462
|
+
part.codeExecutionResult)) {
|
|
463
463
|
messages.push(...formatNonStreamingCandidate(candidate))
|
|
464
464
|
continue
|
|
465
465
|
}
|
|
@@ -9,7 +9,11 @@ const ANTHROPIC_PROVIDER_NAME = 'anthropic'
|
|
|
9
9
|
const BEDROCK_PROVIDER_NAME = 'amazon_bedrock'
|
|
10
10
|
const OPENAI_PROVIDER_NAME = 'openai'
|
|
11
11
|
|
|
12
|
-
|
|
12
|
+
// Providers that ship their own LLMObs integration. When one of these is also
|
|
13
|
+
// enabled, the LangChain model span is demoted to `workflow` so the provider
|
|
14
|
+
// integration emits the single `llm` span — avoiding two llm spans (and
|
|
15
|
+
// double-counted tokens/cost) for one underlying call.
|
|
16
|
+
const SUPPORTED_INTEGRATIONS = new Set(['openai', 'anthropic'])
|
|
13
17
|
const LLM_SPAN_TYPES = new Set(['llm', 'chat_model', 'embedding'])
|
|
14
18
|
const LLM = 'llm'
|
|
15
19
|
const WORKFLOW = 'workflow'
|
|
@@ -14,7 +14,7 @@ class PregelStreamLLMObsPlugin extends LLMObsPlugin {
|
|
|
14
14
|
getLLMObsSpanRegisterOptions (ctx) {
|
|
15
15
|
const name = ctx.self.name || 'LangGraph'
|
|
16
16
|
|
|
17
|
-
const enabled = this._tracerConfig.llmobs.
|
|
17
|
+
const enabled = this._tracerConfig.llmobs.DD_LLMOBS_ENABLED
|
|
18
18
|
if (!enabled) return
|
|
19
19
|
|
|
20
20
|
const span = ctx.currentStore?.span
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
const { channel } = require('dc-polyfill')
|
|
4
4
|
|
|
5
|
-
const { isError
|
|
5
|
+
const { isError } = require('../util')
|
|
6
6
|
const tracerVersion = require('../../../../package.json').version
|
|
7
7
|
const logger = require('../log')
|
|
8
8
|
const { getValueFromEnvSources } = require('../config/helper')
|
|
@@ -49,7 +49,7 @@ class LLMObs extends NoopLLMObs {
|
|
|
49
49
|
}
|
|
50
50
|
|
|
51
51
|
get enabled () {
|
|
52
|
-
return this._config.llmobs.
|
|
52
|
+
return this._config.llmobs.DD_LLMOBS_ENABLED ?? false
|
|
53
53
|
}
|
|
54
54
|
|
|
55
55
|
enable (options = {}) {
|
|
@@ -65,15 +65,17 @@ class LLMObs extends NoopLLMObs {
|
|
|
65
65
|
|
|
66
66
|
logger.debug('Enabling LLMObs')
|
|
67
67
|
|
|
68
|
-
|
|
68
|
+
// skipDefault: only an explicit DD_LLMOBS_ENABLED=false blocks enable(); an unset value
|
|
69
|
+
// (its default is false) must still allow this programmatic opt-in.
|
|
70
|
+
const DD_LLMOBS_ENABLED = getValueFromEnvSources('DD_LLMOBS_ENABLED', true)
|
|
69
71
|
|
|
70
|
-
if (DD_LLMOBS_ENABLED
|
|
72
|
+
if (DD_LLMOBS_ENABLED === false) {
|
|
71
73
|
logger.debug('LLMObs.enable() called when DD_LLMOBS_ENABLED is false. No action taken.')
|
|
72
74
|
return
|
|
73
75
|
}
|
|
74
76
|
|
|
75
77
|
// TODO: These configs should be passed through directly at construction time instead.
|
|
76
|
-
this._config.llmobs.
|
|
78
|
+
this._config.llmobs.DD_LLMOBS_ENABLED = true
|
|
77
79
|
this._config.llmobs.mlApp = options.mlApp
|
|
78
80
|
this._config.llmobs.agentlessEnabled = options.agentlessEnabled
|
|
79
81
|
|
|
@@ -94,7 +96,7 @@ class LLMObs extends NoopLLMObs {
|
|
|
94
96
|
|
|
95
97
|
logger.debug('Disabling LLMObs')
|
|
96
98
|
|
|
97
|
-
this._config.llmobs.
|
|
99
|
+
this._config.llmobs.DD_LLMOBS_ENABLED = false
|
|
98
100
|
|
|
99
101
|
// disable writers and channel subscribers
|
|
100
102
|
this._llmobsModule.disable()
|
|
@@ -33,6 +33,8 @@ const {
|
|
|
33
33
|
ROUTING_API_KEY,
|
|
34
34
|
ROUTING_SITE,
|
|
35
35
|
LLMOBS_SUBMITTED_TAG_KEY,
|
|
36
|
+
SAMPLE_RATE,
|
|
37
|
+
SAMPLING_DECISION,
|
|
36
38
|
} = require('./constants/tags')
|
|
37
39
|
const { UNSERIALIZABLE_VALUE_TEXT } = require('./constants/text')
|
|
38
40
|
const telemetry = require('./telemetry')
|
|
@@ -81,7 +83,7 @@ class LLMObsSpanProcessor {
|
|
|
81
83
|
|
|
82
84
|
// TODO: instead of relying on the tagger's weakmap registry, can we use some namespaced storage correlation?
|
|
83
85
|
process (span) {
|
|
84
|
-
if (!this.#config.llmobs.
|
|
86
|
+
if (!this.#config.llmobs.DD_LLMOBS_ENABLED) return
|
|
85
87
|
// if the span is not in our private tagger map, it is not an llmobs span
|
|
86
88
|
if (!LLMObsTagger.tagMap.has(span)) return
|
|
87
89
|
|
|
@@ -248,6 +250,8 @@ class LLMObsSpanProcessor {
|
|
|
248
250
|
_dd: {
|
|
249
251
|
span_id: span.context().toSpanId(),
|
|
250
252
|
trace_id: span.context().toTraceId(true),
|
|
253
|
+
sample_rate: mlObsTags[SAMPLE_RATE],
|
|
254
|
+
sampling_decision: mlObsTags[SAMPLING_DECISION],
|
|
251
255
|
},
|
|
252
256
|
}
|
|
253
257
|
|