From aafc5eded40a334419e1aa211ddc50980a00c34b Mon Sep 17 00:00:00 2001 From: "opencode-agent[bot]" Date: Sat, 22 Aug 2026 03:11:44 +0000 Subject: [PATCH] fix(app): wait for session route id --- .../src/session/session-resolution.test.ts | 23 +++++++++++++++++++ .../app/src/session/session-resolution.ts | 12 +++++++--- 2 files changed, 32 insertions(+), 3 deletions(-) create mode 100644 packages/app/src/session/session-resolution.test.ts diff --git a/packages/app/src/session/session-resolution.test.ts b/packages/app/src/session/session-resolution.test.ts new file mode 100644 index 00000000000..672f8a8ca32 --- /dev/null +++ b/packages/app/src/session/session-resolution.test.ts @@ -0,0 +1,23 @@ +import { describe, expect, test } from "bun:test" +import { createRoot } from "solid-js" +import { createSessionResolution } from "./session-resolution" + +describe("session resolution", () => { + test("waits for a route session ID", () => { + createRoot((dispose) => { + let syncs = 0 + const sessions = { + get: () => undefined, + sync: () => { + syncs++ + return Promise.resolve() + }, + } + const session = createSessionResolution(() => undefined, () => sessions) + + expect(session()).toBeUndefined() + expect(syncs).toBe(0) + dispose() + }) + }) +}) diff --git a/packages/app/src/session/session-resolution.ts b/packages/app/src/session/session-resolution.ts index b8d76264483..977f9c97320 100644 --- a/packages/app/src/session/session-resolution.ts +++ b/packages/app/src/session/session-resolution.ts @@ -29,15 +29,20 @@ type Resolution = { id: string; store: SessionStore } & ( // session that simply has not resolved yet. Resolve failures rethrow on read so // the enclosing SessionRouteErrorBoundary renders the scoped session error. export function createSessionResolution( - sessionID: () => string, + sessionID: () => string | undefined, sessions: () => SessionStore, options?: { children?: boolean }, ) { - const cached = createMemo(() => sessions().get(sessionID())) + const cached = createMemo(() => { + const id = sessionID() + if (!id) return + return sessions().get(id) + }) const [status, setStatus] = createSignal>() createEffect( on([sessionID, sessions] as const, ([id, store]) => { + if (!id) return let stale = false onCleanup(() => { stale = true @@ -60,10 +65,11 @@ export function createSessionResolution( return createMemo(() => { const id = sessionID() + if (!id) return const value = cached() if (value) return value const state = status() - if (state?.id !== id || state.store !== sessions()) return undefined + if (!state || state.id !== id || state.store !== sessions()) return undefined if (state.state === "failed") throw state.failure // A session missing after settlement was deleted, possibly by another client. // Match the resolve error so the boundary shows the