Hmbown/CodeWhale · error · anyhow::Error
Automation admission belongs to a different task store; it…
Error message
Automation admission belongs to a different task store; it cannot be replayed here
What it means
Automation replay dispatch verifies that the task data directory recorded on the AutomationDispatch matches the directory of the SharedTaskManager it is being replayed into. This error means the dispatch was created against a different task store (different data_dir), so replaying it here would write tasks into the wrong store. It is a cross-store consistency guard, not a data corruption.
Solutions
- Replay the dispatch against the task manager whose data_dir matches dispatch.task_data_dir.
- Re-generate the dispatch in the current store instead of replaying the foreign one.
- If the store was intentionally moved, restore it to its original canonical path, or recreate the dispatch so task_data_dir points at the current directory.
Example fix
// before
replay_dispatch(&stale_dispatch, &other_tasks).await?;
// after
if stale_dispatch.task_data_dir.canonicalize()? == other_tasks.data_dir().canonicalize()? {
replay_dispatch(&stale_dispatch, &other_tasks).await?;
} else {
let fresh = create_dispatch_in(&other_tasks).await?;
replay_dispatch(&fresh, &other_tasks).await?;
} Defensive patterns
Strategy: validation
Validate before calling
if std::fs::canonicalize(&dispatch.task_data_dir)? != std::fs::canonicalize(tasks.data_dir())? {
// skip replay: foreign task store
} Try / catch
match check_dispatch_store(&dispatch, &tasks) {
Ok(()) => replay(dispatch).await,
Err(e) if e.to_string().contains("different task store") => recreate_dispatch(&tasks).await,
Err(e) => return Err(e),
} Prevention
- Keep one canonical data directory per profile and never relocate it between sessions.
- Tag serialized dispatches with the store path they were produced against and verify before replay.
- When migrating stores, always re-generate dispatches in the target store instead of copying them.
When it happens
Trigger: Calling dispatch_bound_task (or a replay/restore path that reaches check_dispatch_store) with a serialized AutomationDispatch whose task_data_dir canonicalizes to a path different from tasks.data_dir() — e.g. replaying an automation dump on a machine or profile with a different data directory.
Common situations: Copying automation state files between machines or users; running the TUI with a different CODEX_HOME / data dir than the one that produced the dispatch; restoring backups into a relocated store; pointing two profiles at each other's task stores.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- Archive this pet recording before accepting more telemetry.
- Automation admission execution ownership is unverified or…
- Automation name is required
- Automation prompt is required
- Automation run schema v
AI-assisted analysis of Hmbown/CodeWhale@73e0f67d83 (2026-09-22).
Data as JSON: /api/errors/ff937b405662da15.
Report an issue: GitHub.
Appendix: source
Thrown at crates/tui/src/automation_manager.rs:2107
execution_scope: automation.execution_scope.clone(),
request: automation_task_request(automation),
task_data_dir: task_data_dir
.canonicalize()
.context("resolve task store before automation admission")?,
accepted: false,
delivery_mode: automation.delivery_mode(),
suppress_report: false,
schedule: scheduled.then(|| AdmittedSchedule {
updated_at: automation.updated_at,
rrule: automation.rrule.clone(),
}),
});
Ok(())
}
fn check_dispatch_store(dispatch: &AutomationDispatch, tasks: &SharedTaskManager) -> Result<()> {
if tasks.data_dir().canonicalize()? != dispatch.task_data_dir.canonicalize()? {
bail!("Automation admission belongs to a different task store; it cannot be replayed here");
}
Ok(())
}
async fn dispatch_bound_task(
dispatch: &mut AutomationDispatch,
task_id: &str,
tasks: &SharedTaskManager,
) -> Result<crate::task_manager::TaskRecord> {
check_dispatch_store(dispatch, tasks)?;
if dispatch.execution_scope.as_deref() != Some(tasks.execution_scope()) {
bail!(
"Automation admission execution ownership is unverified or belongs to another Runtime"
);
}
let task = if dispatch.accepted {
tasks
.read_bound_task(task_id)?View on GitHub (pinned to 73e0f67d83)