1use core::fmt::Debug;
2use std::{
3 eprintln,
4 process::{Command, Stdio},
5};
6
7use alloc::{boxed::Box, format, string::String};
8
9use crate::workflow_getter;
10
11#[derive(Debug)]
12pub enum Error {
13 FailedToExecuteCommand(std::io::Error),
14 CommandListTooShort { name: String },
15 Other(Box<dyn std::error::Error>),
16}
17
18impl core::fmt::Display for Error {
19 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
20 match self {
21 Self::FailedToExecuteCommand(e) => write!(f, "Failed to execute command: {}", e),
22 Self::CommandListTooShort { name } => {
23 write!(f, "Command list is empty in {} (workspaces.toml)", name)
24 }
25 Self::Other(e) => write!(f, "{e}"),
26 }
27 }
28}
29
30impl std::error::Error for Error {}
31
32pub fn run(workflow_name: &str, debug: bool) -> Result<(), Error> {
34 let workflow = match workflow_getter::get_workflow(workflow_name) {
35 Ok(v) => v,
36 Err(e) => return Err(Error::Other(Box::new(e))),
37 };
38
39 let (env, commands) = (workflow.env, workflow.commands);
40
41 let env = env.unwrap_or(Default::default());
42
43 for (k, v) in commands {
44 if debug {
45 eprintln!("[running \"{}\"]", k)
46 }
47 if v.is_empty() {
48 return Err(Error::CommandListTooShort {
49 name: format!("{}.{}", workflow_name, k),
50 });
51 }
52
53 let _output = match Command::new(&v[0])
54 .args(&v[1..])
55 .envs(&env)
56 .stdin(Stdio::inherit())
57 .stdout(Stdio::inherit())
58 .stderr(Stdio::inherit())
59 .output()
60 {
61 Ok(v) => v,
62 Err(e) => return Err(Error::FailedToExecuteCommand(e)),
63 };
64 }
65
66 Ok(())
67}