rm: use uucore::prompt_yes over custom prompt function

This commit is contained in:
Terts Diepraam 2022-11-16 15:16:39 +01:00
parent 91df2b1709
commit 33cbc94f25
2 changed files with 33 additions and 72 deletions

View file

@ -11,12 +11,12 @@ use clap::{crate_version, parser::ValueSource, Arg, ArgAction, Command};
use remove_dir_all::remove_dir_all; use remove_dir_all::remove_dir_all;
use std::collections::VecDeque; use std::collections::VecDeque;
use std::fs::{self, File, Metadata}; use std::fs::{self, File, Metadata};
use std::io::{stderr, stdin, BufRead, ErrorKind, Write}; use std::io::ErrorKind;
use std::ops::BitOr; use std::ops::BitOr;
use std::path::{Path, PathBuf}; use std::path::{Path, PathBuf};
use uucore::display::Quotable; use uucore::display::Quotable;
use uucore::error::{UResult, USimpleError, UUsageError}; use uucore::error::{UResult, USimpleError, UUsageError};
use uucore::{format_usage, show_error}; use uucore::{format_usage, prompt_yes, show_error};
use walkdir::{DirEntry, WalkDir}; use walkdir::{DirEntry, WalkDir};
#[derive(Eq, PartialEq, Clone, Copy)] #[derive(Eq, PartialEq, Clone, Copy)]
@ -133,11 +133,11 @@ pub fn uumain(args: impl uucore::Args) -> UResult<()> {
}; };
if options.interactive == InteractiveMode::Once && (options.recursive || files.len() > 3) { if options.interactive == InteractiveMode::Once && (options.recursive || files.len() > 3) {
let msg = if options.recursive { let msg = if options.recursive {
"Remove all arguments recursively? " "Remove all arguments recursively?"
} else { } else {
"Remove all arguments? " "Remove all arguments?"
}; };
if !prompt(msg) { if !prompt_yes!("{}", msg) {
return Ok(()); return Ok(());
} }
} }
@ -451,7 +451,7 @@ fn prompt_file(path: &Path, options: &Options, is_dir: bool) -> bool {
if options.interactive == InteractiveMode::Always { if options.interactive == InteractiveMode::Always {
if let Ok(metadata) = fs::symlink_metadata(path) { if let Ok(metadata) = fs::symlink_metadata(path) {
if metadata.is_symlink() { if metadata.is_symlink() {
return prompt(&(format!("remove symbolic link {}? ", path.quote()))); return prompt_yes!("remove symbolic link {}?", path.quote());
} }
} }
} }
@ -470,25 +470,18 @@ fn prompt_file(path: &Path, options: &Options, is_dir: bool) -> bool {
if let Ok(metadata) = file.metadata() { if let Ok(metadata) = file.metadata() {
if metadata.permissions().readonly() { if metadata.permissions().readonly() {
if metadata.len() == 0 { if metadata.len() == 0 {
prompt( prompt_yes!(
&(format!( "remove write-protected regular empty file {}?",
"remove write-protected regular empty file {}? ", path.quote()
path.quote()
)),
) )
} else { } else {
prompt( prompt_yes!("remove write-protected regular file {}?", path.quote())
&(format!(
"remove write-protected regular file {}? ",
path.quote()
)),
)
} }
} else if options.interactive == InteractiveMode::Always { } else if options.interactive == InteractiveMode::Always {
if metadata.len() == 0 { if metadata.len() == 0 {
prompt(&(format!("remove regular empty file {}? ", path.quote()))) prompt_yes!("remove regular empty file {}?", path.quote())
} else { } else {
prompt(&(format!("remove file {}? ", path.quote()))) prompt_yes!("remove file {}?", path.quote())
} }
} else { } else {
true true
@ -501,22 +494,15 @@ fn prompt_file(path: &Path, options: &Options, is_dir: bool) -> bool {
if err.kind() == ErrorKind::PermissionDenied { if err.kind() == ErrorKind::PermissionDenied {
if let Ok(metadata) = fs::metadata(path) { if let Ok(metadata) = fs::metadata(path) {
if metadata.len() == 0 { if metadata.len() == 0 {
prompt( prompt_yes!(
&(format!( "remove write-protected regular empty file {}?",
"remove write-protected regular empty file {}? ", path.quote()
path.quote()
)),
) )
} else { } else {
prompt( prompt_yes!("remove write-protected regular file {}?", path.quote())
&(format!(
"remove write-protected regular file {}? ",
path.quote()
)),
)
} }
} else { } else {
prompt(&(format!("remove write-protected regular file {}? ", path.quote()))) prompt_yes!("remove write-protected regular file {}?", path.quote())
} }
} else { } else {
true true
@ -536,9 +522,9 @@ fn handle_writable_directory(path: &Path, options: &Options, metadata: &Metadata
// Why is S_IWUSR showing up as a u16 on macos? // Why is S_IWUSR showing up as a u16 on macos?
let user_writable = (mode & (libc::S_IWUSR as u32)) != 0; let user_writable = (mode & (libc::S_IWUSR as u32)) != 0;
if !user_writable { if !user_writable {
prompt(&(format!("remove write-protected directory {}? ", path.quote()))) prompt_yes!("remove write-protected directory {}?", path.quote())
} else if options.interactive == InteractiveMode::Always { } else if options.interactive == InteractiveMode::Always {
prompt(&(format!("remove directory {}? ", path.quote()))) prompt_yes!("remove directory {}?", path.quote())
} else { } else {
true true
} }
@ -551,9 +537,9 @@ fn handle_writable_directory(path: &Path, options: &Options, metadata: &Metadata
use windows_sys::Win32::Storage::FileSystem::FILE_ATTRIBUTE_READONLY; use windows_sys::Win32::Storage::FileSystem::FILE_ATTRIBUTE_READONLY;
let not_user_writable = (metadata.file_attributes() & FILE_ATTRIBUTE_READONLY) != 0; let not_user_writable = (metadata.file_attributes() & FILE_ATTRIBUTE_READONLY) != 0;
if not_user_writable { if not_user_writable {
prompt(&(format!("remove write-protected directory {}? ", path.quote()))) prompt_yes!("remove write-protected directory {}?", path.quote())
} else if options.interactive == InteractiveMode::Always { } else if options.interactive == InteractiveMode::Always {
prompt(&(format!("remove directory {}? ", path.quote()))) prompt_yes!("remove directory {}?", path.quote())
} else { } else {
true true
} }
@ -564,14 +550,14 @@ fn handle_writable_directory(path: &Path, options: &Options, metadata: &Metadata
#[cfg(not(unix))] #[cfg(not(unix))]
fn handle_writable_directory(path: &Path, options: &Options, metadata: &Metadata) -> bool { fn handle_writable_directory(path: &Path, options: &Options, metadata: &Metadata) -> bool {
if options.interactive == InteractiveMode::Always { if options.interactive == InteractiveMode::Always {
prompt(&(format!("remove directory {}? ", path.quote()))) prompt_yes!("remove directory {}?", path.quote())
} else { } else {
true true
} }
} }
fn prompt_descend(path: &Path) -> bool { fn prompt_descend(path: &Path) -> bool {
prompt(&(format!("descend into directory {}? ", path.quote()))) prompt_yes!("descend into directory {}?", path.quote())
} }
fn normalize(path: &Path) -> PathBuf { fn normalize(path: &Path) -> PathBuf {
@ -582,20 +568,6 @@ fn normalize(path: &Path) -> PathBuf {
uucore::fs::normalize_path(path) uucore::fs::normalize_path(path)
} }
fn prompt(msg: &str) -> bool {
let _ = stderr().write_all(format!("{}: {}", uucore::util_name(), msg).as_bytes());
let _ = stderr().flush();
let mut buf = Vec::new();
let stdin = stdin();
let mut stdin = stdin.lock();
let read = stdin.read_until(b'\n', &mut buf);
match read {
Ok(x) if x > 0 => matches!(buf[0], b'y' | b'Y'),
_ => false,
}
}
#[cfg(not(windows))] #[cfg(not(windows))]
fn is_symlink_dir(_metadata: &Metadata) -> bool { fn is_symlink_dir(_metadata: &Metadata) -> bool {
false false

View file

@ -460,24 +460,10 @@ fn test_rm_prompts() {
let mut child: Child = scene.ucmd().arg("-ri").arg("a").run_no_wait(); let mut child: Child = scene.ucmd().arg("-ri").arg("a").run_no_wait();
let mut child_stdin = child.stdin.take().unwrap(); let mut child_stdin = child.stdin.take().unwrap();
child_stdin.write_all(yes.as_bytes()).unwrap(); for _ in 0..9 {
child_stdin.flush().unwrap(); child_stdin.write_all(yes.as_bytes()).unwrap();
child_stdin.write_all(yes.as_bytes()).unwrap(); child_stdin.flush().unwrap();
child_stdin.flush().unwrap(); }
child_stdin.write_all(yes.as_bytes()).unwrap();
child_stdin.flush().unwrap();
child_stdin.write_all(yes.as_bytes()).unwrap();
child_stdin.flush().unwrap();
child_stdin.write_all(yes.as_bytes()).unwrap();
child_stdin.flush().unwrap();
child_stdin.write_all(yes.as_bytes()).unwrap();
child_stdin.flush().unwrap();
child_stdin.write_all(yes.as_bytes()).unwrap();
child_stdin.flush().unwrap();
child_stdin.write_all(yes.as_bytes()).unwrap();
child_stdin.flush().unwrap();
child_stdin.write_all(yes.as_bytes()).unwrap();
child_stdin.flush().unwrap();
let output = child.wait_with_output().unwrap(); let output = child.wait_with_output().unwrap();
@ -494,10 +480,10 @@ fn test_rm_prompts() {
trimmed_output.sort(); trimmed_output.sort();
assert!(trimmed_output.len() == answers.len()); assert_eq!(trimmed_output.len(), answers.len());
for (i, checking_string) in trimmed_output.iter().enumerate() { for (i, checking_string) in trimmed_output.iter().enumerate() {
assert!(checking_string == answers[i]); assert_eq!(checking_string, answers[i]);
} }
assert!(!at.dir_exists("a")); assert!(!at.dir_exists("a"));
@ -530,7 +516,10 @@ fn test_rm_force_prompts_order() {
let output = child.wait_with_output().unwrap(); let output = child.wait_with_output().unwrap();
let string_output = let string_output =
String::from_utf8(output.stderr).expect("Couldn't convert output.stderr to string"); String::from_utf8(output.stderr).expect("Couldn't convert output.stderr to string");
assert!(string_output.trim() == "rm: remove regular empty file 'empty'?"); assert_eq!(
string_output.trim(),
"rm: remove regular empty file 'empty'?"
);
assert!(!at.file_exists(empty_file)); assert!(!at.file_exists(empty_file));
at.touch(empty_file); at.touch(empty_file);