{"record":{"id":"2e2cc964d25033b5","repo":"Yeachan-Heo/oh-my-codex","slug":"job-not-input-accepting-session-mismatch-active","errorCode":null,"errorMessage":"job_not_input_accepting:session_mismatch:${active.session_id}","messagePattern":"job_not_input_accepting:session_mismatch:(.+?)","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/exec/followup.ts","lineNumber":235,"sourceCode":"  options: InjectExecFollowupOptions,\n): Promise<InjectExecFollowupResult> {\n  const sessionId = normalizeSessionId(options.sessionId);\n  const prompt = normalizePrompt(options.prompt);\n  const actor = normalizeActor(options.actor);\n  const nowIso = options.nowIso ?? new Date().toISOString();\n\n  const active = await readUsableSessionState(options.cwd);\n  const activeUsable = active && isSessionStateUsable(active, options.cwd);\n  if (!activeUsable && !options.allowInactiveSession) {\n    throw new Error(\"job_not_input_accepting:no_active_exec_session\");\n  }\n  if (\n    activeUsable\n    && active.session_id !== sessionId\n    && active.native_session_id !== sessionId\n    && !options.allowInactiveSession\n  ) {\n    throw new Error(`job_not_input_accepting:session_mismatch:${active.session_id}`);\n  }\n\n  const canonicalSessionId = activeUsable && (active.session_id === sessionId || active.native_session_id === sessionId)\n    ? active.session_id\n    : sessionId;\n  const queuePath = sessionQueuePath(options.cwd, canonicalSessionId);\n  const queued: ExecFollowupRecord = {\n    id: randomUUID(),\n    session_id: canonicalSessionId,\n    actor,\n    prompt,\n    created_at: nowIso,\n  };\n  await withQueueLock(queuePath, async () => {\n    const queue = await readQueue(queuePath, canonicalSessionId, {\n      cwd: options.cwd,\n      nowIso,\n      recoverCorrupt: true,","sourceCodeStart":217,"sourceCodeEnd":253,"githubUrl":"https://github.com/Yeachan-Heo/oh-my-codex/blob/3ad79a8a6fe6e95fdbb8c00e40716fffe4011ce2/src/exec/followup.ts#L217-L253","documentation":"Thrown by injectExecFollowup when the supplied session id does not match the currently usable session in that cwd. The active session's session_id and native_session_id both differ from the requested id, so the library refuses to inject into a session that is no longer the active one (unless allowInactiveSession is set). The message embeds the actual active session id for diagnosis.","triggerScenarios":"Passing a stale session id from a previous exec session while a new one is active in the same cwd; hardcoding or caching a session id that has since been rotated; copy-pasting an id from another checkout; racing with a session restart between reading the id and injecting.","commonSituations":"Scripts cache the session id from an earlier run and reuse it after the session was restarted; orchestrator reads the id at job start but the session rotates mid-job; multiple sessions historically ran in the directory and an old id is used.","solutions":["Re-read the current session id from the active session state (or the error message, which contains active.session_id) and retry with that id.","If injecting into a superseded session is intentional, pass allowInactiveSession: true.","Make your orchestrator re-resolve the session id immediately before each injection rather than caching it.","Guard against races by retrying once with the freshly resolved id on session_mismatch."],"exampleFix":"// before\nawait injectExecFollowup(cwd, cachedSessionId, { prompt });\n\n// after\nconst active = await readUsableSessionState(cwd);\nif (!active) throw new Error('no active session');\nawait injectExecFollowup(cwd, active.session_id, { prompt });","handlingStrategy":"validation","validationCode":"const active = await readUsableSessionState(cwd);\nif (!active) throw new Error('no active session');\nconst id = (active.session_id === wanted || active.native_session_id === wanted) ? active.session_id : active.session_id;\nawait injectExecFollowup(cwd, id, { prompt });","typeGuard":"function sessionMatches(active: SessionState, id: string): boolean {\n  return active.session_id === id || active.native_session_id === id;\n}","tryCatchPattern":"try { await injectExecFollowup(cwd, sessionId, { prompt }); }\ncatch (e) {\n  const m = e instanceof Error && e.message.match(/^job_not_input_accepting:session_mismatch:(.+)$/);\n  if (m) return injectExecFollowup(cwd, m[1]!, { prompt }); // retry with active id\n  throw e;\n}","preventionTips":["Never cache session ids across session restarts.","Resolve the active session id at call time.","Handle races by retrying once with the id from the error message."],"tags":["session-state","session-mismatch","exec-followup","validation"],"backgroundTag":"session-id-mismatch","analyzedSha":"3ad79a8a6fe6e95fdbb8c00e40716fffe4011ce2","analyzedAt":"2026-08-27T22:18:39.783Z","schemaVersion":2},"datasetVersion":"2026-08-28T00:17:15.603Z"}