mirror of
https://github.com/RGBCube/uutils-coreutils
synced 2025-07-28 19:47:45 +00:00
ls: extract most of the content into functions
This commit is contained in:
parent
1a8f2a78c0
commit
33d4ab82ba
1 changed files with 189 additions and 165 deletions
|
@ -426,11 +426,8 @@ struct PaddingCollection {
|
||||||
block_size: usize,
|
block_size: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Config {
|
fn extract_format(options: &clap::ArgMatches) -> (Format, Option<&'static str>) {
|
||||||
#[allow(clippy::cognitive_complexity)]
|
if let Some(format_) = options.get_one::<String>(options::FORMAT) {
|
||||||
pub fn from(options: &clap::ArgMatches) -> UResult<Self> {
|
|
||||||
let context = options.get_flag(options::CONTEXT);
|
|
||||||
let (mut format, opt) = if let Some(format_) = options.get_one::<String>(options::FORMAT) {
|
|
||||||
(
|
(
|
||||||
match format_.as_str() {
|
match format_.as_str() {
|
||||||
"long" | "verbose" => Format::Long,
|
"long" | "verbose" => Format::Long,
|
||||||
|
@ -455,7 +452,168 @@ impl Config {
|
||||||
(Format::Columns, None)
|
(Format::Columns, None)
|
||||||
} else {
|
} else {
|
||||||
(Format::OneLine, None)
|
(Format::OneLine, None)
|
||||||
};
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn extract_files(options: &clap::ArgMatches) -> Files {
|
||||||
|
if options.get_flag(options::files::ALL) {
|
||||||
|
Files::All
|
||||||
|
} else if options.get_flag(options::files::ALMOST_ALL) {
|
||||||
|
Files::AlmostAll
|
||||||
|
} else {
|
||||||
|
Files::Normal
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn extract_sort(options: &clap::ArgMatches) -> Sort {
|
||||||
|
if let Some(field) = options.get_one::<String>(options::SORT) {
|
||||||
|
match field.as_str() {
|
||||||
|
"none" => Sort::None,
|
||||||
|
"name" => Sort::Name,
|
||||||
|
"time" => Sort::Time,
|
||||||
|
"size" => Sort::Size,
|
||||||
|
"version" => Sort::Version,
|
||||||
|
"extension" => Sort::Extension,
|
||||||
|
// below should never happen as clap already restricts the values.
|
||||||
|
_ => unreachable!("Invalid field for --sort"),
|
||||||
|
}
|
||||||
|
} else if options.get_flag(options::sort::TIME) {
|
||||||
|
Sort::Time
|
||||||
|
} else if options.get_flag(options::sort::SIZE) {
|
||||||
|
Sort::Size
|
||||||
|
} else if options.get_flag(options::sort::NONE) {
|
||||||
|
Sort::None
|
||||||
|
} else if options.get_flag(options::sort::VERSION) {
|
||||||
|
Sort::Version
|
||||||
|
} else if options.get_flag(options::sort::EXTENSION) {
|
||||||
|
Sort::Extension
|
||||||
|
} else {
|
||||||
|
Sort::Name
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn extract_time(options: &clap::ArgMatches) -> Time {
|
||||||
|
if let Some(field) = options.get_one::<String>(options::TIME) {
|
||||||
|
match field.as_str() {
|
||||||
|
"ctime" | "status" => Time::Change,
|
||||||
|
"access" | "atime" | "use" => Time::Access,
|
||||||
|
"birth" | "creation" => Time::Birth,
|
||||||
|
// below should never happen as clap already restricts the values.
|
||||||
|
_ => unreachable!("Invalid field for --time"),
|
||||||
|
}
|
||||||
|
} else if options.get_flag(options::time::ACCESS) {
|
||||||
|
Time::Access
|
||||||
|
} else if options.get_flag(options::time::CHANGE) {
|
||||||
|
Time::Change
|
||||||
|
} else {
|
||||||
|
Time::Modification
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn extract_color(options: &clap::ArgMatches) -> bool {
|
||||||
|
match options.get_one::<String>(options::COLOR) {
|
||||||
|
None => options.contains_id(options::COLOR),
|
||||||
|
Some(val) => match val.as_str() {
|
||||||
|
"" | "always" | "yes" | "force" => true,
|
||||||
|
"auto" | "tty" | "if-tty" => std::io::stdout().is_terminal(),
|
||||||
|
/* "never" | "no" | "none" | */ _ => false,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn extract_quoting_style(options: &clap::ArgMatches, show_control: bool) -> QuotingStyle {
|
||||||
|
let opt_quoting_style = options
|
||||||
|
.get_one::<String>(options::QUOTING_STYLE)
|
||||||
|
.map(|cmd_line_qs| cmd_line_qs.to_owned());
|
||||||
|
|
||||||
|
if let Some(style) = opt_quoting_style {
|
||||||
|
match style.as_str() {
|
||||||
|
"literal" => QuotingStyle::Literal { show_control },
|
||||||
|
"shell" => QuotingStyle::Shell {
|
||||||
|
escape: false,
|
||||||
|
always_quote: false,
|
||||||
|
show_control,
|
||||||
|
},
|
||||||
|
"shell-always" => QuotingStyle::Shell {
|
||||||
|
escape: false,
|
||||||
|
always_quote: true,
|
||||||
|
show_control,
|
||||||
|
},
|
||||||
|
"shell-escape" => QuotingStyle::Shell {
|
||||||
|
escape: true,
|
||||||
|
always_quote: false,
|
||||||
|
show_control,
|
||||||
|
},
|
||||||
|
"shell-escape-always" => QuotingStyle::Shell {
|
||||||
|
escape: true,
|
||||||
|
always_quote: true,
|
||||||
|
show_control,
|
||||||
|
},
|
||||||
|
"c" => QuotingStyle::C {
|
||||||
|
quotes: quoting_style::Quotes::Double,
|
||||||
|
},
|
||||||
|
"escape" => QuotingStyle::C {
|
||||||
|
quotes: quoting_style::Quotes::None,
|
||||||
|
},
|
||||||
|
_ => unreachable!("Should have been caught by Clap"),
|
||||||
|
}
|
||||||
|
} else if options.get_flag(options::quoting::LITERAL) {
|
||||||
|
QuotingStyle::Literal { show_control }
|
||||||
|
} else if options.get_flag(options::quoting::ESCAPE) {
|
||||||
|
QuotingStyle::C {
|
||||||
|
quotes: quoting_style::Quotes::None,
|
||||||
|
}
|
||||||
|
} else if options.get_flag(options::quoting::C) {
|
||||||
|
QuotingStyle::C {
|
||||||
|
quotes: quoting_style::Quotes::Double,
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// TODO: use environment variable if available
|
||||||
|
QuotingStyle::Shell {
|
||||||
|
escape: true,
|
||||||
|
always_quote: false,
|
||||||
|
show_control,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn extract_indicator_style(options: &clap::ArgMatches) -> IndicatorStyle {
|
||||||
|
if let Some(field) = options.get_one::<String>(options::INDICATOR_STYLE) {
|
||||||
|
match field.as_str() {
|
||||||
|
"none" => IndicatorStyle::None,
|
||||||
|
"file-type" => IndicatorStyle::FileType,
|
||||||
|
"classify" => IndicatorStyle::Classify,
|
||||||
|
"slash" => IndicatorStyle::Slash,
|
||||||
|
&_ => IndicatorStyle::None,
|
||||||
|
}
|
||||||
|
} else if let Some(field) = options.get_one::<String>(options::indicator_style::CLASSIFY) {
|
||||||
|
match field.as_str() {
|
||||||
|
"never" | "no" | "none" => IndicatorStyle::None,
|
||||||
|
"always" | "yes" | "force" => IndicatorStyle::Classify,
|
||||||
|
"auto" | "tty" | "if-tty" => {
|
||||||
|
if std::io::stdout().is_terminal() {
|
||||||
|
IndicatorStyle::Classify
|
||||||
|
} else {
|
||||||
|
IndicatorStyle::None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
&_ => IndicatorStyle::None,
|
||||||
|
}
|
||||||
|
} else if options.get_flag(options::indicator_style::SLASH) {
|
||||||
|
IndicatorStyle::Slash
|
||||||
|
} else if options.get_flag(options::indicator_style::FILE_TYPE) {
|
||||||
|
IndicatorStyle::FileType
|
||||||
|
} else {
|
||||||
|
IndicatorStyle::None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Config {
|
||||||
|
#[allow(clippy::cognitive_complexity)]
|
||||||
|
pub fn from(options: &clap::ArgMatches) -> UResult<Self> {
|
||||||
|
let context = options.get_flag(options::CONTEXT);
|
||||||
|
let (mut format, opt) = extract_format(options);
|
||||||
|
let files = extract_files(options);
|
||||||
|
|
||||||
// The -o, -n and -g options are tricky. They cannot override with each
|
// The -o, -n and -g options are tricky. They cannot override with each
|
||||||
// other because it's possible to combine them. For example, the option
|
// other because it's possible to combine them. For example, the option
|
||||||
|
@ -504,63 +662,11 @@ impl Config {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let files = if options.get_flag(options::files::ALL) {
|
let sort = extract_sort(options);
|
||||||
Files::All
|
|
||||||
} else if options.get_flag(options::files::ALMOST_ALL) {
|
|
||||||
Files::AlmostAll
|
|
||||||
} else {
|
|
||||||
Files::Normal
|
|
||||||
};
|
|
||||||
|
|
||||||
let sort = if let Some(field) = options.get_one::<String>(options::SORT) {
|
let time = extract_time(options);
|
||||||
match field.as_str() {
|
|
||||||
"none" => Sort::None,
|
|
||||||
"name" => Sort::Name,
|
|
||||||
"time" => Sort::Time,
|
|
||||||
"size" => Sort::Size,
|
|
||||||
"version" => Sort::Version,
|
|
||||||
"extension" => Sort::Extension,
|
|
||||||
// below should never happen as clap already restricts the values.
|
|
||||||
_ => unreachable!("Invalid field for --sort"),
|
|
||||||
}
|
|
||||||
} else if options.get_flag(options::sort::TIME) {
|
|
||||||
Sort::Time
|
|
||||||
} else if options.get_flag(options::sort::SIZE) {
|
|
||||||
Sort::Size
|
|
||||||
} else if options.get_flag(options::sort::NONE) {
|
|
||||||
Sort::None
|
|
||||||
} else if options.get_flag(options::sort::VERSION) {
|
|
||||||
Sort::Version
|
|
||||||
} else if options.get_flag(options::sort::EXTENSION) {
|
|
||||||
Sort::Extension
|
|
||||||
} else {
|
|
||||||
Sort::Name
|
|
||||||
};
|
|
||||||
|
|
||||||
let time = if let Some(field) = options.get_one::<String>(options::TIME) {
|
let mut needs_color = extract_color(options);
|
||||||
match field.as_str() {
|
|
||||||
"ctime" | "status" => Time::Change,
|
|
||||||
"access" | "atime" | "use" => Time::Access,
|
|
||||||
"birth" | "creation" => Time::Birth,
|
|
||||||
// below should never happen as clap already restricts the values.
|
|
||||||
_ => unreachable!("Invalid field for --time"),
|
|
||||||
}
|
|
||||||
} else if options.get_flag(options::time::ACCESS) {
|
|
||||||
Time::Access
|
|
||||||
} else if options.get_flag(options::time::CHANGE) {
|
|
||||||
Time::Change
|
|
||||||
} else {
|
|
||||||
Time::Modification
|
|
||||||
};
|
|
||||||
|
|
||||||
let mut needs_color = match options.get_one::<String>(options::COLOR) {
|
|
||||||
None => options.contains_id(options::COLOR),
|
|
||||||
Some(val) => match val.as_str() {
|
|
||||||
"" | "always" | "yes" | "force" => true,
|
|
||||||
"auto" | "tty" | "if-tty" => std::io::stdout().is_terminal(),
|
|
||||||
/* "never" | "no" | "none" | */ _ => false,
|
|
||||||
},
|
|
||||||
};
|
|
||||||
|
|
||||||
let cmd_line_bs = options.get_one::<String>(options::size::BLOCK_SIZE);
|
let cmd_line_bs = options.get_one::<String>(options::size::BLOCK_SIZE);
|
||||||
let opt_si = cmd_line_bs.is_some()
|
let opt_si = cmd_line_bs.is_some()
|
||||||
|
@ -681,90 +787,8 @@ impl Config {
|
||||||
!std::io::stdout().is_terminal()
|
!std::io::stdout().is_terminal()
|
||||||
};
|
};
|
||||||
|
|
||||||
let opt_quoting_style = options
|
let mut quoting_style = extract_quoting_style(options, show_control);
|
||||||
.get_one::<String>(options::QUOTING_STYLE)
|
let indicator_style = extract_indicator_style(options);
|
||||||
.map(|cmd_line_qs| cmd_line_qs.to_owned());
|
|
||||||
|
|
||||||
let mut quoting_style = if let Some(style) = opt_quoting_style {
|
|
||||||
match style.as_str() {
|
|
||||||
"literal" => QuotingStyle::Literal { show_control },
|
|
||||||
"shell" => QuotingStyle::Shell {
|
|
||||||
escape: false,
|
|
||||||
always_quote: false,
|
|
||||||
show_control,
|
|
||||||
},
|
|
||||||
"shell-always" => QuotingStyle::Shell {
|
|
||||||
escape: false,
|
|
||||||
always_quote: true,
|
|
||||||
show_control,
|
|
||||||
},
|
|
||||||
"shell-escape" => QuotingStyle::Shell {
|
|
||||||
escape: true,
|
|
||||||
always_quote: false,
|
|
||||||
show_control,
|
|
||||||
},
|
|
||||||
"shell-escape-always" => QuotingStyle::Shell {
|
|
||||||
escape: true,
|
|
||||||
always_quote: true,
|
|
||||||
show_control,
|
|
||||||
},
|
|
||||||
"c" => QuotingStyle::C {
|
|
||||||
quotes: quoting_style::Quotes::Double,
|
|
||||||
},
|
|
||||||
"escape" => QuotingStyle::C {
|
|
||||||
quotes: quoting_style::Quotes::None,
|
|
||||||
},
|
|
||||||
_ => unreachable!("Should have been caught by Clap"),
|
|
||||||
}
|
|
||||||
} else if options.get_flag(options::quoting::LITERAL) {
|
|
||||||
QuotingStyle::Literal { show_control }
|
|
||||||
} else if options.get_flag(options::quoting::ESCAPE) {
|
|
||||||
QuotingStyle::C {
|
|
||||||
quotes: quoting_style::Quotes::None,
|
|
||||||
}
|
|
||||||
} else if options.get_flag(options::quoting::C) {
|
|
||||||
QuotingStyle::C {
|
|
||||||
quotes: quoting_style::Quotes::Double,
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
// TODO: use environment variable if available
|
|
||||||
QuotingStyle::Shell {
|
|
||||||
escape: true,
|
|
||||||
always_quote: false,
|
|
||||||
show_control,
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
let indicator_style = if let Some(field) =
|
|
||||||
options.get_one::<String>(options::INDICATOR_STYLE)
|
|
||||||
{
|
|
||||||
match field.as_str() {
|
|
||||||
"none" => IndicatorStyle::None,
|
|
||||||
"file-type" => IndicatorStyle::FileType,
|
|
||||||
"classify" => IndicatorStyle::Classify,
|
|
||||||
"slash" => IndicatorStyle::Slash,
|
|
||||||
&_ => IndicatorStyle::None,
|
|
||||||
}
|
|
||||||
} else if let Some(field) = options.get_one::<String>(options::indicator_style::CLASSIFY) {
|
|
||||||
match field.as_str() {
|
|
||||||
"never" | "no" | "none" => IndicatorStyle::None,
|
|
||||||
"always" | "yes" | "force" => IndicatorStyle::Classify,
|
|
||||||
"auto" | "tty" | "if-tty" => {
|
|
||||||
if std::io::stdout().is_terminal() {
|
|
||||||
IndicatorStyle::Classify
|
|
||||||
} else {
|
|
||||||
IndicatorStyle::None
|
|
||||||
}
|
|
||||||
}
|
|
||||||
&_ => IndicatorStyle::None,
|
|
||||||
}
|
|
||||||
} else if options.get_flag(options::indicator_style::SLASH) {
|
|
||||||
IndicatorStyle::Slash
|
|
||||||
} else if options.get_flag(options::indicator_style::FILE_TYPE) {
|
|
||||||
IndicatorStyle::FileType
|
|
||||||
} else {
|
|
||||||
IndicatorStyle::None
|
|
||||||
};
|
|
||||||
let time_style = parse_time_style(options)?;
|
let time_style = parse_time_style(options)?;
|
||||||
|
|
||||||
let mut ignore_patterns: Vec<Pattern> = Vec::new();
|
let mut ignore_patterns: Vec<Pattern> = Vec::new();
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue