mirror of
https://github.com/sxyazi/yazi.git
synced 2026-07-25 08:41:05 +00:00
refactor and add comment
This commit is contained in:
parent
131e44d7bf
commit
822fdb2bad
1 changed files with 45 additions and 43 deletions
88
core/src/external/shell.rs
vendored
88
core/src/external/shell.rs
vendored
|
|
@ -106,8 +106,45 @@ mod cmdexpand {
|
||||||
Ok(expanded)
|
Ok(expanded)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn escaped_char(input: &str) -> IResult<&str, &str> {
|
fn expand_text<T>(text: &str, args: &[T]) -> Result<String>
|
||||||
recognize(pair(char('\\'), anychar))(input)
|
where
|
||||||
|
T: AsRef<str>,
|
||||||
|
{
|
||||||
|
let quote = if text.starts_with("\"") {
|
||||||
|
Quote::DoubleQuote
|
||||||
|
} else if text.starts_with("'") {
|
||||||
|
Quote::SingleQuote
|
||||||
|
} else {
|
||||||
|
Quote::NoQuote
|
||||||
|
};
|
||||||
|
|
||||||
|
let parts = parse_text(text)?;
|
||||||
|
let mut expanded = String::new();
|
||||||
|
for part in parts {
|
||||||
|
match part {
|
||||||
|
TextPart::NormalText(s) => expanded.push_str(s),
|
||||||
|
TextPart::PercentNumber(i) => {
|
||||||
|
if i > 0 {
|
||||||
|
let replace_text = args
|
||||||
|
.get(i - 1)
|
||||||
|
.map(|content| preprocess(content.as_ref(), quote))
|
||||||
|
.unwrap_or_default();
|
||||||
|
expanded.push_str(&replace_text);
|
||||||
|
} else {
|
||||||
|
// Does not support %0, replace it with ""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
TextPart::PercentStar => {
|
||||||
|
for (i, arg) in args.iter().enumerate() {
|
||||||
|
expanded.push_str(&preprocess(arg.as_ref(), quote));
|
||||||
|
if i + 1 < args.len() {
|
||||||
|
expanded.push_str(" ");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Ok(expanded)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn parse_cmd(cmd: &str) -> Result<Vec<CommandPart>> {
|
fn parse_cmd(cmd: &str) -> Result<Vec<CommandPart>> {
|
||||||
|
|
@ -145,48 +182,11 @@ mod cmdexpand {
|
||||||
Ok(parts)
|
Ok(parts)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn expand_text<T>(text: &str, args: &[T]) -> Result<String>
|
|
||||||
where
|
|
||||||
T: AsRef<str>,
|
|
||||||
{
|
|
||||||
let quote = if text.starts_with("\"") {
|
|
||||||
Quote::DoubleQuote
|
|
||||||
} else if text.starts_with("'") {
|
|
||||||
Quote::SingleQuote
|
|
||||||
} else {
|
|
||||||
Quote::NoQuote
|
|
||||||
};
|
|
||||||
|
|
||||||
let parts = parse_text(text)?;
|
|
||||||
let mut expanded = String::new();
|
|
||||||
for part in parts {
|
|
||||||
match part {
|
|
||||||
TextPart::NormalText(s) => expanded.push_str(s),
|
|
||||||
TextPart::PercentNumber(i) => {
|
|
||||||
if i > 0 {
|
|
||||||
let replace_text = args
|
|
||||||
.get(i - 1)
|
|
||||||
.map(|content| preprocess(content.as_ref(), quote))
|
|
||||||
.unwrap_or_default();
|
|
||||||
expanded.push_str(&replace_text);
|
|
||||||
} else {
|
|
||||||
// Not sure what to do with %0
|
|
||||||
}
|
|
||||||
}
|
|
||||||
TextPart::PercentStar => {
|
|
||||||
for (i, arg) in args.iter().enumerate() {
|
|
||||||
expanded.push_str(&preprocess(arg.as_ref(), quote));
|
|
||||||
if i + 1 < args.len() {
|
|
||||||
expanded.push_str(" ");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Ok(expanded)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn parse_text(text: &str) -> Result<Vec<TextPart>> {
|
fn parse_text(text: &str) -> Result<Vec<TextPart>> {
|
||||||
|
fn escaped_char(input: &str) -> IResult<&str, &str> {
|
||||||
|
recognize(pair(char('\\'), anychar))(input)
|
||||||
|
}
|
||||||
|
|
||||||
fn normal_text(input: &str) -> IResult<&str, TextPart> {
|
fn normal_text(input: &str) -> IResult<&str, TextPart> {
|
||||||
let (input, output) = recognize(many1(alt((escaped_char, is_not("\\%")))))(input)?;
|
let (input, output) = recognize(many1(alt((escaped_char, is_not("\\%")))))(input)?;
|
||||||
Ok((input, TextPart::NormalText(output)))
|
Ok((input, TextPart::NormalText(output)))
|
||||||
|
|
@ -208,6 +208,8 @@ mod cmdexpand {
|
||||||
Ok(parts)
|
Ok(parts)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Preprocess the content inside %x before replacing it in the command text
|
||||||
|
// to make sure white space and quote inside %x does not mess up the command.
|
||||||
fn preprocess(content: &str, quote: Quote) -> String {
|
fn preprocess(content: &str, quote: Quote) -> String {
|
||||||
let inner_space = content.chars().any(|c| c.is_whitespace());
|
let inner_space = content.chars().any(|c| c.is_whitespace());
|
||||||
match (quote, inner_space) {
|
match (quote, inner_space) {
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue