From a64a622b6d3549744fc8de43f661c58e923b6065 Mon Sep 17 00:00:00 2001 From: Sameh Khamis Date: Sat, 12 Sep 2026 13:00:43 -0700 Subject: [PATCH] test: pin voice schemas independently of source formatting --- src/firstRunExperience.test.mjs | 25 +++++++++---------------- src/keySetupCore.test.mjs | 2 +- src/voice/gevActions.test.mjs | 7 ++----- 3 files changed, 12 insertions(+), 22 deletions(-) diff --git a/src/firstRunExperience.test.mjs b/src/firstRunExperience.test.mjs index 5a5a83a79..f5ed953e3 100644 --- a/src/firstRunExperience.test.mjs +++ b/src/firstRunExperience.test.mjs @@ -1,3 +1,4 @@ +import { GEV_REALTIME_TOOLS } from '../server/providers/openai/tools.js'; import test from 'node:test'; import assert from 'node:assert/strict'; import fs from 'node:fs'; @@ -645,27 +646,19 @@ test('the DISPLAY rail starts collapsed on a first run, and a stored choice wins ); }); -// ── Voice: instruction-only, tool schema byte-unchanged ───────────────────── +// ── Voice: instruction-only, tool schema unchanged ───────────────────── -test('the voice TOOL SCHEMA is byte-identical to main — the mission mapping is instructions only', () => { - const src = fs.readFileSync(new URL('../server/providers/openai/tools.js', import.meta.url), 'utf8'); - const start = src.indexOf('const GEV_REALTIME_TOOLS = ['); - assert.ok(start > 0, 'GEV_REALTIME_TOOLS must still be a single literal array'); - const end = src.indexOf('\n];\n', start); - const block = src.slice(start, end + 4); - - // Re-pinned 2026-08-28: the Provider Settings / Esri release DELIBERATELY - // extends set_map_stack's enum with 'esri-imagery' (a real new basemap — - // exactly the kind of schema change this pin exists to make loud). The - // guarded claim is unchanged: first-run missions ride existing tools, and - // any NEW drift from this recorded schema still fails here. - assert.equal(block.length, 31189, 'tool schema byte length drifted from the pinned release schema'); +test('the voice TOOL SCHEMA matches the pinned release — the mission mapping is instructions only', () => { + // Canonical serialization pins every tool name, description, property and + // ordering while allowing source formatting. Derived from the unchanged + // release schema before formatting (the previous source-byte pin passed). + const block = JSON.stringify(GEV_REALTIME_TOOLS); + assert.equal(block.length, 26121, 'serialized tool schema length drifted'); assert.equal( crypto.createHash('sha256').update(block).digest('hex'), - '73aaabdb169a5478893d28688f327a21edd32ed3ec16fc6287bd944ed77beecf', + '11680affb4a7aebf142642c8185b28f2ee7d523407054c5b0c3962d933b045eb', 'the first-run missions must ride EXISTING tools: no schema edit, no cache bust', ); - const instructions = fs.readFileSync(new URL('../server/providers/openai/instructions.js', import.meta.url), 'utf8'); // ...and the mapping that makes them reachable by voice is one instruction diff --git a/src/keySetupCore.test.mjs b/src/keySetupCore.test.mjs index 9636aee4f..05f406009 100644 --- a/src/keySetupCore.test.mjs +++ b/src/keySetupCore.test.mjs @@ -31,7 +31,7 @@ test('the boot provenance snapshot survives in-process Vite config re-evaluation const source = readFileSync(new URL('../server/standalone/key-setup.js', import.meta.url), 'utf8'); assert.match( source, - /const PROVIDER_ENV_AT_BOOT = globalThis\.__GEV_PROVIDER_ENV_AT_BOOT \?\?= Object\.freeze\(/, + /const PROVIDER_ENV_AT_BOOT\s*=\s*\(?globalThis\.__GEV_PROVIDER_ENV_AT_BOOT\s*\?\?=\s*Object\.freeze\(/, ); }); diff --git a/src/voice/gevActions.test.mjs b/src/voice/gevActions.test.mjs index 6233609a9..5fbd7cff3 100644 --- a/src/voice/gevActions.test.mjs +++ b/src/voice/gevActions.test.mjs @@ -17,7 +17,7 @@ import { normalizeStackId, } from './gevActions.js'; import { MAP_STACKS } from '../mapStackController.js'; -import { readFileSync } from 'node:fs'; +import { GEV_REALTIME_TOOLS } from '../../server/providers/openai/tools.js'; test('every live basemap is reachable by its own id — no enum value without a voice alias', () => { // B1 regression: a stack added to MAP_STACKS (and the set_map_stack enum) @@ -35,10 +35,7 @@ test('every live basemap is reachable by its own id — no enum value without a assert.equal(normalizeStackId('Esri'), 'esri-imagery'); assert.equal(normalizeStackId('esri imagery'), 'esri-imagery'); // And the voice tool's enum must equal the set of live ids — no drift either way. - const config = readFileSync(new URL('../../server/providers/openai/tools.js', import.meta.url), 'utf8'); - const enumMatch = config.match(/enum: \[('photoreal'[^\]]*)\],\s*\n\s*description: 'photoreal = Google 3D/); - assert.ok(enumMatch, 'set_map_stack enum literal must still be findable'); - const enumIds = enumMatch[1].split(',').map((s) => s.trim().replace(/^'|'$/g, '')); + const enumIds = GEV_REALTIME_TOOLS.find(tool => tool.name === 'set_map_stack').parameters.properties.stack.enum; assert.deepEqual( [...enumIds].sort(), MAP_STACKS.map((s) => s.id).sort(),