{"record":{"id":"e6684771f2a0eb16","repo":"can1357/oh-my-pi","slug":"cannot-resume-session-resolvedsessionfile-th","errorCode":null,"errorMessage":"Cannot resume session \"${resolvedSessionFile}\": the session header is missing or malformed. The file was not modified.","messagePattern":"Cannot resume session \"(.+?)\": the session header is missing or malformed\\. The file was not modified\\.","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/coding-agent/src/session/session-manager.ts","lineNumber":1403,"sourceCode":"\t\t\tthis.#forceFileCreation = true;\n\t\t\tthis.#rewriteRequired = true;\n\t\t\tawait this.#rewriteAtomically();\n\t\t}\n\t}\n\t/** Switch to a different session file (resume / branch). */\n\tasync setSessionFile(sessionFile: string): Promise<void> {\n\t\tawait this.#setSessionFile(sessionFile);\n\t}\n\n\tasync #setSessionFile(sessionFile: string, loadedSession?: SessionLoadResult): Promise<void> {\n\t\tawait this.#drainAndCloseWriter();\n\t\tthis.#clearDiskError();\n\t\tthis.#draftOnlySessionCleanupArmed = false;\n\n\t\tconst resolvedSessionFile = path.resolve(sessionFile);\n\t\tconst loaded = loadedSession ?? (await loadSessionFile(resolvedSessionFile, this.#storage));\n\t\tif (loaded.invalidHeader) {\n\t\t\tthrow new Error(\n\t\t\t\t`Cannot resume session \"${resolvedSessionFile}\": the session header is missing or malformed. The file was not modified.`,\n\t\t\t);\n\t\t}\n\n\t\tthis.#sessionFile = resolvedSessionFile;\n\t\tthis.#rememberBreadcrumb(this.#cwd, resolvedSessionFile);\n\n\t\tconst { entries: fileEntries, titleSlot } = loaded;\n\t\tif (fileEntries.length === 0) {\n\t\t\t// Explicit but empty/missing path (e.g. --session flag): start fresh but\n\t\t\t// keep the requested path and materialize the header immediately.\n\t\t\tthis.#resetToNewSession(undefined, resolvedSessionFile);\n\t\t\tthis.#forceFileCreation = true;\n\t\t\tawait this.#rewriteAtomically();\n\t\t\tthis.#fileIsCurrent = true;\n\t\t\treturn;\n\t\t}\n","sourceCodeStart":1385,"sourceCodeEnd":1421,"githubUrl":"https://github.com/can1357/oh-my-pi/blob/969062200754ea02cfac922e5ebb8c608c079e15/packages/coding-agent/src/session/session-manager.ts#L1385-L1421","documentation":"Thrown when resuming a session file whose header (the JSON metadata block at the top of the JSONL session file) is missing or cannot be parsed. loadSessionFile flags invalidHeader, and resume refuses to proceed without modifying the file, protecting potentially salvageable data from being overwritten by a malformed-header write path.","triggerScenarios":"Calling the resume path (loadSession/resume in SessionManager, session-manager.ts:1403) with a path to a file that is empty, truncated mid-write, hand-edited so the header line is missing/invalid JSON, or written by an incompatible older format.","commonSituations":"Crash or disk-full during the first write of a session; user edited the file; restoring a partial backup; passing the wrong file (e.g. a log or artifacts file) to resume.","solutions":["Verify the file is an omp session JSONL file and starts with a valid header JSON line.","Restore the session file from backup or version control.","Repair or reconstruct the header line manually (off a known-good session file as a template) at your own risk.","Start a new session and re-import needed content from the broken file's message lines."],"exampleFix":"// before: resuming a truncated/edited file\nawait mgr.resume(\"session.jsonl\"); // invalidHeader\n// after: validate header first\nconst first = readFileSync(file, \"utf8\").split(\"\\n\")[0];\nif (JSON.parse(first).type !== \"header\") await mgr.resume(\"good-backup.jsonl\");","handlingStrategy":"validation","validationCode":"function looksLikeSessionFile(path) {\n  const first = readFileSync(path, \"utf8\").split(\"\\n\", 1)[0];\n  try { return typeof JSON.parse(first) === \"object\"; } catch { return false; }\n}","typeGuard":"function isValidHeader(line) {\n  try { const h = JSON.parse(line); return h != null && typeof h === \"object\" && h.type === \"header\"; }\n  catch { return false; }\n}","tryCatchPattern":"try {\n  await mgr.resume(file);\n} catch (err) {\n  if (err.message.includes(\"header is missing or malformed\")) {\n    // restore from backup or start a new session; file was NOT modified\n  } else throw err;\n}","preventionTips":["Never hand-edit session JSONL files.","Ensure the writing process completes (avoid killing the process mid-write, watch disk space).","Keep backups of session files; validate header before resuming after a crash."],"tags":["session","parsing","resume","data-corruption"],"backgroundTag":"invalid-session-header","analyzedSha":"969062200754ea02cfac922e5ebb8c608c079e15","analyzedAt":"2026-08-31T10:29:35.737Z","schemaVersion":2},"datasetVersion":"2026-08-31T14:17:45.589Z"}