dd-trace 5.71.0 → 5.73.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 (84) hide show
  1. package/LICENSE-3rdparty.csv +7 -0
  2. package/index.d.ts +114 -1
  3. package/package.json +25 -4
  4. package/packages/datadog-esbuild/index.js +8 -0
  5. package/packages/datadog-instrumentations/src/azure-event-hubs.js +37 -0
  6. package/packages/datadog-instrumentations/src/azure-functions.js +3 -0
  7. package/packages/datadog-instrumentations/src/azure-service-bus.js +49 -22
  8. package/packages/datadog-instrumentations/src/cookie-parser.js +2 -0
  9. package/packages/datadog-instrumentations/src/cucumber.js +7 -7
  10. package/packages/datadog-instrumentations/src/helpers/hooks.js +1 -0
  11. package/packages/datadog-instrumentations/src/jest.js +85 -47
  12. package/packages/datadog-instrumentations/src/mocha/main.js +8 -9
  13. package/packages/datadog-instrumentations/src/mocha/utils.js +4 -5
  14. package/packages/datadog-instrumentations/src/mocha/worker.js +2 -2
  15. package/packages/datadog-instrumentations/src/pg.js +1 -1
  16. package/packages/datadog-instrumentations/src/playwright.js +5 -5
  17. package/packages/datadog-instrumentations/src/vitest.js +8 -8
  18. package/packages/datadog-plugin-amqplib/src/consumer.js +1 -1
  19. package/packages/datadog-plugin-aws-sdk/src/services/bedrockruntime/utils.js +73 -27
  20. package/packages/datadog-plugin-azure-event-hubs/src/index.js +15 -0
  21. package/packages/datadog-plugin-azure-event-hubs/src/producer.js +82 -0
  22. package/packages/datadog-plugin-azure-functions/src/index.js +50 -3
  23. package/packages/datadog-plugin-azure-service-bus/src/index.js +1 -1
  24. package/packages/datadog-plugin-azure-service-bus/src/producer.js +60 -12
  25. package/packages/datadog-plugin-cucumber/src/index.js +3 -3
  26. package/packages/datadog-plugin-cypress/src/cypress-plugin.js +9 -9
  27. package/packages/datadog-plugin-jest/src/index.js +53 -18
  28. package/packages/datadog-plugin-jest/src/util.js +10 -2
  29. package/packages/datadog-plugin-mocha/src/index.js +2 -2
  30. package/packages/datadog-plugin-playwright/src/index.js +2 -2
  31. package/packages/datadog-plugin-vitest/src/index.js +2 -2
  32. package/packages/datadog-plugin-ws/src/close.js +1 -1
  33. package/packages/datadog-plugin-ws/src/producer.js +1 -1
  34. package/packages/datadog-plugin-ws/src/receiver.js +1 -1
  35. package/packages/datadog-plugin-ws/src/server.js +5 -3
  36. package/packages/dd-trace/src/appsec/index.js +9 -1
  37. package/packages/dd-trace/src/appsec/reporter.js +2 -3
  38. package/packages/dd-trace/src/ci-visibility/test-management/get-test-management-tests.js +5 -0
  39. package/packages/dd-trace/src/config.js +108 -26
  40. package/packages/dd-trace/src/config_defaults.js +12 -0
  41. package/packages/dd-trace/src/git_properties.js +90 -5
  42. package/packages/dd-trace/src/llmobs/plugins/ai/util.js +8 -3
  43. package/packages/dd-trace/src/llmobs/plugins/base.js +11 -12
  44. package/packages/dd-trace/src/llmobs/sdk.js +20 -4
  45. package/packages/dd-trace/src/llmobs/tagger.js +12 -0
  46. package/packages/dd-trace/src/noop/proxy.js +3 -0
  47. package/packages/dd-trace/src/openfeature/constants/constants.js +51 -0
  48. package/packages/dd-trace/src/openfeature/flagging_provider.js +45 -0
  49. package/packages/dd-trace/src/openfeature/index.js +77 -0
  50. package/packages/dd-trace/src/openfeature/noop.js +101 -0
  51. package/packages/dd-trace/src/openfeature/writers/base.js +181 -0
  52. package/packages/dd-trace/src/openfeature/writers/exposures.js +173 -0
  53. package/packages/dd-trace/src/openfeature/writers/util.js +43 -0
  54. package/packages/dd-trace/src/opentelemetry/logs/batch_log_processor.js +100 -0
  55. package/packages/dd-trace/src/opentelemetry/logs/index.js +87 -0
  56. package/packages/dd-trace/src/opentelemetry/logs/logger.js +77 -0
  57. package/packages/dd-trace/src/opentelemetry/logs/logger_provider.js +126 -0
  58. package/packages/dd-trace/src/opentelemetry/logs/otlp_http_log_exporter.js +53 -0
  59. package/packages/dd-trace/src/opentelemetry/logs/otlp_transformer.js +252 -0
  60. package/packages/dd-trace/src/opentelemetry/otlp/common.proto +116 -0
  61. package/packages/dd-trace/src/opentelemetry/otlp/logs.proto +226 -0
  62. package/packages/dd-trace/src/opentelemetry/otlp/logs_service.proto +78 -0
  63. package/packages/dd-trace/src/opentelemetry/otlp/metrics.proto +720 -0
  64. package/packages/dd-trace/src/opentelemetry/otlp/metrics_service.proto +78 -0
  65. package/packages/dd-trace/src/opentelemetry/otlp/otlp_http_exporter_base.js +177 -0
  66. package/packages/dd-trace/src/opentelemetry/otlp/otlp_transformer_base.js +163 -0
  67. package/packages/dd-trace/src/opentelemetry/otlp/protobuf_loader.js +66 -0
  68. package/packages/dd-trace/src/opentelemetry/otlp/resource.proto +45 -0
  69. package/packages/dd-trace/src/plugins/ci_plugin.js +7 -6
  70. package/packages/dd-trace/src/plugins/index.js +1 -0
  71. package/packages/dd-trace/src/plugins/util/test.js +6 -5
  72. package/packages/dd-trace/src/profiling/config.js +21 -1
  73. package/packages/dd-trace/src/profiling/exporters/event_serializer.js +3 -2
  74. package/packages/dd-trace/src/profiling/profiler.js +44 -22
  75. package/packages/dd-trace/src/profiling/profilers/events.js +12 -3
  76. package/packages/dd-trace/src/profiling/profilers/space.js +35 -24
  77. package/packages/dd-trace/src/profiling/profilers/wall.js +14 -6
  78. package/packages/dd-trace/src/proxy.js +22 -1
  79. package/packages/dd-trace/src/remote_config/capabilities.js +1 -0
  80. package/packages/dd-trace/src/remote_config/index.js +1 -0
  81. package/packages/dd-trace/src/service-naming/schemas/v0/messaging.js +4 -0
  82. package/packages/dd-trace/src/service-naming/schemas/v1/messaging.js +8 -0
  83. package/packages/dd-trace/src/supported-configurations.json +18 -0
  84. package/packages/dd-trace/src/telemetry/telemetry.js +13 -1
