dd-trace 6.7.0 → 6.9.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.
Files changed (272) hide show
  1. package/ci/diagnose.js +27 -25
  2. package/ci/init.js +6 -6
  3. package/ci/runbook.md +114 -20
  4. package/ci/test-optimization-validation/approval-artifacts.js +36 -3
  5. package/ci/test-optimization-validation/approval.js +78 -22
  6. package/ci/test-optimization-validation/blocker-category.js +24 -0
  7. package/ci/test-optimization-validation/ci-discovery.js +23 -17
  8. package/ci/test-optimization-validation/ci-package-scripts.js +34 -6
  9. package/ci/test-optimization-validation/ci-remediation.js +1 -1
  10. package/ci/test-optimization-validation/cli.js +280 -52
  11. package/ci/test-optimization-validation/command-blocker.js +159 -20
  12. package/ci/test-optimization-validation/command-output-policy.js +14 -8
  13. package/ci/test-optimization-validation/command-runner.js +9 -7
  14. package/ci/test-optimization-validation/environment.js +4 -2
  15. package/ci/test-optimization-validation/executable.js +15 -13
  16. package/ci/test-optimization-validation/execution-lock.js +70 -0
  17. package/ci/test-optimization-validation/framework-adapters/cucumber-validation.json +3 -0
  18. package/ci/test-optimization-validation/framework-adapters/cucumber.js +657 -5
  19. package/ci/test-optimization-validation/framework-adapters/playwright.js +5 -5
  20. package/ci/test-optimization-validation/framework-adapters/vitest.js +517 -0
  21. package/ci/test-optimization-validation/generated-files.js +47 -37
  22. package/ci/test-optimization-validation/generated-test-contract.js +9 -7
  23. package/ci/test-optimization-validation/generated-verifier.js +24 -17
  24. package/ci/test-optimization-validation/literal-glob.js +52 -0
  25. package/ci/test-optimization-validation/manifest-loader.js +3 -0
  26. package/ci/test-optimization-validation/manifest-scaffold.js +301 -52
  27. package/ci/test-optimization-validation/manifest-schema.js +80 -17
  28. package/ci/test-optimization-validation/offline-fixtures.js +13 -4
  29. package/ci/test-optimization-validation/offline-output.js +6 -6
  30. package/ci/test-optimization-validation/package-check.js +94 -0
  31. package/ci/test-optimization-validation/plan-writer.js +183 -10
  32. package/ci/test-optimization-validation/preflight-runner.js +110 -31
  33. package/ci/test-optimization-validation/project-build-artifact.js +31 -0
  34. package/ci/test-optimization-validation/redaction.js +18 -27
  35. package/ci/test-optimization-validation/report-writer.js +182 -48
  36. package/ci/test-optimization-validation/result-semantics.js +20 -3
  37. package/ci/test-optimization-validation/runner-command.js +41 -21
  38. package/ci/test-optimization-validation/runner-contract.js +79 -43
  39. package/ci/test-optimization-validation/safe-files.js +4 -4
  40. package/ci/test-optimization-validation/scenarios/basic-reporting.js +60 -6
  41. package/ci/test-optimization-validation/scenarios/ci-wiring.js +141 -35
  42. package/ci/test-optimization-validation/scenarios/helpers.js +30 -6
  43. package/ci/test-optimization-validation/scenarios/test-management.js +2 -2
  44. package/ci/test-optimization-validation/static-diagnosis.js +10 -3
  45. package/ci/test-optimization-validation/test-output.js +2 -1
  46. package/ci/test-optimization-validation/validation-blocker.js +21 -0
  47. package/ci/vitest-no-worker-init-setup.mjs +377 -84
  48. package/index.d.ts +175 -14
  49. package/init.js +1 -17
  50. package/initialize.mjs +11 -0
  51. package/loader-hook.mjs +6 -4
  52. package/package.json +12 -4
  53. package/packages/datadog-core/src/utils/src/kebabcase.js +8 -2
  54. package/packages/datadog-core/src/utils/src/parse-tags.js +0 -1
  55. package/packages/datadog-esbuild/index.js +4 -2
  56. package/packages/datadog-esbuild/src/utils.js +17 -2
  57. package/packages/datadog-instrumentations/src/ai.js +61 -34
  58. package/packages/datadog-instrumentations/src/bluebird.js +6 -6
  59. package/packages/datadog-instrumentations/src/claude-agent-sdk.js +85 -9
  60. package/packages/datadog-instrumentations/src/cucumber.js +131 -51
  61. package/packages/datadog-instrumentations/src/dns.js +21 -2
  62. package/packages/datadog-instrumentations/src/electron.js +1 -0
  63. package/packages/datadog-instrumentations/src/fastify.js +3 -1
  64. package/packages/datadog-instrumentations/src/grpc/client.js +4 -2
  65. package/packages/datadog-instrumentations/src/helpers/callback-instrumentor.js +3 -1
  66. package/packages/datadog-instrumentations/src/helpers/extract-package-and-module-path.js +10 -0
  67. package/packages/datadog-instrumentations/src/helpers/hook.js +19 -2
  68. package/packages/datadog-instrumentations/src/helpers/hooks.js +4 -0
  69. package/packages/datadog-instrumentations/src/helpers/register.js +9 -3
  70. package/packages/datadog-instrumentations/src/helpers/rewriter/index.js +34 -9
  71. package/packages/datadog-instrumentations/src/helpers/rewriter/instrumentations/index.js +1 -0
  72. package/packages/datadog-instrumentations/src/helpers/rewriter/instrumentations/webdriverio.js +175 -0
  73. package/packages/datadog-instrumentations/src/helpers/rewriter/loader.mjs +20 -2
  74. package/packages/datadog-instrumentations/src/helpers/rewriter/targets.js +32 -0
  75. package/packages/datadog-instrumentations/src/helpers/rewriter/targets.json +61 -0
  76. package/packages/datadog-instrumentations/src/helpers/rewriter/transforms.js +50 -18
  77. package/packages/datadog-instrumentations/src/helpers/router-helper.js +38 -7
  78. package/packages/datadog-instrumentations/src/helpers/shared-utils.js +39 -0
  79. package/packages/datadog-instrumentations/src/http/client.js +1 -3
  80. package/packages/datadog-instrumentations/src/jest/coverage-backfill.js +1 -1
  81. package/packages/datadog-instrumentations/src/jest.js +986 -246
  82. package/packages/datadog-instrumentations/src/mocha/common.js +1 -3
  83. package/packages/datadog-instrumentations/src/mocha/main.js +109 -51
  84. package/packages/datadog-instrumentations/src/mocha/utils.js +120 -32
  85. package/packages/datadog-instrumentations/src/mocha/webdriverio-protocol.js +44 -0
  86. package/packages/datadog-instrumentations/src/mocha/worker.js +441 -43
  87. package/packages/datadog-instrumentations/src/moleculer/client.js +1 -1
  88. package/packages/datadog-instrumentations/src/mysql.js +1 -1
  89. package/packages/datadog-instrumentations/src/next.js +155 -23
  90. package/packages/datadog-instrumentations/src/openai.js +14 -0
  91. package/packages/datadog-instrumentations/src/pg.js +180 -6
  92. package/packages/datadog-instrumentations/src/playwright.js +176 -81
  93. package/packages/datadog-instrumentations/src/promise-js.js +4 -4
  94. package/packages/datadog-instrumentations/src/promise.js +3 -3
  95. package/packages/datadog-instrumentations/src/rhea.js +1 -1
  96. package/packages/datadog-instrumentations/src/router.js +195 -19
  97. package/packages/datadog-instrumentations/src/vitest-main-no-worker-init.js +567 -65
  98. package/packages/datadog-instrumentations/src/vitest-main.js +438 -54
  99. package/packages/datadog-instrumentations/src/vitest-util.js +42 -7
  100. package/packages/datadog-instrumentations/src/vitest-worker.js +234 -17
  101. package/packages/datadog-instrumentations/src/webdriverio.js +1090 -0
  102. package/packages/datadog-instrumentations/src/when.js +3 -3
  103. package/packages/datadog-instrumentations/src/ws.js +5 -1
  104. package/packages/datadog-plugin-aerospike/src/index.js +1 -3
  105. package/packages/datadog-plugin-amqplib/src/client.js +1 -1
  106. package/packages/datadog-plugin-amqplib/src/producer.js +1 -1
  107. package/packages/datadog-plugin-aws-sdk/src/services/bedrockruntime/utils.js +59 -48
  108. package/packages/datadog-plugin-aws-sdk/src/services/eventbridge.js +2 -2
  109. package/packages/datadog-plugin-aws-sdk/src/services/stepfunctions.js +2 -2
  110. package/packages/datadog-plugin-azure-event-hubs/src/producer.js +1 -3
  111. package/packages/datadog-plugin-azure-service-bus/src/producer.js +5 -3
  112. package/packages/datadog-plugin-bullmq/src/producer.js +3 -3
  113. package/packages/datadog-plugin-child_process/src/index.js +3 -3
  114. package/packages/datadog-plugin-child_process/src/scrub-cmd-params.js +6 -11
  115. package/packages/datadog-plugin-cucumber/src/index.js +5 -1
  116. package/packages/datadog-plugin-cypress/src/cypress-plugin.js +50 -46
  117. package/packages/datadog-plugin-cypress/src/source-map-utils.js +1 -1
  118. package/packages/datadog-plugin-cypress/src/support.js +7 -4
  119. package/packages/datadog-plugin-electron/src/net.js +10 -4
  120. package/packages/datadog-plugin-fastify/src/tracing.js +1 -1
  121. package/packages/datadog-plugin-fs/src/index.js +0 -4
  122. package/packages/datadog-plugin-google-cloud-pubsub/src/consumer.js +14 -7
  123. package/packages/datadog-plugin-google-cloud-pubsub/src/producer.js +19 -10
  124. package/packages/datadog-plugin-graphql/src/execute.js +1 -0
  125. package/packages/datadog-plugin-graphql/src/tools/signature.js +1 -1
  126. package/packages/datadog-plugin-http/src/client.js +3 -2
  127. package/packages/datadog-plugin-http2/src/client.js +1 -1
  128. package/packages/datadog-plugin-jest/src/index.js +3 -21
  129. package/packages/datadog-plugin-jest/src/util.js +4 -1
  130. package/packages/datadog-plugin-kafkajs/src/producer.js +2 -1
  131. package/packages/datadog-plugin-langchain/src/tokens.js +2 -2
  132. package/packages/datadog-plugin-mocha/src/index.js +342 -6
  133. package/packages/datadog-plugin-next/src/index.js +57 -9
  134. package/packages/datadog-plugin-openai/src/tracing.js +4 -0
  135. package/packages/datadog-plugin-pg/src/index.js +65 -1
  136. package/packages/datadog-plugin-playwright/src/index.js +1 -1
  137. package/packages/datadog-plugin-prisma/src/index.js +5 -1
  138. package/packages/datadog-plugin-rhea/src/consumer.js +16 -13
  139. package/packages/datadog-plugin-rhea/src/producer.js +1 -1
  140. package/packages/datadog-plugin-undici/src/index.js +2 -1
  141. package/packages/datadog-plugin-vitest/src/index.js +179 -18
  142. package/packages/datadog-shimmer/src/shimmer.js +6 -2
  143. package/packages/datadog-webpack/index.js +2 -2
  144. package/packages/dd-trace/src/aiguard/sdk.js +3 -0
  145. package/packages/dd-trace/src/appsec/{blocking.js → blocking/index.js} +26 -6
  146. package/packages/dd-trace/src/appsec/downstream_requests.js +1 -1
  147. package/packages/dd-trace/src/appsec/handlers/auth.js +62 -0
  148. package/packages/dd-trace/src/appsec/handlers/http-request.js +215 -0
  149. package/packages/dd-trace/src/appsec/handlers/http-response.js +78 -0
  150. package/packages/dd-trace/src/appsec/handlers/http-shared.js +24 -0
  151. package/packages/dd-trace/src/appsec/handlers/payments.js +104 -0
  152. package/packages/dd-trace/src/appsec/iast/analyzers/hardcoded-base-analyzer.js +1 -1
  153. package/packages/dd-trace/src/appsec/iast/analyzers/hardcoded-password-analyzer.js +1 -1
  154. package/packages/dd-trace/src/appsec/iast/analyzers/hsts-header-missing-analyzer.js +1 -1
  155. package/packages/dd-trace/src/appsec/iast/analyzers/sql-injection-analyzer.js +1 -1
  156. package/packages/dd-trace/src/appsec/iast/taint-tracking/taint-tracking-impl.js +1 -3
  157. package/packages/dd-trace/src/appsec/iast/vulnerabilities-formatter/utils.js +2 -2
  158. package/packages/dd-trace/src/appsec/iast/vulnerability-reporter.js +2 -2
  159. package/packages/dd-trace/src/appsec/index.js +48 -476
  160. package/packages/dd-trace/src/appsec/sdk/track_event.js +10 -1
  161. package/packages/dd-trace/src/appsec/waf/waf_manager.js +1 -1
  162. package/packages/dd-trace/src/ci-visibility/coverage-report-discovery.js +46 -14
  163. package/packages/dd-trace/src/ci-visibility/efd-retry-policy.js +89 -0
  164. package/packages/dd-trace/src/ci-visibility/exporters/ci-validation/sink.js +7 -6
  165. package/packages/dd-trace/src/ci-visibility/exporters/ci-visibility-exporter.js +29 -15
  166. package/packages/dd-trace/src/ci-visibility/exporters/git/git_metadata.js +19 -1
  167. package/packages/dd-trace/src/ci-visibility/exporters/test-worker/index.js +25 -1
  168. package/packages/dd-trace/src/ci-visibility/exporters/test-worker/webdriverio.js +26 -0
  169. package/packages/dd-trace/src/ci-visibility/exporters/test-worker/writer.js +9 -1
  170. package/packages/dd-trace/src/ci-visibility/intelligent-test-runner/get-skippable-suites.js +22 -7
  171. package/packages/dd-trace/src/ci-visibility/requests/get-library-configuration.js +9 -14
  172. package/packages/dd-trace/src/ci-visibility/requests/request.js +3 -3
  173. package/packages/dd-trace/src/ci-visibility/requests/upload-coverage-report.js +21 -5
  174. package/packages/dd-trace/src/ci-visibility/test-optimization-http-cache-schema.js +2 -2
  175. package/packages/dd-trace/src/ci-visibility/test-optimization-http-cache.js +5 -1
  176. package/packages/dd-trace/src/config/defaults.js +14 -6
  177. package/packages/dd-trace/src/config/generated-config-types.d.ts +4 -2
  178. package/packages/dd-trace/src/config/helper.js +2 -0
  179. package/packages/dd-trace/src/config/index.js +31 -5
  180. package/packages/dd-trace/src/config/parsers.js +19 -1
  181. package/packages/dd-trace/src/config/remote_config.js +1 -1
  182. package/packages/dd-trace/src/config/supported-configurations.json +13 -6
  183. package/packages/dd-trace/src/datastreams/encoding.js +3 -4
  184. package/packages/dd-trace/src/debugger/devtools_client/log.js +2 -1
  185. package/packages/dd-trace/src/debugger/devtools_client/probe_sampler.js +1 -4
  186. package/packages/dd-trace/src/debugger/devtools_client/send.js +1 -2
  187. package/packages/dd-trace/src/debugger/devtools_client/snapshot/index.js +2 -2
  188. package/packages/dd-trace/src/debugger/devtools_client/snapshot/redaction.js +16 -2
  189. package/packages/dd-trace/src/debugger/devtools_client/status.js +1 -1
  190. package/packages/dd-trace/src/encode/coverage-ci-visibility.js +0 -1
  191. package/packages/dd-trace/src/encode/tags-processors.js +2 -2
  192. package/packages/dd-trace/src/exporters/common/url.js +3 -5
  193. package/packages/dd-trace/src/exporters/electron/index.js +4 -1
  194. package/packages/dd-trace/src/external-logger/src/index.js +1 -2
  195. package/packages/dd-trace/src/flare/index.js +2 -2
  196. package/packages/dd-trace/src/guardrails/apply-pm2-env.js +16 -0
  197. package/packages/dd-trace/src/guardrails/log.js +1 -10
  198. package/packages/dd-trace/src/id.js +1 -1
  199. package/packages/dd-trace/src/llmobs/constants/tags.js +1 -1
  200. package/packages/dd-trace/src/llmobs/eval-metric.js +249 -0
  201. package/packages/dd-trace/src/llmobs/experiments/client.js +4 -2
  202. package/packages/dd-trace/src/llmobs/experiments/dataset.js +66 -14
  203. package/packages/dd-trace/src/llmobs/experiments/experiment.js +289 -95
  204. package/packages/dd-trace/src/llmobs/experiments/index.js +66 -19
  205. package/packages/dd-trace/src/llmobs/experiments/noop.js +95 -10
  206. package/packages/dd-trace/src/llmobs/experiments/result.js +13 -2
  207. package/packages/dd-trace/src/llmobs/experiments/util.js +220 -0
  208. package/packages/dd-trace/src/llmobs/noop.js +2 -0
  209. package/packages/dd-trace/src/llmobs/plugins/ai/ddTelemetry.js +1 -1
  210. package/packages/dd-trace/src/llmobs/plugins/ai/util.js +1 -1
  211. package/packages/dd-trace/src/llmobs/plugins/anthropic/index.js +1 -1
  212. package/packages/dd-trace/src/llmobs/plugins/bedrockruntime.js +5 -5
  213. package/packages/dd-trace/src/llmobs/plugins/claude-agent-sdk/index.js +1 -1
  214. package/packages/dd-trace/src/llmobs/plugins/genai/index.js +1 -1
  215. package/packages/dd-trace/src/llmobs/plugins/langchain/handlers/index.js +1 -1
  216. package/packages/dd-trace/src/llmobs/plugins/langchain/index.js +1 -1
  217. package/packages/dd-trace/src/llmobs/sdk.js +152 -78
  218. package/packages/dd-trace/src/llmobs/span_processor.js +9 -7
  219. package/packages/dd-trace/src/llmobs/tagger.js +1 -2
  220. package/packages/dd-trace/src/llmobs/telemetry.js +18 -0
  221. package/packages/dd-trace/src/llmobs/writers/base.js +3 -0
  222. package/packages/dd-trace/src/llmobs/writers/spans.js +12 -6
  223. package/packages/dd-trace/src/llmobs/writers/util.js +2 -0
  224. package/packages/dd-trace/src/log/channels.js +1 -9
  225. package/packages/dd-trace/src/log/levels.js +12 -0
  226. package/packages/dd-trace/src/noop/proxy.js +2 -2
  227. package/packages/dd-trace/src/openfeature/writers/exposures.js +1 -1
  228. package/packages/dd-trace/src/openfeature/writers/util.js +1 -1
  229. package/packages/dd-trace/src/opentelemetry/logs/batch_log_processor.js +1 -1
  230. package/packages/dd-trace/src/opentelemetry/metrics/meter.js +8 -4
  231. package/packages/dd-trace/src/opentelemetry/metrics/otlp_transformer.js +1 -1
  232. package/packages/dd-trace/src/opentelemetry/metrics/periodic_metric_reader.js +3 -2
  233. package/packages/dd-trace/src/opentelemetry/span.js +4 -0
  234. package/packages/dd-trace/src/opentracing/span.js +1 -1
  235. package/packages/dd-trace/src/opentracing/span_context.js +1 -1
  236. package/packages/dd-trace/src/plugins/ci_plugin.js +124 -23
  237. package/packages/dd-trace/src/plugins/index.js +2 -0
  238. package/packages/dd-trace/src/plugins/plugin.js +1 -1
  239. package/packages/dd-trace/src/plugins/tracing.js +1 -0
  240. package/packages/dd-trace/src/plugins/util/ci.js +13 -6
  241. package/packages/dd-trace/src/plugins/util/git.js +7 -5
  242. package/packages/dd-trace/src/plugins/util/http-otel-semantics.js +3 -3
  243. package/packages/dd-trace/src/plugins/util/ip_extractor.js +1 -1
  244. package/packages/dd-trace/src/plugins/util/llm.js +2 -2
  245. package/packages/dd-trace/src/plugins/util/stacktrace.js +3 -0
  246. package/packages/dd-trace/src/plugins/util/tags.js +2 -0
  247. package/packages/dd-trace/src/plugins/util/test.js +356 -86
  248. package/packages/dd-trace/src/plugins/util/url.js +5 -5
  249. package/packages/dd-trace/src/plugins/util/user-provided-git.js +1 -1
  250. package/packages/dd-trace/src/plugins/util/web.js +24 -2
  251. package/packages/dd-trace/src/priority_sampler.js +6 -3
  252. package/packages/dd-trace/src/profiler.js +1 -1
  253. package/packages/dd-trace/src/profiling/exporters/event_serializer.js +1 -1
  254. package/packages/dd-trace/src/profiling/profilers/events.js +2 -2
  255. package/packages/dd-trace/src/profiling/profilers/poisson.js +1 -1
  256. package/packages/dd-trace/src/profiling/profilers/shared.js +2 -2
  257. package/packages/dd-trace/src/proxy.js +1 -0
  258. package/packages/dd-trace/src/ritm.js +10 -20
  259. package/packages/dd-trace/src/runtime_metrics/runtime_metrics.js +4 -2
  260. package/packages/dd-trace/src/sampling_rule.js +4 -2
  261. package/packages/dd-trace/src/service-naming/schemas/v0/storage.js +1 -1
  262. package/packages/dd-trace/src/service-naming/schemas/v1/storage.js +1 -1
  263. package/packages/dd-trace/src/startup-log.js +3 -0
  264. package/packages/dd-trace/src/telemetry/logs/index.js +3 -0
  265. package/packages/dd-trace/src/telemetry/logs/log-collector.js +3 -1
  266. package/packages/dd-trace/src/telemetry/telemetry.js +1 -1
  267. package/packages/dd-trace/src/util.js +16 -0
  268. package/vendor/dist/@apm-js-collab/code-transformer/index.js +12 -12
  269. package/vendor/dist/pprof-format/index.js +1 -1
  270. package/vendor/dist/source-map/index.js +1 -1
  271. package/version.js +10 -8
  272. /package/packages/dd-trace/src/appsec/{blocked_templates.js → blocking/templates.js} +0 -0
