diff --git a/services/pascal-editor/apps/editor/lib/pascal-agent-mcp.ts b/services/pascal-editor/apps/editor/lib/pascal-agent-mcp.ts index d4fbb9931..e0a99e082 100644 --- a/services/pascal-editor/apps/editor/lib/pascal-agent-mcp.ts +++ b/services/pascal-editor/apps/editor/lib/pascal-agent-mcp.ts @@ -95,12 +95,6 @@ function readSceneName(result: unknown, fallback: string): string { : fallback } -function readSceneVersion(result: unknown): number | null { - const version = (result as { structuredContent?: { version?: unknown } })?.structuredContent - ?.version - return typeof version === 'number' && Number.isInteger(version) && version > 0 ? version : null -} - function assertToolSucceeded(result: unknown, operation: string): void { if ((result as { isError?: unknown })?.isError === true) { throw new Error(`Pascal MCP ${operation} failed.`) @@ -138,7 +132,6 @@ export async function createPascalAgentMcpSession(params: { ) assertToolSucceeded(loadResult, 'load_scene') const sceneName = readSceneName(loadResult, params.sceneId) - let currentVersion = readSceneVersion(loadResult) const saveScene = withStepTimeout(requireTool(allTools, 'save_scene'), params.stepTimeoutMs) const scopedSaveScene: RequiredTool = { @@ -148,7 +141,7 @@ export async function createPascalAgentMcpSession(params: { const result = await saveScene.execute( { ...candidate, - expectedVersion: currentVersion ?? undefined, + expectedVersion: undefined, graph: undefined, id: params.sceneId, includeCurrentScene: true, @@ -157,8 +150,6 @@ export async function createPascalAgentMcpSession(params: { }, options, ) - const savedVersion = readSceneVersion(result) - if (savedVersion) currentVersion = savedVersion return result }, } diff --git a/services/pascal-editor/packages/mcp/src/tools/scene-lifecycle/save-scene.test.ts b/services/pascal-editor/packages/mcp/src/tools/scene-lifecycle/save-scene.test.ts index fbcb5c92a..67593d970 100644 --- a/services/pascal-editor/packages/mcp/src/tools/scene-lifecycle/save-scene.test.ts +++ b/services/pascal-editor/packages/mcp/src/tools/scene-lifecycle/save-scene.test.ts @@ -167,4 +167,25 @@ describe('save_scene', () => { }) expect(result.isError).toBe(true) }) + + test('uses the active scene version when the caller omits expectedVersion', async () => { + const first = await client.callTool({ + name: 'save_scene', + arguments: { id: 'active-scene', name: 'First' }, + }) + expect(first.isError).toBeFalsy() + + const second = await client.callTool({ + name: 'save_scene', + arguments: { id: 'active-scene', name: 'Second', expectedVersion: 1 }, + }) + expect(second.isError).toBeFalsy() + + const final = await client.callTool({ + name: 'save_scene', + arguments: { id: 'active-scene', name: 'Final' }, + }) + expect(final.isError).toBeFalsy() + expect(parseToolText(final.content as StoredTextContent[]).version).toBe(3) + }) }) diff --git a/services/pascal-editor/packages/mcp/src/tools/scene-lifecycle/save-scene.ts b/services/pascal-editor/packages/mcp/src/tools/scene-lifecycle/save-scene.ts index ee7208776..a404f5105 100644 --- a/services/pascal-editor/packages/mcp/src/tools/scene-lifecycle/save-scene.ts +++ b/services/pascal-editor/packages/mcp/src/tools/scene-lifecycle/save-scene.ts @@ -118,6 +118,10 @@ export function registerSaveScene(server: McpServer, bridge: SceneOperations): v sceneGraph = graph as unknown as SceneGraph } + const activeScene = includeCurrentScene ? bridge.getActiveScene() : null + const resolvedExpectedVersion = + expectedVersion ?? (activeScene && activeScene.id === id ? activeScene.version : undefined) + try { const meta = await bridge.saveScene({ ...(id !== undefined ? { id } : {}), @@ -125,7 +129,9 @@ export function registerSaveScene(server: McpServer, bridge: SceneOperations): v ...(projectId !== undefined ? { projectId } : {}), graph: sceneGraph, ...(thumbnail !== undefined ? { thumbnailUrl: thumbnail } : {}), - ...(expectedVersion !== undefined ? { expectedVersion } : {}), + ...(resolvedExpectedVersion !== undefined + ? { expectedVersion: resolvedExpectedVersion } + : {}), saveMode, ...(publish !== undefined ? { publish } : {}), operation: 'save_scene', @@ -145,7 +151,7 @@ export function registerSaveScene(server: McpServer, bridge: SceneOperations): v } catch (err) { if (err instanceof SceneVersionConflictError) { throwMcpError(ErrorCode.InvalidRequest, 'version_conflict', { - expectedVersion, + expectedVersion: resolvedExpectedVersion, id, }) }