@intentius/chant 0.62.0 → 0.63.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli/handlers/operator.d.ts +13 -0
- package/dist/cli/handlers/operator.d.ts.map +1 -1
- package/dist/cli/handlers/run.d.ts.map +1 -1
- package/dist/cli/main.d.ts.map +1 -1
- package/dist/cli/registry.d.ts +2 -0
- package/dist/cli/registry.d.ts.map +1 -1
- package/dist/components/cli-support.d.ts +3 -0
- package/dist/components/cli-support.d.ts.map +1 -1
- package/dist/components/driver-output.d.ts.map +1 -1
- package/dist/components/driver.d.ts +12 -0
- package/dist/components/driver.d.ts.map +1 -1
- package/dist/fold/fold.d.ts.map +1 -1
- package/dist/fold/subset.d.ts +10 -0
- package/dist/fold/subset.d.ts.map +1 -1
- package/dist/lifecycle/gate-ledger.d.ts +61 -0
- package/dist/lifecycle/gate-ledger.d.ts.map +1 -1
- package/dist/lifecycle/index.d.ts +1 -0
- package/dist/lifecycle/index.d.ts.map +1 -1
- package/dist/lifecycle/plan-digest.d.ts +33 -0
- package/dist/lifecycle/plan-digest.d.ts.map +1 -0
- package/dist/lifecycle/run-ledger.d.ts.map +1 -1
- package/dist/op/activities/lexicon-upgrade.d.ts +14 -2
- package/dist/op/activities/lexicon-upgrade.d.ts.map +1 -1
- package/dist/op/activities/lifecycle.d.ts +27 -0
- package/dist/op/activities/lifecycle.d.ts.map +1 -1
- package/dist/op/activities/reconcile.d.ts +196 -27
- package/dist/op/activities/reconcile.d.ts.map +1 -1
- package/dist/op/builders.d.ts +6 -0
- package/dist/op/builders.d.ts.map +1 -1
- package/dist/op/composites/apply-op.d.ts +6 -0
- package/dist/op/composites/apply-op.d.ts.map +1 -1
- package/dist/op/composites/reconcile-op.d.ts.map +1 -1
- package/dist/op/gate-summary.d.ts +16 -0
- package/dist/op/gate-summary.d.ts.map +1 -1
- package/dist/op/gate.d.ts +104 -13
- package/dist/op/gate.d.ts.map +1 -1
- package/dist/op/index.d.ts +3 -2
- package/dist/op/index.d.ts.map +1 -1
- package/dist/op/local-executor.d.ts +17 -0
- package/dist/op/local-executor.d.ts.map +1 -1
- package/dist/op/local-output.d.ts.map +1 -1
- package/dist/op/op-ir.d.ts +8 -1
- package/dist/op/op-ir.d.ts.map +1 -1
- package/dist/op/runtime.d.ts +2 -0
- package/dist/op/runtime.d.ts.map +1 -1
- package/dist/op/types.d.ts +19 -0
- package/dist/op/types.d.ts.map +1 -1
- package/dist/terraform/__fixtures__/build-graph.d.ts +8 -0
- package/dist/terraform/__fixtures__/build-graph.d.ts.map +1 -1
- package/dist/terraform/graph.d.ts +18 -2
- package/dist/terraform/graph.d.ts.map +1 -1
- package/dist/terraform/parse.d.ts.map +1 -1
- package/dist/terraform/types.d.ts +7 -0
- package/dist/terraform/types.d.ts.map +1 -1
- package/package.json +1 -1
- package/src/cli/handlers/operator.test.ts +130 -0
- package/src/cli/handlers/operator.ts +56 -2
- package/src/cli/handlers/run.ts +19 -0
- package/src/cli/main.ts +2 -0
- package/src/cli/registry.ts +2 -0
- package/src/components/cli-support.ts +29 -4
- package/src/components/driver-output.ts +10 -0
- package/src/components/driver.test.ts +31 -0
- package/src/components/driver.ts +54 -8
- package/src/discovery/fold-import.test.ts +55 -0
- package/src/fold/fold.test.ts +152 -0
- package/src/fold/fold.ts +102 -2
- package/src/fold/subset-doc-parity.test.ts +35 -1
- package/src/fold/subset.ts +10 -0
- package/src/lifecycle/gate-ledger.test.ts +133 -1
- package/src/lifecycle/gate-ledger.ts +108 -0
- package/src/lifecycle/index.ts +1 -0
- package/src/lifecycle/plan-digest.test.ts +49 -0
- package/src/lifecycle/plan-digest.ts +86 -0
- package/src/lifecycle/run-ledger.ts +1 -0
- package/src/op/activities/lexicon-upgrade.test.ts +24 -12
- package/src/op/activities/lexicon-upgrade.ts +19 -3
- package/src/op/activities/lifecycle.ts +51 -2
- package/src/op/activities/reconcile.test.ts +512 -26
- package/src/op/activities/reconcile.ts +307 -34
- package/src/op/builders.ts +7 -1
- package/src/op/composites/apply-op.ts +16 -0
- package/src/op/composites/composites.test.ts +15 -2
- package/src/op/composites/reconcile-op.test.ts +18 -0
- package/src/op/composites/reconcile-op.ts +7 -1
- package/src/op/gate-summary.test.ts +33 -0
- package/src/op/gate-summary.ts +31 -0
- package/src/op/gate.test.ts +111 -1
- package/src/op/gate.ts +181 -23
- package/src/op/index.ts +5 -2
- package/src/op/local-executor.test.ts +226 -3
- package/src/op/local-executor.ts +61 -12
- package/src/op/local-output.test.ts +38 -0
- package/src/op/local-output.ts +24 -1
- package/src/op/op-ir.test.ts +22 -0
- package/src/op/op-ir.ts +9 -0
- package/src/op/runtime.ts +2 -0
- package/src/op/types.ts +19 -0
- package/src/terraform/__fixtures__/build-graph.ts +42 -0
- package/src/terraform/__fixtures__/carve-locals-data.test.ts +138 -0
- package/src/terraform/__fixtures__/depth-estate/main.tf +141 -0
- package/src/terraform/__fixtures__/depth-estate/terraform.tfstate +17 -0
- package/src/terraform/__fixtures__/depth-estate.test.ts +162 -0
- package/src/terraform/graph.test.ts +148 -1
- package/src/terraform/graph.ts +144 -6
- package/src/terraform/parse.ts +4 -1
- package/src/terraform/types.ts +7 -0
package/dist/op/index.d.ts
CHANGED
|
@@ -25,8 +25,9 @@ export type { ActivityProfile, ActivityProfileName } from "./activity-profiles.j
|
|
|
25
25
|
export { NonRetryableActivityError, nonRetryableFailure } from "./activity-failure.js";
|
|
26
26
|
export { runOpLocally, parseDuration, OpRunFailure } from "./local-executor.js";
|
|
27
27
|
export type { StepRecord, OpRunResult, RunOpOptions } from "./local-executor.js";
|
|
28
|
-
export { evaluateGate, gitGateLedgerPort, memoryGateLedgerPort, approveCommand } from "./gate.js";
|
|
29
|
-
export type { GateLedgerPort, GateCheck, GateCheckInput } from "./gate.js";
|
|
28
|
+
export { evaluateGate, gitGateLedgerPort, memoryGateLedgerPort, approveCommand, describeGateMismatch } from "./gate.js";
|
|
29
|
+
export type { GateLedgerPort, GateCheck, GateCheckInput, PendingGatePush, GateDigestMismatch } from "./gate.js";
|
|
30
|
+
export { computePlanDigest, isPlanDigest, describePlanDigest, PLAN_DIGEST_ALGORITHM, } from "../lifecycle/plan-digest.js";
|
|
30
31
|
export { gateName, usesDeprecatedGateKey, DEPRECATED_GATE_KEY_WARNING } from "./gate-name.js";
|
|
31
32
|
export type { GateNamed } from "./gate-name.js";
|
|
32
33
|
export { createLocalOpRuntime } from "./runtimes/local.js";
|
package/dist/op/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/op/index.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/op/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -57,6 +57,14 @@ export interface StepRecord {
|
|
|
57
57
|
timestamp: string;
|
|
58
58
|
url?: string;
|
|
59
59
|
};
|
|
60
|
+
/**
|
|
61
|
+
* Why a step declined to proceed on something that is not a failure
|
|
62
|
+
* (#2300): a gate holding a standing approval for a *different* plan. Names
|
|
63
|
+
* both digests and the `chant approve` line that closes the gap. The step's
|
|
64
|
+
* status is `skipped` and the run's is `gated` — nothing broke, and nothing
|
|
65
|
+
* was applied.
|
|
66
|
+
*/
|
|
67
|
+
refusal?: string;
|
|
60
68
|
}
|
|
61
69
|
export interface OpRunResult {
|
|
62
70
|
op: string;
|
|
@@ -74,6 +82,15 @@ export interface OpRunResult {
|
|
|
74
82
|
startedAt: string;
|
|
75
83
|
/** Present when `status === "gated"`: the pending fact the run ended on. */
|
|
76
84
|
gate?: PendingGateRecord;
|
|
85
|
+
/**
|
|
86
|
+
* Present when `status === "gated"` and this run's own append tried to push:
|
|
87
|
+
* whether it reached the remote (#2310). Absent when the run stopped on a
|
|
88
|
+
* pending fact an earlier run had already recorded — nothing was pushed
|
|
89
|
+
* this run.
|
|
90
|
+
*/
|
|
91
|
+
gatePushed?: boolean;
|
|
92
|
+
/** Set when `gatePushed` is false: why, in one line. */
|
|
93
|
+
gatePushWarning?: string;
|
|
77
94
|
/**
|
|
78
95
|
* The run's ledger record (#2118) — always built, whether or not it was
|
|
79
96
|
* appended. `chant run <op> --json` prints exactly this, so what a caller
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"local-executor.d.ts","sourceRoot":"","sources":["../../src/op/local-executor.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAGH,OAAO,KAAK,EAAE,QAAQ,EAAmB,YAAY,EAAwC,MAAM,SAAS,CAAC;AAC7G,OAAO,EAAmB,KAAK,UAAU,EAAE,KAAK,eAAe,EAAE,MAAM,qBAAqB,CAAC;AAI7F,OAAO,
|
|
1
|
+
{"version":3,"file":"local-executor.d.ts","sourceRoot":"","sources":["../../src/op/local-executor.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"local-output.d.ts","sourceRoot":"","sources":["../../src/op/local-output.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,WAAW,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAGhE,KAAK,MAAM,GAAG,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;AAerC;;;GAGG;AACH,wBAAgB,WAAW,CAAC,MAAM,EAAE,WAAW,EAAE,KAAK,GAAE,MAAe,GAAG,IAAI,
|
|
1
|
+
{"version":3,"file":"local-output.d.ts","sourceRoot":"","sources":["../../src/op/local-output.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,WAAW,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAGhE,KAAK,MAAM,GAAG,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;AAerC;;;GAGG;AACH,wBAAgB,WAAW,CAAC,MAAM,EAAE,WAAW,EAAE,KAAK,GAAE,MAAe,GAAG,IAAI,CA8D7E;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,UAAU,CAAC,MAAM,EAAE,WAAW,EAAE,KAAK,GAAE,MAAe,GAAG,IAAI,CAS5E;AAED,YAAY,EAAE,WAAW,EAAE,UAAU,EAAE,CAAC"}
|
package/dist/op/op-ir.d.ts
CHANGED
|
@@ -80,7 +80,7 @@
|
|
|
80
80
|
* change to `StepOutputRef`'s own fields (`./step-output-ref.ts`) that would
|
|
81
81
|
* silently change this JSON shape gets caught here.
|
|
82
82
|
*/
|
|
83
|
-
import type { OutcomeAttribute, OpConfig, OpSchedule } from "./types.js";
|
|
83
|
+
import type { OutcomeAttribute, OpConfig, OpSchedule, GateStep } from "./types.js";
|
|
84
84
|
import type { EffectReceiptRef } from "./receipt-store.js";
|
|
85
85
|
import type { ActivityContract } from "./activity-contract.js";
|
|
86
86
|
import { type ActivityProfile } from "./activity-profiles.js";
|
|
@@ -120,6 +120,13 @@ export interface OpIRGateStep {
|
|
|
120
120
|
/** Resolved to its effective value — `GateStep.timeout ?? "48h"`. */
|
|
121
121
|
timeout: string;
|
|
122
122
|
description?: string;
|
|
123
|
+
/**
|
|
124
|
+
* The plan this gate approves (#2300) — a digest string, or a
|
|
125
|
+
* {@link StepOutputRef} placeholder a foreign runtime resolves from the
|
|
126
|
+
* named step's result the same way it resolves one in an activity's args.
|
|
127
|
+
* Absent on a gate that binds no plan.
|
|
128
|
+
*/
|
|
129
|
+
plan?: GateStep["plan"];
|
|
123
130
|
}
|
|
124
131
|
export interface OpIREffectStep {
|
|
125
132
|
kind: "effect";
|
package/dist/op/op-ir.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"op-ir.d.ts","sourceRoot":"","sources":["../../src/op/op-ir.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiFG;AAGH,OAAO,KAAK,EACV,gBAAgB,EAChB,QAAQ,EACR,UAAU,
|
|
1
|
+
{"version":3,"file":"op-ir.d.ts","sourceRoot":"","sources":["../../src/op/op-ir.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiFG;AAGH,OAAO,KAAK,EACV,gBAAgB,EAChB,QAAQ,EACR,UAAU,EAIV,QAAQ,EAET,MAAM,SAAS,CAAC;AACjB,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AACxD,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,qBAAqB,CAAC;AAC5D,OAAO,EAAqB,KAAK,eAAe,EAAE,MAAM,qBAAqB,CAAC;AAG9E;;;;;;;;GAQG;AACH,eAAO,MAAM,oBAAoB,QAAQ,CAAC;AAI1C,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,UAAU,CAAC;IACjB,EAAE,EAAE,MAAM,CAAC;IACX,iGAAiG;IACjG,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAC9B,oFAAoF;IACpF,OAAO,EAAE,MAAM,CAAC;IAChB;;;;;;;OAOG;IACH,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,yEAAyE;IACzE,gBAAgB,CAAC,EAAE,gBAAgB,GAAG,gBAAgB,EAAE,CAAC;CAC1D;AAED,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,MAAM,CAAC;IACb,0FAA0F;IAC1F,IAAI,EAAE,MAAM,CAAC;IACb,qEAAqE;IACrE,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;;;OAKG;IACH,IAAI,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,CAAC;CACzB;AAED,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,QAAQ,CAAC;IACf,OAAO,EAAE,gBAAgB,CAAC;IAC1B,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,KAAK,EAAE,KAAK,CAAC,gBAAgB,GAAG,YAAY,CAAC,CAAC;IAC9C,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,MAAM,QAAQ,GAAG,gBAAgB,GAAG,YAAY,GAAG,cAAc,CAAC;AAExE,MAAM,WAAW,SAAS;IACxB,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,OAAO,CAAC;IAClB,KAAK,EAAE,QAAQ,EAAE,CAAC;CACnB;AAED,8EAA8E;AAC9E,MAAM,WAAW,oBAAoB;IACnC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAC9B,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAClC,0NAA0N;IAC1N,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;CACrB;AAED,MAAM,WAAW,IAAI;IACnB,aAAa,EAAE,MAAM,CAAC;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,gGAAgG;IAChG,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC/B;;;;;;OAMG;IACH,QAAQ,CAAC,EAAE,UAAU,CAAC;IACtB,MAAM,EAAE,SAAS,EAAE,CAAC;IACpB,SAAS,EAAE,SAAS,EAAE,CAAC;IACvB,0JAA0J;IAC1J,gBAAgB,EAAE,MAAM,CAAC,MAAM,EAAE,eAAe,CAAC,CAAC;IAClD;;;;OAIG;IACH,iBAAiB,EAAE,MAAM,CAAC,MAAM,EAAE,oBAAoB,CAAC,CAAC;CACzD;AAoGD;;;;;;;;;GASG;AACH,wBAAgB,SAAS,CACvB,MAAM,EAAE,QAAQ,EAChB,gBAAgB,GAAE,WAAW,CAAC,MAAM,EAAE,gBAAgB,CAAgB,EACtE,eAAe,GAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,eAAe,CAAC,CAAqB,GAC7E,IAAI,CA2CN;AAED,sLAAsL;AACtL,wBAAgB,aAAa,CAC3B,MAAM,EAAE,QAAQ,EAChB,gBAAgB,CAAC,EAAE,WAAW,CAAC,MAAM,EAAE,gBAAgB,CAAC,EACxD,eAAe,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,eAAe,CAAC,CAAC,GAC1D,MAAM,CAER;AA+CD,qDAAqD;AACrD,wBAAgB,cAAc,CAAC,EAAE,EAAE,IAAI,GAAG,QAAQ,CAgBjD"}
|
package/dist/op/runtime.d.ts
CHANGED
|
@@ -51,6 +51,8 @@ export interface OpRunStepRecord {
|
|
|
51
51
|
};
|
|
52
52
|
/** The failure message, for `status: "fail"`. */
|
|
53
53
|
error?: string;
|
|
54
|
+
/** Why a gate declined a standing approval that was for another plan (#2300) — see {@link StepRecord.refusal}. */
|
|
55
|
+
refusal?: string;
|
|
54
56
|
}
|
|
55
57
|
/** One phase's steps and the verdict they add up to. */
|
|
56
58
|
export interface OpRunPhaseRecord {
|
package/dist/op/runtime.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../../src/op/runtime.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,SAAS,CAAC;AACxC,OAAO,KAAK,EAAE,UAAU,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAC;AAChE,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,0BAA0B,CAAC;AACrE,OAAO,KAAK,EAAE,oBAAoB,EAAE,mBAAmB,EAAE,MAAM,2BAA2B,CAAC;AAE3F;;;;;;;;GAQG;AACH,MAAM,MAAM,UAAU,GAAG,SAAS,GAAG,WAAW,GAAG,QAAQ,GAAG,OAAO,GAAG,WAAW,CAAC;AAEpF,wEAAwE;AACxE,wBAAgB,UAAU,CAAC,MAAM,EAAE,WAAW,CAAC,QAAQ,CAAC,GAAG,UAAU,CAEpE;AAED,gHAAgH;AAChH,MAAM,WAAW,eAAe;IAC9B,sEAAsE;IACtE,EAAE,EAAE,MAAM,CAAC;IACX,MAAM,EAAE,UAAU,CAAC,QAAQ,CAAC,CAAC;IAC7B,UAAU,EAAE,MAAM,CAAC;IACnB,mEAAmE;IACnE,OAAO,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,OAAO,CAAA;KAAE,CAAC;IAC3C,8EAA8E;IAC9E,QAAQ,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAC;QAAC,GAAG,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;IACjF,iDAAiD;IACjD,KAAK,CAAC,EAAE,MAAM,CAAC;
|
|
1
|
+
{"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../../src/op/runtime.ts"],"names":[],"mappings":"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"}
|
package/dist/op/types.d.ts
CHANGED
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
*/
|
|
7
7
|
import type { EffectReceiptRef } from "./receipt-store.js";
|
|
8
8
|
import type { ActivityProfileName } from "./activity-profiles.js";
|
|
9
|
+
import type { StepOutputRef } from "./step-output-ref.js";
|
|
9
10
|
export interface OpConfig {
|
|
10
11
|
/** Kebab-case identifier. Names the Op's output directory (`dist/ops/<name>/`), and is the name `chant run <name>` and another Op's `depends` refer to. */
|
|
11
12
|
name: string;
|
|
@@ -165,6 +166,24 @@ export interface GateStepBase {
|
|
|
165
166
|
timeout?: string;
|
|
166
167
|
/** Human-readable description of the action required to unblock this gate. */
|
|
167
168
|
description?: string;
|
|
169
|
+
/**
|
|
170
|
+
* The plan this gate approves (#2300), normally a {@link StepOutputRef}
|
|
171
|
+
* into the Plan phase's own digest — `plan.out.planDigest`. The executor
|
|
172
|
+
* resolves it the same way it resolves an activity step's args, and hands
|
|
173
|
+
* the result to `evaluateGate` as `planDigest`.
|
|
174
|
+
*
|
|
175
|
+
* With it, a resolution satisfies this gate only when it was recorded for
|
|
176
|
+
* that exact plan; a resolution for another plan is refused by name.
|
|
177
|
+
* Without it the gate authorises the next run rather than a plan, which is
|
|
178
|
+
* what every gate did before #2300 and what
|
|
179
|
+
* INTENTIUS/choudoufu#1026 measured.
|
|
180
|
+
*
|
|
181
|
+
* A `string` here is a digest computed elsewhere; anything else is a
|
|
182
|
+
* reference resolved at run time. A reference that resolves to no string
|
|
183
|
+
* leaves the gate unbound rather than failing the run — an Op whose Plan
|
|
184
|
+
* phase publishes no digest is not thereby unrunnable.
|
|
185
|
+
*/
|
|
186
|
+
plan?: string | StepOutputRef;
|
|
168
187
|
}
|
|
169
188
|
/**
|
|
170
189
|
* A human approval decided against the gate ledger. The name lives on `gate`;
|
package/dist/op/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/op/types.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AACxD,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/op/types.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,5 +1,13 @@
|
|
|
1
1
|
import { type ExpressionRefs } from "../graph.js";
|
|
2
2
|
import type { Hcl2JsonTree, TfGraph } from "../types.js";
|
|
3
|
+
/**
|
|
4
|
+
* The longest inbound chain anywhere in the graph — the same "depth" column
|
|
5
|
+
* the spike measured (docs/design/carve-dependency-blast-radius-spike.md
|
|
6
|
+
* section 2): 1 hop is a direct dependent, 2 is a dependent of a dependent,
|
|
7
|
+
* and so on. Every shipped fixture tops out at 1; `depth-estate` is built to
|
|
8
|
+
* clear that.
|
|
9
|
+
*/
|
|
10
|
+
export declare function maxTransitiveInboundDepth(graph: TfGraph): number;
|
|
3
11
|
/**
|
|
4
12
|
* Test-only stand-in for the hcl2json expression AST (`parse.ts`'s
|
|
5
13
|
* `resolveExpressionRefs`). Fixture expressions are simple `${<accessor>}`
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"build-graph.d.ts","sourceRoot":"","sources":["../../../src/terraform/__fixtures__/build-graph.ts"],"names":[],"mappings":"AAAA,OAAO,EAAkC,KAAK,cAAc,EAAE,MAAM,UAAU,CAAC;AAC/E,OAAO,KAAK,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,UAAU,CAAC;
|
|
1
|
+
{"version":3,"file":"build-graph.d.ts","sourceRoot":"","sources":["../../../src/terraform/__fixtures__/build-graph.ts"],"names":[],"mappings":"AAAA,OAAO,EAAkC,KAAK,cAAc,EAAE,MAAM,UAAU,CAAC;AAC/E,OAAO,KAAK,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,UAAU,CAAC;AA4BtD;;;;;;GAMG;AACH,wBAAgB,yBAAyB,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAOhE;AAED;;;;;;GAMG;AACH,wBAAgB,eAAe,CAAC,IAAI,EAAE,YAAY,GAAG,cAAc,CASlE;AAED,oGAAoG;AACpG,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,YAAY,GAAG,OAAO,CAE7D"}
|
|
@@ -32,8 +32,15 @@ interface RawRef {
|
|
|
32
32
|
export declare function refFromAccessor(accessor: string): RawRef | null;
|
|
33
33
|
/**
|
|
34
34
|
* Every string value carrying an interpolation across the tree's resource,
|
|
35
|
-
* module and
|
|
36
|
-
* through the AST before `buildGraph` can classify
|
|
35
|
+
* module, output, `locals` and `data` blocks — exactly the expressions
|
|
36
|
+
* `parse.ts` must resolve through the AST before `buildGraph` can classify
|
|
37
|
+
* them.
|
|
38
|
+
*
|
|
39
|
+
* `locals` and `data` are here because a reference can reach a resource
|
|
40
|
+
* through them (#2324): a survivor reading `local.assets_id`, or a `data`
|
|
41
|
+
* source keyed off the carved resource, is a dependency the plan breaks on
|
|
42
|
+
* just as hard as a direct one. Skipping their bodies meant the AST never saw
|
|
43
|
+
* those expressions at all.
|
|
37
44
|
*/
|
|
38
45
|
export declare function collectExpressions(tree: Hcl2JsonTree): string[];
|
|
39
46
|
/**
|
|
@@ -50,6 +57,15 @@ export declare function collectExpressions(tree: Hcl2JsonTree): string[];
|
|
|
50
57
|
* exactly like a resource's does. So an output contributes an edge tagged
|
|
51
58
|
* `fromKind: "output"` from the pseudo-address `output.<name>` (#1638),
|
|
52
59
|
* which the scorer weights lower and `carve bridge` patches.
|
|
60
|
+
*
|
|
61
|
+
* `locals` and `data` blocks are non-node referrers of a third kind (#2324):
|
|
62
|
+
* they carry a reference between two nodes rather than terminating it. A
|
|
63
|
+
* survivor reading `local.assets_id`, or reading a `data` source keyed off the
|
|
64
|
+
* carved resource, depends on that resource, so the reference is resolved
|
|
65
|
+
* through the referrer to the resource it ultimately names and the edge is
|
|
66
|
+
* recorded against the surviving node — the thing a reader can actually carve
|
|
67
|
+
* or leave behind. The referrer's own body is where `carve bridge` then lands
|
|
68
|
+
* the rewrite.
|
|
53
69
|
*/
|
|
54
70
|
export declare function buildGraph(tree: Hcl2JsonTree, exprRefs: ExpressionRefs): TfGraph;
|
|
55
71
|
/** Edges where something in the surviving Terraform depends on `address`. */
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"graph.d.ts","sourceRoot":"","sources":["../../src/terraform/graph.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAIH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,EAAE,OAAO,EAAU,MAAM,SAAS,CAAC;AAErE;;;;;GAKG;AACH,MAAM,MAAM,cAAc,GAAG,WAAW,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC,CAAC;AAKpE,UAAU,MAAM;IACd,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,8EAA8E;IAC9E,GAAG,CAAC,EAAE,MAAM,CAAC;CACd;AA4BD;;;;GAIG;AACH,wBAAgB,eAAe,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAe/D;
|
|
1
|
+
{"version":3,"file":"graph.d.ts","sourceRoot":"","sources":["../../src/terraform/graph.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAIH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,EAAE,OAAO,EAAU,MAAM,SAAS,CAAC;AAErE;;;;;GAKG;AACH,MAAM,MAAM,cAAc,GAAG,WAAW,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC,CAAC;AAKpE,UAAU,MAAM;IACd,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,8EAA8E;IAC9E,GAAG,CAAC,EAAE,MAAM,CAAC;CACd;AA4BD;;;;GAIG;AACH,wBAAgB,eAAe,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAe/D;AAiBD;;;;;;;;;;;GAWG;AACH,wBAAgB,kBAAkB,CAAC,IAAI,EAAE,YAAY,GAAG,MAAM,EAAE,CAiB/D;AA8LD;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,wBAAgB,UAAU,CAAC,IAAI,EAAE,YAAY,EAAE,QAAQ,EAAE,cAAc,GAAG,OAAO,CAsFhF;AAED,6EAA6E;AAC7E,wBAAgB,YAAY,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,MAAM,GAAG,MAAM,EAAE,CAEtE;AAED,0FAA0F;AAC1F,wBAAgB,aAAa,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,MAAM,GAAG,MAAM,EAAE,CAEvE"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"parse.d.ts","sourceRoot":"","sources":["../../src/terraform/parse.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAMH,OAAO,KAAK,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAErD,wDAAwD;AACxD,MAAM,WAAW,QAAQ;IACvB,KAAK,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,KAAK,OAAO,CAAC,YAAY,CAAC,CAAC;IAChE,yFAAyF;IACzF,yBAAyB,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,KAAK,OAAO,CAAC,KAAK,CAAC;QAAE,KAAK,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC,CAAC;CACxG;AAED,qBAAa,oBAAqB,SAAQ,KAAK;gBACjC,KAAK,EAAE,OAAO;CAQ3B;AAED;;;GAGG;AACH,wBAAsB,YAAY,IAAI,OAAO,CAAC,QAAQ,CAAC,CAMtD;
|
|
1
|
+
{"version":3,"file":"parse.d.ts","sourceRoot":"","sources":["../../src/terraform/parse.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAMH,OAAO,KAAK,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAErD,wDAAwD;AACxD,MAAM,WAAW,QAAQ;IACvB,KAAK,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,KAAK,OAAO,CAAC,YAAY,CAAC,CAAC;IAChE,yFAAyF;IACzF,yBAAyB,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,KAAK,OAAO,CAAC,KAAK,CAAC;QAAE,KAAK,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC,CAAC;CACxG;AAED,qBAAa,oBAAqB,SAAQ,KAAK;gBACjC,KAAK,EAAE,OAAO;CAQ3B;AAED;;;GAGG;AACH,wBAAsB,YAAY,IAAI,OAAO,CAAC,QAAQ,CAAC,CAMtD;AAqDD,MAAM,WAAW,qBAAqB;IACpC,iFAAiF;IACjF,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED;;;;;GAKG;AACH,wBAAsB,iBAAiB,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,GAAE,qBAA0B,GAAG,OAAO,CAAC,OAAO,CAAC,CAWvG"}
|
|
@@ -93,6 +93,13 @@ export interface Hcl2JsonTree {
|
|
|
93
93
|
data?: Record<string, Record<string, unknown[]>>;
|
|
94
94
|
/** Root-module `output` blocks. Not nodes — they reference, they are not carvable (#1638). */
|
|
95
95
|
output?: Record<string, unknown[]>;
|
|
96
|
+
/**
|
|
97
|
+
* Root-module `locals` blocks, as hcl2json renders them: one array element
|
|
98
|
+
* per `locals` block, each an object of its assignments. Not nodes either —
|
|
99
|
+
* a local is a substitution — but a reference can reach a resource through
|
|
100
|
+
* one, so the graph resolves `local.x` to what it names (#2324).
|
|
101
|
+
*/
|
|
102
|
+
locals?: unknown[];
|
|
96
103
|
[k: string]: unknown;
|
|
97
104
|
}
|
|
98
105
|
//# sourceMappingURL=types.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/terraform/types.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,+EAA+E;AAC/E,MAAM,WAAW,MAAM;IACrB,sEAAsE;IACtE,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,UAAU,GAAG,QAAQ,CAAC;IAC5B,8DAA8D;IAC9D,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,oDAAoD;IACpD,IAAI,EAAE,MAAM,CAAC;IACb;;;;OAIG;IACH,SAAS,EAAE,MAAM,CAAC;IAClB,uFAAuF;IACvF,UAAU,EAAE,OAAO,CAAC;IACpB;;;;OAIG;IACH,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB;;;;;;OAMG;IACH,gBAAgB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAC3C;AAED;;;;;;GAMG;AACH,MAAM,WAAW,MAAM;IACrB,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,MAAM,CAAC;IACX;;;;;;;OAOG;IACH,QAAQ,CAAC,EAAE,QAAQ,CAAC;IACpB,8DAA8D;IAC9D,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB;;;;;OAKG;IACH,GAAG,EAAE,MAAM,EAAE,CAAC;IACd;;;;OAIG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;CACtB;AAED,MAAM,WAAW,OAAO;IACtB,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB,KAAK,EAAE,MAAM,EAAE,CAAC;CACjB;AAED;;;;;GAKG;AACH,MAAM,WAAW,YAAY;IAC3B,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC;IACrD,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,CAAC;IACnC,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC;IACjD,8FAA8F;IAC9F,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,CAAC;IACnC,CAAC,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC;CACtB"}
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/terraform/types.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,+EAA+E;AAC/E,MAAM,WAAW,MAAM;IACrB,sEAAsE;IACtE,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,UAAU,GAAG,QAAQ,CAAC;IAC5B,8DAA8D;IAC9D,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,oDAAoD;IACpD,IAAI,EAAE,MAAM,CAAC;IACb;;;;OAIG;IACH,SAAS,EAAE,MAAM,CAAC;IAClB,uFAAuF;IACvF,UAAU,EAAE,OAAO,CAAC;IACpB;;;;OAIG;IACH,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB;;;;;;OAMG;IACH,gBAAgB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAC3C;AAED;;;;;;GAMG;AACH,MAAM,WAAW,MAAM;IACrB,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,MAAM,CAAC;IACX;;;;;;;OAOG;IACH,QAAQ,CAAC,EAAE,QAAQ,CAAC;IACpB,8DAA8D;IAC9D,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB;;;;;OAKG;IACH,GAAG,EAAE,MAAM,EAAE,CAAC;IACd;;;;OAIG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;CACtB;AAED,MAAM,WAAW,OAAO;IACtB,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB,KAAK,EAAE,MAAM,EAAE,CAAC;CACjB;AAED;;;;;GAKG;AACH,MAAM,WAAW,YAAY;IAC3B,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC;IACrD,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,CAAC;IACnC,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC;IACjD,8FAA8F;IAC9F,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,CAAC;IACnC;;;;;OAKG;IACH,MAAM,CAAC,EAAE,OAAO,EAAE,CAAC;IACnB,CAAC,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC;CACtB"}
|
package/package.json
CHANGED
|
@@ -349,6 +349,29 @@ describe("runOperatorStatus", () => {
|
|
|
349
349
|
});
|
|
350
350
|
});
|
|
351
351
|
|
|
352
|
+
/**
|
|
353
|
+
* A digest shaped the way `computePlanDigest` produces them (#2300).
|
|
354
|
+
*/
|
|
355
|
+
const PLAN_A = `sha256:${"a".repeat(64)}`;
|
|
356
|
+
|
|
357
|
+
/**
|
|
358
|
+
* The standing pending fact `chant approve` reads the plan off since #2300.
|
|
359
|
+
* Every approve test seeds one, because a gate with nothing pending has no
|
|
360
|
+
* plan to approve and the command refuses rather than recording an approval
|
|
361
|
+
* of whatever runs next — which is its own test below.
|
|
362
|
+
*/
|
|
363
|
+
function seedPending(op: string, gate: string, planDigest: string | undefined): void {
|
|
364
|
+
readGateLedgerMock.mockResolvedValue({
|
|
365
|
+
resolutions: [],
|
|
366
|
+
pending: [{
|
|
367
|
+
version: 1, kind: "pending", op, gate,
|
|
368
|
+
timestamp: "2026-01-01T00:00:00.000Z", expiresAt: "2099-01-01T00:00:00.000Z",
|
|
369
|
+
...(planDigest !== undefined ? { planDigest } : {}),
|
|
370
|
+
}],
|
|
371
|
+
malformed: 0,
|
|
372
|
+
});
|
|
373
|
+
}
|
|
374
|
+
|
|
352
375
|
describe("runApprove", () => {
|
|
353
376
|
test("requires both <op> and <gate>", async () => {
|
|
354
377
|
const errSpy = vi.spyOn(console, "error").mockImplementation(() => undefined);
|
|
@@ -358,6 +381,7 @@ describe("runApprove", () => {
|
|
|
358
381
|
});
|
|
359
382
|
|
|
360
383
|
test("appends a gate-resolution record and pushes, resolving --actor over env fallbacks", async () => {
|
|
384
|
+
seedPending("fountain-apply", "rollout-gate", PLAN_A);
|
|
361
385
|
appendGateResolutionMock.mockResolvedValue({
|
|
362
386
|
commit: "sha",
|
|
363
387
|
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z" },
|
|
@@ -380,6 +404,7 @@ describe("runApprove", () => {
|
|
|
380
404
|
test("--approver wins over --actor and over the CI/shell identity", async () => {
|
|
381
405
|
vi.stubEnv("GITHUB_ACTOR", "ci-bot");
|
|
382
406
|
vi.stubEnv("USER", "alex");
|
|
407
|
+
seedPending("deploy-gated", "approve-deploy", PLAN_A);
|
|
383
408
|
appendGateResolutionMock.mockResolvedValue({
|
|
384
409
|
commit: "sha",
|
|
385
410
|
record: { version: 1, op: "deploy-gated", gate: "approve-deploy", resolvedBy: "you", timestamp: "2026-01-01T00:00:00.000Z" },
|
|
@@ -404,6 +429,7 @@ describe("runApprove", () => {
|
|
|
404
429
|
vi.stubEnv("GITHUB_REF_NAME", "");
|
|
405
430
|
vi.stubEnv("GITHUB_REPOSITORY", "");
|
|
406
431
|
vi.stubEnv("CI_MERGE_REQUEST_PROJECT_URL", "");
|
|
432
|
+
seedPending("fountain-apply", "rollout-gate", PLAN_A);
|
|
407
433
|
appendGateResolutionMock.mockResolvedValue({
|
|
408
434
|
commit: "sha",
|
|
409
435
|
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z", url: "https://github.com/org/repo/pull/9" },
|
|
@@ -427,6 +453,7 @@ describe("runApprove", () => {
|
|
|
427
453
|
vi.stubEnv("GITHUB_SERVER_URL", "https://github.com");
|
|
428
454
|
vi.stubEnv("GITHUB_REPOSITORY", "INTENTIUS/chant");
|
|
429
455
|
vi.stubEnv("GITHUB_REF_NAME", "2028/merge");
|
|
456
|
+
seedPending("fountain-apply", "g", PLAN_A);
|
|
430
457
|
appendGateResolutionMock.mockResolvedValue({
|
|
431
458
|
commit: "sha",
|
|
432
459
|
record: { version: 1, op: "fountain-apply", gate: "g", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z" },
|
|
@@ -488,6 +515,7 @@ describe("runApprove", () => {
|
|
|
488
515
|
|
|
489
516
|
test("warns (but still records) when the op isn't among discovered *.op.ts declarations", async () => {
|
|
490
517
|
discoverOpsMock.mockResolvedValue({ ops: new Map(), errors: [] });
|
|
518
|
+
seedPending("unknown-op", "g", PLAN_A);
|
|
491
519
|
appendGateResolutionMock.mockResolvedValue({
|
|
492
520
|
commit: "sha",
|
|
493
521
|
record: { version: 1, op: "unknown-op", gate: "g", resolvedBy: "unknown", timestamp: "2026-01-01T00:00:00.000Z" },
|
|
@@ -742,8 +770,108 @@ describe("runOperatorLog", () => {
|
|
|
742
770
|
* append must not be reached, because reaching it is what discarded the
|
|
743
771
|
* pending fact in the first place.
|
|
744
772
|
*/
|
|
773
|
+
/**
|
|
774
|
+
* #2300 — an approval is for a plan. `chant approve` records the plan it
|
|
775
|
+
* approves, so the resolution says what was reviewed rather than only who
|
|
776
|
+
* reviewed and when.
|
|
777
|
+
*/
|
|
778
|
+
describe("runApprove — the resolution names the plan it approves (#2300)", () => {
|
|
779
|
+
test("by default it approves the standing pending fact's plan, so the common path stays one command", async () => {
|
|
780
|
+
seedPending("fountain-apply", "rollout-gate", PLAN_A);
|
|
781
|
+
appendGateResolutionMock.mockResolvedValue({
|
|
782
|
+
commit: "sha",
|
|
783
|
+
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z", planDigest: PLAN_A },
|
|
784
|
+
});
|
|
785
|
+
const errSpy = vi.spyOn(console, "error").mockImplementation(() => undefined);
|
|
786
|
+
|
|
787
|
+
expect(await runApprove(ctx({ path: "fountain-apply", extraPositional: "rollout-gate", actor: "alex" }))).toBe(0);
|
|
788
|
+
expect(appendGateResolutionMock).toHaveBeenCalledWith(expect.objectContaining({ planDigest: PLAN_A }));
|
|
789
|
+
expect(errSpy.mock.calls.map((c) => String(c[0])).join("\n")).toContain(`approves the plan ${PLAN_A}`);
|
|
790
|
+
errSpy.mockRestore();
|
|
791
|
+
});
|
|
792
|
+
|
|
793
|
+
test("--plan names one explicitly, and wins over the standing fact's", async () => {
|
|
794
|
+
const other = `sha256:${"b".repeat(64)}`;
|
|
795
|
+
seedPending("fountain-apply", "rollout-gate", PLAN_A);
|
|
796
|
+
appendGateResolutionMock.mockResolvedValue({
|
|
797
|
+
commit: "sha",
|
|
798
|
+
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z", planDigest: other },
|
|
799
|
+
});
|
|
800
|
+
const errSpy = vi.spyOn(console, "error").mockImplementation(() => undefined);
|
|
801
|
+
|
|
802
|
+
expect(await runApprove(ctx({ path: "fountain-apply", extraPositional: "rollout-gate", actor: "alex", plan: other }))).toBe(0);
|
|
803
|
+
expect(appendGateResolutionMock).toHaveBeenCalledWith(expect.objectContaining({ planDigest: other }));
|
|
804
|
+
errSpy.mockRestore();
|
|
805
|
+
});
|
|
806
|
+
|
|
807
|
+
// With nothing pending there is no plan on the ledger to approve, and
|
|
808
|
+
// recording a resolution anyway is exactly how an approval came to mean
|
|
809
|
+
// "the next run" (INTENTIUS/choudoufu#1026).
|
|
810
|
+
test("with no pending record it refuses, writes nothing, and names the fix", async () => {
|
|
811
|
+
readGateLedgerMock.mockResolvedValue({ resolutions: [], pending: [], malformed: 0 });
|
|
812
|
+
const errSpy = vi.spyOn(console, "error").mockImplementation(() => undefined);
|
|
813
|
+
|
|
814
|
+
const code = await runApprove(ctx({ path: "fountain-apply", extraPositional: "rollout-gate", actor: "alex" }));
|
|
815
|
+
|
|
816
|
+
expect(code).toBe(1);
|
|
817
|
+
expect(appendGateResolutionMock).not.toHaveBeenCalled();
|
|
818
|
+
expect(pushLifecycleMock).not.toHaveBeenCalled();
|
|
819
|
+
const out = errSpy.mock.calls.map((c) => String(c[0])).join("\n");
|
|
820
|
+
expect(out).toContain("has no pending fact, so there is no plan to approve");
|
|
821
|
+
expect(out).toContain("chant run fountain-apply");
|
|
822
|
+
expect(out).toContain("--plan <digest>");
|
|
823
|
+
errSpy.mockRestore();
|
|
824
|
+
});
|
|
825
|
+
|
|
826
|
+
// ...but `--plan` is the escape hatch, so approving a plan whose digest you
|
|
827
|
+
// already hold does not need a run to have recorded a pending fact first.
|
|
828
|
+
test("--plan approves with nothing pending", async () => {
|
|
829
|
+
readGateLedgerMock.mockResolvedValue({ resolutions: [], pending: [], malformed: 0 });
|
|
830
|
+
appendGateResolutionMock.mockResolvedValue({
|
|
831
|
+
commit: "sha",
|
|
832
|
+
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z", planDigest: PLAN_A },
|
|
833
|
+
});
|
|
834
|
+
const errSpy = vi.spyOn(console, "error").mockImplementation(() => undefined);
|
|
835
|
+
|
|
836
|
+
expect(await runApprove(ctx({ path: "fountain-apply", extraPositional: "rollout-gate", actor: "alex", plan: PLAN_A }))).toBe(0);
|
|
837
|
+
expect(appendGateResolutionMock).toHaveBeenCalledWith(expect.objectContaining({ planDigest: PLAN_A }));
|
|
838
|
+
errSpy.mockRestore();
|
|
839
|
+
});
|
|
840
|
+
|
|
841
|
+
test("a --plan that is not a digest is refused before anything is written", async () => {
|
|
842
|
+
seedPending("fountain-apply", "rollout-gate", PLAN_A);
|
|
843
|
+
const errSpy = vi.spyOn(console, "error").mockImplementation(() => undefined);
|
|
844
|
+
|
|
845
|
+
const code = await runApprove(ctx({
|
|
846
|
+
path: "fountain-apply", extraPositional: "rollout-gate", actor: "alex", plan: "chant.tfplan",
|
|
847
|
+
}));
|
|
848
|
+
|
|
849
|
+
expect(code).toBe(1);
|
|
850
|
+
expect(appendGateResolutionMock).not.toHaveBeenCalled();
|
|
851
|
+
expect(errSpy.mock.calls.map((c) => String(c[0])).join("\n")).toContain("--plan must be a plan digest");
|
|
852
|
+
errSpy.mockRestore();
|
|
853
|
+
});
|
|
854
|
+
|
|
855
|
+
// A gate that binds no plan records no digest on its pending fact, so the
|
|
856
|
+
// resolution carries none either — and nothing refuses, because nothing
|
|
857
|
+
// ever claimed to bind a plan there.
|
|
858
|
+
test("a gate that binds no plan approves as it always did", async () => {
|
|
859
|
+
seedPending("fountain-apply", "rollout-gate", undefined);
|
|
860
|
+
appendGateResolutionMock.mockResolvedValue({
|
|
861
|
+
commit: "sha",
|
|
862
|
+
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z" },
|
|
863
|
+
});
|
|
864
|
+
const errSpy = vi.spyOn(console, "error").mockImplementation(() => undefined);
|
|
865
|
+
|
|
866
|
+
expect(await runApprove(ctx({ path: "fountain-apply", extraPositional: "rollout-gate", actor: "alex" }))).toBe(0);
|
|
867
|
+
expect(appendGateResolutionMock.mock.calls[0][0]).not.toHaveProperty("planDigest");
|
|
868
|
+
errSpy.mockRestore();
|
|
869
|
+
});
|
|
870
|
+
});
|
|
871
|
+
|
|
745
872
|
describe("runApprove — the ledger branch is read before it is appended to (#2303)", () => {
|
|
746
873
|
test("reads the branch before recording the resolution", async () => {
|
|
874
|
+
seedPending("fountain-apply", "rollout-gate", PLAN_A);
|
|
747
875
|
appendGateResolutionMock.mockResolvedValue({
|
|
748
876
|
commit: "sha",
|
|
749
877
|
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z" },
|
|
@@ -796,6 +924,7 @@ describe("runApprove — the ledger branch is read before it is appended to (#23
|
|
|
796
924
|
*/
|
|
797
925
|
describe("runApprove — a push that does not land is reported (#2309 review)", () => {
|
|
798
926
|
test("a rejected push warns and marks the success line local-only", async () => {
|
|
927
|
+
seedPending("fountain-apply", "rollout-gate", PLAN_A);
|
|
799
928
|
appendGateResolutionMock.mockResolvedValue({
|
|
800
929
|
commit: "sha",
|
|
801
930
|
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z" },
|
|
@@ -814,6 +943,7 @@ describe("runApprove — a push that does not land is reported (#2309 review)",
|
|
|
814
943
|
});
|
|
815
944
|
|
|
816
945
|
test("a project with no remote says nothing was pushed", async () => {
|
|
946
|
+
seedPending("fountain-apply", "rollout-gate", PLAN_A);
|
|
817
947
|
appendGateResolutionMock.mockResolvedValue({
|
|
818
948
|
commit: "sha",
|
|
819
949
|
record: { version: 1, op: "fountain-apply", gate: "rollout-gate", resolvedBy: "alex", timestamp: "2026-01-01T00:00:00.000Z" },
|
|
@@ -34,6 +34,7 @@ import {
|
|
|
34
34
|
latestResolutionSince, latestPendingGate, isPendingGateExpired,
|
|
35
35
|
resolveApprovalUrl, isApprovalUrl,
|
|
36
36
|
} from "../../lifecycle/gate-ledger";
|
|
37
|
+
import { isPlanDigest } from "../../lifecycle/plan-digest";
|
|
37
38
|
import { pushLifecycle, requireLifecycleLedger } from "../../lifecycle/git";
|
|
38
39
|
import { formatError, formatWarning, formatSuccess, formatBold, formatInfo } from "../format";
|
|
39
40
|
import type { CommandContext } from "../registry";
|
|
@@ -689,6 +690,7 @@ export async function runApprove(ctx: CommandContext): Promise<number> {
|
|
|
689
690
|
actor: ctx.args.approver ?? ctx.args.actor,
|
|
690
691
|
note: ctx.args.note,
|
|
691
692
|
url: ctx.args.url,
|
|
693
|
+
plan: ctx.args.plan,
|
|
692
694
|
});
|
|
693
695
|
if (!outcome.ok) return 1;
|
|
694
696
|
|
|
@@ -707,6 +709,12 @@ export interface GateApprovalOptions {
|
|
|
707
709
|
note?: string;
|
|
708
710
|
/** `--url` — the approval surface, validated as absolute http/https. */
|
|
709
711
|
url?: string;
|
|
712
|
+
/**
|
|
713
|
+
* `--plan <digest>` (#2300) — the plan this approval is for. Omitted, the
|
|
714
|
+
* digest is read off the gate's standing pending fact, so the common path
|
|
715
|
+
* stays one command: run, read what it planned, approve it.
|
|
716
|
+
*/
|
|
717
|
+
plan?: string;
|
|
710
718
|
}
|
|
711
719
|
|
|
712
720
|
export type GateApprovalOutcome =
|
|
@@ -720,6 +728,13 @@ export type GateApprovalOutcome =
|
|
|
720
728
|
*
|
|
721
729
|
* Prints the same warning for an undiscovered op and the same success line as
|
|
722
730
|
* `chant approve` always did; the caller adds whatever it does next.
|
|
731
|
+
*
|
|
732
|
+
* Since #2300 the resolution names the plan it approves. By default that is
|
|
733
|
+
* the standing pending fact's plan — the one the gated run produced — so the
|
|
734
|
+
* common path is still `chant run`, read, `chant approve`. With no pending
|
|
735
|
+
* fact and no `--plan`, this refuses: there is nothing on the ledger saying
|
|
736
|
+
* what would be approved, and writing a resolution anyway is what made an
|
|
737
|
+
* approval mean "the next run" instead of "this plan".
|
|
723
738
|
*/
|
|
724
739
|
export async function recordGateApproval(
|
|
725
740
|
opName: string,
|
|
@@ -748,8 +763,6 @@ export async function recordGateApproval(
|
|
|
748
763
|
return { ok: false };
|
|
749
764
|
}
|
|
750
765
|
|
|
751
|
-
const resolvedBy = opts.actor ?? process.env.GITHUB_ACTOR ?? process.env.GITLAB_USER_LOGIN ?? process.env.USER ?? "unknown";
|
|
752
|
-
|
|
753
766
|
// #2028: the resolution's link is typed. `--url` wins; otherwise, running
|
|
754
767
|
// inside the PR/MR job that carries the change is itself the address, the
|
|
755
768
|
// same env fallback `--actor` uses. `--note` stays free-text prose.
|
|
@@ -762,6 +775,40 @@ export async function recordGateApproval(
|
|
|
762
775
|
return { ok: false };
|
|
763
776
|
}
|
|
764
777
|
|
|
778
|
+
// #2300: an approval is for a plan, so this command has to know which one.
|
|
779
|
+
// `--plan` names it outright; otherwise it comes off the gate's standing
|
|
780
|
+
// pending fact — the plan the run that stopped at this gate produced, which
|
|
781
|
+
// is the plan whoever is typing this just read. There is deliberately no
|
|
782
|
+
// third fallback: approving with no plan in sight is the behaviour
|
|
783
|
+
// INTENTIUS/choudoufu#1026 measured, where the resolution authorised the
|
|
784
|
+
// next run rather than anything anyone had seen.
|
|
785
|
+
let planDigest: string | undefined;
|
|
786
|
+
if (opts.plan !== undefined) {
|
|
787
|
+
if (!isPlanDigest(opts.plan)) {
|
|
788
|
+
console.error(formatError({
|
|
789
|
+
message: `--plan must be a plan digest ("sha256:" and 64 hex characters), got "${opts.plan}"`,
|
|
790
|
+
hint: "Copy it from the gated run's `plan :` line, or from the pending-gate summary. It is not a plan file path.",
|
|
791
|
+
}));
|
|
792
|
+
return { ok: false };
|
|
793
|
+
}
|
|
794
|
+
planDigest = opts.plan;
|
|
795
|
+
} else {
|
|
796
|
+
const standing = latestPendingGate((await readGateLedger(opName)).pending, gate);
|
|
797
|
+
if (!standing) {
|
|
798
|
+
console.error(formatError({
|
|
799
|
+
message: `Gate "${gate}" on "${opName}" has no pending fact, so there is no plan to approve`,
|
|
800
|
+
hint:
|
|
801
|
+
`Run \`chant run ${opName}\` first — it plans, stops at the gate, and records the plan this ` +
|
|
802
|
+
`approval would be for. To approve a plan you already have the digest for, pass ` +
|
|
803
|
+
`\`--plan <digest>\`.`,
|
|
804
|
+
}));
|
|
805
|
+
return { ok: false };
|
|
806
|
+
}
|
|
807
|
+
planDigest = standing.planDigest;
|
|
808
|
+
}
|
|
809
|
+
|
|
810
|
+
const resolvedBy = opts.actor ?? process.env.GITHUB_ACTOR ?? process.env.GITLAB_USER_LOGIN ?? process.env.USER ?? "unknown";
|
|
811
|
+
|
|
765
812
|
const { record } = await appendGateResolution({
|
|
766
813
|
op: opName,
|
|
767
814
|
gate,
|
|
@@ -769,6 +816,7 @@ export async function recordGateApproval(
|
|
|
769
816
|
timestamp: new Date().toISOString(),
|
|
770
817
|
...(opts.note ? { note: opts.note } : {}),
|
|
771
818
|
...(url ? { url } : {}),
|
|
819
|
+
...(planDigest !== undefined ? { planDigest } : {}),
|
|
772
820
|
});
|
|
773
821
|
const pushed = await reportedPush(
|
|
774
822
|
`The resolution is recorded locally on ${LIFECYCLE_BRANCH}. Until it reaches the remote, ` +
|
|
@@ -780,5 +828,11 @@ export async function recordGateApproval(
|
|
|
780
828
|
(record.url ? ` (${record.url})` : "") +
|
|
781
829
|
(pushed ? "" : " (local only — the push did not land)"),
|
|
782
830
|
));
|
|
831
|
+
if (record.planDigest) {
|
|
832
|
+
console.error(formatInfo(
|
|
833
|
+
`This approves the plan ${record.planDigest}, and only that plan. A run whose fresh plan ` +
|
|
834
|
+
"differs refuses rather than applying it.",
|
|
835
|
+
));
|
|
836
|
+
}
|
|
783
837
|
return { ok: true, record };
|
|
784
838
|
}
|