tools: the standard argument heal — every registry, both seams
The whitehead incident (2026-10-09): glm-5.3 emitted quiz type with
quotes baked in ('"predict"') — rejected ten times, byte-identical
retries, the lesson never started — and correctAnswer with the JSON
key-value colon glued on ([':parmenides']). Third GLM wobble incident,
and each prior heal was wired only where its incident landed; this one
landed precisely where the practice heal never reached.
Layer 1 — healEncodedArguments moves to core/argument-heal (the display
seam needs it too — the tool-parts law) with withArgumentHeal +
healToolRecord (agent/tools/heal) wired at EVERY registry: prober,
teacher, practice, bareQuestionTools (it had no prepareArguments at
all), demo-builder, and submit-agent (composing after
healStringifiedArrays; the auditor's extraTools wrapped).
Layer 2 — stripModelValueDebris (core/value-debris): leading/trailing
colons, quotes, backticks, whitespace strip at the MEMBERSHIP seams —
coerceCorrectAnswer (boundary check + display + grading in one),
normalizeQuizType (persisted wobbled records keep their role),
resolveTargetId (copy-syntax on targets).
Layer 3 — schema description hygiene: the quiz type and practice
mode/outcome/rung/missClass values now read as bare words — the quoted
JSON-key style invited quote-copying.
Display mirror — parseQuizInput heals the raw record on read, so a
boundary-healed quiz whose record keeps raw args renders instead of
becoming an invisible pending quiz (learner lockout).
Pins: tests/tool-heal.test.ts (the incident shapes end-to-end through
pi-ai validation, the wiring, the strips, the mirror). The stringy-
options pins flip to boundary-parity per tool-parts' own law; the
chat-flow garbage pin keeps its honest-reject intent with an unhealable
shape. 1471 tests, typecheck, lint green.
This commit is contained in:
+14
-7
@@ -23,6 +23,7 @@ import { readTool } from "./tools/read.ts";
|
||||
import { lsTool } from "./tools/ls.ts";
|
||||
import { findTool } from "./tools/find.ts";
|
||||
import { grepTool } from "./tools/grep.ts";
|
||||
import { healToolRecord } from "./tools/heal.ts";
|
||||
import type { GraphStore } from "../core/ports.ts";
|
||||
|
||||
export { jobTools };
|
||||
@@ -246,7 +247,10 @@ export function createProberTools(
|
||||
// unusable as Record<string, AgentTool<any>> downstream).
|
||||
const quizzing: Record<string, AgentTool<any>> =
|
||||
mechanics === "free" ? { explain: probeExplainTool } : { quiz: probeQuizTool };
|
||||
return {
|
||||
// healToolRecord (owner, 2026-10-09 — the whitehead generalization):
|
||||
// the standard argument heal over the WHOLE registry — every tool,
|
||||
// not just the one the latest wobble incident landed on.
|
||||
return healToolRecord({
|
||||
...filterEnabledTools(
|
||||
{
|
||||
...quizzing,
|
||||
@@ -274,10 +278,10 @@ export function createProberTools(
|
||||
: {}),
|
||||
...done,
|
||||
},
|
||||
withoutMechanics(enabled),
|
||||
),
|
||||
...done,
|
||||
};
|
||||
withoutMechanics(enabled),
|
||||
),
|
||||
...done,
|
||||
});
|
||||
}
|
||||
|
||||
// ─── the teacher's question tools (quiz carries the position field) ──────────
|
||||
@@ -378,8 +382,10 @@ export function createTeacherTools(
|
||||
// two differently-typed literals collapses into an unusable union type.
|
||||
const quizzing: Record<string, AgentTool<any>> =
|
||||
mechanics === "free" ? { explain: teachExplainToolFor(ctx) } : { quiz: teachQuizToolFor(ctx) };
|
||||
return filterEnabledTools(
|
||||
{
|
||||
// healToolRecord — same standard as the prober's registry (above).
|
||||
return healToolRecord(
|
||||
filterEnabledTools(
|
||||
{
|
||||
...quizzing,
|
||||
ask_user_question: askUserQuestionTool,
|
||||
// The learner-filesystem set is always-on (user-decided 2026-09,
|
||||
@@ -398,5 +404,6 @@ export function createTeacherTools(
|
||||
...jobTools({ chatId: ctx.chatId, jobStore: ctx.jobStore, spawn: ctx.spawn, searchAvailable: ctx.searchAvailable }),
|
||||
},
|
||||
withoutMechanics(enabled),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user