@@ -29,6 +29,7 @@ const testSessionConfigurationCh = channel('ci:jest:session:configuration')
29
29
 
30
30
  const testSuiteStartCh = channel('ci:jest:test-suite:start')
31
31
  const testSuiteFinishCh = channel('ci:jest:test-suite:finish')
32
+ const testSuiteErrorCh = channel('ci:jest:test-suite:error')
32
33
 
33
34
  const workerReportTraceCh = channel('ci:jest:worker-report:trace')
34
35
  const workerReportCoverageCh = channel('ci:jest:worker-report:coverage')
@@ -46,7 +47,7 @@ const skippableSuitesCh = channel('ci:jest:test-suite:skippable')
46
47
  const libraryConfigurationCh = channel('ci:jest:library-configuration')
47
48
  const knownTestsCh = channel('ci:jest:known-tests')
48
49
  const testManagementTestsCh = channel('ci:jest:test-management-tests')
49
- const impactedTestsCh = channel('ci:jest:modified-tests')
50
+ const modifiedFilesCh = channel('ci:jest:modified-files')
50
51
 
51
52
  const itrSkippedSuitesCh = channel('ci:jest:itr:skipped-suites')
52
53
 
@@ -78,7 +79,7 @@ let isTestManagementTestsEnabled = false
78
79
  let testManagementTests = {}
79
80
  let testManagementAttemptToFixRetries = 0
80
81
  let isImpactedTestsEnabled = false
81
- let modifiedTests = {}
82
+ let modifiedFiles = {}
82
83
 
83
84
  const testContexts = new WeakMap()
84
85
  const originalTestFns = new WeakMap()
@@ -89,6 +90,7 @@ const attemptToFixRetriedTestsStatuses = new Map()
89
90
  const wrappedWorkers = new WeakSet()
90
91
  const testSuiteMockedFiles = new Map()
91
92
  const testsToBeRetried = new Set()
93
+ const testSuiteAbsolutePathsWithFastCheck = new Set()
92
94
 
93
95
  const BREAKPOINT_HIT_GRACE_PERIOD_MS = 200
94
96
 
@@ -197,10 +199,8 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
197
199
 
