denisidoro/navi · error · anyhow
Unable to acquire stdin of finder
Error message
Unable to acquire stdin of finder
What it means
Thrown by `call` in src/finder/mod.rs (via `ask_if_should_import_all`) when spawning the external finder process (e.g. fzf) succeeded, but the child's stdin handle is absent (`child.stdin` is None). Without stdin the library cannot stream data to the finder, so it aborts.
Source
Thrown at src/finder/mod.rs:222
let repo = match self {
Self::Fzf => "https://github.com/junegunn/fzf",
Self::Skim => "https://github.com/lotabout/skim",
};
eprintln!(
"navi was unable to call {cmd}.
Please make sure it's correctly installed.
Refer to {repo} for more info.",
cmd = &finder_str,
repo = repo
);
process::exit(33)
}
};
let stdin = child
.stdin
.as_mut()
.ok_or_else(|| anyhow!("Unable to acquire stdin of finder"))?;
let mut writer: Box<&mut dyn Write> = Box::new(stdin);
let return_value = stdin_fn(&mut writer).context("Failed to pass data to finder")?;
let out = child.wait_with_output().context("Failed to wait for finder")?;
let output = parse(out, finder_opts).context("Unable to get output")?;
Ok((output, return_value))
}
}
View on GitHub (pinned to f7330b9ad5)
Solutions
- Ensure the finder subprocess is configured with `Stdio::piped()` for stdin before spawning
- Run the command in an interactive terminal where the finder can attach to stdin/stdout
- Verify the configured finder binary (fzf/skim) is correctly installed and is the real interactive finder, not a wrapper that closes stdin
- Check that no other code path calls `.stdin.take()` on the child before this point
Example fix
// before
let child = Command::new(finder).stdout(Stdio::piped()).spawn()?;
// after
let child = Command::new(finder)
.stdin(Stdio::piped())
.stdout(Stdio::piped())
.spawn()?; Defensive patterns
Strategy: try-catch
Validate before calling
// before invoking the finder, ensure an interactive stdin is plausible
if !atty::is(atty::Stream::Stdin) {
eprintln!("finder requires an interactive stdin (TTY)");
} Try / catch
match result {
Err(e) if e.to_string().contains("Unable to acquire stdin of finder") => {
eprintln!("Run inside an interactive terminal with a TTY attached.");
}
other => other?,
} Prevention
- Only use finder-backed features in interactive terminals, not CI or detached scripts
- Verify the configured finder binary (fzf/skim) is installed and is the real interactive finder
- Don't wrap the finder in scripts that close or redirect stdin
When it happens
Trigger: Calling a finder-backed operation that needs to pipe input to the spawned finder process when `Command::spawn()` produced a child with `stdin: None` — e.g. the child was spawned with stdin not piped, or stdin was already taken/consumed elsewhere.
Common situations: Running in an environment with no TTY/standard input available (CI, non-interactive shells, detached processes); the finder binary configured in settings cannot accept piped stdin; a prior call already drained the child's stdin.
Related errors
- Could not open file in external editor
- Unable to get selection
- Unable to get query
- Unable to get variable
AI-assisted analysis of denisidoro/navi@f7330b9ad5 (2026-09-03).
Data as JSON: /api/errors/326db7ec2e65ffa4.
Report an issue: GitHub.