@hominis/fireforge 0.45.0 → 0.46.1
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 +409 -446
- package/dist/bin/fireforge.d.ts +1 -1
- package/dist/bin/fireforge.js +21 -15
- package/dist/build-info.json +4 -4
- package/dist/src/cli-usage-error.d.ts +46 -0
- package/dist/src/cli-usage-error.js +81 -0
- package/dist/src/cli.d.ts +7 -2
- package/dist/src/cli.js +47 -47
- package/dist/src/commands/bootstrap-checks.js +2 -1
- package/dist/src/commands/bootstrap.js +3 -4
- package/dist/src/commands/build.js +27 -17
- package/dist/src/commands/config.js +9 -9
- package/dist/src/commands/destructive-decision.d.ts +19 -0
- package/dist/src/commands/destructive-decision.js +31 -0
- package/dist/src/commands/discard.js +5 -5
- package/dist/src/commands/doctor-check-core.d.ts +4 -10
- package/dist/src/commands/doctor-check-core.js +0 -8
- package/dist/src/commands/doctor-external-toolchains.js +2 -2
- package/dist/src/commands/doctor-furnace-config-sync.d.ts +2 -2
- package/dist/src/commands/doctor-furnace-config-sync.js +20 -20
- package/dist/src/commands/doctor-furnace-jar.d.ts +1 -1
- package/dist/src/commands/doctor-furnace-jar.js +1 -1
- package/dist/src/commands/doctor-furnace.js +22 -22
- package/dist/src/commands/doctor-orphaned-harness.d.ts +10 -17
- package/dist/src/commands/doctor-orphaned-harness.js +14 -23
- package/dist/src/commands/doctor-patch-manifest.d.ts +2 -1
- package/dist/src/commands/doctor-patch-manifest.js +7 -6
- package/dist/src/commands/doctor-post-rebase-audit.js +3 -3
- package/dist/src/commands/doctor-source-pin.d.ts +12 -12
- package/dist/src/commands/doctor-source-pin.js +14 -14
- package/dist/src/commands/doctor-working-tree.d.ts +3 -3
- package/dist/src/commands/doctor-working-tree.js +3 -3
- package/dist/src/commands/doctor.d.ts +3 -1
- package/dist/src/commands/doctor.js +15 -16
- package/dist/src/commands/download.js +50 -37
- package/dist/src/commands/export-all.js +29 -12
- package/dist/src/commands/export-flow.d.ts +5 -5
- package/dist/src/commands/export-flow.js +29 -59
- package/dist/src/commands/export-placement-conflicts.d.ts +3 -3
- package/dist/src/commands/export-placement-conflicts.js +12 -12
- package/dist/src/commands/export-placement-gate.d.ts +2 -2
- package/dist/src/commands/export-placement-gate.js +7 -13
- package/dist/src/commands/export-placement-policy.d.ts +1 -1
- package/dist/src/commands/export-placement-policy.js +4 -6
- package/dist/src/commands/export-shared.d.ts +51 -32
- package/dist/src/commands/export-shared.js +17 -32
- package/dist/src/commands/export.js +14 -5
- package/dist/src/commands/furnace/apply.js +16 -16
- package/dist/src/commands/furnace/authoring-config.d.ts +13 -0
- package/dist/src/commands/furnace/authoring-config.js +19 -0
- package/dist/src/commands/furnace/chrome-doc-remove.d.ts +1 -1
- package/dist/src/commands/furnace/chrome-doc-remove.js +2 -2
- package/dist/src/commands/furnace/chrome-doc-templates.d.ts +14 -14
- package/dist/src/commands/furnace/chrome-doc-templates.js +17 -17
- package/dist/src/commands/furnace/chrome-doc-tests.d.ts +2 -2
- package/dist/src/commands/furnace/chrome-doc-tests.js +4 -4
- package/dist/src/commands/furnace/chrome-doc.d.ts +8 -8
- package/dist/src/commands/furnace/chrome-doc.js +18 -18
- package/dist/src/commands/furnace/create-browser-test.d.ts +1 -1
- package/dist/src/commands/furnace/create-browser-test.js +7 -12
- package/dist/src/commands/furnace/create-dry-run.d.ts +4 -4
- package/dist/src/commands/furnace/create-dry-run.js +6 -9
- package/dist/src/commands/furnace/create-features.d.ts +2 -2
- package/dist/src/commands/furnace/create-features.js +2 -2
- package/dist/src/commands/furnace/create-mochikit.d.ts +4 -4
- package/dist/src/commands/furnace/create-mochikit.js +7 -7
- package/dist/src/commands/furnace/create-templates.d.ts +31 -15
- package/dist/src/commands/furnace/create-templates.js +20 -19
- package/dist/src/commands/furnace/create-xpcshell.d.ts +5 -5
- package/dist/src/commands/furnace/create-xpcshell.js +8 -8
- package/dist/src/commands/furnace/create.d.ts +1 -1
- package/dist/src/commands/furnace/create.js +35 -29
- package/dist/src/commands/furnace/deploy.js +15 -6
- package/dist/src/commands/furnace/diff.js +7 -7
- package/dist/src/commands/furnace/index.js +1 -1
- package/dist/src/commands/furnace/init.js +17 -16
- package/dist/src/commands/furnace/list.js +2 -2
- package/dist/src/commands/furnace/override.d.ts +1 -1
- package/dist/src/commands/furnace/override.js +43 -34
- package/dist/src/commands/furnace/preview.js +17 -17
- package/dist/src/commands/furnace/refresh.js +15 -7
- package/dist/src/commands/furnace/remove-mutations.d.ts +9 -10
- package/dist/src/commands/furnace/remove-mutations.js +19 -19
- package/dist/src/commands/furnace/remove-state.d.ts +1 -1
- package/dist/src/commands/furnace/remove-state.js +1 -1
- package/dist/src/commands/furnace/remove.js +4 -8
- package/dist/src/commands/furnace/rename-browser-test.js +10 -15
- package/dist/src/commands/furnace/rename-xpcshell.d.ts +2 -2
- package/dist/src/commands/furnace/rename-xpcshell.js +3 -3
- package/dist/src/commands/furnace/rename.js +36 -36
- package/dist/src/commands/furnace/scan.js +3 -3
- package/dist/src/commands/furnace/status.js +19 -16
- package/dist/src/commands/furnace/sync.js +6 -6
- package/dist/src/commands/furnace/test-file-name.d.ts +28 -0
- package/dist/src/commands/furnace/test-file-name.js +39 -0
- package/dist/src/commands/furnace/validate.js +11 -12
- package/dist/src/commands/furnace/validation-output.d.ts +21 -9
- package/dist/src/commands/furnace/validation-output.js +3 -8
- package/dist/src/commands/import.js +22 -29
- package/dist/src/commands/lint-per-patch.d.ts +2 -2
- package/dist/src/commands/lint-per-patch.js +27 -12
- package/dist/src/commands/lint-per-run-checkjs.d.ts +14 -15
- package/dist/src/commands/lint-per-run-checkjs.js +14 -15
- package/dist/src/commands/lint-report.d.ts +3 -3
- package/dist/src/commands/lint-report.js +4 -4
- package/dist/src/commands/lint.d.ts +5 -4
- package/dist/src/commands/lint.js +36 -36
- package/dist/src/commands/manifest.d.ts +4 -4
- package/dist/src/commands/manifest.js +1 -1
- package/dist/src/commands/package.js +4 -6
- package/dist/src/commands/patch/compact.d.ts +2 -2
- package/dist/src/commands/patch/compact.js +19 -20
- package/dist/src/commands/patch/delete.d.ts +1 -1
- package/dist/src/commands/patch/delete.js +23 -33
- package/dist/src/commands/patch/entry-projection.d.ts +13 -0
- package/dist/src/commands/patch/entry-projection.js +24 -0
- package/dist/src/commands/patch/lint-ignore.d.ts +3 -12
- package/dist/src/commands/patch/lint-ignore.js +33 -44
- package/dist/src/commands/patch/move-files-create.d.ts +2 -2
- package/dist/src/commands/patch/move-files-create.js +29 -15
- package/dist/src/commands/patch/move-files-into.d.ts +2 -2
- package/dist/src/commands/patch/move-files-into.js +41 -37
- package/dist/src/commands/patch/move-files.js +5 -14
- package/dist/src/commands/patch/patch-context.d.ts +1 -1
- package/dist/src/commands/patch/rename.d.ts +4 -4
- package/dist/src/commands/patch/rename.js +35 -49
- package/dist/src/commands/patch/reorder.js +35 -48
- package/dist/src/commands/patch/split-plan.d.ts +7 -8
- package/dist/src/commands/patch/split-plan.js +10 -13
- package/dist/src/commands/patch/split.d.ts +2 -2
- package/dist/src/commands/patch/split.js +50 -48
- package/dist/src/commands/patch/staged-dependency-validate.d.ts +1 -1
- package/dist/src/commands/patch/staged-dependency-validate.js +3 -3
- package/dist/src/commands/patch/staged-dependency.d.ts +1 -1
- package/dist/src/commands/patch/staged-dependency.js +22 -28
- package/dist/src/commands/patch/tier.d.ts +2 -2
- package/dist/src/commands/patch/tier.js +20 -30
- package/dist/src/commands/patch-rename-map.d.ts +19 -0
- package/dist/src/commands/patch-rename-map.js +36 -0
- package/dist/src/commands/pending-resolution.d.ts +15 -0
- package/dist/src/commands/pending-resolution.js +25 -0
- package/dist/src/commands/re-export-adjacent.d.ts +25 -3
- package/dist/src/commands/re-export-adjacent.js +40 -24
- package/dist/src/commands/re-export-bulk-scan.d.ts +3 -3
- package/dist/src/commands/re-export-bulk-scan.js +23 -27
- package/dist/src/commands/re-export-drift.d.ts +10 -10
- package/dist/src/commands/re-export-drift.js +33 -33
- package/dist/src/commands/re-export-files.d.ts +2 -3
- package/dist/src/commands/re-export-files.js +52 -44
- package/dist/src/commands/re-export-lint.d.ts +29 -30
- package/dist/src/commands/re-export-lint.js +36 -29
- package/dist/src/commands/re-export-options.d.ts +1 -1
- package/dist/src/commands/re-export-options.js +1 -1
- package/dist/src/commands/re-export-register.d.ts +1 -1
- package/dist/src/commands/re-export-register.js +1 -1
- package/dist/src/commands/re-export-scan.d.ts +1 -1
- package/dist/src/commands/re-export-scan.js +12 -9
- package/dist/src/commands/re-export-single.d.ts +23 -4
- package/dist/src/commands/re-export-single.js +39 -31
- package/dist/src/commands/re-export.js +35 -17
- package/dist/src/commands/rebase/abort.js +9 -14
- package/dist/src/commands/rebase/continue.js +20 -19
- package/dist/src/commands/rebase/index.d.ts +1 -1
- package/dist/src/commands/rebase/index.js +5 -5
- package/dist/src/commands/rebase/patch-loop.d.ts +2 -2
- package/dist/src/commands/rebase/patch-loop.js +20 -24
- package/dist/src/commands/register.js +5 -5
- package/dist/src/commands/reset.js +1 -1
- package/dist/src/commands/resolve.d.ts +2 -2
- package/dist/src/commands/resolve.js +21 -13
- package/dist/src/commands/run.d.ts +0 -13
- package/dist/src/commands/run.js +38 -51
- package/dist/src/commands/setup-support.d.ts +16 -4
- package/dist/src/commands/setup-support.js +20 -20
- package/dist/src/commands/setup.js +4 -10
- package/dist/src/commands/source.js +9 -2
- package/dist/src/commands/status-check.d.ts +3 -3
- package/dist/src/commands/status-check.js +6 -6
- package/dist/src/commands/status-json.d.ts +14 -13
- package/dist/src/commands/status-json.js +9 -8
- package/dist/src/commands/status-output.d.ts +3 -3
- package/dist/src/commands/status-output.js +5 -5
- package/dist/src/commands/status-ownership.d.ts +3 -3
- package/dist/src/commands/status-ownership.js +3 -3
- package/dist/src/commands/status.js +25 -26
- package/dist/src/commands/test-build-phase.d.ts +3 -3
- package/dist/src/commands/test-build-phase.js +48 -24
- package/dist/src/commands/test-diagnose.d.ts +1 -1
- package/dist/src/commands/test-diagnose.js +20 -20
- package/dist/src/commands/test-modes.d.ts +4 -4
- package/dist/src/commands/test-modes.js +4 -5
- package/dist/src/commands/test-register.js +5 -3
- package/dist/src/commands/test-run.d.ts +11 -11
- package/dist/src/commands/test-run.js +40 -33
- package/dist/src/commands/test-stale-gate.d.ts +12 -12
- package/dist/src/commands/test-stale-gate.js +17 -17
- package/dist/src/commands/test-verdict.d.ts +19 -5
- package/dist/src/commands/test-verdict.js +26 -11
- package/dist/src/commands/test.d.ts +3 -3
- package/dist/src/commands/test.js +73 -36
- package/dist/src/commands/token-coverage.js +3 -3
- package/dist/src/commands/token-list.d.ts +26 -0
- package/dist/src/commands/token-list.js +153 -0
- package/dist/src/commands/token.js +26 -10
- package/dist/src/commands/tree.js +26 -21
- package/dist/src/commands/typecheck.d.ts +6 -6
- package/dist/src/commands/typecheck.js +16 -16
- package/dist/src/commands/verify.d.ts +3 -3
- package/dist/src/commands/verify.js +10 -10
- package/dist/src/commands/watch.js +11 -11
- package/dist/src/commands/wire.js +17 -16
- package/dist/src/core/ast-utils.d.ts +7 -7
- package/dist/src/core/ast-utils.js +8 -8
- package/dist/src/core/branding.d.ts +5 -12
- package/dist/src/core/branding.js +6 -5
- package/dist/src/core/browser-wire.d.ts +1 -1
- package/dist/src/core/browser-wire.js +10 -7
- package/dist/src/core/build-audit-platform.d.ts +32 -3
- package/dist/src/core/build-audit-platform.js +153 -13
- package/dist/src/core/build-audit-registration.d.ts +5 -5
- package/dist/src/core/build-audit-registration.js +10 -9
- package/dist/src/core/build-audit-resolve.d.ts +5 -5
- package/dist/src/core/build-audit-resolve.js +6 -6
- package/dist/src/core/build-audit-skip.d.ts +57 -0
- package/dist/src/core/build-audit-skip.js +112 -0
- package/dist/src/core/build-audit-transforms.d.ts +2 -2
- package/dist/src/core/build-audit-transforms.js +3 -3
- package/dist/src/core/build-audit.d.ts +21 -8
- package/dist/src/core/build-audit.js +142 -40
- package/dist/src/core/build-baseline-types.d.ts +19 -18
- package/dist/src/core/build-baseline-types.js +1 -1
- package/dist/src/core/build-baseline.d.ts +48 -31
- package/dist/src/core/build-baseline.js +20 -43
- package/dist/src/core/build-jar-escalation.d.ts +8 -8
- package/dist/src/core/build-jar-escalation.js +18 -17
- package/dist/src/core/build-overwrite-guard.d.ts +4 -4
- package/dist/src/core/build-overwrite-guard.js +14 -14
- package/dist/src/core/build-prepare.d.ts +4 -12
- package/dist/src/core/build-prepare.js +22 -26
- package/dist/src/core/config-mutate.js +4 -4
- package/dist/src/core/config-paths.d.ts +2 -6
- package/dist/src/core/config-paths.js +4 -2
- package/dist/src/core/config-state.d.ts +0 -6
- package/dist/src/core/config-state.js +3 -21
- package/dist/src/core/config-validate-build-audit.d.ts +8 -0
- package/dist/src/core/config-validate-build-audit.js +80 -0
- package/dist/src/core/config-validate-file-size.d.ts +1 -1
- package/dist/src/core/config-validate-file-size.js +3 -3
- package/dist/src/core/config-validate-patch-policy.d.ts +2 -2
- package/dist/src/core/config-validate-patch-policy.js +3 -3
- package/dist/src/core/config-validate-test-toolchains.d.ts +2 -2
- package/dist/src/core/config-validate-test-toolchains.js +4 -5
- package/dist/src/core/config-validate.js +22 -12
- package/dist/src/core/config.d.ts +12 -12
- package/dist/src/core/config.js +21 -25
- package/dist/src/core/coverage-extend.d.ts +16 -16
- package/dist/src/core/coverage-extend.js +20 -20
- package/dist/src/core/destructive.d.ts +14 -14
- package/dist/src/core/destructive.js +9 -9
- package/dist/src/core/diff-hunks.d.ts +2 -2
- package/dist/src/core/diff-hunks.js +7 -7
- package/dist/src/core/discard-baseline.d.ts +10 -10
- package/dist/src/core/discard-baseline.js +22 -23
- package/dist/src/core/display-state.d.ts +11 -11
- package/dist/src/core/display-state.js +12 -12
- package/dist/src/core/engine-changes.d.ts +2 -2
- package/dist/src/core/engine-changes.js +2 -2
- package/dist/src/core/engine-precondition.d.ts +5 -13
- package/dist/src/core/engine-precondition.js +5 -10
- package/dist/src/core/engine-session-lock.d.ts +18 -18
- package/dist/src/core/engine-session-lock.js +50 -54
- package/dist/src/core/export-moved-code-shape.d.ts +7 -7
- package/dist/src/core/export-moved-code-shape.js +10 -10
- package/dist/src/core/file-lock-owner.d.ts +103 -0
- package/dist/src/core/file-lock-owner.js +259 -0
- package/dist/src/core/file-lock.d.ts +14 -19
- package/dist/src/core/file-lock.js +90 -128
- package/dist/src/core/firefox-cache.d.ts +13 -1
- package/dist/src/core/firefox-cache.js +61 -36
- package/dist/src/core/firefox-download.d.ts +15 -0
- package/dist/src/core/firefox-download.js +38 -22
- package/dist/src/core/firefox-extract.d.ts +8 -7
- package/dist/src/core/firefox-extract.js +45 -27
- package/dist/src/core/firefox.d.ts +34 -36
- package/dist/src/core/firefox.js +13 -44
- package/dist/src/core/furnace-apply-dry-run.d.ts +1 -6
- package/dist/src/core/furnace-apply-dry-run.js +2 -8
- package/dist/src/core/furnace-apply-ftl.d.ts +5 -5
- package/dist/src/core/furnace-apply-ftl.js +8 -8
- package/dist/src/core/furnace-apply-helpers.d.ts +9 -20
- package/dist/src/core/furnace-apply-helpers.js +28 -39
- package/dist/src/core/furnace-apply-output.js +1 -1
- package/dist/src/core/furnace-apply-overwrite-warn.d.ts +9 -9
- package/dist/src/core/furnace-apply-overwrite-warn.js +13 -11
- package/dist/src/core/furnace-apply-undeploy-actions.d.ts +1 -1
- package/dist/src/core/furnace-apply-undeploy-actions.js +1 -1
- package/dist/src/core/furnace-apply.d.ts +4 -4
- package/dist/src/core/furnace-apply.js +50 -29
- package/dist/src/core/furnace-checksum-utils.d.ts +5 -5
- package/dist/src/core/furnace-checksum-utils.js +5 -5
- package/dist/src/core/furnace-config-custom.d.ts +1 -1
- package/dist/src/core/furnace-config-custom.js +2 -2
- package/dist/src/core/furnace-config-order.js +1 -1
- package/dist/src/core/furnace-config-tokens.d.ts +3 -3
- package/dist/src/core/furnace-config-tokens.js +3 -3
- package/dist/src/core/furnace-config-validate.js +2 -2
- package/dist/src/core/furnace-config.d.ts +5 -5
- package/dist/src/core/furnace-config.js +40 -53
- package/dist/src/core/furnace-constants.d.ts +6 -6
- package/dist/src/core/furnace-constants.js +9 -8
- package/dist/src/core/furnace-css-fragments.d.ts +6 -6
- package/dist/src/core/furnace-css-fragments.js +11 -11
- package/dist/src/core/furnace-dir-entry.d.ts +20 -0
- package/dist/src/core/furnace-dir-entry.js +21 -0
- package/dist/src/core/furnace-jsconfig.d.ts +7 -7
- package/dist/src/core/furnace-jsconfig.js +22 -20
- package/dist/src/core/furnace-operation.d.ts +22 -19
- package/dist/src/core/furnace-operation.js +38 -34
- package/dist/src/core/furnace-precondition.d.ts +10 -10
- package/dist/src/core/furnace-precondition.js +8 -8
- package/dist/src/core/furnace-refresh.d.ts +18 -6
- package/dist/src/core/furnace-refresh.js +5 -8
- package/dist/src/core/furnace-registration-ast.d.ts +2 -3
- package/dist/src/core/furnace-registration-ast.js +9 -12
- package/dist/src/core/furnace-registration-remove.d.ts +4 -4
- package/dist/src/core/furnace-registration-remove.js +6 -6
- package/dist/src/core/furnace-registration-validate.d.ts +2 -2
- package/dist/src/core/furnace-registration-validate.js +2 -2
- package/dist/src/core/furnace-registration.d.ts +7 -6
- package/dist/src/core/furnace-registration.js +29 -36
- package/dist/src/core/furnace-rollback.d.ts +1 -1
- package/dist/src/core/furnace-rollback.js +5 -5
- package/dist/src/core/furnace-scanner.js +3 -6
- package/dist/src/core/furnace-stale-export.d.ts +17 -16
- package/dist/src/core/furnace-stale-export.js +16 -15
- package/dist/src/core/furnace-staleness.d.ts +2 -2
- package/dist/src/core/furnace-staleness.js +2 -2
- package/dist/src/core/furnace-state-persist.d.ts +12 -12
- package/dist/src/core/furnace-state-persist.js +10 -10
- package/dist/src/core/furnace-step-errors.d.ts +6 -6
- package/dist/src/core/furnace-step-errors.js +6 -6
- package/dist/src/core/furnace-validate-accessibility.js +14 -14
- package/dist/src/core/furnace-validate-compatibility.js +9 -9
- package/dist/src/core/furnace-validate-registration.d.ts +2 -2
- package/dist/src/core/furnace-validate-registration.js +18 -20
- package/dist/src/core/furnace-validate-structure.d.ts +1 -1
- package/dist/src/core/furnace-validate-structure.js +4 -4
- package/dist/src/core/furnace-validate.js +9 -9
- package/dist/src/core/furnace-version-drift.d.ts +5 -5
- package/dist/src/core/furnace-version-drift.js +5 -5
- package/dist/src/core/git-base.d.ts +6 -4
- package/dist/src/core/git-base.js +29 -7
- package/dist/src/core/git-diff-new-file.d.ts +40 -0
- package/dist/src/core/git-diff-new-file.js +119 -0
- package/dist/src/core/git-diff.d.ts +13 -13
- package/dist/src/core/git-diff.js +121 -189
- package/dist/src/core/git-file-ops.d.ts +6 -13
- package/dist/src/core/git-file-ops.js +11 -35
- package/dist/src/core/git-readonly-index.d.ts +12 -14
- package/dist/src/core/git-readonly-index.js +12 -16
- package/dist/src/core/git-status.d.ts +9 -2
- package/dist/src/core/git-status.js +23 -11
- package/dist/src/core/git.d.ts +3 -9
- package/dist/src/core/git.js +28 -57
- package/dist/src/core/harness-orphans.d.ts +17 -17
- package/dist/src/core/harness-orphans.js +28 -27
- package/dist/src/core/history-log.d.ts +19 -0
- package/dist/src/core/history-log.js +29 -0
- package/dist/src/core/license-headers.d.ts +19 -18
- package/dist/src/core/license-headers.js +29 -28
- package/dist/src/core/mach-build-artifacts.d.ts +21 -21
- package/dist/src/core/mach-build-artifacts.js +23 -23
- package/dist/src/core/mach-error-hints.d.ts +5 -10
- package/dist/src/core/mach-error-hints.js +14 -14
- package/dist/src/core/mach-known-noise-filter.d.ts +42 -38
- package/dist/src/core/mach-known-noise-filter.js +57 -56
- package/dist/src/core/mach-mozconfig.d.ts +6 -6
- package/dist/src/core/mach-mozconfig.js +17 -16
- package/dist/src/core/mach-python.d.ts +3 -0
- package/dist/src/core/mach-python.js +13 -7
- package/dist/src/core/mach-resource-shim.d.ts +24 -12
- package/dist/src/core/mach-resource-shim.js +124 -21
- package/dist/src/core/mach.d.ts +59 -73
- package/dist/src/core/mach.js +47 -115
- package/dist/src/core/marionette-port.d.ts +15 -30
- package/dist/src/core/marionette-port.js +46 -89
- package/dist/src/core/marionette-preflight.d.ts +6 -6
- package/dist/src/core/marionette-preflight.js +32 -50
- package/dist/src/core/markdown-table.d.ts +9 -9
- package/dist/src/core/markdown-table.js +14 -14
- package/dist/src/core/mochitest-server-port.d.ts +8 -8
- package/dist/src/core/mochitest-server-port.js +17 -17
- package/dist/src/core/module-resolution-preflight.d.ts +8 -8
- package/dist/src/core/module-resolution-preflight.js +11 -11
- package/dist/src/core/moz-manifest-helpers.d.ts +7 -7
- package/dist/src/core/moz-manifest-helpers.js +7 -7
- package/dist/src/core/moz-manifest-register.d.ts +1 -1
- package/dist/src/core/moz-manifest-register.js +2 -2
- package/dist/src/core/moz-manifest-rules.js +46 -42
- package/dist/src/core/moz-manifest-tokenizers.js +1 -1
- package/dist/src/core/ownership-table.d.ts +5 -5
- package/dist/src/core/ownership-table.js +7 -7
- package/dist/src/core/parser-fallback.d.ts +3 -3
- package/dist/src/core/parser-fallback.js +3 -3
- package/dist/src/core/patch-apply-fuzz.d.ts +5 -5
- package/dist/src/core/patch-apply-fuzz.js +13 -13
- package/dist/src/core/patch-apply.d.ts +13 -14
- package/dist/src/core/patch-apply.js +36 -42
- package/dist/src/core/patch-export-coverage.d.ts +0 -9
- package/dist/src/core/patch-export-coverage.js +1 -30
- package/dist/src/core/patch-export-update.d.ts +21 -4
- package/dist/src/core/patch-export-update.js +7 -6
- package/dist/src/core/patch-export.d.ts +20 -30
- package/dist/src/core/patch-export.js +55 -77
- package/dist/src/core/patch-files.d.ts +0 -4
- package/dist/src/core/patch-files.js +0 -11
- package/dist/src/core/patch-identifier-suggest.d.ts +1 -1
- package/dist/src/core/patch-identifier-suggest.js +4 -4
- package/dist/src/core/patch-lint-binary.d.ts +12 -18
- package/dist/src/core/patch-lint-cache.d.ts +18 -2
- package/dist/src/core/patch-lint-cache.js +16 -19
- package/dist/src/core/patch-lint-checkjs.d.ts +55 -38
- package/dist/src/core/patch-lint-checkjs.js +78 -64
- package/dist/src/core/patch-lint-chrome-jsdoc.d.ts +8 -9
- package/dist/src/core/patch-lint-chrome-jsdoc.js +10 -11
- package/dist/src/core/patch-lint-creators.d.ts +5 -9
- package/dist/src/core/patch-lint-creators.js +3 -3
- package/dist/src/core/patch-lint-cross.d.ts +27 -19
- package/dist/src/core/patch-lint-cross.js +67 -110
- package/dist/src/core/patch-lint-css.d.ts +1 -1
- package/dist/src/core/patch-lint-css.js +15 -11
- package/dist/src/core/patch-lint-diff-tag.d.ts +5 -5
- package/dist/src/core/patch-lint-diff-tag.js +5 -5
- package/dist/src/core/patch-lint-diff.d.ts +4 -4
- package/dist/src/core/patch-lint-diff.js +4 -4
- package/dist/src/core/patch-lint-file-size.d.ts +3 -3
- package/dist/src/core/patch-lint-file-size.js +6 -6
- package/dist/src/core/patch-lint-forward-registration.d.ts +58 -0
- package/dist/src/core/patch-lint-forward-registration.js +210 -0
- package/dist/src/core/patch-lint-jsdoc.d.ts +2 -2
- package/dist/src/core/patch-lint-jsdoc.js +46 -46
- package/dist/src/core/patch-lint-module-registration.d.ts +3 -9
- package/dist/src/core/patch-lint-module-registration.js +1 -1
- package/dist/src/core/patch-lint-mozbuild.d.ts +1 -1
- package/dist/src/core/patch-lint-mozbuild.js +10 -10
- package/dist/src/core/patch-lint-observer.d.ts +3 -3
- package/dist/src/core/patch-lint-observer.js +7 -7
- package/dist/src/core/patch-lint-ownership.d.ts +6 -6
- package/dist/src/core/patch-lint-ownership.js +6 -6
- package/dist/src/core/patch-lint-prettier.d.ts +6 -6
- package/dist/src/core/patch-lint-prettier.js +7 -7
- package/dist/src/core/patch-lint-queue-types.d.ts +60 -0
- package/dist/src/core/patch-lint-queue-types.js +12 -0
- package/dist/src/core/patch-lint-staged-registration.d.ts +61 -0
- package/dist/src/core/patch-lint-staged-registration.js +90 -0
- package/dist/src/core/patch-lint-unmanaged-companion.d.ts +23 -23
- package/dist/src/core/patch-lint-unmanaged-companion.js +26 -26
- package/dist/src/core/patch-lint.d.ts +41 -35
- package/dist/src/core/patch-lint.js +52 -49
- package/dist/src/core/patch-lock.d.ts +1 -1
- package/dist/src/core/patch-lock.js +11 -11
- package/dist/src/core/patch-manifest-consistency.d.ts +7 -7
- package/dist/src/core/patch-manifest-consistency.js +16 -17
- package/dist/src/core/patch-manifest-files-affected.d.ts +1 -1
- package/dist/src/core/patch-manifest-files-affected.js +3 -3
- package/dist/src/core/patch-manifest-io.d.ts +14 -14
- package/dist/src/core/patch-manifest-io.js +35 -34
- package/dist/src/core/patch-manifest-query.d.ts +1 -1
- package/dist/src/core/patch-manifest-query.js +4 -4
- package/dist/src/core/patch-manifest-resolve.d.ts +5 -5
- package/dist/src/core/patch-manifest-resolve.js +7 -7
- package/dist/src/core/patch-manifest-validate.js +3 -3
- package/dist/src/core/patch-manifest.d.ts +2 -2
- package/dist/src/core/patch-manifest.js +2 -2
- package/dist/src/core/patch-parse.d.ts +32 -21
- package/dist/src/core/patch-parse.js +40 -15
- package/dist/src/core/patch-policy.js +15 -27
- package/dist/src/core/patch-registration-refs.d.ts +4 -4
- package/dist/src/core/patch-registration-refs.js +7 -7
- package/dist/src/core/patch-source-metadata.d.ts +1 -3
- package/dist/src/core/patch-source-metadata.js +0 -4
- package/dist/src/core/patch-transform.d.ts +8 -16
- package/dist/src/core/patch-transform.js +13 -23
- package/dist/src/core/process-cpu-time.d.ts +1 -1
- package/dist/src/core/process-cpu-time.js +6 -6
- package/dist/src/core/rebase-session.d.ts +9 -15
- package/dist/src/core/rebase-session.js +13 -25
- package/dist/src/core/register-browser-content.js +3 -2
- package/dist/src/core/register-browser-test.js +2 -1
- package/dist/src/core/register-module.js +2 -1
- package/dist/src/core/register-result.d.ts +1 -1
- package/dist/src/core/register-result.js +1 -1
- package/dist/src/core/register-scaffold.d.ts +2 -2
- package/dist/src/core/register-scaffold.js +8 -7
- package/dist/src/core/register-shared-css.d.ts +3 -3
- package/dist/src/core/register-shared-css.js +6 -5
- package/dist/src/core/register-xpcshell-test.d.ts +2 -2
- package/dist/src/core/register-xpcshell-test.js +2 -2
- package/dist/src/core/run-log-redact.d.ts +38 -0
- package/dist/src/core/run-log-redact.js +69 -0
- package/dist/src/core/run-log.d.ts +21 -10
- package/dist/src/core/run-log.js +76 -27
- package/dist/src/core/shared-ftl.d.ts +2 -2
- package/dist/src/core/shared-ftl.js +6 -6
- package/dist/src/core/signal-critical.d.ts +2 -2
- package/dist/src/core/signal-critical.js +4 -6
- package/dist/src/core/smoke-patterns.d.ts +5 -6
- package/dist/src/core/smoke-patterns.js +15 -20
- package/dist/src/core/state-file.d.ts +15 -4
- package/dist/src/core/state-file.js +14 -1
- package/dist/src/core/status-binary.d.ts +8 -8
- package/dist/src/core/status-binary.js +12 -12
- package/dist/src/core/status-classify.d.ts +17 -17
- package/dist/src/core/status-classify.js +13 -12
- package/dist/src/core/test-changed-prefs.d.ts +12 -12
- package/dist/src/core/test-changed-prefs.js +40 -25
- package/dist/src/core/test-harness-crash.d.ts +39 -39
- package/dist/src/core/test-harness-crash.js +69 -69
- package/dist/src/core/test-harness-output.d.ts +7 -7
- package/dist/src/core/test-harness-output.js +7 -7
- package/dist/src/core/test-harness-verdict-notes.d.ts +13 -14
- package/dist/src/core/test-harness-verdict-notes.js +4 -4
- package/dist/src/core/test-path-scope.d.ts +8 -8
- package/dist/src/core/test-path-scope.js +11 -11
- package/dist/src/core/test-stale-check.d.ts +22 -23
- package/dist/src/core/test-stale-check.js +31 -30
- package/dist/src/core/test-stale-symlink.d.ts +1 -1
- package/dist/src/core/test-stale-symlink.js +1 -1
- package/dist/src/core/test-stall-triage.d.ts +9 -9
- package/dist/src/core/test-stall-triage.js +22 -22
- package/dist/src/core/test-xpcshell-retry.d.ts +26 -7
- package/dist/src/core/test-xpcshell-retry.js +14 -11
- package/dist/src/core/token-category.d.ts +35 -2
- package/dist/src/core/token-category.js +67 -58
- package/dist/src/core/token-coverage.js +4 -5
- package/dist/src/core/token-dark-mode.d.ts +9 -9
- package/dist/src/core/token-dark-mode.js +13 -25
- package/dist/src/core/token-docs.d.ts +1 -1
- package/dist/src/core/token-inventory.d.ts +56 -0
- package/dist/src/core/token-inventory.js +109 -0
- package/dist/src/core/token-manager.d.ts +4 -4
- package/dist/src/core/token-manager.js +22 -22
- package/dist/src/core/token-scaffold.d.ts +4 -4
- package/dist/src/core/token-scaffold.js +4 -4
- package/dist/src/core/token-variant.d.ts +14 -14
- package/dist/src/core/token-variant.js +52 -53
- package/dist/src/core/toolchain-preflight.d.ts +15 -15
- package/dist/src/core/toolchain-preflight.js +23 -23
- package/dist/src/core/tree-cow.d.ts +3 -5
- package/dist/src/core/tree-cow.js +8 -8
- package/dist/src/core/tree-guard.d.ts +3 -3
- package/dist/src/core/tree-guard.js +23 -23
- package/dist/src/core/tree-store.d.ts +15 -15
- package/dist/src/core/tree-store.js +39 -38
- package/dist/src/core/typecheck-shim.d.ts +16 -15
- package/dist/src/core/typecheck-shim.js +26 -25
- package/dist/src/core/typecheck.d.ts +12 -12
- package/dist/src/core/typecheck.js +33 -33
- package/dist/src/core/wire-destroy.d.ts +2 -2
- package/dist/src/core/wire-destroy.js +5 -5
- package/dist/src/core/wire-dom-fragment.d.ts +3 -3
- package/dist/src/core/wire-dom-fragment.js +12 -23
- package/dist/src/core/wire-init.d.ts +2 -2
- package/dist/src/core/wire-init.js +7 -7
- package/dist/src/core/wire-subscript.d.ts +1 -1
- package/dist/src/core/wire-subscript.js +3 -3
- package/dist/src/core/wire-utils.d.ts +9 -9
- package/dist/src/core/wire-utils.js +16 -28
- package/dist/src/core/xpcshell-appdir.d.ts +20 -20
- package/dist/src/core/xpcshell-appdir.js +28 -30
- package/dist/src/core/xpcshell-profile-dir.d.ts +3 -3
- package/dist/src/core/xpcshell-profile-dir.js +7 -7
- package/dist/src/errors/base.d.ts +69 -16
- package/dist/src/errors/base.js +95 -26
- package/dist/src/errors/build.d.ts +6 -6
- package/dist/src/errors/build.js +26 -34
- package/dist/src/errors/codes.d.ts +10 -10
- package/dist/src/errors/codes.js +10 -10
- package/dist/src/errors/config.d.ts +0 -14
- package/dist/src/errors/config.js +13 -34
- package/dist/src/errors/download.d.ts +13 -0
- package/dist/src/errors/download.js +53 -24
- package/dist/src/errors/furnace.d.ts +2 -2
- package/dist/src/errors/furnace.js +8 -9
- package/dist/src/errors/git.d.ts +9 -9
- package/dist/src/errors/git.js +21 -31
- package/dist/src/errors/patch.d.ts +3 -3
- package/dist/src/errors/patch.js +11 -13
- package/dist/src/errors/rebase.d.ts +1 -1
- package/dist/src/errors/rebase.js +8 -8
- package/dist/src/errors/run.d.ts +1 -1
- package/dist/src/errors/run.js +1 -1
- package/dist/src/index.d.ts +4 -4
- package/dist/src/index.js +4 -4
- package/dist/src/types/commands/options.d.ts +155 -200
- package/dist/src/types/commands/patches.d.ts +19 -19
- package/dist/src/types/commands/project.d.ts +3 -3
- package/dist/src/types/config.d.ts +52 -19
- package/dist/src/types/furnace.d.ts +17 -17
- package/dist/src/types/index.d.ts +0 -1
- package/dist/src/types/json.d.ts +3 -3
- package/dist/src/types/json.js +2 -2
- package/dist/src/types/typecheck.d.ts +3 -3
- package/dist/src/utils/assert.d.ts +4 -16
- package/dist/src/utils/assert.js +7 -24
- package/dist/src/utils/build-info.d.ts +6 -6
- package/dist/src/utils/build-info.js +6 -6
- package/dist/src/utils/child-env.d.ts +7 -6
- package/dist/src/utils/child-env.js +5 -5
- package/dist/src/utils/concurrency.d.ts +2 -2
- package/dist/src/utils/concurrency.js +2 -2
- package/dist/src/utils/elapsed.js +10 -1
- package/dist/src/utils/errors.d.ts +8 -8
- package/dist/src/utils/errors.js +8 -8
- package/dist/src/utils/fs.d.ts +1 -1
- package/dist/src/utils/fs.js +15 -20
- package/dist/src/utils/hash.d.ts +12 -0
- package/dist/src/utils/hash.js +16 -0
- package/dist/src/utils/line-dispatch.d.ts +15 -0
- package/dist/src/utils/line-dispatch.js +48 -0
- package/dist/src/utils/logger.d.ts +4 -4
- package/dist/src/utils/logger.js +11 -11
- package/dist/src/utils/machine-output.js +2 -2
- package/dist/src/utils/options.d.ts +14 -20
- package/dist/src/utils/options.js +26 -27
- package/dist/src/utils/package-root.js +5 -14
- package/dist/src/utils/paths.d.ts +4 -4
- package/dist/src/utils/paths.js +4 -4
- package/dist/src/utils/platform.d.ts +0 -4
- package/dist/src/utils/process-group.d.ts +10 -9
- package/dist/src/utils/process-group.js +37 -36
- package/dist/src/utils/process.d.ts +70 -55
- package/dist/src/utils/process.js +129 -179
- package/dist/src/utils/ps-duration.d.ts +4 -4
- package/dist/src/utils/ps-duration.js +9 -9
- package/dist/src/utils/regex.d.ts +4 -4
- package/dist/src/utils/regex.js +7 -7
- package/dist/src/utils/sleep.d.ts +26 -0
- package/dist/src/utils/sleep.js +31 -0
- package/dist/src/utils/stdio-drain.d.ts +7 -7
- package/dist/src/utils/stdio-drain.js +8 -8
- package/dist/src/utils/validation.d.ts +12 -49
- package/dist/src/utils/validation.js +26 -36
- package/docs/README.md +2 -2
- package/docs/configuration.md +163 -69
- package/docs/exit-codes.md +66 -49
- package/docs/furnace.md +20 -19
- package/docs/lifecycle-invariants.md +414 -247
- package/docs/machine-output.md +58 -34
- package/docs/patch-workflow.md +48 -44
- package/docs/run-logs.md +72 -28
- package/docs/testing.md +105 -98
- package/docs/verification-trees.md +23 -22
- package/package.json +7 -6
- package/dist/src/commands/rebase.d.ts +0 -4
- package/dist/src/commands/rebase.js +0 -5
- package/dist/src/core/patch-artifact-normalize.d.ts +0 -21
- package/dist/src/core/patch-artifact-normalize.js +0 -24
- package/dist/src/core/patch-lint-reexports.d.ts +0 -7
- package/dist/src/core/patch-lint-reexports.js +0 -8
- package/dist/src/core/wire-targets.d.ts +0 -7
- package/dist/src/core/wire-targets.js +0 -8
|
@@ -9,12 +9,13 @@ import { assertBuildArtifacts } from '../core/mach-build-artifacts.js';
|
|
|
9
9
|
import { assertMarionettePortAvailable, ensureLaunchableBrowserNotRunning, ensureMarionettePortAvailable, extractForwardedMarionettePort, forwardedMachArgsIncludeMarionetteClient, shouldAutoForwardMarionettePortToMach, } from '../core/marionette-port.js';
|
|
10
10
|
import { formatMarionettePreflightLine, reportMarionettePreflight, runMarionettePreflight, } from '../core/marionette-preflight.js';
|
|
11
11
|
import { ensureMochitestServerPortAvailable } from '../core/mochitest-server-port.js';
|
|
12
|
-
import { closeActiveRunLog, openRunLog, setActiveRunLog } from '../core/run-log.js';
|
|
12
|
+
import { closeActiveRunLog, openRunLog, setActiveRunLog, writeToActiveRunLog, } from '../core/run-log.js';
|
|
13
13
|
import { createPostRebuildFailureContext } from '../core/test-harness-output.js';
|
|
14
14
|
import { analyzeTestPathScopes, formatScopeNotice, } from '../core/test-path-scope.js';
|
|
15
15
|
import { assertObjdirMatchesTreeMarker } from '../core/tree-store.js';
|
|
16
|
-
import { GeneralError } from '../errors/base.js';
|
|
16
|
+
import { FireForgeError, GeneralError, PreflightRefusalError } from '../errors/base.js';
|
|
17
17
|
import { BuildError } from '../errors/build.js';
|
|
18
|
+
import { toError } from '../utils/errors.js';
|
|
18
19
|
import { pathExists } from '../utils/fs.js';
|
|
19
20
|
import { info, intro, notice, outro, verbose } from '../utils/logger.js';
|
|
20
21
|
import { stripEnginePrefix } from '../utils/paths.js';
|
|
@@ -41,7 +42,7 @@ async function assertTestPathsExist(engineDir, testPaths) {
|
|
|
41
42
|
* auto-routes to the suite-specific command (`mach xpcshell-test` /
|
|
42
43
|
* `mach mochitest`), which degrades a broken host resource monitor to a
|
|
43
44
|
* warning instead of crashing generic `mach test` at startup. Mixed runs are
|
|
44
|
-
* rejected before this point
|
|
45
|
+
* rejected before this point. A path-less "run all" or an explicit
|
|
45
46
|
* `--generic-mach-test` opt-out stays on the generic command.
|
|
46
47
|
*/
|
|
47
48
|
function resolveTestSuite(classification, forceGeneric) {
|
|
@@ -101,14 +102,14 @@ function logTestSelection(scopes) {
|
|
|
101
102
|
}
|
|
102
103
|
/**
|
|
103
104
|
* Runs the `--doctor` marionette handshake probe. With no test paths the
|
|
104
|
-
* probe is the entire command (returns `'stop'` after reporting)
|
|
105
|
-
* paths it gates the mach invocation
|
|
105
|
+
* probe is the entire command (returns `'stop'` after reporting). With
|
|
106
|
+
* paths it gates the mach invocation, where a FAIL throws before mach runs.
|
|
106
107
|
*/
|
|
107
108
|
async function runDoctorPreflight(args) {
|
|
108
109
|
const { engineDir, effectivePort, hasTestPaths, objDir, binaryName, launchablePath } = args;
|
|
109
110
|
// Non-TTY captures need the banner even if clack's renderer defers output
|
|
110
|
-
// in pipe mode
|
|
111
|
-
// written twice
|
|
111
|
+
// in pipe mode. TTY users need the clack framing. Gated rather than
|
|
112
|
+
// written twice: the unconditional pair printed the same line twice on a
|
|
112
113
|
// terminal.
|
|
113
114
|
if (process.stdout.isTTY) {
|
|
114
115
|
info('Running marionette preflight...');
|
|
@@ -124,7 +125,7 @@ async function runDoctorPreflight(args) {
|
|
|
124
125
|
// can drop the summary under non-TTY capture.
|
|
125
126
|
//
|
|
126
127
|
// Gated on non-TTY: unconditional, it stacks with the two clack renderings
|
|
127
|
-
// below and the same line appears
|
|
128
|
+
// below and the same line appears three times on a terminal. Captured
|
|
128
129
|
// streams are exactly where this branch still fires.
|
|
129
130
|
const directLine = formatMarionettePreflightLine(preflight);
|
|
130
131
|
if (!process.stdout.isTTY) {
|
|
@@ -138,7 +139,7 @@ async function runDoctorPreflight(args) {
|
|
|
138
139
|
throw new GeneralError('Marionette preflight reported FAIL — see output above.');
|
|
139
140
|
}
|
|
140
141
|
// Doctor-only runs end here, so they carry their own verdict line
|
|
141
|
-
// (reason=preflight on failure)
|
|
142
|
+
// (reason=preflight on failure). With test paths the verdict comes
|
|
142
143
|
// from the actual harness run downstream.
|
|
143
144
|
emitPassVerdict();
|
|
144
145
|
outro('Test completed');
|
|
@@ -160,12 +161,12 @@ async function runDoctorPreflight(args) {
|
|
|
160
161
|
function appendMarionetteForwardingArgs(extraArgs, options, forwardedPort, xpcshellOnly = false) {
|
|
161
162
|
// Auto-forward the Marionette port to mach when `--marionette-port` is set.
|
|
162
163
|
// `--setpref=marionette.port=<n>` configures where the browser listener
|
|
163
|
-
// binds
|
|
164
|
+
// binds. `--marionette=127.0.0.1:<n>` tells the mochitest harness client to
|
|
164
165
|
// connect there (default client is 127.0.0.1:2828). xpcshell ignores both
|
|
165
166
|
// for browser Marionette.
|
|
166
167
|
//
|
|
167
168
|
// Skip setpref forwarding when the operator already supplied an equivalent
|
|
168
|
-
// arg via `--mach-arg
|
|
169
|
+
// arg via `--mach-arg`: duplicates would confuse without changing
|
|
169
170
|
// semantics. Skip when mach args explicitly request `--flavor=xpcshell` (or
|
|
170
171
|
// `xpcshell-tests`): the preflight still honours `--marionette-port`, but
|
|
171
172
|
// mach does not use the marionette.port pref on that harness. Any other arg
|
|
@@ -177,7 +178,7 @@ function appendMarionetteForwardingArgs(extraArgs, options, forwardedPort, xpcsh
|
|
|
177
178
|
if (options.marionettePort === undefined)
|
|
178
179
|
return;
|
|
179
180
|
if (xpcshellOnly) {
|
|
180
|
-
// Manifest classification says every requested path is xpcshell
|
|
181
|
+
// Manifest classification says every requested path is xpcshell.
|
|
181
182
|
// xpcshell ignores the browser Marionette path entirely, and forwarding
|
|
182
183
|
// the mochitest client flags here makes mach reject the dispatch.
|
|
183
184
|
info(`--marionette-port=${options.marionettePort} applied to the preflight probe only: the requested paths are xpcshell-only, and xpcshell ignores the browser Marionette port. Not forwarding --setpref=marionette.port or --marionette to mach.`);
|
|
@@ -271,9 +272,9 @@ const TEST_BUILD_PREFLIGHT = {
|
|
|
271
272
|
*
|
|
272
273
|
* Owns the run's exactly-one-`FIREFORGE-VERDICT:`-line guarantee: the sink
|
|
273
274
|
* is re-armed at entry, and any failure that reaches this boundary without
|
|
274
|
-
* an inner writer having emitted
|
|
275
|
-
* build, config errors, stale-build and port gates, missing paths
|
|
276
|
-
* harness process that failed to start
|
|
275
|
+
* an inner writer having emitted (the preflight ladder: missing engine or
|
|
276
|
+
* build, config errors, stale-build and port gates, missing paths, and a
|
|
277
|
+
* harness process that failed to start) emits `FAIL reason=preflight`,
|
|
277
278
|
* since no harness classification exists for such a run. Writers closer to
|
|
278
279
|
* the harness (doctor, canary, single, sharded, the engine-generation
|
|
279
280
|
* guard) emit first and win.
|
|
@@ -284,7 +285,7 @@ const TEST_BUILD_PREFLIGHT = {
|
|
|
284
285
|
export async function testCommand(projectRoot, testPaths, options = {}) {
|
|
285
286
|
intro('FireForge Test');
|
|
286
287
|
resetVerdictEmission();
|
|
287
|
-
// Opened before
|
|
288
|
+
// Opened before any work so a preflight refusal is logged too. Those are
|
|
288
289
|
// exactly the runs whose only output a `tail` throws away. Closed in
|
|
289
290
|
// `finally`, after the verdict line has already read the path.
|
|
290
291
|
setActiveRunLog(await openRunLog(projectRoot, 'test'));
|
|
@@ -292,19 +293,55 @@ export async function testCommand(projectRoot, testPaths, options = {}) {
|
|
|
292
293
|
await runTestCommandBody(projectRoot, testPaths, options);
|
|
293
294
|
}
|
|
294
295
|
catch (error) {
|
|
295
|
-
if (!verdictEmitted())
|
|
296
|
-
|
|
296
|
+
if (!verdictEmitted()) {
|
|
297
|
+
renderPreflightRefusal(error);
|
|
298
|
+
emitFailVerdict('preflight', refusalNote(error));
|
|
299
|
+
}
|
|
297
300
|
throw error;
|
|
298
301
|
}
|
|
299
302
|
finally {
|
|
300
303
|
await closeActiveRunLog();
|
|
301
304
|
}
|
|
302
305
|
}
|
|
306
|
+
/** The refusal class a preflight gate named, when it named one. */
|
|
307
|
+
function refusalNote(error) {
|
|
308
|
+
return error instanceof PreflightRefusalError ? error.note : undefined;
|
|
309
|
+
}
|
|
310
|
+
/**
|
|
311
|
+
* Puts a preflight refusal's own text on the operator's channel before the
|
|
312
|
+
* verdict line, and into the run log.
|
|
313
|
+
*
|
|
314
|
+
* Both halves matter, and neither happened before:
|
|
315
|
+
*
|
|
316
|
+
* - `withErrorHandling` renders `error.userMessage` back in `cli.ts`, but
|
|
317
|
+
* by then `emitFailVerdict` has called `setStdoutSealed(true)`, the seal
|
|
318
|
+
* that keeps the verdict the last stdout write, so `logError` routes to
|
|
319
|
+
* stderr. A run captured with `> file` therefore kept the verdict and
|
|
320
|
+
* dropped the reason.
|
|
321
|
+
* - That same rendering happens after this function's caller returns, and
|
|
322
|
+
* the `finally` below has already closed the run log. So the artifact the
|
|
323
|
+
* verdict's own `log=` key points at did not contain the refusal either,
|
|
324
|
+
* which is what left `.fireforge/logs/test-*.log` holding only the
|
|
325
|
+
* pre-test build.
|
|
326
|
+
*
|
|
327
|
+
* Writing here, before the seal, fixes both without trading away the
|
|
328
|
+
* contract: the refusal lands on stdout and in the log, and the verdict
|
|
329
|
+
* line still comes last.
|
|
330
|
+
*/
|
|
331
|
+
function renderPreflightRefusal(error) {
|
|
332
|
+
const text = error instanceof FireForgeError ? error.userMessage : toError(error).message;
|
|
333
|
+
const block = `Preflight refused:\n${text}\n`;
|
|
334
|
+
// Raw stdout rather than the clack logger: this must land on the captured
|
|
335
|
+
// stream verbatim, and clack's renderer can drop output under non-TTY
|
|
336
|
+
// capture, the same reason the verdict line is written this way.
|
|
337
|
+
process.stdout.write(block);
|
|
338
|
+
writeToActiveRunLog(block);
|
|
339
|
+
}
|
|
303
340
|
/**
|
|
304
341
|
* Verifies `engine/` did not change under the run before any PASS verdict
|
|
305
|
-
* may print. On failure the run's verdict is `FAIL reason=inconclusive
|
|
306
|
-
* the harness result exists but cannot be trusted (`preflight` would
|
|
307
|
-
* misdescribe a run whose harness already executed)
|
|
342
|
+
* may print. On failure the run's verdict is `FAIL reason=inconclusive`,
|
|
343
|
+
* because the harness result exists but cannot be trusted (`preflight` would
|
|
344
|
+
* misdescribe a run whose harness already executed). It is emitted here so the
|
|
308
345
|
* guard's throw can never leave a stale or missing verdict line behind.
|
|
309
346
|
*/
|
|
310
347
|
async function verifyEngineGenerationOrEmitInconclusive(engineDir, before) {
|
|
@@ -324,7 +361,7 @@ async function runTestCommandBody(projectRoot, testPaths, options = {}) {
|
|
|
324
361
|
const buildCheck = await hasBuildArtifacts(paths.engine);
|
|
325
362
|
assertBuildArtifacts(paths.engine, buildCheck, TEST_BUILD_PREFLIGHT);
|
|
326
363
|
// Inside a verification tree, only the objdir the marker records was
|
|
327
|
-
// proven rewritten-and-reconfigured to the tree
|
|
364
|
+
// proven rewritten-and-reconfigured to the tree. Refuse any other.
|
|
328
365
|
await assertObjdirMatchesTreeMarker(projectRoot, buildCheck.objDir);
|
|
329
366
|
// Load the project config once so both the build and the port
|
|
330
367
|
// probe have access to `binaryName` (the port probe uses it to
|
|
@@ -332,11 +369,11 @@ async function runTestCommandBody(projectRoot, testPaths, options = {}) {
|
|
|
332
369
|
const projectConfig = await loadConfig(projectRoot);
|
|
333
370
|
const canaryPath = resolveCanaryPath(options, projectConfig);
|
|
334
371
|
assertTestModeCombinations(testPaths, options, canaryPath);
|
|
335
|
-
// `hasBuildArtifacts` only confirms `obj-*/dist/` exists
|
|
372
|
+
// `hasBuildArtifacts` only confirms `obj-*/dist/` exists. A partial build
|
|
336
373
|
// (linker failed, packaging step interrupted) can satisfy that check
|
|
337
374
|
// without ever writing the launchable binary the marionette preflight
|
|
338
375
|
// needs to spawn. `fireforge run` already uses `hasRunnableBundle` to fail
|
|
339
|
-
// fast with a precise message
|
|
376
|
+
// fast with a precise message. Mirroring it here makes `test --doctor`
|
|
340
377
|
// against an incomplete build surface the missing-bundle path instead of a
|
|
341
378
|
// cryptic `Browser process exited during spawn (exit code 1, signal none).
|
|
342
379
|
// stderr tail: (empty)`.
|
|
@@ -345,8 +382,8 @@ async function runTestCommandBody(projectRoot, testPaths, options = {}) {
|
|
|
345
382
|
// Normalized engine-relative request paths, hoisted above the build/stale
|
|
346
383
|
// gate: the pre-test build records them as the packaging-coverage claim,
|
|
347
384
|
// and the --allow-stale-build path checks the request against the
|
|
348
|
-
// recorded coverage. (Existence is still asserted later, after the gate
|
|
349
|
-
// stale/coverage refusals keep precedence over missing-path errors.)
|
|
385
|
+
// recorded coverage. (Existence is still asserted later, after the gate,
|
|
386
|
+
// so stale/coverage refusals keep precedence over missing-path errors.)
|
|
350
387
|
const requestedPaths = canaryPath !== undefined ? [canaryPath] : testPaths;
|
|
351
388
|
const normalizedPaths = requestedPaths.map((p) => stripEnginePrefix(p).trim());
|
|
352
389
|
const { classification, xpcshellOnly } = await classifyBeforeDispatch(paths.engine, normalizedPaths, { allowMixed: options.buildOnly === true });
|
|
@@ -392,26 +429,26 @@ async function runTestCommandBody(projectRoot, testPaths, options = {}) {
|
|
|
392
429
|
extraArgs.push('--auto');
|
|
393
430
|
}
|
|
394
431
|
if (canaryPath !== undefined) {
|
|
395
|
-
extraArgs.push(`--timeout=${
|
|
432
|
+
extraArgs.push(`--timeout=${canaryTimeoutSeconds(projectConfig)}`);
|
|
396
433
|
}
|
|
397
434
|
// --mach-arg is a verbatim passthrough for upstream mach/xpcshell/mochitest
|
|
398
435
|
// flags FireForge does not model directly (see the xpcshell appdir hint
|
|
399
|
-
// above for why). Appended
|
|
436
|
+
// above for why). Appended after --headless so mach sees
|
|
400
437
|
// the FireForge-managed flags first and the escape-valve ones last, which
|
|
401
438
|
// keeps the override precedence predictable.
|
|
402
439
|
if (forwardedMachArgs.length > 0) {
|
|
403
440
|
extraArgs.push(...forwardedMachArgs);
|
|
404
441
|
}
|
|
405
442
|
appendMarionetteForwardingArgs(extraArgs, options, forwardedPort, xpcshellOnly);
|
|
406
|
-
// Directory arguments mean
|
|
443
|
+
// Directory arguments mean exactly that directory: mozbuild's test
|
|
407
444
|
// resolver matches paths by string prefix, so a bare directory arg
|
|
408
|
-
// silently sweeps in prefix-named siblings
|
|
409
|
-
// `…/test/hominis-tiles`, with no indication the scope widened. Each
|
|
445
|
+
// silently sweeps in prefix-named siblings, with `…/test/hominis` also
|
|
446
|
+
// running `…/test/hominis-tiles`, with no indication the scope widened. Each
|
|
410
447
|
// directory argument therefore dispatches as its enumerated explicit
|
|
411
|
-
// test-file list, which cannot prefix-match a sibling
|
|
448
|
+
// test-file list, which cannot prefix-match a sibling. A trailing-`/`
|
|
412
449
|
// normalization does not work, as mach still sweeps the sibling in. Any
|
|
413
450
|
// prefix-siblings are echoed so the narrowed scope is visible.
|
|
414
|
-
// Classification above intentionally used the raw argument forms
|
|
451
|
+
// Classification above intentionally used the raw argument forms. Only the
|
|
415
452
|
// mach dispatch needs the exact-match shape.
|
|
416
453
|
const scopes = await analyzeTestPathScopes(paths.engine, normalizedPaths);
|
|
417
454
|
const dispatchGroups = scopes.map((scope) => ({
|
|
@@ -445,10 +482,10 @@ async function runTestCommandBody(projectRoot, testPaths, options = {}) {
|
|
|
445
482
|
: undefined;
|
|
446
483
|
// Multi-argument requests shard into sequential harness runs by default:
|
|
447
484
|
// one shared mochitest profile across files bleeds pref/media-query state
|
|
448
|
-
// into later files. Sharding is per path
|
|
485
|
+
// into later files. Sharding is per path argument: a directory argument
|
|
449
486
|
// keeps its enumerated files together in one invocation, preserving the
|
|
450
487
|
// one-browser-instance semantics of a directory run. `--no-shard` restores
|
|
451
|
-
// the combined invocation. The default must not be
|
|
488
|
+
// the combined invocation. The default must not be silent: a cross-file
|
|
452
489
|
// pollution repro otherwise "passes" because the comparison run was
|
|
453
490
|
// sharded without saying so, misattributing a suite-context bug upstream.
|
|
454
491
|
// Hence the one-line notice stating what sharding does and does not
|
|
@@ -463,7 +500,7 @@ async function runTestCommandBody(projectRoot, testPaths, options = {}) {
|
|
|
463
500
|
summary = await runShardedTests(runCtx, dispatchGroups, (outcome, label) => diagnoseShardOutcome(outcome, label, projectConfig.binaryName, postRebuildContext));
|
|
464
501
|
}
|
|
465
502
|
finally {
|
|
466
|
-
// Runs
|
|
503
|
+
// Runs before the aggregate verdict below: a mutated engine/ emits
|
|
467
504
|
// `FAIL reason=inconclusive` and throws, so an invalidated run can
|
|
468
505
|
// never print `PASS shards=N/N` first. (A throw here masks an
|
|
469
506
|
// in-flight shard error, as the plain assert always did.)
|
|
@@ -34,11 +34,11 @@ export async function tokenCoverageCommand(projectRoot) {
|
|
|
34
34
|
.map((f) => f.file);
|
|
35
35
|
// Also scan CSS files deployed by Furnace custom components. Deployed
|
|
36
36
|
// files can be committed (and therefore absent from `git status`) while
|
|
37
|
-
// still being the primary surface where token adoption matters
|
|
37
|
+
// still being the primary surface where token adoption matters. Looking
|
|
38
38
|
// only at modified files silently undercounts projects where Furnace
|
|
39
39
|
// writes many component-CSS files into the engine.
|
|
40
40
|
const furnaceCssFiles = await collectFurnaceCustomCssFiles(projectRoot, paths.engine, tokensCssPath);
|
|
41
|
-
// De-dupe so a file that is both a custom deploy target
|
|
41
|
+
// De-dupe so a file that is both a custom deploy target and modified is
|
|
42
42
|
// scanned exactly once.
|
|
43
43
|
const cssFiles = [...new Set([...statusCssFiles, ...furnaceCssFiles])];
|
|
44
44
|
const tokenSourceFiles = [...new Set(statusTokenCssFiles)];
|
|
@@ -129,7 +129,7 @@ async function validateTokenSourceFiles(engineDir, tokenSourceFiles, tokenPrefix
|
|
|
129
129
|
/**
|
|
130
130
|
* Returns engine-relative `.css` paths deployed by every Furnace custom
|
|
131
131
|
* component registered in `furnace.json`. Only files that actually exist
|
|
132
|
-
* on disk are included
|
|
132
|
+
* on disk are included. A component whose deploy target is missing (e.g.
|
|
133
133
|
* `furnace apply` has not run yet) is skipped silently so a fresh
|
|
134
134
|
* `furnace init` followed immediately by `token coverage` does not error.
|
|
135
135
|
*
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/** Options accepted by {@link tokenListCommand}. */
|
|
2
|
+
export interface TokenListOptions {
|
|
3
|
+
/** Restrict the report to one category. */
|
|
4
|
+
category?: string;
|
|
5
|
+
/** Emit the machine-readable envelope instead of the human report. */
|
|
6
|
+
json?: boolean;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Lists the categories declared in the tokens CSS with their token names,
|
|
10
|
+
* in file order.
|
|
11
|
+
*
|
|
12
|
+
* @param projectRoot - Root directory of the project
|
|
13
|
+
* @param options - Filter and output-mode options
|
|
14
|
+
*/
|
|
15
|
+
export declare function tokenListCommand(projectRoot: string, options?: TokenListOptions): Promise<void>;
|
|
16
|
+
/**
|
|
17
|
+
* Reports one token: the category that owns it and the value it takes in
|
|
18
|
+
* every block that declares it.
|
|
19
|
+
*
|
|
20
|
+
* @param projectRoot - Root directory of the project
|
|
21
|
+
* @param tokenName - Custom-property name, with or without the leading `--`
|
|
22
|
+
* @param options - Output-mode options
|
|
23
|
+
*/
|
|
24
|
+
export declare function tokenShowCommand(projectRoot: string, tokenName: string, options?: {
|
|
25
|
+
json?: boolean;
|
|
26
|
+
}): Promise<void>;
|
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
// SPDX-License-Identifier: EUPL-1.2
|
|
2
|
+
/**
|
|
3
|
+
* `token list` and `token show`: the read half of design-token management.
|
|
4
|
+
*
|
|
5
|
+
* `token add` requires `--category` and refuses an unknown one, but nothing
|
|
6
|
+
* reported the categories a project has, so naming one meant hand-parsing a
|
|
7
|
+
* neighbouring `= Category =` banner out of the tokens CSS. Both commands
|
|
8
|
+
* read through `token-inventory.ts`, which is built on the same banner and
|
|
9
|
+
* `:root`-bounds primitives `token add` and `token coverage` use, because
|
|
10
|
+
* a second tokens-CSS parser would let the report and the writer disagree about
|
|
11
|
+
* which section a token lives in.
|
|
12
|
+
*
|
|
13
|
+
* Helper module: no registrar, called from `token.ts`.
|
|
14
|
+
*/
|
|
15
|
+
import { join } from 'node:path';
|
|
16
|
+
import { getProjectPaths, loadConfig } from '../core/config.js';
|
|
17
|
+
import { collectTokenBlockValues, collectTokenInventory, } from '../core/token-inventory.js';
|
|
18
|
+
import { getTokensCssPath } from '../core/token-manager.js';
|
|
19
|
+
import { GeneralError } from '../errors/base.js';
|
|
20
|
+
import { toError } from '../utils/errors.js';
|
|
21
|
+
import { pathExists, readText } from '../utils/fs.js';
|
|
22
|
+
import { info, intro, outro, setMachineOutputMode, setStdoutSealed } from '../utils/logger.js';
|
|
23
|
+
import { emitMachineError, MACHINE_OUTPUT_SCHEMA_VERSION } from '../utils/machine-output.js';
|
|
24
|
+
/** Reads the project's tokens CSS as lines, refusing when it is absent. */
|
|
25
|
+
async function readTokensCssLines(projectRoot) {
|
|
26
|
+
const paths = getProjectPaths(projectRoot);
|
|
27
|
+
const config = await loadConfig(projectRoot);
|
|
28
|
+
const tokensCssPath = getTokensCssPath(config.binaryName);
|
|
29
|
+
const filePath = join(paths.engine, tokensCssPath);
|
|
30
|
+
if (!(await pathExists(filePath))) {
|
|
31
|
+
throw new GeneralError(`Token CSS file not found: ${tokensCssPath}. Run "fireforge furnace init" to seed it.`);
|
|
32
|
+
}
|
|
33
|
+
return { lines: (await readText(filePath)).split('\n'), tokensCssPath };
|
|
34
|
+
}
|
|
35
|
+
/** Applies the `--category` filter, refusing a name the file does not carry. */
|
|
36
|
+
function filterByCategory(groups, category, tokensCssPath) {
|
|
37
|
+
const matched = groups.filter((group) => group.category === category);
|
|
38
|
+
if (matched.length > 0)
|
|
39
|
+
return matched;
|
|
40
|
+
// Same "name the alternatives" contract `token add` gives for an unknown
|
|
41
|
+
// category: a filter that silently prints nothing reads as "this
|
|
42
|
+
// category is empty", which is a different fact.
|
|
43
|
+
const available = groups
|
|
44
|
+
.map((group) => group.category)
|
|
45
|
+
.filter((name) => name !== null);
|
|
46
|
+
const suffix = available.length > 0
|
|
47
|
+
? `Available categories: ${available.map((name) => `"${name}"`).join(', ')}.`
|
|
48
|
+
: 'The file declares no category banners.';
|
|
49
|
+
throw new GeneralError(`Category "${category}" not found in ${tokensCssPath}.\n\n${suffix}`);
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Lists the categories declared in the tokens CSS with their token names,
|
|
53
|
+
* in file order.
|
|
54
|
+
*
|
|
55
|
+
* @param projectRoot - Root directory of the project
|
|
56
|
+
* @param options - Filter and output-mode options
|
|
57
|
+
*/
|
|
58
|
+
export async function tokenListCommand(projectRoot, options = {}) {
|
|
59
|
+
if (options.json === true) {
|
|
60
|
+
// stdout belongs exclusively to the payload from here on. A later
|
|
61
|
+
// diagnostic (including withErrorHandling's) routes to stderr.
|
|
62
|
+
setMachineOutputMode(true);
|
|
63
|
+
try {
|
|
64
|
+
const { lines, tokensCssPath } = await readTokensCssLines(projectRoot);
|
|
65
|
+
const all = collectTokenInventory(lines);
|
|
66
|
+
const groups = options.category === undefined
|
|
67
|
+
? all
|
|
68
|
+
: filterByCategory(all, options.category, tokensCssPath);
|
|
69
|
+
process.stdout.write(`${JSON.stringify({
|
|
70
|
+
schemaVersion: MACHINE_OUTPUT_SCHEMA_VERSION,
|
|
71
|
+
tokensCssPath,
|
|
72
|
+
categories: groups.map((group) => ({
|
|
73
|
+
category: group.category,
|
|
74
|
+
tokens: group.tokens.map((token) => ({
|
|
75
|
+
name: token.name,
|
|
76
|
+
line: token.line,
|
|
77
|
+
value: token.value,
|
|
78
|
+
})),
|
|
79
|
+
})),
|
|
80
|
+
}, null, 2)}\n`);
|
|
81
|
+
setStdoutSealed(true);
|
|
82
|
+
}
|
|
83
|
+
catch (error) {
|
|
84
|
+
emitMachineError('token-list-failed', toError(error).message);
|
|
85
|
+
}
|
|
86
|
+
finally {
|
|
87
|
+
setMachineOutputMode(false);
|
|
88
|
+
}
|
|
89
|
+
return;
|
|
90
|
+
}
|
|
91
|
+
const { lines, tokensCssPath } = await readTokensCssLines(projectRoot);
|
|
92
|
+
const all = collectTokenInventory(lines);
|
|
93
|
+
const groups = options.category === undefined ? all : filterByCategory(all, options.category, tokensCssPath);
|
|
94
|
+
intro('Design Tokens');
|
|
95
|
+
info(tokensCssPath);
|
|
96
|
+
if (groups.length === 0) {
|
|
97
|
+
outro('No token declarations found in the :root block');
|
|
98
|
+
return;
|
|
99
|
+
}
|
|
100
|
+
let total = 0;
|
|
101
|
+
for (const group of groups) {
|
|
102
|
+
info(` ${group.category ?? '(no category)'} — ${String(group.tokens.length)} token(s)`);
|
|
103
|
+
for (const token of group.tokens) {
|
|
104
|
+
info(` ${token.name}`);
|
|
105
|
+
}
|
|
106
|
+
total += group.tokens.length;
|
|
107
|
+
}
|
|
108
|
+
outro(`${String(groups.length)} category/categories, ${String(total)} token(s)`);
|
|
109
|
+
}
|
|
110
|
+
/**
|
|
111
|
+
* Reports one token: the category that owns it and the value it takes in
|
|
112
|
+
* every block that declares it.
|
|
113
|
+
*
|
|
114
|
+
* @param projectRoot - Root directory of the project
|
|
115
|
+
* @param tokenName - Custom-property name, with or without the leading `--`
|
|
116
|
+
* @param options - Output-mode options
|
|
117
|
+
*/
|
|
118
|
+
export async function tokenShowCommand(projectRoot, tokenName, options = {}) {
|
|
119
|
+
const emit = async () => {
|
|
120
|
+
const { lines, tokensCssPath } = await readTokensCssLines(projectRoot);
|
|
121
|
+
const name = tokenName.startsWith('--') ? tokenName : `--${tokenName}`;
|
|
122
|
+
const declarations = collectTokenBlockValues(lines, name);
|
|
123
|
+
if (declarations.length === 0) {
|
|
124
|
+
throw new GeneralError(`Token "${name}" is not declared in ${tokensCssPath}. ` +
|
|
125
|
+
'Run "fireforge token list" to see the declared tokens.');
|
|
126
|
+
}
|
|
127
|
+
const owning = collectTokenInventory(lines).find((group) => group.tokens.some((token) => token.name === name));
|
|
128
|
+
return { tokensCssPath, name, category: owning?.category ?? null, declarations };
|
|
129
|
+
};
|
|
130
|
+
if (options.json === true) {
|
|
131
|
+
setMachineOutputMode(true);
|
|
132
|
+
try {
|
|
133
|
+
const report = await emit();
|
|
134
|
+
process.stdout.write(`${JSON.stringify({ schemaVersion: MACHINE_OUTPUT_SCHEMA_VERSION, ...report }, null, 2)}\n`);
|
|
135
|
+
setStdoutSealed(true);
|
|
136
|
+
}
|
|
137
|
+
catch (error) {
|
|
138
|
+
emitMachineError('token-show-failed', toError(error).message);
|
|
139
|
+
}
|
|
140
|
+
finally {
|
|
141
|
+
setMachineOutputMode(false);
|
|
142
|
+
}
|
|
143
|
+
return;
|
|
144
|
+
}
|
|
145
|
+
const report = await emit();
|
|
146
|
+
intro('Design Token');
|
|
147
|
+
info(`${report.name} — category: ${report.category ?? '(no category)'}`);
|
|
148
|
+
info(report.tokensCssPath);
|
|
149
|
+
for (const declaration of report.declarations) {
|
|
150
|
+
info(` ${declaration.block}: ${declaration.value} (line ${String(declaration.line)})`);
|
|
151
|
+
}
|
|
152
|
+
outro(`${String(report.declarations.length)} declaration(s)`);
|
|
153
|
+
}
|
|
@@ -10,6 +10,7 @@ import { info, intro, outro, success, warn } from '../utils/logger.js';
|
|
|
10
10
|
import { pickDefined } from '../utils/options.js';
|
|
11
11
|
import { normalizeTokenName } from '../utils/validation.js';
|
|
12
12
|
import { tokenCoverageCommand } from './token-coverage.js';
|
|
13
|
+
import { tokenListCommand, tokenShowCommand } from './token-list.js';
|
|
13
14
|
async function normalizeTokenNameForProject(projectRoot, rawTokenName) {
|
|
14
15
|
if (rawTokenName.startsWith('--')) {
|
|
15
16
|
return normalizeTokenName(rawTokenName);
|
|
@@ -20,7 +21,7 @@ async function normalizeTokenNameForProject(projectRoot, rawTokenName) {
|
|
|
20
21
|
const strippedPrefix = furnaceConfig.tokenPrefix.replace(/^--/, '').replace(/-$/, '');
|
|
21
22
|
const strippedName = rawTokenName.replace(/^--/, '');
|
|
22
23
|
// A bare name that already starts with the configured prefix text is
|
|
23
|
-
// treated as fully qualified
|
|
24
|
+
// treated as fully qualified. Blindly prepending would silently
|
|
24
25
|
// produce a double-prefixed token (e.g. "--hominis-hominis-shadow-low").
|
|
25
26
|
if (strippedName === strippedPrefix || strippedName.startsWith(`${strippedPrefix}-`)) {
|
|
26
27
|
info(`Token name "${rawTokenName}" already starts with the configured prefix ` +
|
|
@@ -36,12 +37,12 @@ async function normalizeTokenNameForProject(projectRoot, rawTokenName) {
|
|
|
36
37
|
return normalizeTokenName(rawTokenName);
|
|
37
38
|
}
|
|
38
39
|
/**
|
|
39
|
-
* Reports a no-op add, naming
|
|
40
|
+
* Reports a no-op add, naming where the existing declaration lives.
|
|
40
41
|
*
|
|
41
|
-
* A variant skip has no category to name
|
|
42
|
-
* `:root<selector>` block
|
|
42
|
+
* A variant skip has no category to name, because the declaration lives in
|
|
43
|
+
* a `:root<selector>` block, so the location reads as that block. The
|
|
43
44
|
* variant path used to report no location at all, so a re-run meant to
|
|
44
|
-
*
|
|
45
|
+
* change a value exited 0 having silently changed nothing.
|
|
45
46
|
*
|
|
46
47
|
* @param tokenName - Full token name including prefix
|
|
47
48
|
* @param result - Result carrying the skip location, when known
|
|
@@ -52,7 +53,7 @@ function reportSkippedToken(tokenName, result, options) {
|
|
|
52
53
|
? `:root${options.variant}`
|
|
53
54
|
: `category "${result.skippedExisting?.category ?? options.category ?? ''}"`;
|
|
54
55
|
const where = result.skippedExisting
|
|
55
|
-
? ` in ${scope} (line ${
|
|
56
|
+
? ` in ${scope} (line ${result.skippedExisting.line}), unchanged`
|
|
56
57
|
: '';
|
|
57
58
|
info(`Token ${tokenName} already exists${where} (skipped)`);
|
|
58
59
|
}
|
|
@@ -68,8 +69,8 @@ export async function tokenAddCommand(projectRoot, tokenName, value, options) {
|
|
|
68
69
|
intro('Token Add');
|
|
69
70
|
// A fresh project without furnace.json otherwise fails deep inside the
|
|
70
71
|
// token-manager's `assertTokenCategoryExists` with "Token CSS file not
|
|
71
|
-
// found: browser/themes/shared/<binary>-tokens.css"
|
|
72
|
-
// but the operator's actual next step is to initialize Furnace, which
|
|
72
|
+
// found: browser/themes/shared/<binary>-tokens.css", which is technically
|
|
73
|
+
// correct, but the operator's actual next step is to initialize Furnace, which
|
|
73
74
|
// scaffolds the tokens CSS file. Catching the uninitialized case here
|
|
74
75
|
// gives the right guidance before the generic "file not found" error.
|
|
75
76
|
if (!(await furnaceConfigExists(projectRoot))) {
|
|
@@ -170,9 +171,9 @@ export function registerToken(program, { getProjectRoot, withErrorHandling }) {
|
|
|
170
171
|
// Commander's argument parsing.
|
|
171
172
|
// Description ends with `(required)` because Commander's
|
|
172
173
|
// `makeOptionMandatory` does not render a required marker in `--help`
|
|
173
|
-
// output
|
|
174
|
+
// output. Only `.requiredOption` does that, and switching to
|
|
174
175
|
// `.requiredOption` would lose the `.choices()` enforcement. The
|
|
175
|
-
// explicit suffix keeps the runtime validation
|
|
176
|
+
// explicit suffix keeps the runtime validation and surfaces required
|
|
176
177
|
// status in help alongside the other options that use `.requiredOption`.
|
|
177
178
|
new Option('--mode <mode>', 'Dark mode behavior (required)')
|
|
178
179
|
.choices(['auto', 'static', 'override'])
|
|
@@ -201,6 +202,21 @@ export function registerToken(program, { getProjectRoot, withErrorHandling }) {
|
|
|
201
202
|
}),
|
|
202
203
|
});
|
|
203
204
|
}));
|
|
205
|
+
token
|
|
206
|
+
.command('list')
|
|
207
|
+
.description('List the design-token categories declared in the tokens CSS with their token names, in file order')
|
|
208
|
+
.option('--category <name>', 'Restrict the report to one category')
|
|
209
|
+
.option('--json', 'Emit the machine-readable envelope on stdout (see docs/machine-output.md)')
|
|
210
|
+
.action(withErrorHandling(async (options) => {
|
|
211
|
+
await tokenListCommand(getProjectRoot(), pickDefined({ category: options.category, json: options.json }));
|
|
212
|
+
}));
|
|
213
|
+
token
|
|
214
|
+
.command('show <token-name>')
|
|
215
|
+
.description('Show one token: its category, the value it takes in every declaring block, and where it is defined. The leading `--` is optional; with it, use the `--` separator first (e.g. `fireforge token show -- --my-token`).')
|
|
216
|
+
.option('--json', 'Emit the machine-readable envelope on stdout (see docs/machine-output.md)')
|
|
217
|
+
.action(withErrorHandling(async (tokenName, options) => {
|
|
218
|
+
await tokenShowCommand(getProjectRoot(), tokenName, pickDefined({ json: options.json }));
|
|
219
|
+
}));
|
|
204
220
|
token
|
|
205
221
|
.command('coverage')
|
|
206
222
|
.description('Measure design token usage across modified CSS files')
|