dd-trace 5.117.0 → 5.118.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/ci/diagnose.js +162 -21
- package/ci/init.js +0 -1
- package/ci/runbook.md +187 -180
- package/ci/test-optimization-validation/approval-artifacts.js +3 -1
- package/ci/test-optimization-validation/approval.js +52 -15
- package/ci/test-optimization-validation/ci-command-candidate.js +26 -32
- package/ci/test-optimization-validation/ci-discovery.js +1 -1
- package/ci/test-optimization-validation/ci-package-scripts.js +141 -0
- package/ci/test-optimization-validation/ci-remediation.js +112 -39
- package/ci/test-optimization-validation/cli.js +516 -681
- package/ci/test-optimization-validation/command-blocker.js +188 -33
- package/ci/test-optimization-validation/command-output-policy.js +3 -26
- package/ci/test-optimization-validation/command-runner.js +189 -245
- package/ci/test-optimization-validation/environment.js +90 -0
- package/ci/test-optimization-validation/executable.js +159 -388
- package/ci/test-optimization-validation/framework-adapters/cucumber.js +119 -0
- package/ci/test-optimization-validation/framework-adapters/cypress.js +107 -0
- package/ci/test-optimization-validation/framework-adapters/playwright.js +181 -0
- package/ci/test-optimization-validation/generated-files.js +75 -13
- package/ci/test-optimization-validation/generated-test-contract.js +283 -0
- package/ci/test-optimization-validation/generated-verifier.js +49 -16
- package/ci/test-optimization-validation/literal-environment.js +57 -0
- package/ci/test-optimization-validation/manifest-loader.js +2 -22
- package/ci/test-optimization-validation/manifest-scaffold.js +816 -515
- package/ci/test-optimization-validation/manifest-schema.js +494 -702
- package/ci/test-optimization-validation/offline-fixtures.js +4 -1
- package/ci/test-optimization-validation/plan-writer.js +243 -984
- package/ci/test-optimization-validation/preflight-runner.js +49 -55
- package/ci/test-optimization-validation/redaction.js +2 -1
- package/ci/test-optimization-validation/report-writer.js +391 -1357
- package/ci/test-optimization-validation/result-semantics.js +86 -0
- package/ci/test-optimization-validation/runner-command.js +249 -0
- package/ci/test-optimization-validation/runner-contract.js +664 -0
- package/ci/test-optimization-validation/scenarios/auto-test-retries.js +29 -3
- package/ci/test-optimization-validation/scenarios/basic-reporting.js +240 -543
- package/ci/test-optimization-validation/scenarios/ci-wiring.js +450 -670
- package/ci/test-optimization-validation/scenarios/early-flake-detection.js +4 -3
- package/ci/test-optimization-validation/scenarios/helpers.js +67 -9
- package/ci/test-optimization-validation/scenarios/test-management.js +4 -3
- package/ci/test-optimization-validation/source-text.js +87 -0
- package/ci/test-optimization-validation/test-output.js +12 -22
- package/ext/tags.d.ts +1 -0
- package/index.d.ts +7 -0
- package/package.json +2 -2
- package/packages/datadog-instrumentations/src/helpers/hooks.js +2 -0
- package/packages/datadog-instrumentations/src/helpers/rewriter/instrumentations/index.js +1 -0
- package/packages/datadog-instrumentations/src/helpers/rewriter/instrumentations/openai-agents.js +31 -0
- package/packages/datadog-instrumentations/src/openai-agents.js +159 -0
- package/packages/datadog-plugin-openai-agents/src/index.js +74 -0
- package/packages/datadog-plugin-openai-agents/src/integration.js +503 -0
- package/packages/datadog-plugin-openai-agents/src/processor.js +108 -0
- package/packages/datadog-plugin-openai-agents/src/util.js +60 -0
- package/packages/dd-trace/src/ci-visibility/exporters/ci-visibility-exporter.js +48 -49
- package/packages/dd-trace/src/ci-visibility/requests/get-library-configuration.js +161 -33
- package/packages/dd-trace/src/ci-visibility/test-optimization-http-cache-schema.js +6 -4
- package/packages/dd-trace/src/config/generated-config-types.d.ts +2 -0
- package/packages/dd-trace/src/config/supported-configurations.json +7 -0
- package/packages/dd-trace/src/encode/span-stats.js +7 -1
- package/packages/dd-trace/src/exporter.js +16 -9
- package/packages/dd-trace/src/llmobs/index.js +9 -1
- package/packages/dd-trace/src/llmobs/plugins/ai/util.js +104 -22
- package/packages/dd-trace/src/llmobs/plugins/openai/index.js +5 -9
- package/packages/dd-trace/src/llmobs/plugins/openai/utils.js +20 -0
- package/packages/dd-trace/src/llmobs/plugins/openai-agents/utils.js +321 -0
- package/packages/dd-trace/src/llmobs/sdk.js +2 -1
- package/packages/dd-trace/src/llmobs/span_processor.js +7 -2
- package/packages/dd-trace/src/llmobs/tagger.js +23 -3
- package/packages/dd-trace/src/llmobs/util.js +56 -3
- package/packages/dd-trace/src/openfeature/agentless_configuration_source.js +3 -6
- package/packages/dd-trace/src/openfeature/configuration_source.js +5 -8
- package/packages/dd-trace/src/opentelemetry/metrics/otlp_span_stats_transformer.js +5 -1
- package/packages/dd-trace/src/plugins/ci_plugin.js +9 -3
- package/packages/dd-trace/src/plugins/index.js +1 -0
- package/packages/dd-trace/src/plugins/outbound.js +4 -1
- package/packages/dd-trace/src/span_processor.js +1 -1
- package/packages/dd-trace/src/span_stats.js +22 -4
- package/ci/test-optimization-validation/command-suitability.js +0 -471
- package/ci/test-optimization-validation/init-probe-preload.js +0 -163
- package/ci/test-optimization-validation/init-probe.js +0 -246
- package/ci/test-optimization-validation/late-initialization.js +0 -63
- package/ci/test-optimization-validation/local-command.js +0 -163
- package/ci/test-optimization-validation/setup-runner.js +0 -97
- package/ci/test-optimization-validation-manifest.schema.json +0 -1
package/ci/diagnose.js
CHANGED
|
@@ -34,6 +34,7 @@ const SKIPPED_DIRECTORIES = new Set([
|
|
|
34
34
|
'.yarn',
|
|
35
35
|
'build',
|
|
36
36
|
'coverage',
|
|
37
|
+
'dd-test-optimization-validation-results',
|
|
37
38
|
'dist',
|
|
38
39
|
'node_modules',
|
|
39
40
|
'out',
|
|
@@ -90,6 +91,14 @@ const WATCH_MODE_RE = /(?:^|\s)(?:watch|--watch|--watchAll)(?!(?:=false)(?:\s|$)
|
|
|
90
91
|
const CYPRESS_MANUAL_PLUGIN_RE = /dd-trace\/ci\/cypress\/(?:plugin|after-run|after-spec)\b/
|
|
91
92
|
const CYPRESS_SUPPORT_RE = /dd-trace\/ci\/cypress\/support\b/
|
|
92
93
|
const CYPRESS_SUPPORT_DISABLED_RE = /supportFile\s*:\s*false|"supportFile"\s*:\s*false/
|
|
94
|
+
const CUCUMBER_RUNNER_COMMAND_RE = new RegExp(
|
|
95
|
+
String.raw`(?:^|(?:&&|\|\||[;|])\s*)` +
|
|
96
|
+
String.raw`(?:(?:[A-Za-z_][A-Za-z0-9_]*=(?:"[^"]*"|'[^']*'|[^\s;&|]+)|` +
|
|
97
|
+
String.raw`cross-env|env|npx|nyc|c8|npm\s+exec|pnpm\s+exec|yarn\s+exec|--?[^\s;&|]+)\s+)*` +
|
|
98
|
+
String.raw`(?:(?:[^\s"';&|]+[\/\\])?(?:cucumber-js(?:\.cmd)?|cucumber(?:\.cmd)?)|` +
|
|
99
|
+
String.raw`node(?:\.exe)?\s+(?:[^\s"';&|]+[\/\\])?bin[\/\\]cucumber\.js)` +
|
|
100
|
+
String.raw`(?=$|[\s"';&|])`
|
|
101
|
+
)
|
|
93
102
|
const CUCUMBER_PARALLEL_RE =
|
|
94
103
|
/\bcucumber(?:-js)?\b[\s\S]{0,200}\s--parallel\b|--parallel\b[\s\S]{0,200}\bcucumber(?:-js)?\b/
|
|
95
104
|
const JEST_FORCE_EXIT_RE = /\bforceExit\s*:\s*true\b|--forceExit\b|"forceExit"\s*:\s*true/
|
|
@@ -123,9 +132,8 @@ function getFrameworkDefinitions (ddMajor) {
|
|
|
123
132
|
commandPatterns: [/\bjest\b/],
|
|
124
133
|
configPatterns: [/^jest\.config\./, /^config-jest\./],
|
|
125
134
|
supportedRange: ddMajor >= 6 ? '>=28.0.0' : '>=24.8.0',
|
|
126
|
-
recommendation:
|
|
127
|
-
|
|
128
|
-
: 'Upgrade Jest to >=24.8.0.',
|
|
135
|
+
recommendation: 'Use a Jest and dd-trace combination whose documented support ranges overlap; this ' +
|
|
136
|
+
`dd-trace version requires Jest ${ddMajor >= 6 ? '>=28.0.0' : '>=24.8.0'}.`,
|
|
129
137
|
},
|
|
130
138
|
{
|
|
131
139
|
id: 'mocha',
|
|
@@ -134,9 +142,8 @@ function getFrameworkDefinitions (ddMajor) {
|
|
|
134
142
|
commandPatterns: [/\bmocha\b/],
|
|
135
143
|
configPatterns: [/^\.mocharc\./],
|
|
136
144
|
supportedRange: ddMajor >= 6 ? '>=8.0.0' : '>=5.2.0',
|
|
137
|
-
recommendation:
|
|
138
|
-
|
|
139
|
-
: 'Upgrade Mocha to >=5.2.0.',
|
|
145
|
+
recommendation: 'Use a Mocha and dd-trace combination whose documented support ranges overlap; this ' +
|
|
146
|
+
`dd-trace version requires Mocha ${ddMajor >= 6 ? '>=8.0.0' : '>=5.2.0'}.`,
|
|
140
147
|
notes: [
|
|
141
148
|
'Impacted tests are detected at suite level for Mocha.',
|
|
142
149
|
],
|
|
@@ -145,7 +152,7 @@ function getFrameworkDefinitions (ddMajor) {
|
|
|
145
152
|
id: 'cucumber',
|
|
146
153
|
name: 'Cucumber',
|
|
147
154
|
packages: ['@cucumber/cucumber'],
|
|
148
|
-
commandPatterns: [
|
|
155
|
+
commandPatterns: [CUCUMBER_RUNNER_COMMAND_RE],
|
|
149
156
|
configPatterns: [/^cucumber\./],
|
|
150
157
|
supportedRange: '>=7.0.0',
|
|
151
158
|
recommendation: 'Upgrade @cucumber/cucumber to >=7.0.0.',
|
|
@@ -158,9 +165,8 @@ function getFrameworkDefinitions (ddMajor) {
|
|
|
158
165
|
configPatterns: [/^cypress\.config\./, /^cypress\.json$/],
|
|
159
166
|
supportedRange: ddMajor >= 6 ? '>=12.0.0' : '>=6.7.0',
|
|
160
167
|
autoInstrumentationRange: ddMajor >= 6 ? '>=12.0.0' : '>=10.2.0',
|
|
161
|
-
recommendation:
|
|
162
|
-
|
|
163
|
-
: 'Upgrade Cypress to >=6.7.0.',
|
|
168
|
+
recommendation: 'Use a Cypress and dd-trace combination whose documented support ranges overlap; this ' +
|
|
169
|
+
`dd-trace version requires Cypress ${ddMajor >= 6 ? '>=12.0.0' : '>=6.7.0'}.`,
|
|
164
170
|
},
|
|
165
171
|
{
|
|
166
172
|
id: 'playwright',
|
|
@@ -169,9 +175,8 @@ function getFrameworkDefinitions (ddMajor) {
|
|
|
169
175
|
commandPatterns: [/\bplaywright\s+test\b/],
|
|
170
176
|
configPatterns: [/^playwright\.config\./],
|
|
171
177
|
supportedRange: ddMajor >= 6 ? '>=1.38.0' : '>=1.18.0',
|
|
172
|
-
recommendation:
|
|
173
|
-
|
|
174
|
-
: 'Upgrade Playwright to >=1.18.0.',
|
|
178
|
+
recommendation: 'Use a Playwright and dd-trace combination whose documented support ranges overlap; this ' +
|
|
179
|
+
`dd-trace version requires Playwright ${ddMajor >= 6 ? '>=1.38.0' : '>=1.18.0'}.`,
|
|
175
180
|
notes: [
|
|
176
181
|
'Test Impact Analysis suite skipping is not supported for Playwright.',
|
|
177
182
|
'Impacted tests are detected at suite level for Playwright.',
|
|
@@ -199,7 +204,7 @@ const UNSUPPORTED_FRAMEWORKS = [
|
|
|
199
204
|
id: 'node-test',
|
|
200
205
|
name: 'Node.js test runner',
|
|
201
206
|
packages: [],
|
|
202
|
-
commandPatterns: [/\bnode\s+--test\b/, /\bnode\s+--experimental-test-coverage\b/],
|
|
207
|
+
commandPatterns: [/\bnode\s+--test\b/, /\bnode\s+--experimental-test-coverage\b/, /\bbnt\b/],
|
|
203
208
|
},
|
|
204
209
|
{ id: 'ava', name: 'AVA', packages: ['ava'], commandPatterns: [/\bava\b/] },
|
|
205
210
|
{ id: 'tap', name: 'tap', packages: ['tap'], commandPatterns: [/\btap\b/] },
|
|
@@ -1106,9 +1111,13 @@ function collectScripts (manifests) {
|
|
|
1106
1111
|
*/
|
|
1107
1112
|
function detectSupportedFrameworks (root, definitions, manifests, scripts, textFiles) {
|
|
1108
1113
|
const frameworks = []
|
|
1114
|
+
const projectPreferenceScores = getProjectPreferenceScores(root, manifests)
|
|
1109
1115
|
|
|
1110
1116
|
for (const definition of definitions) {
|
|
1111
|
-
const dependencyEntries =
|
|
1117
|
+
const dependencyEntries = [
|
|
1118
|
+
...findDependencyEntries(manifests, definition.packages),
|
|
1119
|
+
...findPackageIdentityEntries(manifests, definition.packages),
|
|
1120
|
+
]
|
|
1112
1121
|
const scriptMatches = findScriptMatches(scripts, definition.commandPatterns)
|
|
1113
1122
|
const configMatches = findConfigMatches(textFiles, definition.configPatterns)
|
|
1114
1123
|
|
|
@@ -1119,6 +1128,7 @@ function detectSupportedFrameworks (root, definitions, manifests, scripts, textF
|
|
|
1119
1128
|
dependencyEntries,
|
|
1120
1129
|
scriptMatches,
|
|
1121
1130
|
configMatches,
|
|
1131
|
+
projectPreferenceScores,
|
|
1122
1132
|
locations: unique([
|
|
1123
1133
|
...dependencyEntries.map(entry => entry.relativePath),
|
|
1124
1134
|
...scriptMatches.map(script => script.relativePath),
|
|
@@ -1193,23 +1203,117 @@ function getSupportedVersionDetection (framework, relativePath) {
|
|
|
1193
1203
|
* @returns {object|undefined} eligible command match
|
|
1194
1204
|
*/
|
|
1195
1205
|
function getEligibleCommandMatch (framework) {
|
|
1196
|
-
const scriptMatches = framework.scriptMatches || []
|
|
1206
|
+
const scriptMatches = [...(framework.scriptMatches || [])].sort((left, right) => {
|
|
1207
|
+
return compareProjectScope(left, right, framework.projectPreferenceScores) ||
|
|
1208
|
+
getFrameworkCommandPreference(framework.id, left) - getFrameworkCommandPreference(framework.id, right) ||
|
|
1209
|
+
left.relativePath.localeCompare(right.relativePath)
|
|
1210
|
+
})
|
|
1197
1211
|
|
|
1198
1212
|
for (const script of scriptMatches) {
|
|
1199
1213
|
if (isIneligibleFrameworkCommand(framework.id, script.command)) continue
|
|
1200
1214
|
return script
|
|
1201
1215
|
}
|
|
1202
1216
|
|
|
1203
|
-
if (
|
|
1204
|
-
|
|
1205
|
-
|
|
1206
|
-
|
|
1217
|
+
if (framework.id === 'cucumber' || framework.id === 'cypress' || framework.id === 'jest' ||
|
|
1218
|
+
framework.id === 'mocha' || framework.id === 'playwright' || framework.id === 'vitest') {
|
|
1219
|
+
const dependencyEntries = [...(framework.dependencyEntries || [])].sort((left, right) => {
|
|
1220
|
+
return compareProjectPreference(left, right, framework.projectPreferenceScores)
|
|
1221
|
+
})
|
|
1222
|
+
return dependencyEntries[0] && {
|
|
1207
1223
|
command: `direct ${framework.id} binary`,
|
|
1208
|
-
relativePath:
|
|
1224
|
+
relativePath: dependencyEntries[0].relativePath,
|
|
1209
1225
|
}
|
|
1210
1226
|
}
|
|
1211
1227
|
}
|
|
1212
1228
|
|
|
1229
|
+
/**
|
|
1230
|
+
* Prefers direct, single-stage framework scripts over aggregate coverage or setup chains.
|
|
1231
|
+
*
|
|
1232
|
+
* @param {string} frameworkId framework id
|
|
1233
|
+
* @param {object} script package script
|
|
1234
|
+
* @returns {number} lower is preferred
|
|
1235
|
+
*/
|
|
1236
|
+
function getFrameworkCommandPreference (frameworkId, script) {
|
|
1237
|
+
let score = 0
|
|
1238
|
+
if (/coverage|all|full/i.test(script.name)) score += 4
|
|
1239
|
+
if (/[\r\n;&|`]|\$\(/.test(script.command)) score += 4
|
|
1240
|
+
const invokesFramework = frameworkId === 'cucumber'
|
|
1241
|
+
? isCucumberRunnerCommand(script.command)
|
|
1242
|
+
: script.command.toLowerCase().includes(frameworkId.toLowerCase())
|
|
1243
|
+
if (invokesFramework) score--
|
|
1244
|
+
return score
|
|
1245
|
+
}
|
|
1246
|
+
|
|
1247
|
+
/**
|
|
1248
|
+
* Scores package manifests by how closely their names match the repository directory name.
|
|
1249
|
+
*
|
|
1250
|
+
* @param {string} root repository root
|
|
1251
|
+
* @param {Array<object>} manifests package manifests
|
|
1252
|
+
* @returns {Map<string, number>} preference score by package.json path
|
|
1253
|
+
*/
|
|
1254
|
+
function getProjectPreferenceScores (root, manifests) {
|
|
1255
|
+
const repositoryTokens = getIdentityTokens(path.basename(root))
|
|
1256
|
+
const scores = new Map()
|
|
1257
|
+
|
|
1258
|
+
for (const manifest of manifests) {
|
|
1259
|
+
const projectName = manifest.json.name || (manifest.relativePath === 'package.json'
|
|
1260
|
+
? path.basename(root)
|
|
1261
|
+
: path.basename(path.dirname(manifest.relativePath)))
|
|
1262
|
+
const projectTokens = getIdentityTokens(projectName)
|
|
1263
|
+
let score = 0
|
|
1264
|
+
for (const token of projectTokens) {
|
|
1265
|
+
if (repositoryTokens.has(token)) score++
|
|
1266
|
+
}
|
|
1267
|
+
scores.set(manifest.relativePath, score)
|
|
1268
|
+
}
|
|
1269
|
+
|
|
1270
|
+
return scores
|
|
1271
|
+
}
|
|
1272
|
+
|
|
1273
|
+
/**
|
|
1274
|
+
* Normalizes repository and package names for conservative identity comparison.
|
|
1275
|
+
*
|
|
1276
|
+
* @param {string} value repository or package name
|
|
1277
|
+
* @returns {Set<string>} normalized identity tokens
|
|
1278
|
+
*/
|
|
1279
|
+
function getIdentityTokens (value) {
|
|
1280
|
+
const tokens = String(value || '').toLowerCase().split(/[^a-z0-9]+/).filter(Boolean)
|
|
1281
|
+
const normalized = new Set()
|
|
1282
|
+
for (const token of tokens) {
|
|
1283
|
+
if (['monorepo', 'package', 'packages', 'project', 'repo', 'root', 'workspace'].includes(token)) continue
|
|
1284
|
+
normalized.add(token.endsWith('js') && token.length > 2 ? token.slice(0, -2) : token)
|
|
1285
|
+
}
|
|
1286
|
+
return normalized
|
|
1287
|
+
}
|
|
1288
|
+
|
|
1289
|
+
/**
|
|
1290
|
+
* Orders command owners by repository identity, then by scope and stable path.
|
|
1291
|
+
*
|
|
1292
|
+
* @param {object} left first command or dependency entry
|
|
1293
|
+
* @param {object} right second command or dependency entry
|
|
1294
|
+
* @param {Map<string, number>|undefined} scores package preference scores
|
|
1295
|
+
* @returns {number} sort order
|
|
1296
|
+
*/
|
|
1297
|
+
function compareProjectPreference (left, right, scores) {
|
|
1298
|
+
return compareProjectScope(left, right, scores) ||
|
|
1299
|
+
left.relativePath.localeCompare(right.relativePath)
|
|
1300
|
+
}
|
|
1301
|
+
|
|
1302
|
+
/**
|
|
1303
|
+
* Orders command owners by repository identity and package depth.
|
|
1304
|
+
*
|
|
1305
|
+
* @param {object} left first command or dependency entry
|
|
1306
|
+
* @param {object} right second command or dependency entry
|
|
1307
|
+
* @param {Map<string, number>|undefined} scores package preference scores
|
|
1308
|
+
* @returns {number} sort order before stable path tie-breaking
|
|
1309
|
+
*/
|
|
1310
|
+
function compareProjectScope (left, right, scores) {
|
|
1311
|
+
const scoreDifference = (scores?.get(right.relativePath) || 0) - (scores?.get(left.relativePath) || 0)
|
|
1312
|
+
if (scoreDifference !== 0) return scoreDifference
|
|
1313
|
+
|
|
1314
|
+
return left.relativePath.split('/').length - right.relativePath.split('/').length
|
|
1315
|
+
}
|
|
1316
|
+
|
|
1213
1317
|
/**
|
|
1214
1318
|
* Checks whether a framework command is ineligible for live validation.
|
|
1215
1319
|
*
|
|
@@ -1218,12 +1322,23 @@ function getEligibleCommandMatch (framework) {
|
|
|
1218
1322
|
* @returns {boolean} whether the command is ineligible
|
|
1219
1323
|
*/
|
|
1220
1324
|
function isIneligibleFrameworkCommand (frameworkId, command) {
|
|
1325
|
+
if (frameworkId === 'cucumber' && !isCucumberRunnerCommand(command)) return true
|
|
1221
1326
|
if (frameworkId === 'vitest' && /\bvitest\s+bench\b/.test(command)) return true
|
|
1222
1327
|
if (WATCH_MODE_RE.test(command)) return true
|
|
1223
1328
|
|
|
1224
1329
|
return false
|
|
1225
1330
|
}
|
|
1226
1331
|
|
|
1332
|
+
/**
|
|
1333
|
+
* Checks whether a package command invokes the Cucumber runner instead of merely naming a Cucumber config file.
|
|
1334
|
+
*
|
|
1335
|
+
* @param {string} command package script command
|
|
1336
|
+
* @returns {boolean} whether the command invokes Cucumber
|
|
1337
|
+
*/
|
|
1338
|
+
function isCucumberRunnerCommand (command) {
|
|
1339
|
+
return CUCUMBER_RUNNER_COMMAND_RE.test(String(command || ''))
|
|
1340
|
+
}
|
|
1341
|
+
|
|
1227
1342
|
/**
|
|
1228
1343
|
* Detects unsupported test frameworks.
|
|
1229
1344
|
*
|
|
@@ -1317,6 +1432,28 @@ function findDependencyEntries (manifests, packageNames) {
|
|
|
1317
1432
|
return entries
|
|
1318
1433
|
}
|
|
1319
1434
|
|
|
1435
|
+
/**
|
|
1436
|
+
* Treats a repository containing a framework's own package as a local version source.
|
|
1437
|
+
*
|
|
1438
|
+
* @param {Array<object>} manifests package manifests
|
|
1439
|
+
* @param {string[]} packageNames framework package names
|
|
1440
|
+
* @returns {Array<object>} local package identities
|
|
1441
|
+
*/
|
|
1442
|
+
function findPackageIdentityEntries (manifests, packageNames) {
|
|
1443
|
+
const packageSet = new Set(packageNames)
|
|
1444
|
+
const entries = []
|
|
1445
|
+
for (const manifest of manifests) {
|
|
1446
|
+
if (!packageSet.has(manifest.json.name) || typeof manifest.json.version !== 'string') continue
|
|
1447
|
+
entries.push({
|
|
1448
|
+
packageName: manifest.json.name,
|
|
1449
|
+
rawVersion: manifest.json.version,
|
|
1450
|
+
section: 'package',
|
|
1451
|
+
relativePath: manifest.relativePath,
|
|
1452
|
+
})
|
|
1453
|
+
}
|
|
1454
|
+
return entries
|
|
1455
|
+
}
|
|
1456
|
+
|
|
1320
1457
|
/**
|
|
1321
1458
|
* Resolves framework package versions from installed modules and manifest ranges.
|
|
1322
1459
|
*
|
|
@@ -2011,6 +2148,8 @@ function formatLocations (locations) {
|
|
|
2011
2148
|
* @returns {object} serializable framework summary
|
|
2012
2149
|
*/
|
|
2013
2150
|
function serializeSupportedFramework (framework) {
|
|
2151
|
+
const eligibleCommand = getEligibleCommandMatch(framework)
|
|
2152
|
+
const supportedVersion = getSupportedVersionDetection(framework, eligibleCommand?.relativePath)
|
|
2014
2153
|
return {
|
|
2015
2154
|
id: framework.id,
|
|
2016
2155
|
name: framework.name,
|
|
@@ -2018,6 +2157,8 @@ function serializeSupportedFramework (framework) {
|
|
|
2018
2157
|
supportedRange: framework.supportedRange,
|
|
2019
2158
|
locations: framework.locations,
|
|
2020
2159
|
versionDetections: framework.versionDetections,
|
|
2160
|
+
eligibleCommand,
|
|
2161
|
+
supportedVersion,
|
|
2021
2162
|
}
|
|
2022
2163
|
}
|
|
2023
2164
|
|