fix: persist agent scene mutations reliably
This commit is contained in:
parent
67ff51d194
commit
54b0020af7
@ -95,6 +95,18 @@ 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.`)
|
||||
}
|
||||
}
|
||||
|
||||
export async function createPascalAgentMcpSession(params: {
|
||||
abortSignal?: AbortSignal
|
||||
env?: NodeJS.ProcessEnv
|
||||
@ -124,16 +136,19 @@ export async function createPascalAgentMcpSession(params: {
|
||||
{ id: params.sceneId },
|
||||
toolExecutionOptions(params.abortSignal),
|
||||
)
|
||||
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 = {
|
||||
...saveScene,
|
||||
execute: async (input, options) => {
|
||||
const candidate = input && typeof input === 'object' ? input : {}
|
||||
return saveScene.execute(
|
||||
const result = await saveScene.execute(
|
||||
{
|
||||
...candidate,
|
||||
expectedVersion: currentVersion ?? undefined,
|
||||
graph: undefined,
|
||||
id: params.sceneId,
|
||||
includeCurrentScene: true,
|
||||
@ -142,6 +157,9 @@ export async function createPascalAgentMcpSession(params: {
|
||||
},
|
||||
options,
|
||||
)
|
||||
const savedVersion = readSceneVersion(result)
|
||||
if (savedVersion) currentVersion = savedVersion
|
||||
return result
|
||||
},
|
||||
}
|
||||
|
||||
@ -168,7 +186,7 @@ export async function createPascalAgentMcpSession(params: {
|
||||
sceneName,
|
||||
tools,
|
||||
saveDraft: async (abortSignal) => {
|
||||
await scopedSaveScene.execute(
|
||||
const result = await scopedSaveScene.execute(
|
||||
{
|
||||
id: params.sceneId,
|
||||
includeCurrentScene: true,
|
||||
@ -177,6 +195,7 @@ export async function createPascalAgentMcpSession(params: {
|
||||
},
|
||||
toolExecutionOptions(abortSignal),
|
||||
)
|
||||
assertToolSucceeded(result, 'save_scene')
|
||||
},
|
||||
}
|
||||
} catch (error) {
|
||||
|
||||
@ -272,19 +272,23 @@ class SceneOperationsFacade implements SceneOperations {
|
||||
}
|
||||
|
||||
async saveScene(options: SceneSaveOptions): Promise<SceneMeta> {
|
||||
return this.requireStore().save(options)
|
||||
const store = this.requireStore()
|
||||
return store.save(options)
|
||||
}
|
||||
|
||||
async loadStoredScene(id: string): Promise<SceneWithGraph | null> {
|
||||
return this.requireStore().load(id)
|
||||
const store = this.requireStore()
|
||||
return store.load(id)
|
||||
}
|
||||
|
||||
async listScenes(options?: SceneListOptions): Promise<SceneMeta[]> {
|
||||
return this.requireStore().list(options)
|
||||
const store = this.requireStore()
|
||||
return store.list(options)
|
||||
}
|
||||
|
||||
async deleteStoredScene(id: string, options?: SceneMutateOptions): Promise<boolean> {
|
||||
return this.requireStore().delete(id, options)
|
||||
const store = this.requireStore()
|
||||
return store.delete(id, options)
|
||||
}
|
||||
|
||||
async renameStoredScene(
|
||||
@ -292,21 +296,22 @@ class SceneOperationsFacade implements SceneOperations {
|
||||
newName: string,
|
||||
options?: SceneMutateOptions,
|
||||
): Promise<SceneMeta> {
|
||||
return this.requireStore().rename(id, newName, options)
|
||||
const store = this.requireStore()
|
||||
return store.rename(id, newName, options)
|
||||
}
|
||||
|
||||
async appendSceneEvent(options: SceneEventAppendOptions): Promise<SceneEvent | null> {
|
||||
const append = this.requireStore().appendSceneEvent
|
||||
if (!append) return null
|
||||
return append(options)
|
||||
const store = this.requireStore()
|
||||
if (!store.appendSceneEvent) return null
|
||||
return store.appendSceneEvent(options)
|
||||
}
|
||||
|
||||
async listSceneEvents(id: string, options?: SceneEventListOptions): Promise<SceneEvent[]> {
|
||||
const list = this.requireStore().listSceneEvents
|
||||
if (!list) {
|
||||
const store = this.requireStore()
|
||||
if (!store.listSceneEvents) {
|
||||
throw new Error('scene_events_unavailable')
|
||||
}
|
||||
return list(id, options)
|
||||
return store.listSceneEvents(id, options)
|
||||
}
|
||||
|
||||
private requireBridge(): SceneBridge {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user