atuinsh/atuin · error
Failed to read from input
Error message
Failed to read from input
What it means
In `change_password.rs::run`, when `--current-password` was not supplied the command prompts interactively with `prompt_password(...)` and `.expect("Failed to read from input")`s the result. The prompt fails when stdin cannot be read — EOF/closed stdin, non-interactive environments, or terminal read errors — causing a panic instead of a friendly CLI error.
Solutions
- Pass the current password explicitly with `--current-password <pw>` (avoiding the prompt)
- Run the command in an interactive terminal
- If scripting, pipe the password via stdin ensuring stdin stays open until the prompt completes
Example fix
// before
let current_password = self.current_password.clone().unwrap_or_else(|| {
prompt_password("Please enter the current password: ")
.expect("Failed to read from input")
});
// after
let current_password = match self.current_password.clone() {
Some(p) => p,
None => match prompt_password("Please enter the current password: ") {
Ok(p) => p,
Err(e) => bail!("failed to read current password from input: {e}"),
},
}; Defensive patterns
Strategy: validation
Validate before calling
// check interactivity before prompting
if atty::is(atty::Stream::Stdin) || std::env::var_os("ATUIN_CURRENT_PASSWORD").is_some() { /* safe to prompt */ } Try / catch
match prompt_password("Please enter the current password: ") {
Ok(p) => p,
Err(e) => bail!("could not read current password (is stdin a terminal?): {e}"),
} Prevention
- Always pass --current-password in scripts and CI
- Support reading the password from an env var or stdin for non-interactive use
- Check stdin is a TTY before prompting and emit an actionable error otherwise
When it happens
Trigger: Running `atuin account change-password` without `--current-password` in a non-interactive context: piped/closed stdin, CI jobs, nohup, or scripts that don't allocate a TTY.
Common situations: Automation and CI pipelines invoking the password change; detached shells where no terminal is attached; users piping input that ends before the prompt reads it.
Understand the failure class
Background: "no subcommand specified" and "... is required": CLI errors when a required argument is missing — this error's family across 13 libraries.
Related errors
- Failed to read from input
- please provide a new password
- please provide a password
- please provide the current password
- please provide your password
AI-assisted analysis of atuinsh/atuin@900007c480 (2026-09-19).
Data as JSON: /api/errors/4f2cdb6f50b3bf75.
Report an issue: GitHub.
Appendix: source
Thrown at crates/atuin/src/command/client/account/change_password.rs:30
#[clap(long, short)]
pub new_password: Option<String>,
/// The two-factor authentication code for your account, if any
#[clap(long, short)]
pub totp_code: Option<String>,
}
impl Cmd {
pub async fn run(&self, settings: &Settings) -> Result<()> {
if !settings.logged_in().await? {
bail!("You are not logged in");
}
let client = auth::auth_client(settings).await;
let current_password = self.current_password.clone().unwrap_or_else(|| {
prompt_password("Please enter the current password: ")
.expect("Failed to read from input")
});
if current_password.is_empty() {
bail!("please provide the current password");
}
let new_password = self.new_password.clone().unwrap_or_else(|| {
prompt_password("Please enter the new password: ").expect("Failed to read from input")
});
if new_password.is_empty() {
bail!("please provide a new password");
}
let mut totp_code = self.totp_code.clone();
loop {
let response = clientView on GitHub (pinned to 900007c480)