198
200
  if (this.isImpactedTestsEnabled) {
199
201
  try {
200
- const hasImpactedTests = Object.keys(modifiedTests).length > 0
201
- this.modifiedTestsForThisSuite = hasImpactedTests
202
- ? this.getModifiedTestForThisSuite(modifiedTests)
203
- : this.getModifiedTestForThisSuite(this.testEnvironmentOptions._ddModifiedTests)
202
+ const hasImpactedTests = Object.keys(modifiedFiles).length > 0
203
+ this.modifiedFiles = hasImpactedTests ? modifiedFiles : this.testEnvironmentOptions._ddModifiedFiles
204
204
  } catch (e) {
205
205
  log.error('Error parsing impacted tests', e)
206
206
  this.isImpactedTestsEnabled = false
@@ -290,19 +290,6 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
290
290
  return result
291
291
  }
292
292
 
293
- getModifiedTestForThisSuite (modifiedTests) {
294
- if (this.modifiedTestsForThisSuite) {
295
- return this.modifiedTestsForThisSuite
296
- }
297
- let modifiedTestsForThisSuite = modifiedTests
298
- // If jest is using workers, modified tests are serialized to json.
299
- // If jest runs in band, they are not.
300
- if (typeof modifiedTestsForThisSuite === 'string') {
301
- modifiedTestsForThisSuite = JSON.parse(modifiedTestsForThisSuite)
302
- }
303
- return modifiedTestsForThisSuite
304
- }
305
-
306
293
  // Generic function to handle test retries
307
294
  retryTest ({
308
295
  jestEvent,
@@ -319,9 +306,13 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
319
306
  }
320
307
  }
321
308
 
309
+ getShouldStripSeedFromTestName () {
310
+ return testSuiteAbsolutePathsWithFastCheck.has(this.testSuiteAbsolutePath)
311
+ }
312
+
322
313
  // At the `add_test` event we don't have the test object yet, so we can't use it
323
314
  getTestNameFromAddTestEvent (event, state) {
324
- const describeSuffix = getJestTestName(state.currentDescribeBlock)
315
+ const describeSuffix = getJestTestName(state.currentDescribeBlock, this.getShouldStripSeedFromTestName())
325
316
  return describeSuffix ? `${describeSuffix} ${event.testName}` : event.testName
326
317
  }
327
318
 
@@ -344,7 +335,7 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
344
335
  })
345
336
  }
346
337
  if (event.name === 'test_start') {
347
- const testName = getJestTestName(event.test)
338
+ const testName = getJestTestName(event.test, this.getShouldStripSeedFromTestName())
348
339
  if (testsToBeRetried.has(testName)) {
349
340
  // This is needed because we're trying tests with the same name
350
341
  this.resetSnapshotState()
@@ -378,7 +369,7 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
378
369
  this.testSourceFile,
379
370
  testStartLine,
380
371
  testEndLine,
381
- this.modifiedTestsForThisSuite,
372
+ this.modifiedFiles,
382
373
  'jest'
383
374
  )
384
375
  }
@@ -407,7 +398,8 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
407
398
  isJestRetry,
408
399
  isDisabled,
409
400
  isQuarantined,
410
- isModified
401
+ isModified,
402
+ testSuiteAbsolutePath: this.testSuiteAbsolutePath
411
403
  }
412
404
  testContexts.set(event.test, ctx)
413
405
 
@@ -465,7 +457,7 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
465
457
  this.testSourceFile,
466
458
  testStartLine,
467
459
  testEndLine,
468
- this.modifiedTestsForThisSuite,
460
+ this.modifiedFiles,
469
461
  'jest'
470
462
  )
