chat: send cwd on every message instead of reading it back from session metadata
Simpler + more efficient than the previous per-turn GET /session: the client already has the selected cwd, so it now sends it on every message (it's constant for a session). The server uses msg.cwd directly for OpenCode's per-turn working-directory system prompt, and still tags the cwd at creation for listing. Drops the getSession round-trip. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -146,12 +146,6 @@ class ServerConnection {
|
||||
return (await res.json()) as OpenCodeSessionInfo[];
|
||||
}
|
||||
|
||||
async getSession(sessionId: string): Promise<OpenCodeSessionInfo | null> {
|
||||
const res = await fetch(`${this.baseUrl}/session/${sessionId}`);
|
||||
if (!res.ok) return null;
|
||||
return (await res.json()) as OpenCodeSessionInfo;
|
||||
}
|
||||
|
||||
async getMessages(sessionId: string): Promise<OpenCodeStoredMessage[]> {
|
||||
const res = await fetch(`${this.baseUrl}/session/${sessionId}/message`);
|
||||
if (!res.ok) throw new Error(`opencode GET /session/${sessionId}/message → ${res.status}`);
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import type { ChatEvent } from '@@/api/chat/types';
|
||||
import { logger } from '@@/api/chat/logger';
|
||||
import { ensureServer } from '@@/api/chat/opencode/server-manager';
|
||||
import { getConnection, officerMeta } from '@@/api/chat/opencode/client';
|
||||
import { getConnection } from '@@/api/chat/opencode/client';
|
||||
import { createEventMapper } from '@@/api/chat/opencode/event-mapper';
|
||||
import { getOpenCodeSession, setOpenCodeSession } from '@@/api/chat/opencode/state';
|
||||
|
||||
@@ -51,25 +51,17 @@ export async function sendOpenCodeStreaming(params: OpenCodeStreamingParams): Pr
|
||||
const conn = getConnection(baseUrl);
|
||||
|
||||
// Resolve the OpenCode session: a known mapping, or — when resuming from history — the sessionKey is
|
||||
// itself the OpenCode session id (`ses_…`); otherwise create a new one.
|
||||
const existingId =
|
||||
// itself the OpenCode session id (`ses_…`); otherwise create a new one, tagged with its cwd (for
|
||||
// listing). The cwd rides every message from the client, so the system prompt below stays consistent.
|
||||
let opencodeSessionId =
|
||||
getOpenCodeSession(params.sessionKey) ??
|
||||
(params.sessionKey.startsWith('ses_') ? params.sessionKey : undefined) ??
|
||||
params.resumeSessionId;
|
||||
|
||||
// The session's working directory is bound at creation (metadata.officer.cwd). msg.cwd only rides
|
||||
// the first message, so for an existing/resumed session read the bound cwd back and reuse it — this
|
||||
// keeps the system prompt (and session tagging) consistent across every turn.
|
||||
let sessionId: string;
|
||||
let cwd = params.cwd;
|
||||
if (existingId) {
|
||||
sessionId = existingId;
|
||||
const bound = officerMeta((await conn.getSession(existingId))?.metadata).cwd;
|
||||
if (bound) cwd = bound;
|
||||
} else {
|
||||
sessionId = await conn.createSession(cwd ? { officer: { cwd } } : undefined);
|
||||
if (!opencodeSessionId) {
|
||||
opencodeSessionId = await conn.createSession(params.cwd ? { officer: { cwd: params.cwd } } : undefined);
|
||||
}
|
||||
setOpenCodeSession(params.sessionKey, sessionId);
|
||||
setOpenCodeSession(params.sessionKey, opencodeSessionId);
|
||||
const sessionId = opencodeSessionId;
|
||||
|
||||
let unsub = () => {};
|
||||
const mapper = createEventMapper((event: ChatEvent) => {
|
||||
@@ -79,7 +71,7 @@ export async function sendOpenCodeStreaming(params: OpenCodeStreamingParams): Pr
|
||||
unsub = conn.subscribe(sessionId, mapper);
|
||||
|
||||
const { providerID, modelID } = splitModel(params.model ?? '');
|
||||
const system = cwd ? officerSystemPrompt(cwd) : undefined;
|
||||
const system = params.cwd ? officerSystemPrompt(params.cwd) : undefined;
|
||||
|
||||
// Fire the turn; assistant tokens + tool calls stream back over the SSE subscription above.
|
||||
conn.postMessage(sessionId, providerID, modelID, params.prompt, system).catch((err) => {
|
||||
|
||||
Reference in New Issue
Block a user