@@ -8,13 +8,13 @@ const HTTP2_HEADER_AUTHORITY = ':authority'
8
8
  const HTTP2_HEADER_SCHEME = ':scheme'
9
9
  const HTTP2_HEADER_PATH = ':path'
10
10
 
11
- const PATH_REGEX = /^(?:[a-z]+:\/\/(?:[^?/]+))?(?<path>\/[^?]*)(?:(\?).*)?$/
11
+ const PATH_REGEX = /^(?:[a-z]+:\/\/[^?/]+)?(?<path>\/[^?]*)(?:(\?).*)?$/
12
12
 
13
13
  const INT_SEGMENT = /^[1-9][0-9]+$/ // Integer of size at least 2 (>=10)
14
- const INT_ID_SEGMENT = /^(?=.*[0-9].*)[0-9._-]{3,}$/ // Mixed string with digits and delimiters
15
- const HEX_SEGMENT = /^(?=.*[0-9].*)[A-Fa-f0-9]{6,}$/ // Hexadecimal digits of size at least 6 with at least one decimal digit
16
- const HEX_ID_SEGMENT = /^(?=.*[0-9].*)[A-Fa-f0-9._-]{6,}$/ // Mixed string with hex digits and delimiters
17
- const STRING_SEGMENT = /^.{20,}|.*[%&'()*+,:=@].*$/ // Long string or a string containing special characters
14
+ const INT_ID_SEGMENT = /^(?=.*[0-9])[0-9._-]{3,}$/ // Mixed string with digits and delimiters
15
+ const HEX_SEGMENT = /^(?=.*[0-9])[A-Fa-f0-9]{6,}$/ // Hexadecimal digits of size at least 6 with at least one decimal digit
16
+ const HEX_ID_SEGMENT = /^(?=.*[0-9])[A-Fa-f0-9._-]{6,}$/ // Mixed string with hex digits and delimiters
17
+ const STRING_SEGMENT = /(?:^.{20,}|[%&'()*+,:=@])/ // Long string or a string containing special characters
18
18
 
19
19
  /**
20
20
  * Extract full URL from HTTP request
@@ -36,7 +36,7 @@ function removeEmptyValues (tagsAndValues) {
36
36
  // https://github.com/jonschlinkert/is-git-url/blob/396965ffabf2f46656c8af4c47bef1d69f09292e/index.js#L9C15-L9C87
37
37
  // The `.git` suffix is optional in this version
38
38
  function validateGitRepositoryUrl (repoUrl) {
39
- return /(?:git|ssh|https?|git@[-\w.]+):(\/\/)?(.*?)(\/?|#[-\w.]+?)$/.test(repoUrl)
39
+ return /(?:git|ssh|https?|git@[-\w.]+):(\/\/)?(.*?)(\/?|#[-\w.]+)$/.test(repoUrl)
40
40
  }
41
41
 
42
42
  function validateGitCommitSha (gitCommitSha) {
@@ -34,6 +34,7 @@ const HTTP_CLIENT_IP = tags.HTTP_CLIENT_IP
34
34
  const MANUAL_DROP = tags.MANUAL_DROP
35
35
 
36
36
  const contexts = new WeakMap()
37
+ const requests = new WeakMap()
37
38
 
38
39
  // TODO: change this to no longer rely on creating a dummy plugin to be able to access startSpan
39
40
  function createWebPlugin (tracer, config = {}) {
@@ -127,6 +128,7 @@ const web = {
127
128
  context.tracer = tracer
128
129
  context.span = span
129
130
  context.res = res
131
+ requests.set(span, req)
130
132
 
131
133
  this.setConfig(req, config)
132
134
  addRequestTags(context, this.TYPE)
@@ -219,7 +221,7 @@ const web = {
219
221
  const store = legacyStorage.getStore()
220
222
  const pubsubSpan = store?.span?._name === 'pubsub.push.receive' ? store.span : null
221
223
 
222
- let childOf = pubsubSpan || tracer.extract(FORMAT_HTTP_HEADERS, headers)
224
+ let childOf = pubsubSpan || this.extractIncomingServerContext(tracer, headers)
223
225
 
224
226
  // we may have headers signaling a router proxy span should be created (such as for AWS API Gateway)
225
227
  if (tracer._config?.inferredProxyServicesEnabled) {
@@ -232,6 +234,10 @@ const web = {
232
234
  return startSpanHelper(tracer, name, { childOf }, traceCtx, config)
233
235
  },
234
236
 
237
+ extractIncomingServerContext (tracer, headers) {
238
+ return tracer.extract(FORMAT_HTTP_HEADERS, normalizeHeadersCarrier(headers))
239
+ },
240
+
235
241
  // Validate a request's status code and then add error tags if necessary
236
242
  addStatusError (req, statusCode) {
237
243
  const context = contexts.get(req)
@@ -307,6 +313,7 @@ const web = {
307
313
  web.finishMiddleware(context)
308
314
 
309
315
  web.finishSpan(context, spanType)
316
+ requests.delete(context.span)
310
317
 
311
318
  finishInferredProxySpan(context)
312
319
  },
@@ -336,6 +343,9 @@ const web = {
336
343
  getContext (req) {
337
344
  return contexts.get(req)
338
345
  },
346
+ getRequest (span) {
347
+ return requests.get(span)
348
+ },
339
349
  setRouteOrEndpointTag (req) {
340
350
  const context = contexts.get(req)
341
351
 
@@ -345,6 +355,18 @@ const web = {
345
355
  },
346
356
  }
347
357
 
358
+ function normalizeHeadersCarrier (headers) {
359
+ if (!headers || typeof headers.get !== 'function' || typeof headers[Symbol.iterator] !== 'function') {
360
+ return headers
361
+ }
362
+
363
+ const carrier = {}
364
+ for (const [key, value] of headers) {
365
+ carrier[String(key).toLowerCase()] = value
366
+ }
367
+ return carrier
368
+ }
369
+
348
370
  function addAllowHeaders (req, res, headers) {
349
371
  const allowHeaders = splitHeader(headers['access-control-allow-headers'])
350
372
  const requestHeaders = splitHeader(req.headers['access-control-request-headers'])
@@ -376,7 +398,7 @@ function isOriginAllowed (req, headers) {
376
398
  }
377
399
 
378
400
  function splitHeader (str) {
379
- return typeof str === 'string' ? str.split(/\s*,\s*/) : []
401
+ return typeof str === 'string' ? str.split(',').map((header) => header.trim()) : []
380
402
  }
381
403
 
382
404
  function addRequestTags (context, spanType) {
@@ -140,7 +140,7 @@ class PrioritySampler {
140
140
  samplers[key] = new Sampler(rates[key])
141
141
  }
142
142
 
143
- samplers[DEFAULT_KEY] = samplers[DEFAULT_KEY] || defaultSampler
143
+ samplers[DEFAULT_KEY] ||= defaultSampler
144
144
 
145
145
  this._samplers = samplers
146
146
 
@@ -257,8 +257,11 @@ class PrioritySampler {
257
257
  context._trace[SAMPLING_RULE_DECISION] = rule.sampleRate
258
258
  context._trace.tags[SAMPLING_KNUTH_RATE] = formatKnuthRate(rule.sampleRate)
259
259
  context._sampling.mechanism = SAMPLING_MECHANISM_RULE
260
- if (rule.provenance === 'customer') context._sampling.mechanism = SAMPLING_MECHANISM_REMOTE_USER
261
- if (rule.provenance === 'dynamic') context._sampling.mechanism = SAMPLING_MECHANISM_REMOTE_DYNAMIC
260
+ if (rule.provenance === 'customer') {
261
+ context._sampling.mechanism = SAMPLING_MECHANISM_REMOTE_USER
262
+ } else if (rule.provenance === 'dynamic') {
263
+ context._sampling.mechanism = SAMPLING_MECHANISM_REMOTE_DYNAMIC
264
+ }
262
265
 
263
266
  return rule.sample(context) && this._isSampledByRateLimit(context)
264
267
  ? USER_KEEP
@@ -20,7 +20,7 @@ module.exports = {
20
20
 
21
21
  /**
22
22
  * Declares the set of custom label keys that will be used with
23
- * {@link runWithLabels}.
23
+ * `runWithLabels`.
24
24
  *
25
25
  * @param {Iterable<string>} keys - Custom label key names
26
26
  */
@@ -43,7 +43,7 @@ class EventSerializer {
43
43
 
44
44
  /**
45
45
  * Returns the destination URL for the near-OOM export subprocess, or nothing when this exporter
46
- * does not support OOM export. Overridden by {@link AgentExporter} and {@link FileExporter}.
46
+ * does not support OOM export. Overridden by `AgentExporter` and `FileExporter`.
47
47
  *
48
48
  * @returns {URL | undefined}
49
49
  */
@@ -2,7 +2,7 @@
2
2
 
3
3
  const { performance, constants, PerformanceObserver } = require('perf_hooks')
4
4
  const {
5
- Function,
5
+ Function: PprofFunction,
6
6
  Label,
7
7
  Line,
8
8
  Location,
@@ -256,7 +256,7 @@ class EventSerializer {
256
256
  // A synthetic single-frame location to serve as the location for timeline
257
257
  // samples. We need these as the profiling backend (mimicking official pprof
258
258
  // tool's behavior) ignores these.
259
- const fn = new Function({ id: this.functions.length + 1, name: this.stringTable.dedup('') })
259
+ const fn = new PprofFunction({ id: this.functions.length + 1, name: this.stringTable.dedup('') })
260
260
  this.functions.push(fn)
261
261
  const line = new Line({ functionId: fn.id })
262
262
  const location = new Location({ id: this.locations.length + 1, line: [line] })
@@ -6,7 +6,7 @@ class PoissonProcessSamplingFilter {
6
6
  #samplingInterval
7
7
  #resetInterval
8
8
  #now
9
- #lastNow = Number.NEGATIVE_INFINITY
9
+ #lastNow = -Infinity
10
10
  #samplingInstantCount = 0
11
11
 
12
12
  constructor ({ samplingInterval, now, resetInterval }) {
@@ -17,8 +17,8 @@ function getThreadLabels () {
17
17
  const nativeThreadId = pprof.getNativeThreadId()
18
18
  return {
19
19
  [THREAD_NAME_LABEL]: eventLoopThreadName,
20
- [THREAD_ID_LABEL]: `${threadId}`,
21
- [OS_THREAD_ID_LABEL]: `${nativeThreadId}`,
20
+ [THREAD_ID_LABEL]: threadId.toString(),
21
+ [OS_THREAD_ID_LABEL]: nativeThreadId.toString(),
22
22
  }
23
23
  }
24
24
 
@@ -49,6 +49,7 @@ class LazyModule {
49
49
 
50
50
  /**
51
51
  * @param {import('./config/config-base')} config - Tracer configuration
52
+ * @param {...unknown} args - Extra arguments forwarded to the lazily loaded module
52
53
  */
53
54
  enable (config, ...args) {
54
55
  this.module = this.provider()
@@ -7,7 +7,11 @@ const Module = require('module')
7
7
  const dc = require('dc-polyfill')
8
8
 
9
9
  const parse = require('../../../vendor/dist/module-details-from-path')
10
- const { isRelativeRequire } = require('../../datadog-instrumentations/src/helpers/shared-utils')
10
+ const {
11
+ isBuiltinModuleName,
12
+ isRelativeRequire,
13
+ normalizeModuleName,
14
+ } = require('../../datadog-instrumentations/src/helpers/shared-utils')
11
15
  const { getConfiguredEnvName, getEnvironmentVariable } = require('./config/helper')
12
16
 
13
17
  const origRequire = Module.prototype.require
@@ -22,25 +26,6 @@ let patchedRequire = null
22
26
  const moduleLoadStartChannel = dc.channel('dd-trace:moduleLoadStart')
23
27
  const moduleLoadEndChannel = dc.channel('dd-trace:moduleLoadEnd')
24
28
 
25
- function stripNodePrefix (name) {
26
- if (typeof name !== 'string') return name
27
- return name.startsWith('node:') ? name.slice(5) : name
28
- }
29
-
30
- const builtinModules = new Set(Module.builtinModules.map(stripNodePrefix))
31
-
32
- function isBuiltinModuleName (name) {
33
- if (typeof name !== 'string') return false
34
- if (name === 'electron') return true
35
- return builtinModules.has(stripNodePrefix(name))
36
- }
37
-
38
- function normalizeModuleName (name) {
39
- if (typeof name !== 'string') return name
40
- const stripped = stripNodePrefix(name)
41
- return builtinModules.has(stripped) ? stripped : name
42
- }
43
-
44
29
  /**
45
30
  * @overload
46
31
  * @param {string[]} modules list of modules to hook into
@@ -52,6 +37,11 @@ function normalizeModuleName (name) {
52
37
  * @param {string[]} modules list of modules to hook into
53
38
  * @param {Function} onrequire callback to be executed upon encountering module
54
39
  */
40
+ /**
41
+ * @param {string[]} modules list of modules to hook into
42
+ * @param {object | Function} [options] hook options, or the `onrequire` callback
43
+ * @param {Function} [onrequire] callback to be executed upon encountering module
44
+ */
55
45
  function Hook (modules, options, onrequire) {
56
46
  if (!(this instanceof Hook)) return new Hook(modules, options, onrequire)
57
47
  if (typeof options === 'function') {
@@ -11,11 +11,13 @@ const { NODE_MAJOR, NODE_MINOR } = require('../../../../version')
11
11
  const { createMetricsClient } = require('./client')
12
12
 
13
13
  const eventLoopDelayResolution = 4
14
- const EVENT_LOOP_SAMPLE_PER_ITERATION_AVAILABLE = NODE_MAJOR > 26 || (NODE_MAJOR === 26 && NODE_MINOR >= 5)
14
+ const EVENT_LOOP_SAMPLE_PER_ITERATION_AVAILABLE = NODE_MAJOR > 26 ||
15
+ (NODE_MAJOR === 26 && NODE_MINOR >= 5) ||
16
+ (NODE_MAJOR === 24 && NODE_MINOR >= 19)
15
17
 
16
18
  // @datadog/native-metrics is only needed on Node versions where
17
19
  // monitorEventLoopDelay's samplePerIteration option is unavailable.
18
- // TODO: remove @datadog/native-metrics and this branch once Node < 26.5 is no longer supported.
20
+ // TODO: remove @datadog/native-metrics and this branch once all supported Node versions provide this option.
19
21
  const NATIVE_METRICS_REQUIRED = !EVENT_LOOP_SAMPLE_PER_ITERATION_AVAILABLE
20
22
 
21
23
  let nativeMetrics = null
@@ -180,8 +180,10 @@ class SamplingRule {
180
180
  if (resource) {
181
181
  this.matchers.push(matcher(resource, resourceLocator))
182
182
  }
183
- for (const [key, value] of Object.entries(tags || {})) {
184
- this.matchers.push(matcher(value, makeTagLocator(key)))
183
+ if (tags) {
184
+ for (const [key, value] of Object.entries(tags)) {
185
+ this.matchers.push(matcher(value, makeTagLocator(key)))
186
+ }
185
187
  }
186
188
 
187
189
  this._sampler = new Sampler(sampleRate)
@@ -150,7 +150,7 @@ const storage = {
150
150
  },
151
151
  },
152
152
  pg: {
153
- opName: () => 'pg.query',
153
+ opName: ({ operation = 'query' }) => `pg.${operation}`,
154
154
  serviceName: withSuffixFunction('postgres'),
155
155
  serviceSource: ({ tracerService, pluginConfig, connectionName }) => {
156
156
  return optionServiceSource({ tracerService, pluginConfig, connectionName, integration: 'pg' })
@@ -82,7 +82,7 @@ const storage = {
82
82
  serviceSource: optionServiceSource,
83
83
  },
84
84
  pg: {
85
- opName: () => 'postgresql.query',
85
+ opName: ({ operation = 'query' }) => `postgresql.${operation}`,
86
86
  serviceName: withFunction,
87
87
  serviceSource: optionServiceSource,
88
88
  },
@@ -108,6 +108,9 @@ function configInfo () {
108
108
  profiling_enabled: profilingEnabled === 'true' || profilingEnabled === 'auto',
109
109
  appsec_enabled: config.appsec.enabled,
110
110
  data_streams_enabled: !!config.dsmEnabled,
111
+ otlp_traces_export_enabled: config.OTEL_TRACES_EXPORTER === 'otlp' && !config.isCiVisibility,
112
+ otlp_metrics_export_enabled: !!config.DD_METRICS_OTEL_ENABLED,
113
+ otlp_logs_export_enabled: !!config.DD_LOGS_OTEL_ENABLED,
111
114
  }
112
115
  }
113
116
 
@@ -13,6 +13,9 @@ let enabled = false
13
13
  * Telemetry logs api defines only ERROR, WARN and DEBUG levels:
14
14
  * - WARN level is enabled by default
15
15
  * - DEBUG level will be possible to activate with an env var or telemetry config property
16
+ *
17
+ * @param {string | undefined} level
18
+ * @returns {boolean}
16
19
  */
17
20
  function isLevelEnabled (level) {
18
21
  return isValidLevel(level)
@@ -31,7 +31,9 @@ function isValid (logEntry) {
31
31
  }
32
32
 
33
33
  const EOL = '\n'
34
- const STACK_FRAME_LINE_REGEX = /^\s*at\s/gm
34
+ // `[ \t]*` (horizontal whitespace) cannot span line terminators, so under `m` the `^`-anchored
35
+ // match runs once per line instead of rescanning across lines. Stack frames indent with spaces.
36
+ const STACK_FRAME_LINE_REGEX = /^[ \t]*at\s/gm
35
37
 
36
38
  function sanitize (logEntry) {
37
39
  const stack = logEntry.stack_trace
@@ -130,7 +130,7 @@ function updateRetryData (error, retryObj) {
130
130
 
131
131
  function getIntegrations () {
132
132
  const newIntegrations = /** @type {Integration[]} */ ([])
133
- for (const pluginName of Object.keys(pluginManager._pluginsByName ?? {})) {
133
+ for (const pluginName of Object.keys(pluginManager._pluginsByName)) {
134
134
  if (!sentIntegrations.has(pluginName)) {
135
135
  newIntegrations.push({
136
136
  name: pluginName,
@@ -102,6 +102,21 @@ function getSegment (string, separator, index, fallback) {
102
102
  return end === -1 ? string.slice(start) : string.slice(start, end)
103
103
  }
104
104
 
105
+ /**
106
+ * Return the path portion of a request target, dropping any query string and fragment.
107
+ * The two scans avoid the array and substring a `split(/[?#]/)` allocates per call.
108
+ *
109
+ * @param {string} target
110
+ */
111
+ function stripQueryAndFragment (target) {
112
+ let cut = target.indexOf('?')
113
+ const fragment = target.indexOf('#')
114
+ if (cut === -1 || (fragment !== -1 && fragment < cut)) {
115
+ cut = fragment
116
+ }
117
+ return cut === -1 ? target : target.slice(0, cut)
118
+ }
119
+
105
120
  function calculateDDBasePath (dirname) {
106
121
  const dirSteps = dirname.split(path.sep)
107
122
  const packagesIndex = dirSteps.lastIndexOf('packages')
@@ -136,6 +151,7 @@ module.exports = {
136
151
  isError,
137
152
  globMatch,
138
153
  getSegment,
154
+ stripQueryAndFragment,
139
155
  ddBasePath: globalThis.__DD_ESBUILD_BASEPATH || calculateDDBasePath(__dirname),
140
156
  normalizePluginEnvName,
141
157
  formatKnuthRate,