Skip to main content

vv_agent/runtime/shell/
command.rs

1use super::{resolve_shell_invocation, PreparedShellCommand};
2
3const WINDOWS_AUTO_CONFIRM_LINES: usize = 512;
4
5pub fn build_shell_invocation(
6    command: &str,
7    shell: Option<&str>,
8    windows_shell_priority: Option<&[String]>,
9) -> Result<Vec<String>, String> {
10    let resolved = resolve_shell_invocation(shell, windows_shell_priority)?;
11    let mut invocation = resolved.prefix;
12    invocation.push(command.to_string());
13    Ok(invocation)
14}
15
16pub fn prepare_shell_execution(
17    command: &str,
18    auto_confirm: bool,
19    stdin: Option<&str>,
20    shell: Option<&str>,
21    windows_shell_priority: Option<&[String]>,
22) -> Result<PreparedShellCommand, String> {
23    let resolved = resolve_shell_invocation(shell, windows_shell_priority)?;
24    if !auto_confirm {
25        let mut prepared = resolved.prefix.clone();
26        prepared.push(command.to_string());
27        return Ok(PreparedShellCommand {
28            kind: resolved.kind,
29            command: prepared,
30            shell: Some(resolved.name),
31            stdin: stdin.map(str::to_string),
32        });
33    }
34
35    if resolved.kind == "bash" {
36        let mut prepared = resolved.prefix.clone();
37        prepared.push(format!("yes | ({command})"));
38        Ok(PreparedShellCommand {
39            kind: resolved.kind,
40            command: prepared,
41            shell: Some(resolved.name),
42            stdin: stdin.map(str::to_string),
43        })
44    } else {
45        let mut prepared = resolved.prefix.clone();
46        prepared.push(command.to_string());
47        Ok(PreparedShellCommand {
48            kind: resolved.kind,
49            command: prepared,
50            shell: Some(resolved.name),
51            stdin: Some(format!(
52                "{}{}",
53                "y\n".repeat(WINDOWS_AUTO_CONFIRM_LINES),
54                stdin.unwrap_or("")
55            )),
56        })
57    }
58}