471
463
  if (isModified && !retriedTestsToNumAttempts.has(testFullName) && this.isEarlyFlakeDetectionEnabled) {
@@ -506,7 +498,7 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
506
498
  let failedAllTests = false
507
499
  let isAttemptToFix = false
508
500
  if (this.isTestManagementTestsEnabled) {
509
- const testName = getJestTestName(event.test)
501
+ const testName = getJestTestName(event.test, this.getShouldStripSeedFromTestName())
510
502
  isAttemptToFix = this.testManagementTestsForThisSuite?.attemptToFix?.includes(testName)
511
503
  if (isAttemptToFix) {
512
504
  if (attemptToFixRetriedTestsStatuses.has(testName)) {
@@ -534,7 +526,7 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
534
526
  let isEfdRetry = false
535
527
  // We'll store the test statuses of the retries
536
528
  if (this.isKnownTestsEnabled) {
537
- const testName = getJestTestName(event.test)
529
+ const testName = getJestTestName(event.test, this.getShouldStripSeedFromTestName())
538
530
  const isNewTest = retriedTestsToNumAttempts.has(testName)
539
531
  if (isNewTest) {
540
532
  if (newTestsTestStatuses.has(testName)) {
@@ -594,16 +586,17 @@ function getWrappedEnvironment (BaseEnvironment, jestVersion) {
594
586
  }
595
587
  }
596
588
  if (event.name === 'test_skip' || event.name === 'test_todo') {
589
+ const testName = getJestTestName(event.test, this.getShouldStripSeedFromTestName())
597
590
  testSkippedCh.publish({
598
591
  test: {
599
- name: getJestTestName(event.test),
592
+ name: testName,
600
593
  suite: this.testSuite,
601
594
  testSourceFile: this.testSourceFile,
602
595
  displayName: this.displayName,
603
596
  frameworkVersion: jestVersion,
604
597
  testStartLine: getTestLineStart(event.test.asyncError, this.testSuite)
605
598
  },
606
- isDisabled: this.testManagementTestsForThisSuite?.disabled?.includes(getJestTestName(event.test))
599
+ isDisabled: this.testManagementTestsForThisSuite?.disabled?.includes(testName)
607
600
  })
608
601
  }
609
602
  }
@@ -818,11 +811,15 @@ function getCliWrapper (isNewJestVersion) {
818
811
 
819
812
  try {
820
813
  const { err, testManagementTests: receivedTestManagementTests } = await testManagementTestsPromise
821
- if (!err) {
814
+ if (err) {
815
+ isTestManagementTestsEnabled = false
816
+ testManagementTests = {}
817
+ } else {
822
818
  testManagementTests = receivedTestManagementTests
823
819
  }
824
820
  } catch (err) {
825
821
  log.error('Jest test management tests error', err)
822
+ isTestManagementTestsEnabled = false
826
823
  }
827
824
  }
828
825
 
@@ -831,12 +828,12 @@ function getCliWrapper (isNewJestVersion) {
831
828
  onDone = resolve
832
829
  })
833
830
 
834
- impactedTestsCh.publish({ onDone })
831
+ modifiedFilesCh.publish({ onDone })
835
832
 
836
833
  try {
837
- const { err, modifiedTests: receivedModifiedTests } = await impactedTestsPromise
834
+ const { err, modifiedFiles: receivedModifiedFiles } = await impactedTestsPromise
838
835
  if (!err) {
839
- modifiedTests = receivedModifiedTests
836
+ modifiedFiles = receivedModifiedFiles
840
837
  }
841
838
  } catch (err) {
842
839
  log.error('Jest impacted tests error', err)
@@ -1101,7 +1098,8 @@ function jestAdapterWrapper (jestAdapter, jestVersion) {
1101
1098
  testEnvironmentOptions: environment.testEnvironmentOptions,
1102
1099
  testSourceFile: environment.testSourceFile,
1103
1100
  displayName: environment.displayName,
1104
- frameworkVersion: jestVersion
1101
+ frameworkVersion: jestVersion,
1102
+ testSuiteAbsolutePath: environment.testSuiteAbsolutePath
1105
1103
  })
1106
1104
  return adapter.apply(this, arguments).then(suiteResults => {
1107
1105
  const { numFailingTests, skipped, failureMessage: errorMessage } = suiteResults
@@ -1125,12 +1123,17 @@ function jestAdapterWrapper (jestAdapter, jestVersion) {
1125
1123
  const coverageFiles = getFilesWithPath(getCoveredFilenamesFromCoverage(environment.global.__coverage__))
1126
1124
  const mockedFiles = getFilesWithPath(testSuiteMockedFiles.get(environment.testSuiteAbsolutePath) || [])
1127
1125
 
1128
- testSuiteCodeCoverageCh.publish({ coverageFiles, testSuite: environment.testSourceFile, mockedFiles })
1126
+ testSuiteCodeCoverageCh.publish({
1127
+ coverageFiles,
1128
+ testSuite: environment.testSourceFile,
1129
+ mockedFiles,
1130
+ testSuiteAbsolutePath: environment.testSuiteAbsolutePath
1131
+ })
1129
1132
  }
1130
- testSuiteFinishCh.publish({ status, errorMessage })
1133
+ testSuiteFinishCh.publish({ status, errorMessage, testSuiteAbsolutePath: environment.testSuiteAbsolutePath })
1131
1134
  return suiteResults
1132
1135
  }).catch(error => {
1133
- testSuiteFinishCh.publish({ status: 'fail', error })
1136
+ testSuiteFinishCh.publish({ status: 'fail', error, testSuiteAbsolutePath: environment.testSuiteAbsolutePath })
1134
1137
  throw error
1135
1138
  })
1136
1139
  })
@@ -1237,7 +1240,7 @@ addHook({
1237
1240
  _ddIsTestManagementTestsEnabled,
1238
1241
  _ddTestManagementTests,
1239
1242
  _ddTestManagementAttemptToFixRetries,
1240
- _ddModifiedTests,
1243
+ _ddModifiedFiles,
1241
1244
  ...restOfTestEnvironmentOptions
1242
1245
  } = testEnvironmentOptions
1243
1246
 
@@ -1310,12 +1313,49 @@ addHook({
1310
1313
  })
1311
1314
 
1312
1315
  shimmer.wrap(Runtime.prototype, 'requireModuleOrMock', requireModuleOrMock => function (from, moduleName) {
1313
- // TODO: do this for every library that we instrument
1314
- if (LIBRARIES_BYPASSING_JEST_REQUIRE_ENGINE.has(moduleName)) {
1315
- // To bypass jest's own require engine
1316
- return this._requireCoreModule(moduleName)
1316
+ // `requireModuleOrMock` may log errors to the console. If we don't remove ourselves
1317
+ // from the stack trace, the user might see a useless stack trace rather than the error
1318
+ // that `jest` tries to show.
1319
+ const originalPrepareStackTrace = Error.prepareStackTrace
1320
+ Error.prepareStackTrace = function (error, structuredStackTrace) {
1321
+ const filteredStackTrace = structuredStackTrace
1322
+ .filter(callSite => !callSite.getFileName()?.includes('datadog-instrumentations/src/jest.js'))
1323
+
1324
+ return originalPrepareStackTrace(error, filteredStackTrace)
1325
+ }
1326
+ try {
1327
+ // TODO: do this for every library that we instrument
1328
+ if (LIBRARIES_BYPASSING_JEST_REQUIRE_ENGINE.has(moduleName)) {
1329
+ // To bypass jest's own require engine
1330
+ return this._requireCoreModule(moduleName)
1331
+ }
1332
+ // This means that `@fast-check/jest` is used in the test file.
1333
+ if (moduleName === '@fast-check/jest') {
1334
+ testSuiteAbsolutePathsWithFastCheck.add(this._testPath)
1335
+ }
1336
+ const returnedValue = requireModuleOrMock.apply(this, arguments)
1337
+ if (process.exitCode === 1) {
1338
+ if (this.loggedReferenceErrors.size > 0) {
1339
+ const errorMessage = [...this.loggedReferenceErrors][0]
1340
+ testSuiteErrorCh.publish({
1341
+ errorMessage,
1342
+ testSuiteAbsolutePath: this._testPath
1343
+ })
1344
+ } else {
1345
+ testSuiteErrorCh.publish({
1346
+ errorMessage: 'An error occurred while importing a module',
1347
+ testSuiteAbsolutePath: this._testPath
1348
+ })
1349
+ }
1350
+ }
1351
+ return returnedValue
1352
+ } catch (error) {
1353
+ testSuiteErrorCh.publish({ error, testSuiteAbsolutePath: this._testPath })
1354
+ throw error
1355
+ } finally {
1356
+ // Restore original prepareStackTrace
1357
+ Error.prepareStackTrace = originalPrepareStackTrace
1317
1358
  }
1318
- return requireModuleOrMock.apply(this, arguments)
1319
1359
  })
1320
1360
 
1321
1361
  return runtimePackage
@@ -1365,17 +1405,15 @@ function sendWrapper (send) {
1365
1405
 
1366
1406
  const suiteTestManagementTests = testManagementTests?.jest?.suites?.[testSuite]?.tests || {}
1367
1407
 
1368
- const suiteModifiedTests = Object.keys(modifiedTests).length > 0
1369
- ? modifiedTests
1370
- : {}
1371
-
1372
1408
  args[0].config = {
1373
1409
  ...config,
1374
1410
  testEnvironmentOptions: {
1375
1411
  ...config.testEnvironmentOptions,
1376
1412
  _ddKnownTests: suiteKnownTests,
1377
1413
  _ddTestManagementTests: suiteTestManagementTests,
1378
- _ddModifiedTests: suiteModifiedTests
1414
+ // TODO: figure out if we can reduce the size of the modified files object
1415
+ // Can we use `testSuite` (it'd have to be relative to repository root though)
1416
+ _ddModifiedFiles: modifiedFiles
1379
1417
  }
1380
1418
  }
1381
1419
  }
@@ -68,7 +68,7 @@ const skippableSuitesCh = channel('ci:mocha:test-suite:skippable')
68
68
  const mochaGlobalRunCh = channel('ci:mocha:global:run')
69
69
 
70
70
  const testManagementTestsCh = channel('ci:mocha:test-management-tests')
71
- const impactedTestsCh = channel('ci:mocha:modified-tests')
71
+ const modifiedFilesCh = channel('ci:mocha:modified-files')
72
72
  const workerReportTraceCh = channel('ci:mocha:worker-report:trace')
73
73
  const testSessionStartCh = channel('ci:mocha:session:start')
74
74
  const testSessionFinishCh = channel('ci:mocha:session:finish')
@@ -233,12 +233,12 @@ function getExecutionConfiguration (runner, isParallel, frameworkVersion, onFini
233
233
  })
234
234
  }
235
235
 
236
- const onReceivedImpactedTests = ({ err, modifiedTests: receivedModifiedTests }) => {
236
+ const onReceivedImpactedTests = ({ err, modifiedFiles: receivedModifiedFiles }) => {
237
237
  if (err) {
238
- config.modifiedTests = []
238
+ config.modifiedFiles = []
239
239
  config.isImpactedTestsEnabled = false
240
240
  } else {
241
- config.modifiedTests = receivedModifiedTests
241
+ config.modifiedFiles = receivedModifiedFiles
242
242
  }
243
243
  if (config.isSuitesSkippingEnabled) {
244
244
  ctx.onDone = onReceivedSkippableSuites
@@ -260,7 +260,7 @@ function getExecutionConfiguration (runner, isParallel, frameworkVersion, onFini
260
260
  }
261
261
  if (config.isImpactedTestsEnabled) {
262
262
  ctx.onDone = onReceivedImpactedTests
263
- impactedTestsCh.runStores(ctx, () => {})
263
+ modifiedFilesCh.runStores(ctx, () => {})
264
264
  } else if (config.isSuitesSkippingEnabled) {
265
265
  ctx.onDone = onReceivedSkippableSuites
266
266
  skippableSuitesCh.runStores(ctx, () => {})
@@ -284,7 +284,7 @@ function getExecutionConfiguration (runner, isParallel, frameworkVersion, onFini
284
284
  testManagementTestsCh.runStores(ctx, () => {})
285
285
  } if (config.isImpactedTestsEnabled) {
286
286
  ctx.onDone = onReceivedImpactedTests
287
- impactedTestsCh.runStores(ctx, () => {})
287
+ modifiedFilesCh.runStores(ctx, () => {})
288
288
  } else if (config.isSuitesSkippingEnabled) {
289
289
  ctx.onDone = onReceivedSkippableSuites
290
290
  skippableSuitesCh.runStores(ctx, () => {})
@@ -321,7 +321,7 @@ function getExecutionConfiguration (runner, isParallel, frameworkVersion, onFini
321
321
  testManagementTestsCh.runStores(ctx, () => {})
322
322
  } else if (config.isImpactedTestsEnabled) {
323
323
  ctx.onDone = onReceivedImpactedTests
324
- impactedTestsCh.runStores(ctx, () => {})
324
+ modifiedFilesCh.runStores(ctx, () => {})
325
325
  } else if (config.isSuitesSkippingEnabled) {
326
326
  ctx.onDone = onReceivedSkippableSuites
327
327
  skippableSuitesCh.runStores(ctx, () => {})
@@ -696,9 +696,8 @@ addHook({
696
696
  }
697
697
 
698
698
  if (config.isImpactedTestsEnabled) {
699
- const testSuiteImpactedTests = config.modifiedTests || {}
700
699
  newWorkerArgs._ddIsImpactedTestsEnabled = true
701
- newWorkerArgs._ddModifiedTests = testSuiteImpactedTests
700
+ newWorkerArgs._ddModifiedFiles = config.modifiedFiles || {}
702
701
  }
703
702
 
704
703
  // We pass the known tests for the test file to the worker
@@ -163,14 +163,13 @@ function runnableWrapper (RunnablePackage, libraryConfig) {
163
163
  const ctx = getTestContext(test)
164
164
 
165
165
  if (ctx) {
166
- const originalFn = this.fn
167
166
  // we bind the test fn to the correct context
168
- const newFn = function () {
167
+ const newFn = shimmer.wrapFunction(this.fn, originalFn => function () {
169
168
  return testFnCh.runStores(ctx, () => originalFn.apply(this, arguments))
170
- }
169
+ })
171
170
 
172
171
  // we store the original function, not to lose it
173
- originalFns.set(newFn, originalFn)
172
+ originalFns.set(newFn, this.fn)
174
173
  this.fn = newFn
175
174
 
176
175
  wrappedFunctions.add(this.fn)
@@ -446,7 +445,7 @@ function getRunTestsWrapper (runTests, config) {
446
445
  if (config.isImpactedTestsEnabled) {
447
446
  suite.tests.forEach((test) => {
448
447
  isModifiedCh.publish({
449
- modifiedTests: config.modifiedTests,
448
+ modifiedFiles: config.modifiedFiles,
450
449
  file: suite.file,
451
450
  onDone: (isModified) => {
452
451
  if (isModified) {
@@ -36,9 +36,9 @@ addHook({
36
36
  }
37
37
  if (this.options._ddIsImpactedTestsEnabled) {
38
38
  config.isImpactedTestsEnabled = true
39
- config.modifiedTests = this.options._ddModifiedTests
39
+ config.modifiedFiles = this.options._ddModifiedFiles
40
40
  delete this.options._ddIsImpactedTestsEnabled
41
- delete this.options._ddModifiedTests
41
+ delete this.options._ddModifiedFiles
42
42
  }
43
43
  if (this.options._ddIsTestManagementTestsEnabled) {
44
44
  config.isTestManagementTestsEnabled = true
@@ -20,7 +20,7 @@ addHook({ name: 'pg', versions: ['>=8.0.3'], file: 'lib/native/client.js' }, Cli
20
20
  return Client
21
21
  })
22
22
 
23
- addHook({ name: 'pg', versions: ['>=8.0.3 <8.15.0', '>=8.15.0 <9'], file: 'lib/client.js' }, Client => {
23
+ addHook({ name: 'pg', versions: ['>=8.0.3'], file: 'lib/client.js' }, Client => {
24
24
  shimmer.wrap(Client.prototype, 'query', query => wrapQuery(query))
25
25
  return Client
26
26
  })
@@ -21,7 +21,7 @@ const testSessionFinishCh = channel('ci:playwright:session:finish')
21
21
  const libraryConfigurationCh = channel('ci:playwright:library-configuration')
22
22
  const knownTestsCh = channel('ci:playwright:known-tests')
23
23
  const testManagementTestsCh = channel('ci:playwright:test-management-tests')
24
- const impactedTestsCh = channel('ci:playwright:modified-tests')
24
+ const modifiedFilesCh = channel('ci:playwright:modified-files')
25
25
  const isModifiedCh = channel('ci:playwright:test:is-modified')
26
26
 
27
27
  const testSuiteStartCh = channel('ci:playwright:test-suite:start')
@@ -59,7 +59,7 @@ let isTestManagementTestsEnabled = false
59
59
  let testManagementAttemptToFixRetries = 0
60
60
  let testManagementTests = {}
61
61
  let isImpactedTestsEnabled = false
62
- let modifiedTests = {}
62
+ let modifiedFiles = {}
63
63
  const quarantinedOrDisabledTestsAttemptToFix = []
64
64
  let quarantinedButNotAttemptToFixFqns = new Set()
65
65
  let rootDir = ''
@@ -593,11 +593,11 @@ function runAllTestsWrapper (runAllTests, playwrightVersion) {
593
593
 
594
594
  if (isImpactedTestsEnabled && satisfies(playwrightVersion, MINIMUM_SUPPORTED_VERSION_RANGE_EFD)) {
595
595
  try {
596
- const { err, modifiedTests: receivedModifiedTests } = await getChannelPromise(impactedTestsCh)
596
+ const { err, modifiedFiles: receivedModifiedFiles } = await getChannelPromise(modifiedFilesCh)
597
597
  if (err) {
598
598
  isImpactedTestsEnabled = false
599
599
  } else {
600
- modifiedTests = receivedModifiedTests
600
+ modifiedFiles = receivedModifiedFiles
601
601
  }
602
602
  } catch (err) {
603
603
  isImpactedTestsEnabled = false
@@ -819,7 +819,7 @@ addHook({
819
819
  await Promise.all(allTests.map(async (test) => {
820
820
  const { isModified } = await getChannelPromise(isModifiedCh, {
821
821
  filePath: test._requireFile,
822
- modifiedTests
822
+ modifiedFiles
823
823
  })
824
824
  if (isModified) {
825
825
  test._ddIsModified = true
@@ -32,7 +32,7 @@ const libraryConfigurationCh = channel('ci:vitest:library-configuration')
32
32
  const knownTestsCh = channel('ci:vitest:known-tests')
33
33
  const isEarlyFlakeDetectionFaultyCh = channel('ci:vitest:is-early-flake-detection-faulty')
34
34
  const testManagementTestsCh = channel('ci:vitest:test-management-tests')
35
- const impactedTestsCh = channel('ci:vitest:modified-tests')
35
+ const modifiedFilesCh = channel('ci:vitest:modified-files')
36
36
 
37
37
  const workerReportTraceCh = channel('ci:vitest:worker-report:trace')
38
38
  const workerReportLogsCh = channel('ci:vitest:worker-report:logs')
@@ -92,7 +92,7 @@ function getProvidedContext () {
92
92
  _ddTestManagementTests: testManagementTests,
93
93
  _ddIsFlakyTestRetriesEnabled: isFlakyTestRetriesEnabled,
94
94
  _ddIsImpactedTestsEnabled: isImpactedTestsEnabled,
95
- _ddModifiedTests: modifiedTests
95
+ _ddModifiedFiles: modifiedFiles
96
96
  } = globalThis.__vitest_worker__.providedContext
97
97
 
98
98
  return {
@@ -106,7 +106,7 @@ function getProvidedContext () {
106
106
  testManagementTests,
107
107
  isFlakyTestRetriesEnabled,
108
108
  isImpactedTestsEnabled,
109
- modifiedTests
109
+ modifiedFiles
110
110
  }
111
111
  } catch {
112
112
  log.error('Vitest workers could not parse provided context, so some features will not work.')
@@ -121,7 +121,7 @@ function getProvidedContext () {
121
121
  testManagementTests: {},
122
122
  isFlakyTestRetriesEnabled: false,
123
123
  isImpactedTestsEnabled: false,
124
- modifiedTests: {}
124
+ modifiedFiles: {}
125
125
  }
126
126
  }
127
127
  }
@@ -316,14 +316,14 @@ function getSortWrapper (sort, frameworkVersion) {
316
316
  }
317
317
 
318
318
  if (isImpactedTestsEnabled) {
319
- const { err, modifiedTests } = await getChannelPromise(impactedTestsCh)
319
+ const { err, modifiedFiles } = await getChannelPromise(modifiedFilesCh)
320
320
  if (err) {
321
321
  log.error('Could not get modified tests.')
322
322
  } else {
323
323
  try {
324
324
  const workspaceProject = this.ctx.getCoreWorkspaceProject()
325
325
  workspaceProject._provided._ddIsImpactedTestsEnabled = isImpactedTestsEnabled
326
- workspaceProject._provided._ddModifiedTests = modifiedTests
326
+ workspaceProject._provided._ddModifiedFiles = modifiedFiles
327
327
  } catch {
328
328
  log.warn('Could not send modified tests to workers so Impacted Tests will not work.')
329
329
  }
@@ -464,7 +464,7 @@ addHook({
464
464
  testManagementAttemptToFixRetries,
465
465
  testManagementTests,
466
466
  isImpactedTestsEnabled,
467
- modifiedTests
467
+ modifiedFiles
468
468
  } = getProvidedContext()
469
469
 
470
470
  if (isTestManagementTestsEnabled) {
@@ -499,7 +499,7 @@ addHook({
499
499
 
500
500
  if (isImpactedTestsEnabled) {
501
501
  isModifiedCh.publish({
502
- modifiedTests,
502
+ modifiedFiles,
503
503
  testSuiteAbsolutePath: task.file.filepath,
504
504
  onDone: (isImpacted) => {
505
505
  if (isImpacted) {
@@ -10,7 +10,7 @@ class AmqplibConsumerPlugin extends ConsumerPlugin {
10
10
  static operation = 'consume'
11
11
 
12
12
  bindStart (ctx) {
13
- const { method, fields, message, queue } = ctx
13
+ const { method, fields = {}, message, queue } = ctx
14
14
 
15
15
  if (method !== 'basic.deliver' && method !== 'basic.get') return
16
16
 
@@ -53,10 +53,13 @@ function extractTextAndResponseReasonFromStream (chunks, modelProvider, modelNam
53
53
 
54
54
  switch (modelProviderUpper) {
55
55
  case PROVIDER.AMAZON: {
56
- message += body?.outputText
57
-
58
- inputTokens = body?.inputTextTokenCount
59
- outputTokens = body?.totalOutputTextTokenCount
56
+ if (body?.outputText) {
57
+ message += body?.outputText
58
+ inputTokens = body?.inputTextTokenCount
59
+ outputTokens = body?.totalOutputTextTokenCount
60
+ } else if (body?.contentBlockDelta?.delta?.text) {
61
+ message += body.contentBlockDelta.delta.text
62
+ }
60
63
 
61
64
  break
62
65
  }
@@ -155,17 +158,16 @@ class RequestParams {
155
158
  stream = '',
156
159
  n
157
160
  } = {}) {
158
- // stringify prompt as it could be a single prompt as well as a list of message objects
159
- this.prompt = typeof prompt === 'string' ? prompt : JSON.stringify(prompt) || ''
160
- this.temperature = temperature === undefined ? undefined : temperature
161
- this.topP = topP === undefined ? undefined : topP
162
- this.topK = topK === undefined ? undefined : topK
163
- this.maxTokens = maxTokens === undefined ? undefined : maxTokens
161
+ this.prompt = prompt
162
+ this.temperature = temperature
163
+ this.topP = topP
164
+ this.topK = topK
165
+ this.maxTokens = maxTokens
164
166
  this.stopSequences = stopSequences || []
165
167
  this.inputType = inputType || ''
166
168
  this.truncate = truncate || ''
167
169
  this.stream = stream || ''
168
- this.n = n === undefined ? undefined : n
170
+ this.n = n
169
171
  }
170
172
  }
171
173
 
@@ -234,17 +236,48 @@ function extractRequestParams (params, provider) {
234
236
  })
235
237
  }
236
238
  case PROVIDER.AMAZON: {
239
+ const prompt = requestBody.inputText
237
240
  if (modelId.includes('embed')) {
238
- return new RequestParams({ prompt: requestBody.inputText })
241
+ return new RequestParams({ prompt })
242
+ } else if (prompt !== undefined) {
243
+ const textGenerationConfig = requestBody.textGenerationConfig || {}
244
+ return new RequestParams({
245
+ prompt,
246
+ temperature: textGenerationConfig.temperature,
247
+ topP: textGenerationConfig.topP,
248
+ maxTokens: textGenerationConfig.maxTokenCount,
249
+ stopSequences: textGenerationConfig.stopSequences
250
+ })
251
+ } else if (Array.isArray(requestBody.messages)) {
252
+ const inferenceConfig = requestBody.inferenceConfig || {}
253
+ const messages = []
254
+ if (Array.isArray(requestBody.system)) {
255
+ for (const sysMsg of requestBody.system) {
256
+ messages.push({
257
+ content: sysMsg.text,
258
+ role: 'system'
259
+ })
260
+ }
261
+ }
262
+ for (const message of requestBody.messages) {
263
+ const textBlocks = message.content?.filter(block => block.text) || []
264
+ if (textBlocks.length > 0) {
265
+ messages.push({
266
+ content: textBlocks.map(block => block.text).join(''),
267
+ role: message.role
268
+ })
269
+ }
270
+ }
271
+ return new RequestParams({
272
+ prompt: messages,
273
+ temperature: inferenceConfig.temperature,
274
+ topP: inferenceConfig.topP,
275
+ maxTokens: inferenceConfig.maxTokens,
276
+ stopSequences: inferenceConfig.stopSequences
277
+ })
239
278
  }
240
- const textGenerationConfig = requestBody.textGenerationConfig || {}
241
- return new RequestParams({
242
- prompt: requestBody.inputText,
243
- temperature: textGenerationConfig.temperature,
244
- topP: textGenerationConfig.topP,
245
- maxTokens: textGenerationConfig.maxTokenCount,
246
- stopSequences: textGenerationConfig.stopSequences
247
- })
279
+
280
+ return new RequestParams({ prompt })
248
281
  }
249
282
  case PROVIDER.ANTHROPIC: {
250
283
  let prompt = requestBody.prompt
@@ -350,14 +383,27 @@ function extractTextAndResponseReason (response, provider, modelName) {
350
383
  if (modelName.includes('embed')) {
351
384
  return new Generation({ message: body.embedding })
352
385
  }
353
- const results = body.results || []
354
- if (results.length > 0) {
355
- const result = results[0]
386
+ if (body.results) {
387
+ const results = body.results || []
388
+ if (results.length > 0) {
389
+ const result = results[0]
390
+ return new Generation({
391
+ message: result.outputText,
392
+ finishReason: result.completionReason,
393
+ inputTokens: body.inputTextTokenCount,
394
+ outputTokens: result.tokenCount
395
+ })
396
+ }
397
+ } else if (body.output) {
398
+ const output = body.output || {}
356
399
  return new Generation({
357
- message: result.outputText,
358
- finishReason: result.completionReason,
359
- inputTokens: body.inputTextTokenCount,
360
- outputTokens: result.tokenCount
400
+ message: output.message?.content[0]?.text ?? 'Unsupported content type',
401
+ finishReason: body.stopReason,
402
+ role: output.message?.role,
403
+ inputTokens: body.usage?.inputTokens,
404
+ outputTokens: body.usage?.outputTokens,
405
+ cacheReadInputTokenCount: body.usage?.cacheReadInputTokenCount,
406
+ cacheWriteInputTokenCount: body.usage?.cacheWriteInputTokenCount
361
407
  })
362
408
  }
363
409
  break