nikivdev/code · error
codex skill-eval launchd install failed: {}
Error message
codex skill-eval launchd install failed: {} What it means
Flow installs a launchd job for the codex skill-eval daemon by shelling out to a helper installer binary (with FLOW_CODEX_SKILL_EVAL_F_BIN pointing at the current executable). If that subprocess exits with a non-zero status, Flow bubbles up its trimmed stderr with this error.
Source
Thrown at src/ai.rs:9621
.arg(script)
.arg("install")
.arg("--minutes")
.arg(minutes.to_string())
.arg("--limit")
.arg(limit.to_string())
.arg("--max-targets")
.arg(max_targets.to_string())
.arg("--within-hours")
.arg(within_hours.to_string());
if dry_run {
command.arg("--dry-run");
}
command.env("FLOW_CODEX_SKILL_EVAL_F_BIN", current_exe);
let output = command
.output()
.context("failed to run codex skill-eval launchd installer")?;
if !output.status.success() {
bail!(
"codex skill-eval launchd install failed: {}",
String::from_utf8_lossy(&output.stderr).trim()
);
}
Ok(String::from_utf8_lossy(&output.stdout).trim().to_string())
}
fn codex_enable_global(
dry_run: bool,
install_launchd: bool,
start_daemon: bool,
sync_skills: bool,
full: bool,
minutes: usize,
limit: usize,
max_targets: usize,
within_hours: u64,
provider: Provider,View on GitHub (pinned to a747e741ae)
Solutions
- Read the stderr text embedded in the error — it is the installer's own message and names the concrete failure.
- Re-run the installer manually (the same command Flow invokes, with FLOW_CODEX_SKILL_EVAL_F_BIN set) to see full output.
- Ensure ~/Library/LaunchAgents exists and is writable, and that launchctl is available (run inside a GUI session, not a bare SSH context).
- Reinstall/update Flow so the installer helper matches the current version, then retry `f codex enable-global`.
Example fix
// before $ f codex enable-global Error: codex skill-eval launchd install failed: launchctl: could not bootstrap domain // after: fix environment, then verify $ mkdir -p ~/Library/LaunchAgents $ launchctl print gui/$(id -u) >/dev/null # confirm launchd domain accessible $ f codex enable-global
Defensive patterns
Strategy: try-catch
Validate before calling
use std::path::Path;
// preflight before install:
let agents_dir = dirs::home_dir().map(|h| h.join("Library/LaunchAgents"));
let writable = agents_dir
.as_deref()
.map(std::path::Path::is_dir)
.unwrap_or(false);
assert!(writable, "~/Library/LaunchAgents must exist and be writable"); Try / catch
match result {
Err(e) if e.to_string().contains("codex skill-eval launchd install failed") => {
// e.to_string() embeds the installer's stderr; log it and inspect
// ~/Library/LaunchAgents permissions and launchctl availability before retrying.
eprintln!("launchd install failed: {e}");
}
Err(e) => return Err(e),
Ok(out) => println!("installed: {out}"),
} Prevention
- Run install commands inside a GUI macOS session (launchctl user domains are limited over bare SSH).
- Keep Flow and its installer helper binary in sync — reinstall after upgrades.
- Confirm ~/Library/LaunchAgents exists and is writable before installing launchd jobs.
- Capture and read the stderr embedded in the error; it names the concrete installer failure.
When it happens
Trigger: Running `f codex enable-global` (or install-launchd / full setup) when the launchd installer subprocess fails — e.g. it cannot write to ~/Library/LaunchAgents, launchctl rejects the plist, or the installer binary itself errors.
Common situations: macOS permission issues (LaunchAgents directory not writable or protected), malformed plist due to unusual HOME, an outdated or mismatched installer binary after a Flow upgrade, launchctl failing in non-GUI/SSH sessions where the user's launchd domain is unavailable.
Related errors
- Flow Codex wrapper is missing at {}; build or sync Flow firs
- enable-global is only supported for Codex sessions; use `f c
- pbcopy exited with status {}
- failed to stash working tree: {}
- {} failed
AI-assisted analysis of nikivdev/code@a747e741ae (2026-09-01).
Data as JSON: /api/errors/02cb3b96a1e38e93.
Report an issue: GitHub.