Yeachan-Heo/oh-my-codex · error · Error
tmux source authority transaction failed: ${result.stderr}
Error message
tmux source authority transaction failed: ${result.stderr} What it means
runSourceAuthorizedTmux wraps a tmux effect in `if-shell -F` against the source pane's authority predicate; the wrapper tmux invocation itself failed (non-zero). This is a transport/execution failure of the transaction, not an authority failure — that is reported separately as 'changed before effect'.
Source
Thrown at src/team/tmux-session.ts:373
const firstFormatIndex = effect.indexOf(SPLIT_WINDOW_PANE_FORMAT);
if (firstFormatIndex < 0 || effect.indexOf(SPLIT_WINDOW_PANE_FORMAT, firstFormatIndex + SPLIT_WINDOW_PANE_FORMAT.length) >= 0) {
throw new Error('tmux_split_window_format_contract_invalid');
}
return `${effect.slice(0, firstFormatIndex)}-F '#{pane_id}:${receipt}'${effect.slice(firstFormatIndex + SPLIT_WINDOW_PANE_FORMAT.length)}`;
}
function bindSplitReceiptToPaneCommand(command: string, receipt: string): string {
return `${command} # ${receipt}`;
}
/** Queue an effect in the source pane's tmux server only when its exact pane/session/window incarnation still matches. */
export function runSourceAuthorizedTmux(source: SourcePaneAuthority, effect: string, receipt: string = sourceTransactionReceipt()): string {
const result = runTmux([
'if-shell', '-F', '-t', source.paneId, sourceAuthorityPredicate(source),
`${effect} ; display-message -p ${shellQuoteSingle(receipt)}`,
"display-message -p ''",
]);
if (!result.ok) throw new Error(`tmux source authority transaction failed: ${result.stderr}`);
if (result.stdout !== receipt) throw new Error('tmux source authority changed before effect');
return receipt;
}
export function runSourceAuthorizedSplit(
source: SourcePaneAuthority,
buildEffect: (receipt: string) => string,
): string {
// Reconcile against the immutable window ID, not the mutable session:index
// target: a concurrent renumber between the guarded split and the after-read
// must never turn an unrelated window's pane into kill authority.
const windowTarget = source.windowId;
const beforeTopology = listPanesResult(windowTarget);
if (beforeTopology.error) {
throw new Error(`failed to read tmux pane topology before split: ${beforeTopology.error}`);
}
const beforePaneIds = new Set(beforeTopology.panes.map((pane) => pane.paneId));
const receipt = sourceTransactionReceipt();View on GitHub (pinned to 3ad79a8a6f)
Solutions
- Inspect embedded stderr: 'lost server' → re-establish tmux; 'no such pane' → re-capture authority
- Retry the whole capture+effect sequence from a fresh captureSourcePaneAuthority
- Sanitize any custom effect strings for shell/tmux quoting (shellQuoteSingle)
Defensive patterns
Strategy: retry
Try / catch
catch (e) { if (/source authority transaction failed/.test(e.message)) { if (/lost server|no such pane/.test(e.message)) recapture(); else retryOnce(); return; } throw e; } Prevention
- Quote effect strings with shellQuoteSingle
- Re-capture authority before each retry; never blind-retry the effect
When it happens
Trigger: Calling runSourceAuthorizedTmux/runSourceAuthorizedSplit when the tmux server dies mid-command, the target pane disappears before if-shell resolves, or quoting of the effect string breaks the tmux command line.
Common situations: tmux server restart or socket loss during a split/kill effect; malformed effect built by a custom buildEffect callback (unbalanced quotes); pane closed concurrently.
Related errors
- tmux source authority changed before effect
- invalid auth slot path
- auth directory must not be a symlink: ${dir}
- auth path is not a directory: ${dir}
- ${label} is not a file: ${path}
AI-assisted analysis of Yeachan-Heo/oh-my-codex@3ad79a8a6f (2026-08-27).
Data as JSON: /api/errors/292be6b3baae841a.
Report an issue: GitHub.