From 98f05fcd5b452704131a35ff09486f5c04c6959a Mon Sep 17 00:00:00 2001 From: Dotta Date: Fri, 30 Oct 2026 14:30:03 -0500 Subject: [PATCH] Validate idle goal tails through their stored wire bindings Co-Authored-By: Paperclip --- .../remote-warm-session-recovery.test.ts | 14 +++++++++----- .../native-runtime/remote-warm-session-recovery.ts | 8 ++++++-- 2 files changed, 15 insertions(+), 7 deletions(-) diff --git a/server/src/services/native-runtime/remote-warm-session-recovery.test.ts b/server/src/services/native-runtime/remote-warm-session-recovery.test.ts index fcdac76aabf..d1f8098f7aa 100644 --- a/server/src/services/native-runtime/remote-warm-session-recovery.test.ts +++ b/server/src/services/native-runtime/remote-warm-session-recovery.test.ts @@ -3,8 +3,10 @@ import { isSettledRemoteWarmControlState } from "./remote-warm-session-recovery. const identity = { runId: "run", normalizedSessionId: "session", runnerInstanceId: "runner", environmentLeaseId: "lease", turnId: "turn", itemId: "item" }; const terminal = { eventType: "run.terminal", envelope: { ...identity } }; -const snapshot = { eventType: "session.goal.snapshot", envelope: { ...identity, sourceInstanceId: "runner", sourceKind: "runner", - payload: { schema: "paperclip.session_goal.snapshot.v1", goal: null, workingNow: false } } }; +const goal = { schema: "paperclip.session_goal.snapshot.v1", goal: null, workingNow: false }; +const notification = { schema: "paperclip.prp.event.v1", eventType: "session.goal.snapshot", runId: identity.runId, + normalizedSessionId: identity.normalizedSessionId, sourceInstanceId: "runner", sourceKind: "runner", payload: goal }; +const snapshot = { eventType: "session.goal.snapshot", envelope: { ...identity, payload: notification } }; const state = (events: unknown[]) => ({ identity, commands: [{ status: "completed" }], committedEvents: events }); describe("settled remote warm control evidence", () => { @@ -16,13 +18,15 @@ describe("settled remote warm control evidence", () => { }); it.each([ - ["active goal", { ...snapshot, envelope: { ...snapshot.envelope, payload: { ...snapshot.envelope.payload, goal: { status: "active" } } } }], - ["provider work", { ...snapshot, envelope: { ...snapshot.envelope, payload: { ...snapshot.envelope.payload, workingNow: true } } }], + ["active goal", { ...snapshot, envelope: { ...snapshot.envelope, payload: { ...notification, payload: { ...goal, goal: { status: "active" } } } } }], + ["provider work", { ...snapshot, envelope: { ...snapshot.envelope, payload: { ...notification, payload: { ...goal, workingNow: true } } } }], ["unknown event", { ...snapshot, eventType: "unknown" }], ["new turn", { ...snapshot, eventType: "turn.started" }], ["foreign run", { ...snapshot, envelope: { ...snapshot.envelope, runId: "other" } }], ["foreign session", { ...snapshot, envelope: { ...snapshot.envelope, normalizedSessionId: "other" } }], - ["foreign source", { ...snapshot, envelope: { ...snapshot.envelope, sourceInstanceId: "other" } }], + ["foreign source", { ...snapshot, envelope: { ...snapshot.envelope, payload: { ...notification, sourceInstanceId: "other" } } }], + ["foreign lease", { ...snapshot, envelope: { ...snapshot.envelope, environmentLeaseId: "other" } }], + ["foreign notification", { ...snapshot, envelope: { ...snapshot.envelope, payload: { ...notification, runId: "other" } } }], ["missing payload", { ...snapshot, envelope: { ...identity } }], ])("holds a %s suffix", (_name, suffix) => { expect(isSettledRemoteWarmControlState(state([terminal, suffix]), identity)).toBe(false); diff --git a/server/src/services/native-runtime/remote-warm-session-recovery.ts b/server/src/services/native-runtime/remote-warm-session-recovery.ts index 704805ab561..b751e5224ff 100644 --- a/server/src/services/native-runtime/remote-warm-session-recovery.ts +++ b/server/src/services/native-runtime/remote-warm-session-recovery.ts @@ -32,9 +32,13 @@ export function isSettledRemoteWarmControlState(control: Record if (!matchesSession(events[terminalIndex])) return false; return events.slice(terminalIndex + 1).every(event => { const envelope = record(record(event).envelope); - const payload = record(envelope.payload); + const notification = record(envelope.payload); + const payload = record(notification.payload); return record(event).eventType === "session.goal.snapshot" && matchesSession(event) && - envelope.sourceInstanceId === identity.runnerInstanceId && envelope.sourceKind === "runner" && + Object.entries(identity).every(([key, value]) => envelope[key] === value) && + notification.schema === "paperclip.prp.event.v1" && notification.eventType === "session.goal.snapshot" && + notification.sourceInstanceId === identity.runnerInstanceId && notification.sourceKind === "runner" && + notification.runId === identity.runId && notification.normalizedSessionId === identity.normalizedSessionId && payload.schema === "paperclip.session_goal.snapshot.v1" && payload.goal === null && payload.workingNow === false; }); }