fix bash commands being incorrectly quoted in display (#2313)
The "display format" of commands was sometimes producing incorrect quoting like `echo foo '>' bar`, which is importantly different from the actual command that was being run. This refactors ParsedCommand to have a string in `cmd` instead of a vec, as a `vec` can't accurately capture a full command.
This commit is contained in:
File diff suppressed because it is too large
Load Diff
@@ -206,7 +206,7 @@ fn exec_history_cell_shows_working_then_completed() {
|
|||||||
command: vec!["bash".into(), "-lc".into(), "echo done".into()],
|
command: vec!["bash".into(), "-lc".into(), "echo done".into()],
|
||||||
cwd: std::env::current_dir().unwrap_or_else(|_| PathBuf::from(".")),
|
cwd: std::env::current_dir().unwrap_or_else(|_| PathBuf::from(".")),
|
||||||
parsed_cmd: vec![codex_core::parse_command::ParsedCommand::Unknown {
|
parsed_cmd: vec![codex_core::parse_command::ParsedCommand::Unknown {
|
||||||
cmd: vec!["echo".into(), "done".into()],
|
cmd: "echo done".into(),
|
||||||
}],
|
}],
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
@@ -248,7 +248,7 @@ fn exec_history_cell_shows_working_then_failed() {
|
|||||||
command: vec!["bash".into(), "-lc".into(), "false".into()],
|
command: vec!["bash".into(), "-lc".into(), "false".into()],
|
||||||
cwd: std::env::current_dir().unwrap_or_else(|_| PathBuf::from(".")),
|
cwd: std::env::current_dir().unwrap_or_else(|_| PathBuf::from(".")),
|
||||||
parsed_cmd: vec![codex_core::parse_command::ParsedCommand::Unknown {
|
parsed_cmd: vec![codex_core::parse_command::ParsedCommand::Unknown {
|
||||||
cmd: vec!["false".into()],
|
cmd: "false".into(),
|
||||||
}],
|
}],
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -248,18 +248,19 @@ fn new_parsed_command(
|
|||||||
ParsedCommand::Read { name, .. } => format!("📖 {name}"),
|
ParsedCommand::Read { name, .. } => format!("📖 {name}"),
|
||||||
ParsedCommand::ListFiles { cmd, path } => match path {
|
ParsedCommand::ListFiles { cmd, path } => match path {
|
||||||
Some(p) => format!("📂 {p}"),
|
Some(p) => format!("📂 {p}"),
|
||||||
None => format!("📂 {}", shlex_join_safe(cmd)),
|
None => format!("📂 {cmd}"),
|
||||||
},
|
},
|
||||||
ParsedCommand::Search { query, path, cmd } => match (query, path) {
|
ParsedCommand::Search { query, path, cmd } => match (query, path) {
|
||||||
(Some(q), Some(p)) => format!("🔎 {q} in {p}"),
|
(Some(q), Some(p)) => format!("🔎 {q} in {p}"),
|
||||||
(Some(q), None) => format!("🔎 {q}"),
|
(Some(q), None) => format!("🔎 {q}"),
|
||||||
(None, Some(p)) => format!("🔎 {p}"),
|
(None, Some(p)) => format!("🔎 {p}"),
|
||||||
(None, None) => format!("🔎 {}", shlex_join_safe(cmd)),
|
(None, None) => format!("🔎 {cmd}"),
|
||||||
},
|
},
|
||||||
ParsedCommand::Format { .. } => "✨ Formatting".to_string(),
|
ParsedCommand::Format { .. } => "✨ Formatting".to_string(),
|
||||||
ParsedCommand::Test { cmd } => format!("🧪 {}", shlex_join_safe(cmd)),
|
ParsedCommand::Test { cmd } => format!("🧪 {cmd}"),
|
||||||
ParsedCommand::Lint { cmd, .. } => format!("🧹 {}", shlex_join_safe(cmd)),
|
ParsedCommand::Lint { cmd, .. } => format!("🧹 {cmd}"),
|
||||||
ParsedCommand::Unknown { cmd } => format!("⌨️ {}", shlex_join_safe(cmd)),
|
ParsedCommand::Unknown { cmd } => format!("⌨️ {cmd}"),
|
||||||
|
ParsedCommand::Noop { cmd } => format!("🔄 {cmd}"),
|
||||||
};
|
};
|
||||||
|
|
||||||
let first_prefix = if i == 0 { " └ " } else { " " };
|
let first_prefix = if i == 0 { " └ " } else { " " };
|
||||||
@@ -856,13 +857,6 @@ fn format_mcp_invocation<'a>(invocation: McpInvocation) -> Line<'a> {
|
|||||||
Line::from(invocation_spans)
|
Line::from(invocation_spans)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn shlex_join_safe(command: &[String]) -> String {
|
|
||||||
match shlex::try_join(command.iter().map(|s| s.as_str())) {
|
|
||||||
Ok(cmd) => cmd,
|
|
||||||
Err(_) => command.join(" "),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use super::*;
|
use super::*;
|
||||||
@@ -870,7 +864,7 @@ mod tests {
|
|||||||
#[test]
|
#[test]
|
||||||
fn parsed_command_with_newlines_starts_each_line_at_origin() {
|
fn parsed_command_with_newlines_starts_each_line_at_origin() {
|
||||||
let parsed = vec![ParsedCommand::Unknown {
|
let parsed = vec![ParsedCommand::Unknown {
|
||||||
cmd: vec!["printf".into(), "foo\nbar".into()],
|
cmd: "printf 'foo\nbar'".to_string(),
|
||||||
}];
|
}];
|
||||||
let lines = exec_command_lines(&[], &parsed, None);
|
let lines = exec_command_lines(&[], &parsed, None);
|
||||||
assert!(lines.len() >= 3);
|
assert!(lines.len() >= 3);
|
||||||
|
|||||||
Reference in New Issue
Block a user