[object Object]

← back to Tk 10965 Zero Price Analysis

isolate fixture runs from canary heartbeat

7709f2cdab2623e8ce5df42d23801dd890de6478 · 2026-08-30 23:15:38 -0700 · Steve Abrams

Files touched

Diff

commit 7709f2cdab2623e8ce5df42d23801dd890de6478
Author: Steve Abrams <steve@designerwallcoverings.com>
Date:   Sun Aug 30 23:15:38 2026 -0700

    isolate fixture runs from canary heartbeat
---
 tk10964-canary-guard/check.mjs | 12 +++++++++---
 tk10964-canary-guard/test.mjs  | 16 +++++++++++++++-
 2 files changed, 24 insertions(+), 4 deletions(-)

diff --git a/tk10964-canary-guard/check.mjs b/tk10964-canary-guard/check.mjs
index beff799..468f041 100644
--- a/tk10964-canary-guard/check.mjs
+++ b/tk10964-canary-guard/check.mjs
@@ -6,7 +6,11 @@ import fs from 'node:fs';
 import path from 'node:path';
 
 const HERE = path.dirname(new URL(import.meta.url).pathname);
-const OUT = process.env.ZERO_PRICE_CANARY_OUT || path.join(HERE, 'data', 'latest.json');
+const FIXTURE_MODE = process.argv.includes('--fixture');
+// Fixture invocations are probes/tests, not scheduler heartbeats. They must not
+// overwrite the production artifact unless the caller deliberately supplies an
+// isolated output path.
+const OUT = process.env.ZERO_PRICE_CANARY_OUT || (FIXTURE_MODE ? null : path.join(HERE, 'data', 'latest.json'));
 export const SEARCHES = [
   `status:active AND (tag:'quote-only' OR tag:'Quote Only' OR tag:'quote_only' OR tag:'Quote-Only')`,
   `status:active AND (tag:'quotes' OR tag:'contact-for-price' OR tag:'Needs-Price')`,
@@ -51,8 +55,10 @@ export function summarize(products, ts = new Date().toISOString()) {
 }
 
 function writeResult(result) {
-  fs.mkdirSync(path.dirname(OUT), { recursive: true });
-  fs.writeFileSync(OUT, JSON.stringify(result, null, 2) + '\n');
+  if (OUT) {
+    fs.mkdirSync(path.dirname(OUT), { recursive: true });
+    fs.writeFileSync(OUT, JSON.stringify(result, null, 2) + '\n');
+  }
   console.log(`${result.verdict}: ${result.zero_price_orderable} zero-price-orderable of ${result.searched_active_unique} uniquely searched active`);
 }
 
diff --git a/tk10964-canary-guard/test.mjs b/tk10964-canary-guard/test.mjs
index 44e403f..26cf612 100644
--- a/tk10964-canary-guard/test.mjs
+++ b/tk10964-canary-guard/test.mjs
@@ -1,6 +1,8 @@
 #!/usr/bin/env node
 import assert from 'node:assert/strict';
 import fs from 'node:fs';
+import { spawnSync } from 'node:child_process';
+import { fileURLToPath } from 'node:url';
 import { SEARCHES, exitCodeFor, hydrateVariantPages, inScope, summarize } from './check.mjs';
 
 const products = JSON.parse(fs.readFileSync(new URL('./fixtures/mixed.json', import.meta.url)));
@@ -32,4 +34,16 @@ await hydrateVariantPages([variant21Product], async (_query, variables) => {
 const variant21Result = summarize([variant21Product]);
 assert.equal(pageCalls, 1, 'only products with another variant page should incur a follow-up read');
 assert.equal(variant21Result.zero_price_orderable, 1, 'bad variant #21 must not be a false negative');
-console.log('PASS: broad searches, Fentucci blind spot, dedupe, variant pagination, defect predicate, and controls');
+
+const productionArtifact = fileURLToPath(new URL('./data/latest.json', import.meta.url));
+const productionBefore = fs.readFileSync(productionArtifact, 'utf8');
+const fixtureRun = spawnSync(process.execPath, [
+  fileURLToPath(new URL('./check.mjs', import.meta.url)),
+  '--fixture',
+  fileURLToPath(new URL('./fixtures/mixed.json', import.meta.url))
+], { encoding: 'utf8' });
+assert.equal(fixtureRun.status, 2, fixtureRun.stderr);
+assert.equal(fs.readFileSync(productionArtifact, 'utf8'), productionBefore, 'fixture CLI must not overwrite production heartbeat');
+assert.match(fixtureRun.stdout, /^WARN: 2 zero-price-orderable/m);
+
+console.log('PASS: broad searches, Fentucci blind spot, dedupe, pagination, controls, and fixture heartbeat isolation');

← ee159c0 fix(A): execute on_hand=0 remediation on 1743 live variants  ·  back to Tk 10965 Zero Price Analysis  ·  chore: lint, refactor, v1.1.1 (session close) 55f8804 →