use std::process::{Command, ExitStatus}; use crate::result::Result; #[derive(Clone, Debug, Deserialize)] pub struct App { pub name: String, pub command: String, pub args: Vec, pub restart_on_success: Option, pub restart_on_failure: Option, pub restart_on_terminate: Option, pub wait: Option, pub hold: Option, } impl App { pub fn wait_start(&self) -> Result<()> { info!("starting application {}", &self.name); let mut command = Command::new(&self.command); command.args(&self.args); match command.output() { Ok(output) => { if !output.stdout.is_empty() { let s = String::from_utf8(output.stdout)?; for line in s.lines() { info!("[{}] stdout: {}", &self.name, line); } } if !output.stderr.is_empty() { let s = String::from_utf8(output.stderr)?; for line in s.lines() { info!("[{}] stderr: {}", &self.name, line); } } Ok(()) } Err(e) => Err(Box::from(e)), } } pub fn handle_exit(&self, status: ExitStatus) -> bool { if status.success() { info!("application exited: {}", &self.name); self.restart_on_success.unwrap_or(false) } else if let Some(code) = status.code() { info!("application failed: {} ({})", &self.name, code); self.restart_on_failure.unwrap_or(false) } else { info!("application terminated: {}", &self.name); self.restart_on_terminate.unwrap_or(false) } } }