@qawolf/cli 1.36.0 → 1.37.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/dist/cli.js +108 -11
- package/dist/runner-sdk.js +106 -9
- package/package.json +2 -2
- package/skills/qawolf-cli/SKILL.md +2 -1
- package/skills/qawolf-cli/references/run-results.md +9 -3
package/dist/cli.js
CHANGED
|
@@ -16617,6 +16617,10 @@ var publicRunStatusValues = [
|
|
|
16617
16617
|
"failed",
|
|
16618
16618
|
"canceled"
|
|
16619
16619
|
];
|
|
16620
|
+
var publicRunSummaryStatusValues = [
|
|
16621
|
+
...publicRunStatusValues,
|
|
16622
|
+
"superseded"
|
|
16623
|
+
];
|
|
16620
16624
|
var makeRunSummaryFields = (ids) => ({
|
|
16621
16625
|
completedAt: exports_iso.datetime().optional().describe("When the run finished executing. Absent while queued or running, and also absent for a terminal run that never completed execution (e.g. every flow was canceled or skipped)."),
|
|
16622
16626
|
createdAt: exports_iso.datetime(),
|
|
@@ -16628,7 +16632,11 @@ var makeRunSummaryFields = (ids) => ({
|
|
|
16628
16632
|
}).describe("The branch and commit under test. The fields are present when a deploy notification started the run, and absent for runs started another way, for example manually or with run.create."),
|
|
16629
16633
|
needsReview: boolean2().optional().describe("True once every flow has finished its attempts and at least one failed flow still has no diagnosis, including one whose investigation carried over to a later run. `status` stays `running` until that failure is diagnosed, so a caller that is not waiting for a diagnosis can stop polling here and read the run's failed flows."),
|
|
16630
16634
|
runId: ids.run,
|
|
16631
|
-
status: _enum(
|
|
16635
|
+
status: _enum(publicRunSummaryStatusValues).describe("Whole-run status, and the value to gate a pipeline on. Terminal statuses are passed, failed, canceled, and superseded; poll until one is reached. `failed` means the run found a bug that is still open and serious enough to block — a lower-priority bug, or one since resolved, reads `passed`, and the per-flow diagnoses are still in `flows`. The run stays `running` while any investigation is unresolved, including one that carried over to a later run, so a terminal status always means a settled answer, and `needsReview` tells such a run apart from one that is still executing. `superseded` means a newer run replaced this one before it finished: it is not a pass, this run will never change again, and the verdict belongs to the run in `supersededBy`."),
|
|
16636
|
+
supersededBy: object({
|
|
16637
|
+
runId: ids.run,
|
|
16638
|
+
url: url().describe("Absolute URL of the replacement run's page.")
|
|
16639
|
+
}).optional().describe("The run that replaced this one, present only when `status` is `superseded`. A newer deployment to the same branch and environment (and service, when the deployment named one) cancels the older run's unfinished flows and takes over. Deduplication ignores the commit, so the replacement may be testing a later commit than this run did. Only the direct replacement is named; that run can itself be superseded.")
|
|
16632
16640
|
});
|
|
16633
16641
|
|
|
16634
16642
|
// node_modules/@qawolf/api-contracts/dist/v1/deployment/didNotRunReason.js
|
|
@@ -16843,6 +16851,7 @@ var defaultIdSchemas = {
|
|
|
16843
16851
|
issue: string2().min(1).describe("The id of the issue."),
|
|
16844
16852
|
legacyTrigger: string2().min(1).describe("The id of the legacy trigger, from legacyTrigger.find."),
|
|
16845
16853
|
run: string2().min(1).describe("The id of the run."),
|
|
16854
|
+
runAttempt: string2().min(1).describe("The id of the run attempt."),
|
|
16846
16855
|
trigger: string2().min(1).describe("The id of the trigger."),
|
|
16847
16856
|
workspace: string2().min(1).describe("The id of the workspace.")
|
|
16848
16857
|
};
|
|
@@ -19045,7 +19054,7 @@ var makeAddFlowsToIssueContract = (ids) => {
|
|
|
19045
19054
|
// node_modules/@qawolf/api-contracts/dist/v1/issue/create.js
|
|
19046
19055
|
var makeCreateIssueContract = (ids) => {
|
|
19047
19056
|
const commonFields = {
|
|
19048
|
-
description: string2().optional().describe("The issue description
|
|
19057
|
+
description: string2().optional().describe("The issue description in Markdown, which is stored as rich text. Text without Markdown is stored as written, one paragraph per line."),
|
|
19049
19058
|
name: string2().trim().min(1).max(255),
|
|
19050
19059
|
priority: issuePrioritySchema.optional().describe('Defaults to "unprioritized" for bug reports and coverage requests.'),
|
|
19051
19060
|
workspaceId: ids.workspace.optional().describe("The workspace to create the issue in. Required when authenticating with an organization or user API key.")
|
|
@@ -19110,7 +19119,7 @@ var makeRemoveFlowsFromIssueContract = (ids) => {
|
|
|
19110
19119
|
|
|
19111
19120
|
// node_modules/@qawolf/api-contracts/dist/v1/issue/update.js
|
|
19112
19121
|
var makeUpdateIssueContract = (ids) => {
|
|
19113
|
-
const descriptionSchema = string2().describe("The issue description
|
|
19122
|
+
const descriptionSchema = string2().describe("The issue description in Markdown, which is stored as rich text. Text without Markdown is stored as written, one paragraph per line.");
|
|
19114
19123
|
const nameSchema = string2().trim().min(1).max(255);
|
|
19115
19124
|
const input = object({
|
|
19116
19125
|
description: descriptionSchema.optional(),
|
|
@@ -19294,9 +19303,11 @@ var makeFindRunsContract = (ids) => {
|
|
|
19294
19303
|
});
|
|
19295
19304
|
const output = object({
|
|
19296
19305
|
nextCursor: nextCursorSchema,
|
|
19297
|
-
runs: array(resource(
|
|
19298
|
-
|
|
19299
|
-
|
|
19306
|
+
runs: array(resource({
|
|
19307
|
+
...makeRunSummaryFields(ids),
|
|
19308
|
+
failedAttemptCount: number2().int().nonnegative().optional(),
|
|
19309
|
+
hasFailedAttempts: boolean2().optional()
|
|
19310
|
+
}, { urlFieldDescription: "Absolute URL of the run page." })).describe("The environment's runs, newest first. Per-flow results are available via run.get.")
|
|
19300
19311
|
});
|
|
19301
19312
|
return {
|
|
19302
19313
|
annotations: {
|
|
@@ -19304,7 +19315,7 @@ var makeFindRunsContract = (ids) => {
|
|
|
19304
19315
|
openWorldHint: false,
|
|
19305
19316
|
readOnlyHint: true
|
|
19306
19317
|
},
|
|
19307
|
-
description: "List an environment's recent runs, newest first.",
|
|
19318
|
+
description: "List an environment's recent runs, newest first, including failed-attempt discovery metadata.",
|
|
19308
19319
|
input,
|
|
19309
19320
|
kind: "read",
|
|
19310
19321
|
name: "run.find",
|
|
@@ -19328,6 +19339,7 @@ var makeGetRunContract = (ids) => {
|
|
|
19328
19339
|
const automatedAttempt = discriminatedUnion("status", [
|
|
19329
19340
|
object({
|
|
19330
19341
|
...artifactUrls,
|
|
19342
|
+
attemptId: ids.runAttempt.optional(),
|
|
19331
19343
|
completedAt: exports_iso.datetime(),
|
|
19332
19344
|
kind: automatedKind,
|
|
19333
19345
|
startedAt: exports_iso.datetime(),
|
|
@@ -19335,12 +19347,14 @@ var makeGetRunContract = (ids) => {
|
|
|
19335
19347
|
}),
|
|
19336
19348
|
object({
|
|
19337
19349
|
...artifactUrls,
|
|
19350
|
+
attemptId: ids.runAttempt.optional(),
|
|
19338
19351
|
completedAt: exports_iso.datetime(),
|
|
19339
19352
|
kind: automatedKind,
|
|
19340
19353
|
startedAt: exports_iso.datetime().optional().describe("Absent when the attempt failed before it could start."),
|
|
19341
19354
|
status: literal("failed")
|
|
19342
19355
|
}),
|
|
19343
19356
|
object({
|
|
19357
|
+
attemptId: ids.runAttempt.optional(),
|
|
19344
19358
|
completedAt: exports_iso.datetime().optional(),
|
|
19345
19359
|
kind: automatedKind,
|
|
19346
19360
|
startedAt: exports_iso.datetime().optional(),
|
|
@@ -19348,6 +19362,7 @@ var makeGetRunContract = (ids) => {
|
|
|
19348
19362
|
})
|
|
19349
19363
|
]);
|
|
19350
19364
|
const manualAttempt = object({
|
|
19365
|
+
attemptId: ids.runAttempt.optional(),
|
|
19351
19366
|
completedAt: exports_iso.datetime(),
|
|
19352
19367
|
kind: literal("manual").describe("The attempt ran by hand in the Wolf Browser."),
|
|
19353
19368
|
startedAt: exports_iso.datetime(),
|
|
@@ -19396,6 +19411,83 @@ var makeGetRunContract = (ids) => {
|
|
|
19396
19411
|
};
|
|
19397
19412
|
};
|
|
19398
19413
|
|
|
19414
|
+
// node_modules/@qawolf/api-contracts/dist/v1/run/getAttemptArtifacts.js
|
|
19415
|
+
var makeGetRunAttemptArtifactsContract = (ids) => {
|
|
19416
|
+
const input = object({ attemptId: ids.runAttempt });
|
|
19417
|
+
const attemptStatus = _enum([
|
|
19418
|
+
"passed",
|
|
19419
|
+
"failed",
|
|
19420
|
+
"canceled",
|
|
19421
|
+
"aborted",
|
|
19422
|
+
"skipped"
|
|
19423
|
+
]);
|
|
19424
|
+
const attemptNeighbor = object({
|
|
19425
|
+
attemptId: ids.runAttempt,
|
|
19426
|
+
status: attemptStatus
|
|
19427
|
+
});
|
|
19428
|
+
const response = object({
|
|
19429
|
+
flowId: ids.flow,
|
|
19430
|
+
flowStatus: _enum(publicRunStatusValues),
|
|
19431
|
+
retryContext: object({
|
|
19432
|
+
currentOrdinal: number2().int().min(1),
|
|
19433
|
+
next: attemptNeighbor.optional(),
|
|
19434
|
+
previous: attemptNeighbor.optional(),
|
|
19435
|
+
total: number2().int().min(1)
|
|
19436
|
+
}),
|
|
19437
|
+
runId: ids.run,
|
|
19438
|
+
runStatus: _enum(publicRunSummaryStatusValues)
|
|
19439
|
+
});
|
|
19440
|
+
const attempt = object({
|
|
19441
|
+
attemptId: ids.runAttempt,
|
|
19442
|
+
completedAt: exports_iso.datetime().optional(),
|
|
19443
|
+
createdAt: exports_iso.datetime(),
|
|
19444
|
+
error: string2().optional(),
|
|
19445
|
+
startedAt: exports_iso.datetime().optional()
|
|
19446
|
+
});
|
|
19447
|
+
const output = discriminatedUnion("artifactStatus", [
|
|
19448
|
+
response.extend({
|
|
19449
|
+
artifacts: object({
|
|
19450
|
+
logsUrl: url().optional(),
|
|
19451
|
+
traceUrl: url().optional(),
|
|
19452
|
+
videoUrl: url().optional()
|
|
19453
|
+
}),
|
|
19454
|
+
artifactStatus: literal("signed"),
|
|
19455
|
+
attempt: attempt.extend({
|
|
19456
|
+
kind: literal("automated"),
|
|
19457
|
+
status: attemptStatus
|
|
19458
|
+
})
|
|
19459
|
+
}),
|
|
19460
|
+
response.extend({
|
|
19461
|
+
artifacts: object({}).strict(),
|
|
19462
|
+
artifactStatus: literal("signing-failed"),
|
|
19463
|
+
attempt: attempt.extend({
|
|
19464
|
+
kind: literal("automated"),
|
|
19465
|
+
status: attemptStatus
|
|
19466
|
+
})
|
|
19467
|
+
}),
|
|
19468
|
+
response.extend({
|
|
19469
|
+
artifacts: object({}).strict(),
|
|
19470
|
+
artifactStatus: literal("not-captured"),
|
|
19471
|
+
attempt: attempt.extend({
|
|
19472
|
+
kind: literal("manual"),
|
|
19473
|
+
status: literal("passed")
|
|
19474
|
+
})
|
|
19475
|
+
})
|
|
19476
|
+
]);
|
|
19477
|
+
return {
|
|
19478
|
+
annotations: {
|
|
19479
|
+
destructiveHint: false,
|
|
19480
|
+
openWorldHint: false,
|
|
19481
|
+
readOnlyHint: true
|
|
19482
|
+
},
|
|
19483
|
+
description: "Get metadata and signed artifact URLs for one finished run attempt.",
|
|
19484
|
+
input,
|
|
19485
|
+
kind: "read",
|
|
19486
|
+
name: "run.getAttemptArtifacts",
|
|
19487
|
+
output
|
|
19488
|
+
};
|
|
19489
|
+
};
|
|
19490
|
+
|
|
19399
19491
|
// node_modules/@qawolf/api-contracts/dist/v1/run/reattempt.js
|
|
19400
19492
|
var makeReattemptRunContract = (ids) => {
|
|
19401
19493
|
const input = object({
|
|
@@ -19956,7 +20048,11 @@ var makeListTagsContract = (ids) => {
|
|
|
19956
20048
|
|
|
19957
20049
|
// node_modules/@qawolf/api-contracts/dist/v1/index.js
|
|
19958
20050
|
var makeContractsV1 = (ids) => {
|
|
19959
|
-
const resolvedIds = {
|
|
20051
|
+
const resolvedIds = {
|
|
20052
|
+
...defaultIdSchemas,
|
|
20053
|
+
...ids,
|
|
20054
|
+
runAttempt: ids.runAttempt ?? defaultIdSchemas.runAttempt
|
|
20055
|
+
};
|
|
19960
20056
|
return {
|
|
19961
20057
|
agent: {
|
|
19962
20058
|
get: makeAgentGetContract(resolvedIds),
|
|
@@ -20007,6 +20103,7 @@ var makeContractsV1 = (ids) => {
|
|
|
20007
20103
|
diagnose: makeDiagnoseRunContract(resolvedIds),
|
|
20008
20104
|
find: makeFindRunsContract(resolvedIds),
|
|
20009
20105
|
get: makeGetRunContract(resolvedIds),
|
|
20106
|
+
getAttemptArtifacts: makeGetRunAttemptArtifactsContract(resolvedIds),
|
|
20010
20107
|
reattempt: makeReattemptRunContract(resolvedIds),
|
|
20011
20108
|
stop: makeStopRunContract(resolvedIds)
|
|
20012
20109
|
},
|
|
@@ -22524,7 +22621,7 @@ function startUpdateCheck(deps) {
|
|
|
22524
22621
|
// package.json
|
|
22525
22622
|
var package_default = {
|
|
22526
22623
|
name: "@qawolf/cli",
|
|
22527
|
-
version: "1.
|
|
22624
|
+
version: "1.37.0",
|
|
22528
22625
|
description: "Run and manage QA Wolf flows from the terminal, CI, or an AI agent",
|
|
22529
22626
|
keywords: [
|
|
22530
22627
|
"automation",
|
|
@@ -22595,7 +22692,7 @@ var package_default = {
|
|
|
22595
22692
|
"@clack/prompts": "1.5.1",
|
|
22596
22693
|
"@napi-rs/keyring": "1.3.0",
|
|
22597
22694
|
"@oxc-node/core": "0.1.0",
|
|
22598
|
-
"@qawolf/api-contracts": "0.
|
|
22695
|
+
"@qawolf/api-contracts": "0.74.0",
|
|
22599
22696
|
"@qawolf/emails": "1.1.1",
|
|
22600
22697
|
"@qawolf/flow-targets": "1.0.0",
|
|
22601
22698
|
"@qawolf/flows": "0.1.4",
|
|
@@ -38846,4 +38943,4 @@ createProgram({ signals }).parseAsync().catch(() => {
|
|
|
38846
38943
|
process.exitCode = 1;
|
|
38847
38944
|
}).finally(() => exitWhenIdle(typeof process.exitCode === "number" ? process.exitCode : 0));
|
|
38848
38945
|
|
|
38849
|
-
//# debugId=
|
|
38946
|
+
//# debugId=0EBF9D8CD8CB2E9E64756E2164756E21
|
package/dist/runner-sdk.js
CHANGED
|
@@ -6979,6 +6979,10 @@ var publicRunStatusValues = [
|
|
|
6979
6979
|
"failed",
|
|
6980
6980
|
"canceled"
|
|
6981
6981
|
];
|
|
6982
|
+
var publicRunSummaryStatusValues = [
|
|
6983
|
+
...publicRunStatusValues,
|
|
6984
|
+
"superseded"
|
|
6985
|
+
];
|
|
6982
6986
|
var makeRunSummaryFields = (ids) => ({
|
|
6983
6987
|
completedAt: exports_iso.datetime().optional().describe("When the run finished executing. Absent while queued or running, and also absent for a terminal run that never completed execution (e.g. every flow was canceled or skipped)."),
|
|
6984
6988
|
createdAt: exports_iso.datetime(),
|
|
@@ -6990,7 +6994,11 @@ var makeRunSummaryFields = (ids) => ({
|
|
|
6990
6994
|
}).describe("The branch and commit under test. The fields are present when a deploy notification started the run, and absent for runs started another way, for example manually or with run.create."),
|
|
6991
6995
|
needsReview: boolean2().optional().describe("True once every flow has finished its attempts and at least one failed flow still has no diagnosis, including one whose investigation carried over to a later run. `status` stays `running` until that failure is diagnosed, so a caller that is not waiting for a diagnosis can stop polling here and read the run's failed flows."),
|
|
6992
6996
|
runId: ids.run,
|
|
6993
|
-
status: _enum(
|
|
6997
|
+
status: _enum(publicRunSummaryStatusValues).describe("Whole-run status, and the value to gate a pipeline on. Terminal statuses are passed, failed, canceled, and superseded; poll until one is reached. `failed` means the run found a bug that is still open and serious enough to block — a lower-priority bug, or one since resolved, reads `passed`, and the per-flow diagnoses are still in `flows`. The run stays `running` while any investigation is unresolved, including one that carried over to a later run, so a terminal status always means a settled answer, and `needsReview` tells such a run apart from one that is still executing. `superseded` means a newer run replaced this one before it finished: it is not a pass, this run will never change again, and the verdict belongs to the run in `supersededBy`."),
|
|
6998
|
+
supersededBy: object({
|
|
6999
|
+
runId: ids.run,
|
|
7000
|
+
url: url().describe("Absolute URL of the replacement run's page.")
|
|
7001
|
+
}).optional().describe("The run that replaced this one, present only when `status` is `superseded`. A newer deployment to the same branch and environment (and service, when the deployment named one) cancels the older run's unfinished flows and takes over. Deduplication ignores the commit, so the replacement may be testing a later commit than this run did. Only the direct replacement is named; that run can itself be superseded.")
|
|
6994
7002
|
});
|
|
6995
7003
|
|
|
6996
7004
|
// node_modules/@qawolf/api-contracts/dist/v1/deployment/didNotRunReason.js
|
|
@@ -7205,6 +7213,7 @@ var defaultIdSchemas = {
|
|
|
7205
7213
|
issue: string2().min(1).describe("The id of the issue."),
|
|
7206
7214
|
legacyTrigger: string2().min(1).describe("The id of the legacy trigger, from legacyTrigger.find."),
|
|
7207
7215
|
run: string2().min(1).describe("The id of the run."),
|
|
7216
|
+
runAttempt: string2().min(1).describe("The id of the run attempt."),
|
|
7208
7217
|
trigger: string2().min(1).describe("The id of the trigger."),
|
|
7209
7218
|
workspace: string2().min(1).describe("The id of the workspace.")
|
|
7210
7219
|
};
|
|
@@ -9414,7 +9423,7 @@ var makeAddFlowsToIssueContract = (ids) => {
|
|
|
9414
9423
|
// node_modules/@qawolf/api-contracts/dist/v1/issue/create.js
|
|
9415
9424
|
var makeCreateIssueContract = (ids) => {
|
|
9416
9425
|
const commonFields = {
|
|
9417
|
-
description: string2().optional().describe("The issue description
|
|
9426
|
+
description: string2().optional().describe("The issue description in Markdown, which is stored as rich text. Text without Markdown is stored as written, one paragraph per line."),
|
|
9418
9427
|
name: string2().trim().min(1).max(255),
|
|
9419
9428
|
priority: issuePrioritySchema.optional().describe('Defaults to "unprioritized" for bug reports and coverage requests.'),
|
|
9420
9429
|
workspaceId: ids.workspace.optional().describe("The workspace to create the issue in. Required when authenticating with an organization or user API key.")
|
|
@@ -9479,7 +9488,7 @@ var makeRemoveFlowsFromIssueContract = (ids) => {
|
|
|
9479
9488
|
|
|
9480
9489
|
// node_modules/@qawolf/api-contracts/dist/v1/issue/update.js
|
|
9481
9490
|
var makeUpdateIssueContract = (ids) => {
|
|
9482
|
-
const descriptionSchema = string2().describe("The issue description
|
|
9491
|
+
const descriptionSchema = string2().describe("The issue description in Markdown, which is stored as rich text. Text without Markdown is stored as written, one paragraph per line.");
|
|
9483
9492
|
const nameSchema = string2().trim().min(1).max(255);
|
|
9484
9493
|
const input = object({
|
|
9485
9494
|
description: descriptionSchema.optional(),
|
|
@@ -9663,9 +9672,11 @@ var makeFindRunsContract = (ids) => {
|
|
|
9663
9672
|
});
|
|
9664
9673
|
const output = object({
|
|
9665
9674
|
nextCursor: nextCursorSchema,
|
|
9666
|
-
runs: array(resource(
|
|
9667
|
-
|
|
9668
|
-
|
|
9675
|
+
runs: array(resource({
|
|
9676
|
+
...makeRunSummaryFields(ids),
|
|
9677
|
+
failedAttemptCount: number2().int().nonnegative().optional(),
|
|
9678
|
+
hasFailedAttempts: boolean2().optional()
|
|
9679
|
+
}, { urlFieldDescription: "Absolute URL of the run page." })).describe("The environment's runs, newest first. Per-flow results are available via run.get.")
|
|
9669
9680
|
});
|
|
9670
9681
|
return {
|
|
9671
9682
|
annotations: {
|
|
@@ -9673,7 +9684,7 @@ var makeFindRunsContract = (ids) => {
|
|
|
9673
9684
|
openWorldHint: false,
|
|
9674
9685
|
readOnlyHint: true
|
|
9675
9686
|
},
|
|
9676
|
-
description: "List an environment's recent runs, newest first.",
|
|
9687
|
+
description: "List an environment's recent runs, newest first, including failed-attempt discovery metadata.",
|
|
9677
9688
|
input,
|
|
9678
9689
|
kind: "read",
|
|
9679
9690
|
name: "run.find",
|
|
@@ -9697,6 +9708,7 @@ var makeGetRunContract = (ids) => {
|
|
|
9697
9708
|
const automatedAttempt = discriminatedUnion("status", [
|
|
9698
9709
|
object({
|
|
9699
9710
|
...artifactUrls,
|
|
9711
|
+
attemptId: ids.runAttempt.optional(),
|
|
9700
9712
|
completedAt: exports_iso.datetime(),
|
|
9701
9713
|
kind: automatedKind,
|
|
9702
9714
|
startedAt: exports_iso.datetime(),
|
|
@@ -9704,12 +9716,14 @@ var makeGetRunContract = (ids) => {
|
|
|
9704
9716
|
}),
|
|
9705
9717
|
object({
|
|
9706
9718
|
...artifactUrls,
|
|
9719
|
+
attemptId: ids.runAttempt.optional(),
|
|
9707
9720
|
completedAt: exports_iso.datetime(),
|
|
9708
9721
|
kind: automatedKind,
|
|
9709
9722
|
startedAt: exports_iso.datetime().optional().describe("Absent when the attempt failed before it could start."),
|
|
9710
9723
|
status: literal("failed")
|
|
9711
9724
|
}),
|
|
9712
9725
|
object({
|
|
9726
|
+
attemptId: ids.runAttempt.optional(),
|
|
9713
9727
|
completedAt: exports_iso.datetime().optional(),
|
|
9714
9728
|
kind: automatedKind,
|
|
9715
9729
|
startedAt: exports_iso.datetime().optional(),
|
|
@@ -9717,6 +9731,7 @@ var makeGetRunContract = (ids) => {
|
|
|
9717
9731
|
})
|
|
9718
9732
|
]);
|
|
9719
9733
|
const manualAttempt = object({
|
|
9734
|
+
attemptId: ids.runAttempt.optional(),
|
|
9720
9735
|
completedAt: exports_iso.datetime(),
|
|
9721
9736
|
kind: literal("manual").describe("The attempt ran by hand in the Wolf Browser."),
|
|
9722
9737
|
startedAt: exports_iso.datetime(),
|
|
@@ -9765,6 +9780,83 @@ var makeGetRunContract = (ids) => {
|
|
|
9765
9780
|
};
|
|
9766
9781
|
};
|
|
9767
9782
|
|
|
9783
|
+
// node_modules/@qawolf/api-contracts/dist/v1/run/getAttemptArtifacts.js
|
|
9784
|
+
var makeGetRunAttemptArtifactsContract = (ids) => {
|
|
9785
|
+
const input = object({ attemptId: ids.runAttempt });
|
|
9786
|
+
const attemptStatus = _enum([
|
|
9787
|
+
"passed",
|
|
9788
|
+
"failed",
|
|
9789
|
+
"canceled",
|
|
9790
|
+
"aborted",
|
|
9791
|
+
"skipped"
|
|
9792
|
+
]);
|
|
9793
|
+
const attemptNeighbor = object({
|
|
9794
|
+
attemptId: ids.runAttempt,
|
|
9795
|
+
status: attemptStatus
|
|
9796
|
+
});
|
|
9797
|
+
const response = object({
|
|
9798
|
+
flowId: ids.flow,
|
|
9799
|
+
flowStatus: _enum(publicRunStatusValues),
|
|
9800
|
+
retryContext: object({
|
|
9801
|
+
currentOrdinal: number2().int().min(1),
|
|
9802
|
+
next: attemptNeighbor.optional(),
|
|
9803
|
+
previous: attemptNeighbor.optional(),
|
|
9804
|
+
total: number2().int().min(1)
|
|
9805
|
+
}),
|
|
9806
|
+
runId: ids.run,
|
|
9807
|
+
runStatus: _enum(publicRunSummaryStatusValues)
|
|
9808
|
+
});
|
|
9809
|
+
const attempt = object({
|
|
9810
|
+
attemptId: ids.runAttempt,
|
|
9811
|
+
completedAt: exports_iso.datetime().optional(),
|
|
9812
|
+
createdAt: exports_iso.datetime(),
|
|
9813
|
+
error: string2().optional(),
|
|
9814
|
+
startedAt: exports_iso.datetime().optional()
|
|
9815
|
+
});
|
|
9816
|
+
const output = discriminatedUnion("artifactStatus", [
|
|
9817
|
+
response.extend({
|
|
9818
|
+
artifacts: object({
|
|
9819
|
+
logsUrl: url().optional(),
|
|
9820
|
+
traceUrl: url().optional(),
|
|
9821
|
+
videoUrl: url().optional()
|
|
9822
|
+
}),
|
|
9823
|
+
artifactStatus: literal("signed"),
|
|
9824
|
+
attempt: attempt.extend({
|
|
9825
|
+
kind: literal("automated"),
|
|
9826
|
+
status: attemptStatus
|
|
9827
|
+
})
|
|
9828
|
+
}),
|
|
9829
|
+
response.extend({
|
|
9830
|
+
artifacts: object({}).strict(),
|
|
9831
|
+
artifactStatus: literal("signing-failed"),
|
|
9832
|
+
attempt: attempt.extend({
|
|
9833
|
+
kind: literal("automated"),
|
|
9834
|
+
status: attemptStatus
|
|
9835
|
+
})
|
|
9836
|
+
}),
|
|
9837
|
+
response.extend({
|
|
9838
|
+
artifacts: object({}).strict(),
|
|
9839
|
+
artifactStatus: literal("not-captured"),
|
|
9840
|
+
attempt: attempt.extend({
|
|
9841
|
+
kind: literal("manual"),
|
|
9842
|
+
status: literal("passed")
|
|
9843
|
+
})
|
|
9844
|
+
})
|
|
9845
|
+
]);
|
|
9846
|
+
return {
|
|
9847
|
+
annotations: {
|
|
9848
|
+
destructiveHint: false,
|
|
9849
|
+
openWorldHint: false,
|
|
9850
|
+
readOnlyHint: true
|
|
9851
|
+
},
|
|
9852
|
+
description: "Get metadata and signed artifact URLs for one finished run attempt.",
|
|
9853
|
+
input,
|
|
9854
|
+
kind: "read",
|
|
9855
|
+
name: "run.getAttemptArtifacts",
|
|
9856
|
+
output
|
|
9857
|
+
};
|
|
9858
|
+
};
|
|
9859
|
+
|
|
9768
9860
|
// node_modules/@qawolf/api-contracts/dist/v1/run/reattempt.js
|
|
9769
9861
|
var makeReattemptRunContract = (ids) => {
|
|
9770
9862
|
const input = object({
|
|
@@ -10325,7 +10417,11 @@ var makeListTagsContract = (ids) => {
|
|
|
10325
10417
|
|
|
10326
10418
|
// node_modules/@qawolf/api-contracts/dist/v1/index.js
|
|
10327
10419
|
var makeContractsV1 = (ids) => {
|
|
10328
|
-
const resolvedIds = {
|
|
10420
|
+
const resolvedIds = {
|
|
10421
|
+
...defaultIdSchemas,
|
|
10422
|
+
...ids,
|
|
10423
|
+
runAttempt: ids.runAttempt ?? defaultIdSchemas.runAttempt
|
|
10424
|
+
};
|
|
10329
10425
|
return {
|
|
10330
10426
|
agent: {
|
|
10331
10427
|
get: makeAgentGetContract(resolvedIds),
|
|
@@ -10376,6 +10472,7 @@ var makeContractsV1 = (ids) => {
|
|
|
10376
10472
|
diagnose: makeDiagnoseRunContract(resolvedIds),
|
|
10377
10473
|
find: makeFindRunsContract(resolvedIds),
|
|
10378
10474
|
get: makeGetRunContract(resolvedIds),
|
|
10475
|
+
getAttemptArtifacts: makeGetRunAttemptArtifactsContract(resolvedIds),
|
|
10379
10476
|
reattempt: makeReattemptRunContract(resolvedIds),
|
|
10380
10477
|
stop: makeStopRunContract(resolvedIds)
|
|
10381
10478
|
},
|
|
@@ -15011,4 +15108,4 @@ export {
|
|
|
15011
15108
|
createRunnerSdk
|
|
15012
15109
|
};
|
|
15013
15110
|
|
|
15014
|
-
//# debugId=
|
|
15111
|
+
//# debugId=3EFB50CF5F60CF8264756E2164756E21
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@qawolf/cli",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.37.0",
|
|
4
4
|
"description": "Run and manage QA Wolf flows from the terminal, CI, or an AI agent",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"automation",
|
|
@@ -71,7 +71,7 @@
|
|
|
71
71
|
"@clack/prompts": "1.5.1",
|
|
72
72
|
"@napi-rs/keyring": "1.3.0",
|
|
73
73
|
"@oxc-node/core": "0.1.0",
|
|
74
|
-
"@qawolf/api-contracts": "0.
|
|
74
|
+
"@qawolf/api-contracts": "0.74.0",
|
|
75
75
|
"@qawolf/emails": "1.1.1",
|
|
76
76
|
"@qawolf/flow-targets": "1.0.0",
|
|
77
77
|
"@qawolf/flows": "0.1.4",
|
|
@@ -178,8 +178,9 @@ that `url`; never guess a route and never send a repository link in its place.
|
|
|
178
178
|
| `qawolf legacyTrigger resume` | write | Resume one legacy trigger, the older per-environment kind; use trigger.resume for a current one. Its copies in pull request environments resume too, and a scheduled one jumps to the next upcoming slot even if it was not paused. For migration only; it goes when legacy triggers go. |
|
|
179
179
|
| `qawolf run create` | write | Create a run for the selected flows and/or tags in an environment. |
|
|
180
180
|
| `qawolf run diagnose` | write | Diagnose failed flows in a run as reproductions of a bug or maintenance report owned by the caller's team. The issue's type selects the diagnosis. Each flow must have failed in the run. A flow that is already diagnosed moves to this issue. The diagnosis appears on the run, and the reproduction appears under the issue's reproductions. Coverage requests cannot be diagnosed; use issue.addFlows to cover flows instead. |
|
|
181
|
-
| `qawolf run find` | read | List an environment's recent runs, newest first. |
|
|
181
|
+
| `qawolf run find` | read | List an environment's recent runs, newest first, including failed-attempt discovery metadata. |
|
|
182
182
|
| `qawolf run get` | read | Get a run's status, per-flow results, links, and how many of its bugs are blocking. |
|
|
183
|
+
| `qawolf run getAttemptArtifacts` | read | Get metadata and signed artifact URLs for one finished run attempt. |
|
|
183
184
|
| `qawolf run reattempt` | write | Request new attempts for a run's flows, in the same run. A flow is eligible once its result is failed or canceled and QA Wolf's automatic retries have finished. A fully investigated run no longer accepts reattempts. Attempts run with the latest flow code. Poll run.get for results. |
|
|
184
185
|
| `qawolf run stop` | write | Stop a run, including its queued flows and automatic retries. Stopping is asynchronous and can update run-status messages and commit statuses in connected integrations. Repeated requests are safe, and finished runs keep their results. A run that is still being created returns not found; retry once run.get returns the run. If run.get returns a different runId, use that ID. Poll run.get for results. |
|
|
185
186
|
| `qawolf runner act` | write | Perform one raw action on a runner's screen. A browser runner takes click, double_click, scroll, move, drag, keypress, navigate and type; a mobile runner takes tap, swipe, fill and type. A browser runner answers mobile actions with action-not-supported-on-browser; a mobile runner answers the other browser actions with action-not-supported-on-mobile. Use - to read a whole action as JSON from stdin |
|
|
@@ -59,8 +59,10 @@ A run that has been requested but not yet created answers exit `8` too, and
|
|
|
59
59
|
says it is still being created. That one clears on its own, so read the message
|
|
60
60
|
rather than the code before deciding whether to poll.
|
|
61
61
|
|
|
62
|
-
Poll `status` until it reaches `passed`, `failed` or `
|
|
63
|
-
|
|
62
|
+
Poll `status` until it reaches `passed`, `failed`, `canceled` or `superseded`.
|
|
63
|
+
When it is `superseded`, this run will never change again. Read the replacement
|
|
64
|
+
run in `supersededBy.runId` for the verdict. `queued` and `running` mean the run
|
|
65
|
+
is still going.
|
|
64
66
|
|
|
65
67
|
## Fields a passing run does not show you
|
|
66
68
|
|
|
@@ -185,13 +187,17 @@ Every documented field of the `run.get` response. `[]` marks an array, so
|
|
|
185
187
|
- `git.commitUrl` — Link to the commit on the code host.
|
|
186
188
|
- `needsReview` — True once every flow has finished its attempts and at least one failed flow still has no diagnosis, including one whose investigation carried over to a later run. `status` stays `running` until that failure is diagnosed, so a caller that is not waiting for a diagnosis can stop polling here and read the run's failed flows.
|
|
187
189
|
- `runId` — The run this response describes. Treat it as canonical: it can differ from the id you asked for. A deploy notification returns a run id before the run exists, and if a second notification for the same commit is folded into an earlier run, that id resolves to the earlier run instead.
|
|
188
|
-
- `status` — One of: queued, running, passed, failed, canceled
|
|
190
|
+
- `status` — One of: queued, running, passed, failed, canceled, superseded
|
|
191
|
+
- `supersededBy` — The run that replaced this one, present only when `status` is `superseded`. A newer deployment to the same branch and environment (and service, when the deployment named one) cancels the older run's unfinished flows and takes over. Deduplication ignores the commit, so the replacement may be testing a later commit than this run did. Only the direct replacement is named; that run can itself be superseded.
|
|
192
|
+
- `supersededBy.runId` — The id of the run.
|
|
193
|
+
- `supersededBy.url` — Absolute URL of the replacement run's page.
|
|
189
194
|
- `blockingBugCount` — How many bugs this run found are blocking: still open, and priority urgent, high, or unprioritized — unprioritized counts because nobody has ruled it out yet. This is what `failed` is derived from, so it explains a failure rather than adding a second verdict: gate on `status`, then read this to say how many bugs are holding the build. It counts a bug filed against a later run by an investigation that carried over from this one, and it drops a bug once that bug is resolved.
|
|
190
195
|
- `flows` — The run's flows, ordered alphabetically by name. Only the flows matching flowStatuses when the request set it.
|
|
191
196
|
- `flows[].attempts` — The flow's finished execution attempts, oldest first, including manual Wolf Browser attempts. Present once at least one attempt has finished, so a flow that passed after retries also lists its failed attempts. Artifact URLs appear only on automated attempts that reached a verdict, stay valid for at least a day (call run.get again for fresh ones), and can return 404 when the attempt did not produce that artifact.
|
|
192
197
|
- `flows[].attempts[].logsUrl` — Signed URL for the attempt's execution logs.
|
|
193
198
|
- `flows[].attempts[].traceUrl` — Signed URL for the attempt's Playwright trace (a trace.zip; open it with `npx playwright show-trace`).
|
|
194
199
|
- `flows[].attempts[].videoUrl` — Signed URL for the attempt's screen recording.
|
|
200
|
+
- `flows[].attempts[].attemptId` — The id of the run attempt.
|
|
195
201
|
- `flows[].attempts[].kind` — One of: automated, manual
|
|
196
202
|
- `flows[].attempts[].startedAt` — Absent when the attempt failed before it could start.
|
|
197
203
|
- `flows[].attempts[].status` — One of: passed, failed, canceled
|