@tokenoftrust/cli 3.10.1 → 3.10.2

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@tokenoftrust/cli",
3
- "version": "3.10.1",
3
+ "version": "3.10.2",
4
4
  "description": "Token of Trust developer CLI — clone a tenant store, run it locally with save→reload, and submit it for preview. Installs the `tot` command.",
5
5
  "license": "Apache-2.0",
6
6
  "author": "Token of Trust",
@@ -39,7 +39,7 @@ import { openBrowser } from "../open.mjs";
39
39
  import { missingGrantsOf, refusalHint } from "../admission-hint.mjs";
40
40
  // Reuse `tot ship`'s operator-secret precedence + live-url derivation verbatim so
41
41
  // ship + hotfix speak ONE operator-auth contract.
42
- import { resolveOperatorSecret, liveUrlFor } from "./ship.mjs";
42
+ import { resolveOperatorSecret, liveUrlFor, normalizeLiveDrift } from "./ship.mjs";
43
43
 
44
44
  const DEFAULT_STOREFRONT_URL = "https://storefront.tokenoftrust.store";
45
45
 
@@ -126,6 +126,7 @@ export function normalizeHotfixPlan(data) {
126
126
  bypassedPreviewSha: typeof o.bypassedPreviewSha === "string" ? o.bypassedPreviewSha : null,
127
127
  bypassedPrs: Array.isArray(o.bypassedPrs) ? o.bypassedPrs : [],
128
128
  rollbackTarget: o.rollbackTarget && typeof o.rollbackTarget === "object" ? o.rollbackTarget : null,
129
+ warning: normalizeLiveDrift(o.warning),
129
130
  paywall:
130
131
  o.paywall && typeof o.paywall === "object"
131
132
  ? { allowed: o.paywall.allowed === true, message: typeof o.paywall.message === "string" ? o.paywall.message : null }
@@ -285,6 +286,7 @@ export async function runHotfix(
285
286
  bypassedPrs: plan.bypassedPrs,
286
287
  bypassedPreviewSha: plan.bypassedPreviewSha,
287
288
  rollbackTarget: plan.rollbackTarget,
289
+ liveDrift: plan.warning,
288
290
  paywall: plan.paywall,
289
291
  targets: { live: liveUrl },
290
292
  });
@@ -245,8 +245,8 @@ export function liveUrlFor(tenant) {
245
245
  * paywall:{allowed:boolean,message:string|null}, alreadyShipped:boolean} |
246
246
  * {ok:false, reason:string, message:string}}
247
247
  */
248
- /** The ship-plan CDN drift warning, or null when the ledger and the CDN name the same release. */
249
- function normalizeLiveDrift(warning) {
248
+ /** The plan CDN drift warning, or null when the ledger and the CDN name the same release. */
249
+ export function normalizeLiveDrift(warning) {
250
250
  if (!warning || typeof warning !== "object" || typeof warning.reason !== "string") return null;
251
251
  const target = warning.correctedRollbackTarget;
252
252
  if (!target || typeof target !== "object" || typeof target.aggregateSha !== "string") return null;
package/src/plan.mjs CHANGED
@@ -40,6 +40,20 @@ function targetLabel({ pr, changeId }) {
40
40
  return "this change";
41
41
  }
42
42
 
43
+ /** Empty when the CDN and the ledger name the same release. */
44
+ function cdnDriftLines(liveDrift) {
45
+ if (!liveDrift?.reason) return [];
46
+ return [
47
+ ` ⚠ ${liveDrift.reason}: the CDN serves ${liveDrift.served ?? "an unknown revision"}, not the ledger's live ${liveDrift.live ?? "nothing"}.`,
48
+ ];
49
+ }
50
+
51
+ function rollbackToLine(rollbackTarget, liveDrift) {
52
+ return rollbackTarget
53
+ ? ` rollback to: ${rollbackTarget.aggregateSha} (receipt ${rollbackTarget.receiptId})${liveDrift?.reason ? " — corrected target" : ""}`
54
+ : " rollback to: (none — first-ever ship)";
55
+ }
56
+
43
57
  /**
44
58
  * Build the EXACT plan for a mutating operator verb — structured lines ready
45
59
  * to print verbatim (CLI) or join for a confirm() dialog (admin). Pure: no
@@ -137,16 +151,8 @@ export function planForAction({
137
151
  lines.push(` - ${prLabel}${shortSha}`);
138
152
  }
139
153
  }
140
- if (liveDrift?.reason) {
141
- lines.push(
142
- ` ⚠ ${liveDrift.reason}: the CDN serves ${liveDrift.served ?? "an unknown revision"}, not the ledger's live ${liveDrift.live ?? "nothing"}.`,
143
- );
144
- }
145
- lines.push(
146
- rollbackTarget
147
- ? ` rollback to: ${rollbackTarget.aggregateSha} (receipt ${rollbackTarget.receiptId})${liveDrift?.reason ? " — corrected target" : ""}`
148
- : " rollback to: (none — first-ever ship)",
149
- );
154
+ lines.push(...cdnDriftLines(liveDrift));
155
+ lines.push(rollbackToLine(rollbackTarget, liveDrift));
150
156
  if (paywall && paywall.allowed === false) {
151
157
  lines.push(` ⚠ paywall: ${paywall.message || "go-live is blocked by the storefront subscription gate"}`);
152
158
  }
@@ -206,11 +212,8 @@ export function planForAction({
206
212
  }
207
213
  }
208
214
  if (bypassedPreviewSha) lines.push(` preview head (bypassed): ${bypassedPreviewSha}`);
209
- lines.push(
210
- rollbackTarget
211
- ? ` rollback to: ${rollbackTarget.aggregateSha} (receipt ${rollbackTarget.receiptId})`
212
- : " rollback to: (none — first-ever ship)",
213
- );
215
+ lines.push(...cdnDriftLines(liveDrift));
216
+ lines.push(rollbackToLine(rollbackTarget, liveDrift));
214
217
  if (paywall && paywall.allowed === false) {
215
218
  lines.push(` ⚠ paywall: ${paywall.message || "go-live is blocked by the storefront subscription gate"}`);
216
219
  }