@hominis/fireforge 0.52.0 → 0.53.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/CHANGELOG.md +26 -0
- package/dist/build-info.json +4 -4
- package/dist/src/commands/bootstrap.js +2 -3
- package/dist/src/commands/build-prelock.d.ts +3 -3
- package/dist/src/commands/build-prelock.js +3 -3
- package/dist/src/commands/build.js +4 -0
- package/dist/src/commands/declarations-report.d.ts +9 -3
- package/dist/src/commands/declarations-report.js +18 -11
- package/dist/src/commands/discard.js +3 -3
- package/dist/src/commands/doctor-furnace-config-sync.js +4 -4
- package/dist/src/commands/doctor-furnace.js +5 -5
- package/dist/src/commands/export-adopt-check.d.ts +5 -6
- package/dist/src/commands/export-adopt-check.js +5 -6
- package/dist/src/commands/export-flow.js +6 -9
- package/dist/src/commands/export-staged-registration.d.ts +4 -4
- package/dist/src/commands/export-staged-registration.js +4 -4
- package/dist/src/commands/forward-import-remedy.d.ts +2 -3
- package/dist/src/commands/forward-import-remedy.js +2 -3
- package/dist/src/commands/furnace/create-dry-run.d.ts +2 -2
- package/dist/src/commands/furnace/deploy-fragment-includers.d.ts +2 -2
- package/dist/src/commands/furnace/deploy-fragment-includers.js +2 -2
- package/dist/src/commands/furnace/index.js +2 -2
- package/dist/src/commands/lint.js +4 -4
- package/dist/src/commands/patch/compact.js +1 -1
- package/dist/src/commands/patch/lint-ignore-from.d.ts +3 -4
- package/dist/src/commands/patch/lint-ignore-from.js +3 -4
- package/dist/src/commands/patch/move-files-adopt.d.ts +33 -0
- package/dist/src/commands/patch/move-files-adopt.js +65 -0
- package/dist/src/commands/patch/move-files-create.js +41 -20
- package/dist/src/commands/patch/move-files-into.d.ts +18 -0
- package/dist/src/commands/patch/move-files-into.js +125 -60
- package/dist/src/commands/patch/move-files-retire.d.ts +39 -0
- package/dist/src/commands/patch/move-files-retire.js +91 -0
- package/dist/src/commands/patch/move-files.d.ts +3 -0
- package/dist/src/commands/patch/move-files.js +42 -12
- package/dist/src/commands/patch/move-size-tier.d.ts +27 -0
- package/dist/src/commands/patch/move-size-tier.js +66 -0
- package/dist/src/commands/patch/rename.js +1 -1
- package/dist/src/commands/patch/reorder-projection.d.ts +17 -0
- package/dist/src/commands/patch/reorder-projection.js +49 -0
- package/dist/src/commands/patch/reorder-shift.d.ts +30 -0
- package/dist/src/commands/patch/reorder-shift.js +307 -0
- package/dist/src/commands/patch/reorder.d.ts +9 -15
- package/dist/src/commands/patch/reorder.js +52 -50
- package/dist/src/commands/patch/split-plan.d.ts +31 -3
- package/dist/src/commands/patch/split-plan.js +36 -12
- package/dist/src/commands/patch/split-staged.d.ts +2 -2
- package/dist/src/commands/patch/split-staged.js +2 -2
- package/dist/src/commands/patch/split.js +18 -5
- package/dist/src/commands/patch/staged-dependency-entries.d.ts +9 -1
- package/dist/src/commands/patch/staged-dependency-entries.js +32 -4
- package/dist/src/commands/patch/staged-dependency-from.js +15 -9
- package/dist/src/commands/patch/staged-dependency.js +13 -9
- package/dist/src/commands/patch/tier.js +2 -2
- package/dist/src/commands/patch-rename-map.d.ts +14 -3
- package/dist/src/commands/patch-rename-map.js +21 -3
- package/dist/src/commands/re-export-adjacent.d.ts +4 -5
- package/dist/src/commands/re-export-lint.d.ts +4 -3
- package/dist/src/commands/re-export-lint.js +4 -3
- package/dist/src/commands/re-export-preflight.js +1 -2
- package/dist/src/commands/re-export-purity-scope.d.ts +1 -1
- package/dist/src/commands/re-export-purity-scope.js +13 -7
- package/dist/src/commands/re-export-retired-declarations.d.ts +22 -0
- package/dist/src/commands/re-export-retired-declarations.js +113 -0
- package/dist/src/commands/re-export-single.js +2 -2
- package/dist/src/commands/re-export-stale-registrations.d.ts +27 -6
- package/dist/src/commands/re-export-stale-registrations.js +65 -21
- package/dist/src/commands/re-export.js +4 -0
- package/dist/src/commands/rebase/continue.js +3 -3
- package/dist/src/commands/register.js +5 -4
- package/dist/src/commands/status.js +1 -1
- package/dist/src/commands/test-build-furnace.d.ts +1 -2
- package/dist/src/commands/test-build-furnace.js +1 -2
- package/dist/src/commands/test-build-phase.d.ts +8 -0
- package/dist/src/commands/test-build-phase.js +42 -7
- package/dist/src/commands/test-control-restore.d.ts +40 -0
- package/dist/src/commands/test-control-restore.js +86 -0
- package/dist/src/commands/test-dispatch.js +68 -7
- package/dist/src/commands/test-multi-verdict.js +1 -0
- package/dist/src/commands/test-orchestrate.d.ts +6 -0
- package/dist/src/commands/test-orchestrate.js +28 -0
- package/dist/src/commands/test-perf-scope.d.ts +1 -1
- package/dist/src/commands/test-perf-scope.js +1 -1
- package/dist/src/commands/test-prelock.d.ts +7 -8
- package/dist/src/commands/test-prelock.js +15 -12
- package/dist/src/commands/test-register.js +2 -2
- package/dist/src/commands/test-results.d.ts +10 -1
- package/dist/src/commands/test-results.js +20 -3
- package/dist/src/commands/test-run.d.ts +6 -0
- package/dist/src/commands/test-run.js +23 -4
- package/dist/src/commands/test-shards.d.ts +7 -3
- package/dist/src/commands/test-shards.js +24 -7
- package/dist/src/commands/test-stale-gate.d.ts +6 -1
- package/dist/src/commands/test-stale-gate.js +40 -2
- package/dist/src/commands/test-verdict.d.ts +5 -3
- package/dist/src/commands/test.js +10 -0
- package/dist/src/commands/token.js +2 -2
- package/dist/src/commands/verify.js +1 -1
- package/dist/src/commands/watch.js +1 -1
- package/dist/src/commands/wire.js +1 -1
- package/dist/src/core/build-audit-resolve.d.ts +4 -5
- package/dist/src/core/build-audit-resolve.js +4 -5
- package/dist/src/core/build-audit-skip.d.ts +2 -2
- package/dist/src/core/build-audit.d.ts +3 -4
- package/dist/src/core/build-baseline-types.d.ts +24 -3
- package/dist/src/core/build-baseline-validate.d.ts +30 -1
- package/dist/src/core/build-baseline-validate.js +127 -35
- package/dist/src/core/build-baseline.d.ts +8 -2
- package/dist/src/core/build-baseline.js +25 -16
- package/dist/src/core/build-jar-escalation.d.ts +4 -4
- package/dist/src/core/build-jar-escalation.js +4 -4
- package/dist/src/core/build-prepare.js +4 -4
- package/dist/src/core/config-validate.js +4 -4
- package/dist/src/core/coverage-extend.d.ts +5 -3
- package/dist/src/core/coverage-extend.js +8 -3
- package/dist/src/core/coverage-records.d.ts +4 -5
- package/dist/src/core/coverage-records.js +4 -5
- package/dist/src/core/destructive.d.ts +2 -2
- package/dist/src/core/destructive.js +2 -2
- package/dist/src/core/discard-baseline.d.ts +2 -2
- package/dist/src/core/discard-baseline.js +3 -3
- package/dist/src/core/engine-session-lock.d.ts +1 -1
- package/dist/src/core/engine-session-lock.js +1 -1
- package/dist/src/core/file-lock-owner.d.ts +5 -5
- package/dist/src/core/file-lock-owner.js +5 -5
- package/dist/src/core/file-lock-queue.js +6 -8
- package/dist/src/core/file-lock-shared.d.ts +4 -4
- package/dist/src/core/file-lock-shared.js +4 -4
- package/dist/src/core/file-lock.js +7 -10
- package/dist/src/core/firefox.js +2 -2
- package/dist/src/core/furnace-apply-overwrite-warn.d.ts +1 -1
- package/dist/src/core/furnace-apply-overwrite-warn.js +1 -1
- package/dist/src/core/furnace-apply.js +3 -3
- package/dist/src/core/furnace-operation.js +5 -5
- package/dist/src/core/furnace-registration-jar-inplace.js +5 -6
- package/dist/src/core/furnace-registration-rename.d.ts +5 -5
- package/dist/src/core/furnace-registration-rename.js +5 -5
- package/dist/src/core/furnace-registration-validate.d.ts +2 -1
- package/dist/src/core/furnace-registration-validate.js +2 -1
- package/dist/src/core/furnace-registration.js +2 -2
- package/dist/src/core/git-base.js +4 -3
- package/dist/src/core/git-diff.js +1 -1
- package/dist/src/core/git.js +1 -1
- package/dist/src/core/harness-orphans.d.ts +6 -6
- package/dist/src/core/harness-orphans.js +6 -6
- package/dist/src/core/harness-port-reservation.d.ts +60 -0
- package/dist/src/core/harness-port-reservation.js +122 -0
- package/dist/src/core/history-log-file.d.ts +9 -9
- package/dist/src/core/history-log-file.js +15 -15
- package/dist/src/core/history-log.d.ts +3 -3
- package/dist/src/core/history-log.js +3 -3
- package/dist/src/core/launchable-build.d.ts +39 -0
- package/dist/src/core/launchable-build.js +85 -0
- package/dist/src/core/marionette-port.js +1 -3
- package/dist/src/core/moz-manifest-rules.js +3 -2
- package/dist/src/core/negative-control-compiled.d.ts +13 -3
- package/dist/src/core/negative-control-compiled.js +27 -5
- package/dist/src/core/parser-fallback.d.ts +5 -5
- package/dist/src/core/parser-fallback.js +5 -5
- package/dist/src/core/patch-identifier-suggest.d.ts +6 -0
- package/dist/src/core/patch-identifier-suggest.js +11 -4
- package/dist/src/core/patch-lint-checkjs.d.ts +1 -1
- package/dist/src/core/patch-lint-checkjs.js +1 -1
- package/dist/src/core/patch-lint-css.js +2 -2
- package/dist/src/core/patch-lint-file-size.d.ts +5 -7
- package/dist/src/core/patch-lint-file-size.js +5 -7
- package/dist/src/core/patch-lint-ignore.d.ts +3 -3
- package/dist/src/core/patch-lint-ignore.js +3 -3
- package/dist/src/core/patch-lint-prettier.d.ts +4 -6
- package/dist/src/core/patch-lint-prettier.js +4 -6
- package/dist/src/core/patch-lint-projection.d.ts +1 -1
- package/dist/src/core/patch-lint-projection.js +1 -1
- package/dist/src/core/patch-lint-queue-types.d.ts +2 -2
- package/dist/src/core/patch-lint-queue-types.js +2 -2
- package/dist/src/core/patch-manifest-consistency.d.ts +2 -2
- package/dist/src/core/patch-manifest-consistency.js +2 -2
- package/dist/src/core/patch-manifest-io.d.ts +5 -1
- package/dist/src/core/patch-manifest-io.js +12 -10
- package/dist/src/core/patch-manifest-key-order.d.ts +3 -4
- package/dist/src/core/patch-manifest-key-order.js +3 -4
- package/dist/src/core/patch-parse.d.ts +3 -3
- package/dist/src/core/patch-parse.js +3 -3
- package/dist/src/core/patch-policy.d.ts +1 -1
- package/dist/src/core/patch-policy.js +1 -1
- package/dist/src/core/patch-source-metadata.d.ts +1 -1
- package/dist/src/core/patch-source-metadata.js +1 -1
- package/dist/src/core/patch-subset.d.ts +5 -3
- package/dist/src/core/patch-subset.js +8 -7
- package/dist/src/core/patch-transform.d.ts +2 -2
- package/dist/src/core/patch-transform.js +2 -2
- package/dist/src/core/rebase-session.js +4 -6
- package/dist/src/core/register-xpcshell-test.d.ts +28 -7
- package/dist/src/core/register-xpcshell-test.js +76 -27
- package/dist/src/core/run-log.d.ts +8 -8
- package/dist/src/core/run-log.js +8 -8
- package/dist/src/core/status-classify.d.ts +1 -2
- package/dist/src/core/status-classify.js +1 -2
- package/dist/src/core/test-harness-crash.d.ts +5 -3
- package/dist/src/core/test-harness-crash.js +13 -14
- package/dist/src/core/test-harness-infra.d.ts +32 -0
- package/dist/src/core/test-harness-infra.js +69 -0
- package/dist/src/core/test-harness-signature.d.ts +6 -0
- package/dist/src/core/test-stale-check.d.ts +38 -0
- package/dist/src/core/test-stale-check.js +82 -1
- package/dist/src/core/test-stall-triage.js +5 -7
- package/dist/src/core/token-category.js +2 -2
- package/dist/src/core/token-inventory.js +3 -3
- package/dist/src/core/token-manager.d.ts +2 -2
- package/dist/src/core/token-manager.js +5 -7
- package/dist/src/core/token-variant.d.ts +6 -6
- package/dist/src/core/token-variant.js +7 -7
- package/dist/src/core/typecheck-shim.js +1 -1
- package/dist/src/core/wire-destroy.d.ts +1 -1
- package/dist/src/core/wire-destroy.js +1 -1
- package/dist/src/core/wire-dom-fragment.js +1 -1
- package/dist/src/core/wire-init.d.ts +1 -1
- package/dist/src/core/wire-init.js +1 -1
- package/dist/src/core/wire-subscript.d.ts +1 -1
- package/dist/src/core/wire-subscript.js +1 -1
- package/dist/src/core/wire-utils.d.ts +2 -2
- package/dist/src/core/wire-utils.js +3 -3
- package/dist/src/errors/base.d.ts +1 -1
- package/dist/src/errors/base.js +1 -1
- package/dist/src/errors/rebase.d.ts +1 -1
- package/dist/src/errors/rebase.js +1 -1
- package/dist/src/types/commands/options.d.ts +26 -3
- package/dist/src/types/config.d.ts +5 -7
- package/dist/src/utils/options.js +2 -2
- package/dist/src/utils/process.js +2 -2
- package/dist/src/utils/regex.d.ts +2 -2
- package/dist/src/utils/regex.js +3 -3
- package/dist/src/utils/sleep.d.ts +5 -6
- package/dist/src/utils/sleep.js +5 -6
- package/dist/src/utils/validation.js +2 -2
- package/docs/configuration.md +21 -23
- package/docs/exit-codes.md +8 -11
- package/docs/furnace.md +3 -3
- package/docs/lifecycle-invariants.md +36 -45
- package/docs/machine-output.md +41 -24
- package/docs/patch-workflow.md +129 -24
- package/docs/run-logs.md +8 -9
- package/docs/testing.md +105 -46
- package/package.json +1 -1
package/docs/machine-output.md
CHANGED
|
@@ -2,12 +2,9 @@
|
|
|
2
2
|
|
|
3
3
|
# Machine-readable output contract (internal)
|
|
4
4
|
|
|
5
|
-
The `--json` surface is a contract with scripted consumers.
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
`FIREFORGE-VERDICT:` line, and `lint --per-patch --report` wrote a versioned
|
|
9
|
-
file that nothing ever reads back. This file states what a `--json` command
|
|
10
|
-
has to do, so the next one added does not invent a fifth shape.
|
|
5
|
+
The `--json` surface is a contract with scripted consumers. This file states
|
|
6
|
+
what a `--json` command has to do, so the next one added does not invent a
|
|
7
|
+
shape of its own.
|
|
11
8
|
|
|
12
9
|
## The rules
|
|
13
10
|
|
|
@@ -56,11 +53,11 @@ if (options.json === true) {
|
|
|
56
53
|
| Surface | Shape | Notes |
|
|
57
54
|
| ---------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
58
55
|
| `status --json` | `{ schemaVersion: 1, … }` | Error envelope on three engine preconditions |
|
|
59
|
-
| `status --json` under `--check` | adds `check: { enabled, failOn, allow?, failOnUnknown?, failed, offenders }` |
|
|
56
|
+
| `status --json` under `--check` | adds `check: { enabled, failOn, allow?, failOnUnknown?, failed, offenders }` | On the full payload too, not only `--summary`. `allow` and `failOnUnknown` appear only when set. An offender failing only through `--fail-on-unknown` carries `unnamed: true`. `--patches` adds `scope: { patches }` |
|
|
60
57
|
| `furnace validate --json` | `{ schemaVersion: 1, passed, summary, maxWarnings?, components, issues, excepted, staleExceptions }` | `issues` counts after `validationExceptions`, stale-exception warnings included. `excepted` carries each suppressed finding with its `reason` |
|
|
61
58
|
| `check --json` | `{ schemaVersion: 1, verdict, reason?, summary, steps }` | One entry per step: `name`, `kind`, `command`, `status` (`pass`/`fail`/`skipped`), `exitCode`, `durationMs`, `detail`, and on failure `outputTail` (`timedOut` when killed at its budget). No verdict line under `--json` |
|
|
62
59
|
| `check` verdict line | `FIREFORGE-VERDICT: PASS\|FAIL [reason=step-failures\|lock-timeout\|skipped-steps failed=<steps>] steps=<n> skipped=<n> [skipped-steps=<steps>]` | Not JSON. The last stdout line, after the step table, sealed like `test`'s. Its `reason=` set is its own, not `test`'s |
|
|
63
|
-
| `tree list --json` | `{ schemaVersion: 1, trees }` | Error envelope
|
|
60
|
+
| `tree list --json` | `{ schemaVersion: 1, trees }` | Error envelope on failure |
|
|
64
61
|
| `token list --json` | `{ schemaVersion: 1, tokensCssPath, categories }` | Categories in file order, each with its tokens (`name`, `line`, `value`) |
|
|
65
62
|
| `token show --json` | `{ schemaVersion: 1, name, category, declarations }` | One entry per declaring block, with its selector trail and line |
|
|
66
63
|
| `token lint --json` | `{ schemaVersion: 1, tokensCssPath, tokenPrefix, filesScanned, findings }` | Each finding has `check`, `file`, `line`, `token`, `message`. The document is written even when findings exist; the exit is then non-zero, as with `status --check --json` |
|
|
@@ -80,7 +77,7 @@ it. Follow the rules above rather than inventing a shape.
|
|
|
80
77
|
|
|
81
78
|
The run logs behind `log=` are specified in [`run-logs.md`](run-logs.md).
|
|
82
79
|
|
|
83
|
-
Additive keys
|
|
80
|
+
Additive keys outside `test`:
|
|
84
81
|
|
|
85
82
|
- `check --json`: a skipped step carries `skipKind`, `config` when
|
|
86
83
|
`check.skip` names it and `unavailable` when the project has nothing for
|
|
@@ -92,7 +89,7 @@ Additive keys since 0.51.0 outside `test`:
|
|
|
92
89
|
`@click`). An exception that matched an error adds a
|
|
93
90
|
`validation-exception-on-error` error, and a full run under
|
|
94
91
|
`furnace.json#minComponents` a `component-floor` error on `furnace.json`.
|
|
95
|
-
- `furnace validate --json
|
|
92
|
+
- `furnace validate --json`: a `hardcoded-text` finding
|
|
96
93
|
carries `files`, the component's module file names it was found in.
|
|
97
94
|
|
|
98
95
|
## Versioning
|
|
@@ -110,6 +107,7 @@ moved.
|
|
|
110
107
|
| Reason | Meaning |
|
|
111
108
|
| ------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
112
109
|
| `crash` | The harness or the browser died, so there is no trustworthy suite result. |
|
|
110
|
+
| `server-startup` | A mochitest server never came up (`could not start server on port`, `Timed out while waiting for server startup`) before any test ran. An infrastructure failure, retried like `crash` within `--harness-retries`; this reason is what is left once the budget is spent. |
|
|
113
111
|
| `harness-arguments` | Profile or other harness argument setup failed before any tests could run; a rebuild is not the repair. |
|
|
114
112
|
| `no-tests` | The run dispatched but nothing ran. |
|
|
115
113
|
| `test-failures` | The suite ran and reported unexpected results. |
|
|
@@ -126,15 +124,19 @@ developer browser holding the objdir. An unattended reader whose pipe kept
|
|
|
126
124
|
only the verdict line could not tell those apart, so a preflight refusal that
|
|
127
125
|
can classify itself also emits `note=<class>`.
|
|
128
126
|
|
|
129
|
-
`note=` is additive, like `log=`, `signal=` and `shards=`. `reason=`
|
|
130
|
-
|
|
127
|
+
`note=` is additive, like `log=`, `signal=` and `shards=`. `reason=` always
|
|
128
|
+
comes from the closed set above, so a consumer that
|
|
131
129
|
tokenises `key=value` pairs is unaffected, and a gate that names no class
|
|
132
130
|
emits no `note=` at all. The classes are not a closed set and may grow, so
|
|
133
131
|
consumers should treat an unrecognised one as opaque. Current values:
|
|
134
132
|
`browser-busy`, `stale-browser`, `stale-browser-kill-failed`, `marionette-port-busy`, `mochitest-port-busy`,
|
|
135
133
|
`coverage-replaced`, `stale-build`, `stale-components`, `no-launchable-binary`, `negative-control` (the
|
|
136
134
|
control diff was refused), `negative-control-pending` (an interrupted run's
|
|
137
|
-
control could not be undone safely). `
|
|
135
|
+
control could not be undone safely). Also `stale-compiled`
|
|
136
|
+
(compiled sources changed after the binary under test was linked) and
|
|
137
|
+
`control-built` (the binary still carries a compiled negative control whose
|
|
138
|
+
restore build never ran or failed). An `invalid-build-baseline` refusal
|
|
139
|
+
names the first failing field and its value. `note=negative-control-restore` rides a
|
|
138
140
|
`reason=inconclusive` line whose control could not be restored byte-exact.
|
|
139
141
|
|
|
140
142
|
### Multi-run invocations: `FIREFORGE-RUN:`, `runs=` and `control=`
|
|
@@ -153,7 +155,7 @@ A `FIREFORGE-RUN:` line is never a verdict: the invocation still ends with
|
|
|
153
155
|
exactly one `FIREFORGE-VERDICT:` line. With more than one planned run it
|
|
154
156
|
carries `runs=<passed>/<planned>` and no count keys; a failed aggregate takes
|
|
155
157
|
the most structural reason among its runs (`inconclusive`, `preflight`,
|
|
156
|
-
`crash`, `harness-arguments`, `no-tests`, `test-failures`) and that run's
|
|
158
|
+
`crash`, `server-startup`, `harness-arguments`, `no-tests`, `test-failures`) and that run's
|
|
157
159
|
`note=`. A run that never started (the invocation stopped at a refusal)
|
|
158
160
|
counts toward `<planned>` but not `<passed>`.
|
|
159
161
|
|
|
@@ -185,7 +187,7 @@ A sharded run prints one `FIREFORGE-SHARD:` line per finished shard, before
|
|
|
185
187
|
the verdict line:
|
|
186
188
|
|
|
187
189
|
```
|
|
188
|
-
FIREFORGE-SHARD: PASS|FAIL [reason=…] [checks=<n>] [unexpected=<n>] shard=<i>/<n> path=<label> [failed-files=<path>,…]
|
|
190
|
+
FIREFORGE-SHARD: PASS|FAIL [reason=…] [checks=<n>] [unexpected=<n>] shard=<i>/<n> path=<label> [failed-files=<path>,…] [ports=http:<n>,ssl:<n>,ws:<n>]
|
|
189
191
|
```
|
|
190
192
|
|
|
191
193
|
`path=` is the shard's path argument (whitespace replaced by `_`), or a
|
|
@@ -195,15 +197,31 @@ aggregate verdict appends `failed-shards=<label>,…` after `shards=` when any
|
|
|
195
197
|
shard did not pass; under `--shard-size` `shards=` counts files and
|
|
196
198
|
`failed-shards=` names files. Both are absent on a green run.
|
|
197
199
|
|
|
200
|
+
`ports=` names the mochitest HTTP server, ssltunnel and
|
|
201
|
+
WebSocket ports the shard's harness reported (its "falling back to port"
|
|
202
|
+
lines), in that order and only those it reported; it is absent when the
|
|
203
|
+
harness reported none (an xpcshell shard, or a harness that died before its
|
|
204
|
+
servers). A shard whose server never started says `reason=server-startup`,
|
|
205
|
+
and the aggregate verdict does too when every crashed shard failed that way.
|
|
206
|
+
|
|
198
207
|
### Additive keys of parallel and per-file runs
|
|
199
208
|
|
|
200
209
|
`jobs=<n>` marks a `--jobs` run, `lock=shared` a run that held the engine
|
|
201
|
-
session lock shared, and `results=<path>` names the `--results` document.
|
|
210
|
+
session lock shared, and `results=<path>` names the `--results` document.
|
|
211
|
+
A `--jobs` run whose caller set `MOZ_UPLOAD_DIR` appends
|
|
212
|
+
`upload-dirs=<dir>,…`, the per-instance upload directories
|
|
213
|
+
(`<MOZ_UPLOAD_DIR>/job-<i>`, one per instance that ran), and a `--results`
|
|
214
|
+
record whose `test` is `automation.py` (a harness-level result) carries
|
|
215
|
+
`shardFiles`, plus `file` when its shard has exactly one file. A
|
|
202
216
|
run whose engine changed mid-run only in files the running browser cannot
|
|
203
217
|
see keeps its verdict and appends `drift-tolerated=<n>`. A negative control
|
|
204
|
-
on compiled source appends `control-build=compiled
|
|
218
|
+
on compiled source appends `control-build=compiled`, and
|
|
219
|
+
`control-restore-build=done|failed` for the full build that recompiles the
|
|
220
|
+
restored source after the last run. Every run that reaches
|
|
221
|
+
dispatch appends `build-id=<BuildID>`, read from the launchable build's
|
|
222
|
+
`application.ini` (absent when that file has no `BuildID`). A raw log
|
|
205
223
|
that starts none of a dispatch's requested files counts as
|
|
206
|
-
`started=0/<m> ... started-source=raw
|
|
224
|
+
`started=0/<m> ... started-source=raw`.
|
|
207
225
|
|
|
208
226
|
### The additive `shuffle=` key
|
|
209
227
|
|
|
@@ -223,9 +241,8 @@ preflight, survivors of an earlier run in this objdir under `--reap-orphans`
|
|
|
223
241
|
or `test.reapOrphans: "reap"`; at teardown, helpers this run's harness
|
|
224
242
|
launched (httpd, websocket server, ssltunnel, process bridge, the browser,
|
|
225
243
|
`moz-http2`) that were still alive after mach exited. Summed across the census, every
|
|
226
|
-
retry attempt and every shard. Absent when nothing was reaped, so a green
|
|
227
|
-
a
|
|
228
|
-
distinguishable from it. A run ended by SIGTERM or by the parent-exit
|
|
244
|
+
retry attempt and every shard. Absent when nothing was reaped, so a green after a reap is
|
|
245
|
+
distinguishable from a green on a quiet machine. A run ended by SIGTERM or by the parent-exit
|
|
229
246
|
watchdog writes its verdict before the teardown reap runs, so that line never
|
|
230
247
|
carries the key; the reap is reported on stderr instead.
|
|
231
248
|
|
|
@@ -243,10 +260,10 @@ and measured CPU. These diagnostics annotate a test failure without changing
|
|
|
243
260
|
its classifier reason.
|
|
244
261
|
|
|
245
262
|
Perf runs append `power-source=ac|battery|unknown`. On macOS the source is
|
|
246
|
-
read from `pmset -g ps`, so charging on AC
|
|
263
|
+
read from `pmset -g ps`, so charging on AC reads `ac`. A known source
|
|
247
264
|
transition appends `power-changed=true` and refuses the run as
|
|
248
|
-
`reason=inconclusive`. The producer's sample JSON
|
|
249
|
-
|
|
265
|
+
`reason=inconclusive`. The producer's sample JSON carries an additional
|
|
266
|
+
`fireforgeHost: { start, end, powerSourceChanged }` object, where each host
|
|
250
267
|
state includes `load`, `power` and an optional `topProcess` with CPU and
|
|
251
268
|
command. Consumers should tolerate this additive object. Unknown power
|
|
252
269
|
state is visible but never treated as a proven transition.
|
package/docs/patch-workflow.md
CHANGED
|
@@ -109,7 +109,7 @@ adjacent to it, meaning the re-export would plausibly have to capture it:
|
|
|
109
109
|
moz.build or test-manifest line, `*` globs included).
|
|
110
110
|
|
|
111
111
|
A file in a sibling or nested directory is not adjacent, so a peer
|
|
112
|
-
session's unexported test in `test/hominis-tiles/`
|
|
112
|
+
session's unexported test in `test/hominis-tiles/` does not refuse a
|
|
113
113
|
patch that owns `test/hominis/browser.toml`. The refusal names every file
|
|
114
114
|
with its anchor (`beside engine/<dir>` or `registered by engine/<carrier>`).
|
|
115
115
|
|
|
@@ -139,8 +139,8 @@ fireforge re-export 102 200 --refuse-adjacent-unmanaged --refuse-foreign-drift \
|
|
|
139
139
|
|
|
140
140
|
`--expect-from <file>` reads `--expect` paths from a file, one per line,
|
|
141
141
|
with blank lines and `#` comments ignored. Under zsh a list held in one
|
|
142
|
-
variable reaches FireForge as a single argument, and
|
|
143
|
-
|
|
142
|
+
variable reaches FireForge as a single argument, and a file avoids splitting
|
|
143
|
+
it by hand.
|
|
144
144
|
|
|
145
145
|
Arguments are checked before the run queues for the engine lock: an empty
|
|
146
146
|
or unknown patch name, a positional that is an engine file (the refusal
|
|
@@ -192,6 +192,11 @@ exception. Removing every file would empty the patch and requires `patch
|
|
|
192
192
|
delete` (or `patch retire`, which keeps the order number) instead.
|
|
193
193
|
`--expect-removed` cannot combine with `--scan`, `--files` or `--all`.
|
|
194
194
|
|
|
195
|
+
The same run drops every staged declaration, registration or forward
|
|
196
|
+
import, in any patch of the queue, whose `creates` path it retired and no
|
|
197
|
+
other patch still owns. It prints each one (`would drop` in a dry run) and
|
|
198
|
+
records the drop in the history log (`re-export-staged-prune`).
|
|
199
|
+
|
|
195
200
|
### Forward imports and new modules
|
|
196
201
|
|
|
197
202
|
A re-export (plain or `--scan`) refused because a file imports a module a
|
|
@@ -203,14 +208,35 @@ placeholder. A refused `--scan` adoption, `patch move-files` or `patch split`
|
|
|
203
208
|
also writes every declaration it proposes into one lint-report-shaped JSON
|
|
204
209
|
(`--declarations-out <path>`, by default under `.fireforge/declarations/`)
|
|
205
210
|
and names the single `patch staged-dependency <holder> --add --from <file>`
|
|
206
|
-
call per holding patch that discharges them all
|
|
207
|
-
that owns a shared manifest
|
|
208
|
-
|
|
211
|
+
call per holding patch that discharges them all, so moving tests out of a
|
|
212
|
+
patch that owns a shared manifest needs no declaration typed per manifest
|
|
213
|
+
line.
|
|
214
|
+
|
|
215
|
+
For `patch move-files`, `patch split` and a placed `export`:
|
|
216
|
+
|
|
217
|
+
- The projection of `patch move-files`, `patch split` and a placed `export`
|
|
218
|
+
lints with the queue's whole lint configuration, as the committed `lint
|
|
219
|
+
--per-patch` gate does. With `patchLint.forwardRegistration: "extended"`,
|
|
220
|
+
a shared test manifest's suite entries (`["browser_*.js"]`) are projected
|
|
221
|
+
with the move and written to the `--declarations-out` report, not only its
|
|
222
|
+
`support-files` lines. A dry run that reads clean stays clean after the
|
|
223
|
+
move.
|
|
224
|
+
- A refused `move-files --create` or `split` report names the patch the
|
|
225
|
+
rerun creates as the `owner` (its planned `<order>-<category>-<name>.patch`).
|
|
226
|
+
- The declarations `move-files` and `split` write, and every entry of their
|
|
227
|
+
report, carry a `reason` naming the move, such as
|
|
228
|
+
`"201-ui-tests.patch → 236-ui-suites.patch by patch move-files"`. The
|
|
229
|
+
`--add --from` call the refusal prints then needs no `--reason`; an
|
|
230
|
+
entry's own reason wins over the flag.
|
|
209
231
|
|
|
210
232
|
A re-export also drops a staged registration whose `creates` path no patch
|
|
211
233
|
in the queue owns any more, for example after a merge deleted the file it
|
|
212
234
|
registered. The dry run names the drop, and the write records it in the
|
|
213
|
-
history log (`re-export-staged-prune`).
|
|
235
|
+
history log (`re-export-staged-prune`). A registration whose
|
|
236
|
+
`creates` file exists in engine/, or is an `--expect-new` path of the run,
|
|
237
|
+
is kept and named ("kept: file exists but no patch owns it yet"): the
|
|
238
|
+
manifest owner can re-export after the declaration and before the scan
|
|
239
|
+
that adopts the file, in either order.
|
|
214
240
|
|
|
215
241
|
An `export --order` (or `--before`/`--after`) refused on a new system
|
|
216
242
|
module that no patch registers in moz.build says "register first". When the
|
|
@@ -236,13 +262,61 @@ The re-export policy gate checks the `filesAffected` the export will write,
|
|
|
236
262
|
and only for the patch being written, so one patch's stale row cannot fail
|
|
237
263
|
the other patches in the same call.
|
|
238
264
|
|
|
265
|
+
### Registering files
|
|
266
|
+
|
|
267
|
+
`fireforge register <path>` adds a new file's line to the build manifest
|
|
268
|
+
that packages or runs it: a jar.mn, a moz.build list, a test manifest. Most
|
|
269
|
+
manifests are kept in sorted order, and the entry is inserted
|
|
270
|
+
alphabetically. `--after <entry>` places it after the line containing that
|
|
271
|
+
substring instead, where the manifest's rule supports it. Elsewhere the
|
|
272
|
+
flag is ignored with a warning, and an `--after` that matches nothing falls
|
|
273
|
+
back to sorted order with a warning.
|
|
274
|
+
|
|
275
|
+
An xpcshell test (`test_*.js` outside `browser/base/content/test/`) goes
|
|
276
|
+
into its directory's `xpcshell.toml` as a `["test_*.js"]` section, placed
|
|
277
|
+
as follows:
|
|
278
|
+
|
|
279
|
+
- The new section is inserted ahead of the `#` comment lines directly above
|
|
280
|
+
the entry it precedes, never between a comment and the entry it describes.
|
|
281
|
+
- `--after <entry>` places the new section after the named entry's whole
|
|
282
|
+
block, with its keys and before the next entry's comment. An exact
|
|
283
|
+
section name matches first, then a substring.
|
|
284
|
+
|
|
285
|
+
```sh
|
|
286
|
+
fireforge register browser/components/hominis/test/unit/test_HominisStoreQuota.js \
|
|
287
|
+
--after test_HominisStore.js
|
|
288
|
+
```
|
|
289
|
+
|
|
290
|
+
`--create-manifest` scaffolds a missing manifest and wires it into the
|
|
291
|
+
nearest moz.build instead of refusing with "Manifest not found".
|
|
292
|
+
|
|
239
293
|
## Queue maintenance
|
|
240
294
|
|
|
241
295
|
Under `fireforge patch`:
|
|
242
296
|
|
|
243
297
|
- `patch compact` closes ordinal gaps, and is range-aware when
|
|
244
298
|
`patchPolicy.ranges` is configured.
|
|
245
|
-
- `patch reorder` moves a patch.
|
|
299
|
+
- `patch reorder` moves a patch. `patch reorder --shift <n>
|
|
300
|
+
--from <order> [--through <order>]` (no patch name) renumbers a run of
|
|
301
|
+
patches up by `n` in one transaction, to open room for inserts.
|
|
302
|
+
`--through` defaults to the end of the run of consecutive occupied orders
|
|
303
|
+
of `--from`'s category. Retired and reserved slots inside the run move
|
|
304
|
+
with it (a moved reservation is named, so its holder can be told). A shift
|
|
305
|
+
that would land on an order a patch or slot holds past the run is refused.
|
|
306
|
+
Under `patchPolicy.allowGaps: false` the opened orders are recorded as
|
|
307
|
+
reservations (owner `patch reorder --shift`), so the queue stays valid,
|
|
308
|
+
and the `export --order` or `split --order` that takes each one fills it.
|
|
309
|
+
The shift checks the patch policy, projects the cross-patch lint
|
|
310
|
+
(refusing only on errors the shift adds), and commits under the patch
|
|
311
|
+
lock, refusing if the plan changed while it waited for confirmation.
|
|
312
|
+
`--map-out <file>` on `reorder` (every mode) and on `split` writes the
|
|
313
|
+
committed old-to-new filename map as a JSON object, so references to the
|
|
314
|
+
renumbered patches can be rewritten from the file:
|
|
315
|
+
|
|
316
|
+
```sh
|
|
317
|
+
fireforge patch reorder --shift 4 --from 104 --through 128 --map-out shift-map.json --yes
|
|
318
|
+
```
|
|
319
|
+
|
|
246
320
|
- `patch split <source> --files <paths...> --name <name>` carves files out of
|
|
247
321
|
a patch into a new one as a single transaction, including staged-dependency
|
|
248
322
|
owner rewrites, and supports `--dry-run`. `patch move-files <from> <to>
|
|
@@ -253,6 +327,23 @@ Under `fireforge patch`:
|
|
|
253
327
|
declaration whose declaring file moved goes with it, and a declaration the
|
|
254
328
|
move makes unused is dropped. The patch policy, including the gap rule, is
|
|
255
329
|
checked before any lint runs.
|
|
330
|
+
- `patch move-files` covers a whole split in one call:
|
|
331
|
+
- `--scan-file <path>` (repeatable) adopts a new engine file that no patch
|
|
332
|
+
owns into the destination (`<to>`, or the patch `--create` makes) in
|
|
333
|
+
the same transaction. Both bodies are linted as the transaction leaves
|
|
334
|
+
them, so the source is never judged on a body grown by an adoption the
|
|
335
|
+
move would shrink again. An owned or missing path is refused.
|
|
336
|
+
- `--retire-empty` lets a move into an existing patch take every file of
|
|
337
|
+
the source: the declarations whose `owner` is the source re-point to the
|
|
338
|
+
destination, the source's own declarations go with its files (one that
|
|
339
|
+
becomes self-owned is dropped), and the source is retired as by `patch
|
|
340
|
+
retire`, its order kept as a retired slot. Without the flag, a move that
|
|
341
|
+
would empty the source is refused and names the flag.
|
|
342
|
+
- A per-patch size refusal on either side names a tier change behind it,
|
|
343
|
+
for example `Tier change: the source becomes test tier (it was general
|
|
344
|
+
tier): 9634 lines against 6000.` A source that keeps only test files is
|
|
345
|
+
held to the test tier's ceiling for every line, so move its test files
|
|
346
|
+
out before its last product file.
|
|
256
347
|
- `patch rename` also supports `--category` and `--order`.
|
|
257
348
|
- `patch retire <name>` removes a patch like `patch delete` (same dependency
|
|
258
349
|
refusal, `--dry-run` and confirmation) but keeps its order number as a
|
|
@@ -268,7 +359,7 @@ compact` renumbers through retired slots like any other gap.
|
|
|
268
359
|
nothing owns it, so `status` would report it unmanaged. Delete those files
|
|
269
360
|
first, or pass `--delete-created` to remove them as part of the confirmed
|
|
270
361
|
operation (under the engine lock as well). Files the patch only modifies
|
|
271
|
-
keep their edits and become unmanaged
|
|
362
|
+
keep their edits and become unmanaged.
|
|
272
363
|
- `patch reserve <order> --category <c> --owner <label> [--reason <text>]`
|
|
273
364
|
holds an order for a patch a session has agreed to export but has not
|
|
274
365
|
exported yet. The reservation lives in `patches.json#reserved`. Like a
|
|
@@ -289,22 +380,32 @@ hash-object` and `git update-index`. A collision (two rows at one order) or
|
|
|
289
380
|
an invalid result is refused before the index is touched. The working copy
|
|
290
381
|
is never changed and nothing is committed. Name a patch the working copy
|
|
291
382
|
no longer has by its HEAD filename to stage its removal, and name both
|
|
292
|
-
filenames of a renamed patch.
|
|
383
|
+
filenames of a renamed patch. Every manifest write, a
|
|
384
|
+
re-export's row update included, puts every row, changed or not, in the one
|
|
385
|
+
canonical key order that `patch stage` writes, so after a write the working
|
|
386
|
+
copy and the index do not differ on key order alone.
|
|
293
387
|
- `patch staged-dependency <name> --remove` names the entries to remove by
|
|
294
388
|
any of `--file`, `--specifier`/`--line`, `--creates` and `--owner`. It needs
|
|
295
389
|
`--creates`, or `--file` with the matcher. `--creates` alone removes every
|
|
296
390
|
declaration for that created path, which is the cleanup after a merge
|
|
297
391
|
deletes it. Registration lines compare whitespace-insensitively, as the
|
|
298
|
-
lint does. A selection that matches nothing is refused with exit 8
|
|
299
|
-
|
|
392
|
+
lint does. A selection that matches nothing is refused with exit 8, on a
|
|
393
|
+
dry run too.
|
|
300
394
|
- `patch staged-dependency <name> --add --from <json-file>` adds many
|
|
301
395
|
declarations in one call under one lock hold. The file is a `lint
|
|
302
396
|
--per-patch --report` document (its findings' `stagedDeclarations` for
|
|
303
397
|
that patch) or a JSON array of `{ file, specifier | line, creates, owner?,
|
|
304
398
|
reason?, patch? }` entries; entries naming another patch are skipped, and
|
|
305
399
|
`--reason` fills entries without one. Every `staged-dependency` call logs
|
|
306
|
-
only its delta (`added` / `removed`) in the history
|
|
307
|
-
|
|
400
|
+
only its delta (`added` / `removed`) in the history. A history record may
|
|
401
|
+
carry the whole `before` / `after` lists instead.
|
|
402
|
+
- `--add` (single or `--from`) on a declaration already present
|
|
403
|
+
(same file, specifier or line, creates and owner) with a different
|
|
404
|
+
`reason` replaces the reason in place, keeping the entry's position in its
|
|
405
|
+
list. The summary counts these apart from additions, as in
|
|
406
|
+
`updated the reason of 87`, and the history logs each as the old entry
|
|
407
|
+
removed and the new one added. An `--add` without a reason never clears
|
|
408
|
+
one.
|
|
308
409
|
|
|
309
410
|
### Parking a session's edits
|
|
310
411
|
|
|
@@ -332,7 +433,10 @@ resolves.
|
|
|
332
433
|
|
|
333
434
|
`lint --per-patch --patches` accepts repeated flags, comma lists, full
|
|
334
435
|
filenames or stems, bare order numbers, manifest names, category-prefixed
|
|
335
|
-
slugs, and bare slugs.
|
|
436
|
+
slugs, and bare slugs. A list is also split on whitespace, so
|
|
437
|
+
a list held in one shell variable (`--patches "$P"` under zsh) selects every
|
|
438
|
+
patch it names. A name that matches no patch is refused with that name, its
|
|
439
|
+
nearest matches and the queue size, not with every patch in the queue.
|
|
336
440
|
|
|
337
441
|
`lint --per-patch --max-warnings 0` is the warning-clean form for a release
|
|
338
442
|
gate.
|
|
@@ -341,8 +445,8 @@ gate.
|
|
|
341
445
|
every NOTICE row, for example `NOTICE [large-patch-lines]: 180 across 172
|
|
342
446
|
patch(es), 150 of them suppressed by lintIgnore (see --report)`. On a green
|
|
343
447
|
queue those rows are reviewed waivers and under-threshold measurements, and
|
|
344
|
-
there can be hundreds of them. The default, `--notices full`, prints
|
|
345
|
-
|
|
448
|
+
there can be hundreds of them. The default, `--notices full`, prints every
|
|
449
|
+
row. Errors and warnings always print in full, and the `--report`
|
|
346
450
|
JSON is the same in both modes.
|
|
347
451
|
|
|
348
452
|
`lint --per-patch --report <path>` writes a machine-readable JSON report with
|
|
@@ -361,7 +465,7 @@ programmatic API, with the file-size helpers `isTestFile`,
|
|
|
361
465
|
`file-too-large` measures in a patch: the JS files it creates, and never a
|
|
362
466
|
modified file or a new file of another kind. The rule selects its files
|
|
363
467
|
through that same function, so an audit that uses it cannot drift from the
|
|
364
|
-
rule.
|
|
468
|
+
rule. The API also exports the measurement the size rules
|
|
365
469
|
themselves take, `measurePatchSize(engineDir, diff, filesAffected, config)`
|
|
366
470
|
(lines, test-file lines, files and registration files under the configured
|
|
367
471
|
metric), `isPatchSizeRegistrationFile(file, globs)`, the per-line
|
|
@@ -391,8 +495,8 @@ the real type. See
|
|
|
391
495
|
[`configuration.md`](configuration.md#patchlint) for the project hooks
|
|
392
496
|
(`checkJsExtraShim`, `checkJsTestFiles`, `checkJsTestShim`).
|
|
393
497
|
|
|
394
|
-
For release whitespace checks, use `npm run whitespace:check`. It
|
|
395
|
-
|
|
498
|
+
For release whitespace checks, use `npm run whitespace:check`. It checks
|
|
499
|
+
source diffs while excluding the diff syntax of generated
|
|
396
500
|
`patches/*.patch` files.
|
|
397
501
|
|
|
398
502
|
### Linting single files
|
|
@@ -515,13 +619,14 @@ On a shared engine, `--patches <list>` judges only the named patches:
|
|
|
515
619
|
`status` keeps the files each one owns or claims (and, with `--ownership` or
|
|
516
620
|
the ownership checks, the rows naming it), and `verify` keeps the findings
|
|
517
621
|
that name it. Patches are named the way `lint --per-patch --patches` names
|
|
518
|
-
them (filename, stem, order number, manifest name or slug
|
|
519
|
-
|
|
622
|
+
them (filename, stem, order number, manifest name or slug; repeated, or
|
|
623
|
+
separated by commas or whitespace). A peer's drifted
|
|
624
|
+
patch then does not turn this session's gate red. The limit is the
|
|
520
625
|
point: an unmanaged file belongs to no patch, so a scoped run never judges
|
|
521
626
|
unexported files, this session's included. Run the unscoped gate before a
|
|
522
627
|
commit that should cover them. `lint --per-patch --patches` keeps every
|
|
523
628
|
queue finding that names a scoped patch, even on a file the patch no longer
|
|
524
|
-
touches (a stale `staged-dependency-unused` declaration
|
|
629
|
+
touches (a stale `staged-dependency-unused` declaration). `verify --patches` keeps findings about the
|
|
525
630
|
queue as a whole (a `patches.json` that does not parse) whatever the scope.
|
|
526
631
|
|
|
527
632
|
`verify` resolves every `resource:///modules/…` and `resource://gre/modules/…`
|
|
@@ -586,7 +691,7 @@ as possibly cascading from it, since the replay continues without the
|
|
|
586
691
|
rejected patch. Run it after the download, when HEAD is the new source. The
|
|
587
692
|
header names the previous pin as "from": `firefox.version` in the
|
|
588
693
|
`fireforge.json` committed at the project's HEAD, the tree the queue was
|
|
589
|
-
last applied to
|
|
694
|
+
last applied to. The patch stamps follow on their own line
|
|
590
695
|
(`Patch stamps: 317 at 153.0esr, 5 at 153.3.0esr`), oldest first and
|
|
591
696
|
compared as versions rather than strings, because patches untouched since an
|
|
592
697
|
older hop keep their older stamp. When no committed pin precedes the target
|
package/docs/run-logs.md
CHANGED
|
@@ -8,16 +8,15 @@
|
|
|
8
8
|
|
|
9
9
|
## Why the tool holds the log, not the operator
|
|
10
10
|
|
|
11
|
-
|
|
12
|
-
convenient thing to do when output is long is
|
|
11
|
+
Without a log, a run's diagnosis exists in exactly one place: the terminal.
|
|
12
|
+
The convenient thing to do when output is long is
|
|
13
13
|
`fireforge test … 2>&1 | tail -40`, which keeps the summary, discards the
|
|
14
14
|
`TEST-UNEXPECTED-FAIL` lines that say what broke, and launders the exit code
|
|
15
|
-
as well. Nothing else
|
|
15
|
+
as well. Nothing else holds the output: `runMachCapture` keeps a 2 MB
|
|
16
16
|
in-memory tail that dies with the process, and the shard retry loop discards
|
|
17
17
|
earlier attempts outright.
|
|
18
18
|
|
|
19
|
-
|
|
20
|
-
downstream and broken after each writing. That is a sign it is not an
|
|
19
|
+
An operator rule ("never pipe a run") gets broken, so this is not an
|
|
21
20
|
operator problem. The tool is the only party that can make the log survive
|
|
22
21
|
the mistake.
|
|
23
22
|
|
|
@@ -25,7 +24,7 @@ the mistake.
|
|
|
25
24
|
|
|
26
25
|
- **Complete output, never the echo filter's collapsed form.** The artifact
|
|
27
26
|
exists so that whoever is diagnosing the run can re-read it. Shortening it
|
|
28
|
-
would
|
|
27
|
+
would lose what it is kept for. The one transformation applied is
|
|
29
28
|
the secret-masking pass below, which changes values but never line
|
|
30
29
|
structure.
|
|
31
30
|
- **Secret-shaped values are masked in the file, and only in the file.** The
|
|
@@ -94,11 +93,11 @@ away. The refusal's own explanatory text is written into the log, and to
|
|
|
94
93
|
stdout, before the verdict line seals stdout.
|
|
95
94
|
|
|
96
95
|
Both halves matter. The verdict seal routes everything the CLI error boundary
|
|
97
|
-
renders afterwards to stderr, so a run captured with `> file`
|
|
96
|
+
renders afterwards to stderr, so a run captured with `> file` would keep
|
|
98
97
|
`FIREFORGE-VERDICT: FAIL reason=preflight` and nothing else. That rendering
|
|
99
98
|
also happens after the run log is closed, so the artifact the verdict's own
|
|
100
|
-
`log=` key
|
|
101
|
-
|
|
99
|
+
`log=` key points at would hold only the pre-test build. Writing before the
|
|
100
|
+
seal avoids both without giving up the contract: the reason lands on both channels,
|
|
102
101
|
and the verdict is still the run's last stdout line.
|
|
103
102
|
|
|
104
103
|
## Where the path is announced
|