pub fn build_shell_command(parts: &[&str], values: &[&str]) -> String {
let mut result = String::new();
let context_aware = crate::quote::is_quote_context_enabled();
let mut context = crate::quote::QuoteContext::Unquoted;
for (i, part) in parts.iter().enumerate() {
result.push_str(part);
if context_aware {
context = crate::quote::scan_quote_context(part, context);
}
if i < values.len() {
result.push_str(&crate::quote::quote_for_context(values[i], context));
}
}
crate::quote::warn_on_split_template(&result);
result
}
pub fn create_runner(command: String) -> crate::ProcessRunner {
crate::ProcessRunner::new(
command,
crate::RunOptions {
mirror: true,
capture: true,
..Default::default()
},
)
}
pub fn create_runner_with_options(
command: String,
options: crate::RunOptions,
) -> crate::ProcessRunner {
crate::ProcessRunner::new(command, options)
}
#[macro_export]
macro_rules! cmd {
($cmd:expr) => {{
async {
$crate::run($cmd).await
}
}};
($fmt:expr, $($arg:expr),+ $(,)?) => {{
let mut result = String::new();
let values: Vec<String> = vec![$(format!("{}", $arg)),+];
let values_ref: Vec<&str> = values.iter().map(|s| s.as_str()).collect();
let fmt_parts: Vec<&str> = $fmt.split("{}").collect();
let context_aware = $crate::quote::is_quote_context_enabled();
let mut context = $crate::quote::QuoteContext::Unquoted;
for (i, part) in fmt_parts.iter().enumerate() {
result.push_str(part);
if context_aware {
context = $crate::quote::scan_quote_context(part, context);
}
if i < values_ref.len() {
result.push_str(&$crate::quote::quote_for_context(values_ref[i], context));
}
}
$crate::quote::warn_on_split_template(&result);
async move {
$crate::run(result).await
}
}};
}
#[macro_export]
macro_rules! sh {
($($args:tt)*) => {
$crate::cmd!($($args)*)
};
}
#[macro_export]
macro_rules! s {
($($args:tt)*) => {
$crate::cmd!($($args)*)
};
}
#[macro_export]
macro_rules! cs {
($($args:tt)*) => {
$crate::cmd!($($args)*)
};
}