Skip to content

Commit

Permalink
feat: wait for password-command to exit
Browse files Browse the repository at this point in the history
useful for commands that requires interactive input
  • Loading branch information
istudyatuni committed Jun 22, 2023
1 parent 393afe4 commit c42f30b
Show file tree
Hide file tree
Showing 2 changed files with 19 additions and 6 deletions.
1 change: 1 addition & 0 deletions changelog/new.txt
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,4 @@ New features:
- restore: The restore algorithm has been improved and should now be faster for remote repositories.
- restore: Files are now allocated just before being first processed. This allows easier resumed restores.
- New option: `no-require-git` for backup - if enabled, a git repository is not required to apply `git-ignore` rule.
- fix: wait for password-command to successfully exit, allowing to input something into the command, and read password from stdout.
24 changes: 18 additions & 6 deletions crates/rustic_core/src/repository.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,12 @@ use std::{
fs::File,
io::{BufRead, BufReader},
path::PathBuf,
process::Command,
process::{Command, Stdio},
};

use bytes::Bytes;
use derive_more::Add;
use log::{debug, info};
use log::{debug, error, info};

use nom::{
branch::alt,
Expand Down Expand Up @@ -106,7 +106,7 @@ pub struct RepositoryOptions {
)]
pub password_file: Option<PathBuf>,

/// Command to read the password from
/// Command to read the password from. Password is read from stdout
#[cfg_attr(feature = "clap", clap(
long,
global = true,
Expand Down Expand Up @@ -267,10 +267,22 @@ impl<P> Repository<P> {
.map_err(RepositoryErrorKind::FromNomError)?
.1;
debug!("commands: {commands:?}");
let Ok(output) = Command::new(commands[0]).args(&commands[1..]).output() else {
return Err(
RepositoryErrorKind::PasswordCommandParsingFailed.into());
let command = Command::new(commands[0])
.args(&commands[1..])
.stdout(Stdio::piped())
.spawn()?;
let Ok(output) = command.wait_with_output() else {
return Err(RepositoryErrorKind::PasswordCommandParsingFailed.into());
};
if !output.status.success() {
#[allow(clippy::option_if_let_else)]
let s = match output.status.code() {
Some(c) => format!("exited with status code {c}"),
None => "was terminated".into(),
};
error!("password-command {s}");
return Err(RepositoryErrorKind::ReadingPasswordFromCommandFailed.into());
}

let mut pwd = BufReader::new(&*output.stdout);
Ok(Some(match read_password_from_reader(&mut pwd) {
Expand Down

0 comments on commit c42f30b

Please sign in to comment.