diff --git a/src/pr/pr.rs b/src/pr/pr.rs index c7a833402..a6636eaa7 100644 --- a/src/pr/pr.rs +++ b/src/pr/pr.rs @@ -112,21 +112,6 @@ impl Default for NumberingMode { } } -enum InputType { - Directory, - File, - StdIn, - SymLink, - #[cfg(unix)] - BlockDevice, - #[cfg(unix)] - CharacterDevice, - #[cfg(unix)] - Fifo, - #[cfg(unix)] - Socket, -} - impl From for PrError { fn from(err: Error) -> Self { PrError::EncounteredErrors(err.to_string()) @@ -163,6 +148,10 @@ quick_error! { IsSocket(path: String) { display("pr: cannot open {}, Operation not supported on socket", path) } + + NotExists(path: String) { + display("pr: cannot open {}, No such file or directory", path) + } } } @@ -291,8 +280,7 @@ pub fn uumain(args: Vec) -> i32 { } for f in files { - let header: &String = &matches.opt_str(STRING_HEADER_OPTION).unwrap_or(f.to_string()); - let result_options = build_options(&matches, header, &f); + let result_options = build_options(&matches, &f); if result_options.is_err() { writeln!(&mut stderr(), "{}", result_options.err().unwrap()); return 1; @@ -349,7 +337,8 @@ fn print_usage(opts: &mut Options, matches: &Matches) -> i32 { return 0; } -fn build_options(matches: &Matches, header: &String, path: &String) -> Result { +fn build_options(matches: &Matches, path: &String) -> Result { + let header: String = matches.opt_str(STRING_HEADER_OPTION).unwrap_or(path.to_string()); let numbering_options: Option = matches.opt_str(NUMBERING_MODE_OPTION).map(|i| { NumberingMode { width: i.parse::().unwrap_or(NumberingMode::default().width), @@ -439,7 +428,7 @@ fn build_options(matches: &Matches, header: &String, path: &String) -> Result Result Result, PrError> { - match get_input_type(path) { - Some(InputType::Directory) => Err(PrError::IsDirectory(path.to_string())), - #[cfg(unix)] - Some(InputType::Socket) => { - Err(PrError::IsSocket(path.to_string())) - } - Some(InputType::StdIn) => { - let stdin = stdin(); - Ok(Box::new(stdin) as Box) - } - Some(_) => Ok(Box::new(File::open(path).context(path)?) as Box), - None => Err(PrError::UnknownFiletype(path.to_string())) + if path == FILE_STDIN { + let stdin = stdin(); + return Ok(Box::new(stdin) as Box); } + + metadata(path).map(|i| { + let path_string = path.to_string(); + match i.file_type() { + #[cfg(unix)] + ft if ft.is_block_device() => + { + Err(PrError::UnknownFiletype(path_string)) + } + #[cfg(unix)] + ft if ft.is_char_device() => + { + Err(PrError::UnknownFiletype(path_string)) + } + #[cfg(unix)] + ft if ft.is_fifo() => + { + Err(PrError::UnknownFiletype(path_string)) + } + #[cfg(unix)] + ft if ft.is_socket() => + { + Err(PrError::IsSocket(path_string)) + } + ft if ft.is_dir() => Err(PrError::IsDirectory(path_string)), + ft if ft.is_file() || ft.is_symlink() => Ok(Box::new(File::open(path).context(path)?) as Box), + _ => Err(PrError::UnknownFiletype(path_string)) + } + }).unwrap_or(Err(PrError::NotExists(path.to_string()))) } fn pr(path: &str, options: &OutputOptions) -> Result { @@ -654,38 +663,3 @@ fn trailer_content(options: &OutputOptions) -> Vec { Vec::new() } } - -fn get_input_type(path: &str) -> Option { - if path == FILE_STDIN { - return Some(InputType::StdIn); - } - - metadata(path).map(|i| { - match i.file_type() { - #[cfg(unix)] - ft if ft.is_block_device() => - { - Some(InputType::BlockDevice) - } - #[cfg(unix)] - ft if ft.is_char_device() => - { - Some(InputType::CharacterDevice) - } - #[cfg(unix)] - ft if ft.is_fifo() => - { - Some(InputType::Fifo) - } - #[cfg(unix)] - ft if ft.is_socket() => - { - Some(InputType::Socket) - } - ft if ft.is_dir() => Some(InputType::Directory), - ft if ft.is_file() => Some(InputType::File), - ft if ft.is_symlink() => Some(InputType::SymLink), - _ => None - } - }).unwrap_or(None) -} diff --git a/tests/test_pr.rs b/tests/test_pr.rs index 8ec8ebc0d..5e839bc3a 100644 --- a/tests/test_pr.rs +++ b/tests/test_pr.rs @@ -18,7 +18,7 @@ fn file_last_modified_time(ucmd: &UCommand, path: &str) -> String { #[test] -fn test_output_multi_files_print_all_chars() { +fn test_without_any_options() { let test_file_path = "test_one_page.log"; let mut scenario = new_ucmd!(); let value = file_last_modified_time(&scenario, test_file_path);