1use anyhow::Context;
2use clap::{CommandFactory, Parser, Subcommand};
3
4pub mod build;
5pub mod new;
6mod plugin;
7
8#[derive(Parser, Debug)]
9#[command(
10 name = "pint",
11 about = "Pint's package manager and CLI plugin host",
12 version
13)]
14pub struct Pint {
15 #[command(subcommand)]
16 cmd: Cmd,
17}
18
19#[derive(Debug, Subcommand)]
20enum Cmd {
21 #[command(alias = "b")]
22 Build(build::Args),
23 New(new::Args),
24 Plugins,
26 #[clap(external_subcommand)]
31 Plugin(Vec<String>),
32}
33
34fn print_help_output() -> anyhow::Result<()> {
36 let mut cli = Pint::command();
37 cli.print_help()?;
38 Ok(())
39}
40
41pub fn run(pint: Pint) -> anyhow::Result<()> {
43 match pint.cmd {
44 Cmd::New(arg) => new::cmd(arg),
45 Cmd::Build(arg) => {
46 let (_plan, _built_pkgs) = build::cmd(arg)?;
47 Ok(())
48 }
49 Cmd::Plugins => {
50 plugin::print_all();
51 Ok(())
52 }
53 Cmd::Plugin(args) if !args.is_empty() => {
54 let Some(plugin_exe_path) = plugin::find_exe(&args[0]) else {
55 print_help_output()?;
57 anyhow::bail!("no known command or plugin {:?}", &args[0]);
58 };
59 let output = plugin::exec(&plugin_exe_path, &args[1..])?;
60 std::process::exit(output.status.code().context("unknown exit status")?);
61 }
62 _ => print_help_output(),
63 }
64}