{"record":{"id":"c3eba555c4cf280d","repo":"siyuan-note/siyuan","slug":"agent-runtime-session-id-mismatch","errorCode":null,"errorMessage":"agent runtime session id mismatch","messagePattern":"agent runtime session id mismatch","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"kernel/agent/runtime.go","lineNumber":207,"sourceCode":"}\n\nfunc loadRuntimeLocked(sessionID string) (*agentRuntime, error) {\n\tdata, err := os.ReadFile(runtimePath(sessionID))\n\tif err != nil {\n\t\tif os.IsNotExist(err) {\n\t\t\treturn &agentRuntime{SchemaVersion: 1, SessionID: sessionID}, nil\n\t\t}\n\t\treturn nil, err\n\t}\n\tvar runtime agentRuntime\n\tif err := gulu.JSON.UnmarshalJSON(data, &runtime); err != nil {\n\t\treturn nil, err\n\t}\n\tif runtime.SchemaVersion > 1 {\n\t\treturn nil, fmt.Errorf(\"unsupported agent runtime schema version: %d\", runtime.SchemaVersion)\n\t}\n\tif runtime.SessionID != \"\" && runtime.SessionID != sessionID {\n\t\treturn nil, fmt.Errorf(\"agent runtime session id mismatch\")\n\t}\n\tif runtime.Revision < 0 {\n\t\treturn nil, fmt.Errorf(\"invalid agent runtime revision\")\n\t}\n\tif runtime.ActiveTurn != nil {\n\t\tif runtime.ActiveTurn.TurnID == \"\" {\n\t\t\treturn nil, fmt.Errorf(\"invalid agent runtime turn id\")\n\t\t}\n\t\tswitch runtime.ActiveTurn.State {\n\t\tcase \"running\", \"finished\", \"interrupted\":\n\t\tdefault:\n\t\t\treturn nil, fmt.Errorf(\"invalid agent runtime turn state\")\n\t\t}\n\t}\n\tif runtime.SchemaVersion == 0 {\n\t\truntime.SchemaVersion = 1\n\t}\n\tif runtime.SessionID == \"\" {","sourceCodeStart":189,"sourceCodeEnd":225,"githubUrl":"https://github.com/siyuan-note/siyuan/blob/9f775e8a12daef8255556097396f9b2739078892/kernel/agent/runtime.go#L189-L225","documentation":"loadRuntimeLocked checks that the runtime file's embedded SessionID matches the sessionID being loaded. A non-empty mismatch means the runtime file belongs to a different session — the directory contents and file contents have diverged. This is treated as a corruption/invariant violation rather than silently remapping the data.","triggerScenarios":"Calling any loadRuntimeLocked-backed API for session X while the runtime JSON inside sessions/<X>/ was written for session Y; copying or renaming session directories by hand; a restore that mixed files across session folders.","commonSituations":"Manual file moves/copies between session directories; a botched backup restore; a script that rewrites session IDs without updating the embedded runtime SessionID field.","solutions":["Ensure you are addressing the correct session ID; the runtime file's SessionID field tells you which session the file actually belongs to","If the file was misplaced, move it back to sessions/<embeddedSessionID>/ rather than editing it","If the runtime is genuinely corrupt, remove that session's runtime state so it can be regenerated, preserving other session data"],"exampleFix":null,"handlingStrategy":"validation","validationCode":"const runtime = JSON.parse(readRuntimeFile(sessionDir));\nif (runtime.sessionID && runtime.sessionID !== sessionID) throw new Error(`runtime file belongs to ${runtime.sessionID}, not ${sessionID}`);","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never copy or rename session directories by hand","Restore backups as whole session folders, not mixed files","Treat the runtime file's embedded sessionID as authoritative when locating files"],"tags":["agent","corruption","session-id"],"backgroundTag":"internal-invariant-violation","analyzedSha":"9f775e8a12daef8255556097396f9b2739078892","analyzedAt":"2026-09-19T03:17:15.984Z","contentChangedAt":"2026-09-19T03:17:15.984Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}