pub mod doctor;
pub mod lifecycle;
pub mod run;
pub mod shutdown;
use std::path::PathBuf;
use std::process::ExitCode;
use clap::{Parser, Subcommand};
use crate::workflow::Workflow;
use crate::workflow::loader::WorkflowSchemaLoader;
#[derive(Debug, Parser)]
#[command(
name = "vik",
version,
about = "Vik runs workflow-driven agents for issue tracker work.",
long_about = None,
override_usage = "vik <COMMAND> [WORKFLOW]",
)]
struct Cli {
#[arg(value_name = "WORKFLOW", default_value = "./workflow.yml", global = true)]
workflow: PathBuf,
#[command(subcommand)]
command: Command,
}
#[derive(Debug, Subcommand)]
enum Command {
Doctor(doctor::DoctorArgs),
Run(run::RunArgs),
Status(lifecycle::LifecycleArgs),
Stop(lifecycle::LifecycleArgs),
Restart(lifecycle::RestartArgs),
Uninstall(lifecycle::LifecycleArgs),
}
pub fn run() -> ExitCode {
let cli = match Cli::try_parse() {
Ok(cli) => cli,
Err(err) => {
let _ = err.print();
if err.use_stderr() {
return ExitCode::from(2);
}
return ExitCode::SUCCESS;
},
};
let loaded = match WorkflowSchemaLoader.load(&cli.workflow) {
Ok(loaded) => loaded,
Err(err) => {
eprintln!("{err}");
return ExitCode::from(1);
},
};
match cli.command {
Command::Doctor(args) => doctor::execute(loaded, args),
command => {
let workflow = match Workflow::try_from(loaded) {
Ok(workflow) => workflow,
Err(err) => {
eprintln!("{err}");
return ExitCode::from(1);
},
};
match command {
Command::Run(args) => run::execute(workflow, args),
Command::Status(args) => lifecycle::status(workflow, args),
Command::Stop(args) => lifecycle::stop(workflow, args),
Command::Restart(args) => lifecycle::restart(workflow, args),
Command::Uninstall(args) => lifecycle::uninstall(workflow, args),
Command::Doctor(_) => unreachable!("doctor command already handled"),
}
},
}
}