Codex Desktop: set_thread_archived hangs when an active automation archives its own task
What version of the Codex App are you using?
Codex Desktop 26.707.41301 (build 5103).
What subscription do you have?
ChatGPT Pro.
What platform is your computer?
macOS 26.1, arm64.
What issue are you seeing?
A standalone scheduled automation can call the official set_thread_archived tool on its own currently active task. When it does, the tool call remains pending indefinitely: it neither archives the task nor returns a success or structured error.
This reproduced twice during the same automation run on 12 July 2026, approximately 05:01–05:03 UTC. Each attempt was bounded externally and terminated after approximately 60 seconds.
During both attempts:
- no
thread/archiverequest appeared in the Codex Desktop logs; - no
thread/archivednotification appeared; - the tool call never completed;
- the active automation turn remained blocked waiting for the tool result.
This does not appear to be general archive latency or an app-server outage. Across the same local Desktop log history, 131 other successful archive operations completed with a median response time of 29 ms.
OpenAI’s Codex glossary describes a scheduled run as an execution that may report findings or archive itself:
https://learn.chatgpt.com/docs/glossary
Steps to reproduce
- Create a standalone Codex scheduled task that starts each run in a fresh task.
- Add a terminal instruction requiring the automation to archive its current task by calling:
``text``
set_thread_archived({ archived: true })
- Require the automation to wait for confirmed archive success before returning.
- Run the automation until it reaches that terminal path while its turn is still active.
- Observe that
set_thread_archivedremains pending indefinitely. - Inspect the Desktop logs and observe that no
thread/archiverequest orthread/archivedevent was emitted.
The issue reproduced on two consecutive calls. Retrying did not reach the app server.
Expected behavior
One of the following should happen:
- If self-archival is supported, Desktop should schedule the archive for after the active turn finishes, return a defined acknowledgement, and archive the completed task.
- If self-archival is unsupported while a task has an active turn, the tool should fail immediately with a structured, actionable error.
The official tool call should never remain pending indefinitely.
Actual behavior
Desktop accepts the set_thread_archived tool call but never resolves it and never dispatches thread/archive to the app server.
Because the active automation is waiting for the tool result, the entire run remains blocked until externally terminated. This causes otherwise successful no-action automations to be reported as blocked solely because terminal task cleanup cannot complete.
Local diagnosis
Inspection of the shipped Desktop handler shows that set_thread_archived resolves an omitted target task ID to the calling/source task, then awaits the archive operation before returning the tool result.
The observed failure boundary is before app-server dispatch: neither failed attempt emitted thread/archive. Combined with the handler awaiting archive completion, this suggests a circular wait:
- The active turn calls
set_thread_archivedon itself. - The tool handler waits for archival to complete.
- Archival cannot progress through the normal lifecycle while that same turn is active, or dispatch is deferred until the turn completes.
- The turn cannot complete because it is waiting for the tool result.
This is a high-confidence diagnosis from the shipped handler behaviour and Desktop logs, not a vendor-confirmed root cause.
Related but distinct issues
- #25713: archiving the active thread reaches the backend successfully, then Desktop repeatedly tries to resume the archived thread and freezes. In this report,
thread/archiveis never dispatched. - #28080: thread-management tools intermittently lose handlers or return
No handler registered. In this report, the tool is exposed and invoked but remains pending without returning an error. - #32257: Desktop sends
thread/archivefor a regular task with an active turn and aborts that task. In this report, the active automation explicitly requests self-archival, but the request never reaches the app server and the turn hangs instead of being aborted.
Operational workaround
Do not synchronously archive a task from its own active automation turn. Leave it unarchived, archive it manually, or archive it from a separate controller after the run has completed.
Suggested fix
Guard self-targeting archive calls while the source task has an active turn. Either:
- enqueue archival as a post-turn action and return a defined acknowledgement; or
- reject the call immediately with a structured error explaining that an active task cannot archive itself.
In either case, add a bounded timeout so the tool cannot remain pending indefinitely.
Suggested regression coverage:
- Self-archive from an active automation turn.
- Archive an idle separate task.
- Archive a separate task with an active turn.
- Confirm every path returns a defined result and never leaves the tool call pending.
2 Comments
Newer-build reproduction and misleading success state
Reproduced on Codex Desktop
26.803.61601on macOS Apple Silicon during a naturally scheduled automation.Observed behavior:
set_thread_archived({ archived: true })without a thread ID, targeting its calling task.dynamic tool call was cancelled before receiving a response.Archive requestednorthread/archivefor the affected task. Successful archive operations in the same runtime contain both events.{ archived: true }result.Packaged Desktop inspection also indicates that the dynamic handler resolves the target host with a 15-second background timeout, hydrates the task, and only then performs the archive. A caller with a shorter external bound can therefore finalize first and cancel the request before dispatch. This is a bounded form of the same no-dispatch failure rather than proof that every call would remain pending indefinitely.
As a control, a separate active task successfully dispatched
thread/archiveand archived itself, but doing so immediately interrupted its own turn before it could deliver the required final response.This leaves two unsafe outcomes for active self-archive:
A post-turn or deferred archive acknowledgement would address both. Independently, the activity UI should only display a successful archive update after confirmed archive success; cancellation or missing acknowledgement should be shown as failure or uncertain state.
Private task identifiers and local paths are omitted, but narrow correlation details can be supplied through an OpenAI-controlled private channel if needed.
Adding more information about the scope and impact of this issue, along with a control test that may help isolate it.
Scope
This is reproducible for every Codex scheduled automation we run, across multiple projects.
Each automation completes its actual work and then follows a final instruction to call:
set_thread_archived({ archived: true })on its own current task.
The call remains pending until the run is timed out, and the completed task remains unarchived.
Impact
This is not an occasional cleanup failure.
Every scheduled run creates a new task, so every run leaves another completed task in the active task list. Projects quickly accumulate a large number of unarchived automation tasks and require continuous manual cleanup.
With multiple recurring automations, this makes Codex effectively unusable for automations at scale.
Control test
Our Codex Desktop instance is connected to a remote macOS server, so I tested whether remote hosting was the cause.
On the same remote server and in the same project, I created a normal, non-automation task whose final instruction was to archive its own current task. That task archived successfully.
The equivalent self-archive step fails consistently when executed by a scheduled automation.
This suggests that remote hosting alone is not the cause and narrows the problem to the scheduled-automation execution lifecycle.
Request
Could someone from the Codex Desktop/automations team please prioritize or acknowledge this issue?
A reliable post-run archive mechanism would solve the problem. At minimum, the archive call should return a bounded, actionable error instead of hanging indefinitely.
I’m happy to provide additional logs or test a diagnostic build if that would help.