use crate::*;
pub(crate) use inner_impl::*;
use colored::Colorize;
#[cfg(target_family = "windows")]
mod inner_impl {
use super::*;
use std::borrow::Cow;
use std::collections::BTreeMap;
use std::io::Write;
use std::process::{Command, Output, Stdio};
pub(crate) fn process_input_inner(
example_files: BTreeMap<Cow<'_, str>, ExampleFile>,
dir: &Paths,
args: Args,
) -> Result<()> {
let script_args = args.args;
let mut cfg: ReplayConfig = Default::default();
let output: Output;
let examples_to_run = if args.replay {
cfg = get_last_replay()?;
vec![Cow::Owned(cfg.last_run.name)]
} else if let Some(example) = args.name {
vec![Cow::Owned(example)]
} else {
let example_names: String = example_files
.keys()
.map(|k| k.as_ref())
.collect::<Vec<_>>()
.join("\n");
let mut child = Command::new(FZF_CMD)
.stdin(Stdio::piped())
.stdout(Stdio::piped())
.arg("-m")
.spawn()
.expect("Failed to spawn child process");
let mut stdin = child.stdin.take().expect("Failed to open stdin");
std::thread::spawn(move || {
stdin
.write_all(example_names.as_bytes())
.expect("Failed to write to stdin");
});
output = child.wait_with_output().expect("Failed to read stdout");
std::str::from_utf8(&output.stdout)?
.split_terminator('\n')
.map(Cow::Borrowed)
.collect()
};
let words: Vec<String>;
let example_args = if args.replay {
cfg.last_run.arguments.iter().map(String::as_str).collect()
} else if !script_args.is_empty() {
let mut extra_args = Vec::with_capacity(script_args.len() + 1);
extra_args.push("--");
for arg in script_args.iter() {
extra_args.push(arg);
}
extra_args
} else if args.input_args {
print!("{} ", "Arguments:".cyan().bold());
std::io::stdout().flush()?;
let mut line = String::new();
std::io::stdin().read_line(&mut line)?;
words = shellwords::split(line.trim_end())?;
let mut extra_args = Vec::with_capacity(words.len() + 1);
extra_args.push("--");
for arg in words.iter() {
extra_args.push(arg);
}
extra_args
} else {
Vec::default()
};
let example_args_ref = &example_args;
let root_ref = &dir.root_path;
match examples_to_run.first() {
Some(name) if !args.replay => {
save_last_replay(name, example_args_ref)?;
}
_ => {}
};
for example_name in examples_to_run {
let name = example_name.as_ref();
let example = example_files.get(name).unwrap();
args.cargo.run_example(
&example.path_type,
root_ref,
name,
example_args_ref,
&example.required_features,
)?;
}
Ok(())
}
}
#[cfg(not(target_family = "windows"))]
mod inner_impl {
use super::*;
use std::borrow::Cow;
use std::collections::BTreeMap;
use std::io::Write;
use std::sync::Arc;
use skim::prelude::*;
pub(crate) fn process_input_inner(
example_files: BTreeMap<Cow<'_, str>, ExampleFile>,
dir: &Paths,
args: Args,
) -> Result<()> {
let script_args = args.args;
let selected_items: Vec<Arc<dyn SkimItem>>;
let mut cfg: ReplayConfig = Default::default();
let examples_to_run = if args.replay {
cfg = get_last_replay()?;
vec![Cow::Owned(cfg.last_run.name)]
} else if let Some(example) = args.name {
vec![Cow::Owned(example)]
} else {
let options = SkimOptionsBuilder::default()
.preview_window(Some("right:70%"))
.multi(true)
.preview(Some("")) .build()
.unwrap();
let (tx_item, rx_item): (SkimItemSender, SkimItemReceiver) = unbounded();
for example in example_files.values() {
let _ = tx_item.send(Arc::new(ExampleFileItem {
file_stem: example.name.clone(),
file_path: example.path.clone(),
}));
}
drop(tx_item);
selected_items = Skim::run_with(&options, Some(rx_item))
.map(|out| {
if out.is_abort {
std::process::exit(0);
}
out.selected_items
})
.unwrap_or_else(Vec::new);
selected_items
.iter()
.map(|item| item.text())
.collect::<Vec<_>>()
};
let words: Vec<String>;
let example_args = if args.replay {
cfg.last_run.arguments.iter().map(String::as_str).collect()
} else if !script_args.is_empty() {
let mut extra_args = Vec::with_capacity(script_args.len() + 1);
extra_args.push("--");
for arg in script_args.iter() {
extra_args.push(arg);
}
extra_args
} else if args.input_args {
print!("{} ", "Arguments:".cyan().bold());
std::io::stdout().flush()?;
let mut line = String::new();
std::io::stdin().read_line(&mut line)?;
words = shellwords::split(line.trim_end())?;
let mut extra_args = Vec::with_capacity(words.len() + 1);
extra_args.push("--");
for arg in words.iter() {
extra_args.push(arg);
}
extra_args
} else {
Vec::default()
};
let example_args_ref = &example_args;
let root_ref = &dir.root_path;
match examples_to_run.first() {
Some(name) if !args.replay => {
save_last_replay(name, example_args_ref)?;
}
_ => {}
};
for example_name in examples_to_run {
let name = example_name.as_ref();
let example = example_files.get(name).unwrap();
args.cargo.run_example(
&example.path_type,
root_ref,
name,
example_args_ref,
&example.required_features,
)?;
}
Ok(())
}
}