snarkos_aot/program/
mod.rs

1use anyhow::Result;
2use clap::{Args, Subcommand};
3use clap_stdin::FileOrStdin;
4use serde_json::json;
5use snarkvm::synthesizer::Program;
6
7use crate::Network;
8pub mod cost;
9
10/// A command to help gather information about a program, including its cost and
11/// imports.
12#[derive(Debug, Subcommand)]
13pub enum ProgramCommand<N: Network> {
14    /// Get the ID of a given program.
15    Id(ProgramInfo<N>),
16    /// List the functions and their inputs/outputs of a given program.
17    #[clap(alias = "fn")]
18    Functions(ProgramInfo<N>),
19    /// List the inputs of a given program.
20    Imports(ProgramInfo<N>),
21    Cost(cost::CostCommand<N>),
22}
23
24impl<N: Network> ProgramCommand<N> {
25    pub fn parse(self) -> Result<()> {
26        match self {
27            ProgramCommand::Id(ProgramInfo { program, json }) => {
28                if json {
29                    println!("{}", serde_json::to_string(&program.contents()?.id())?);
30                } else {
31                    println!("{}", program.contents()?.id());
32                }
33                Ok(())
34            }
35            ProgramCommand::Functions(ProgramInfo { program, json }) => {
36                let program = program.contents()?;
37                if json {
38                    let mut functions = indexmap::IndexMap::new();
39                    for (id, function) in program.functions() {
40                        functions.insert(
41                            id,
42                            json!({
43                                "inputs": function.input_types(),
44                                "outputs": function.output_types(),
45                            }),
46                        );
47                    }
48                    println!("{}", serde_json::to_string(&functions)?);
49                } else {
50                    for (id, function) in program.functions() {
51                        println!("name: {id}");
52                        println!("inputs:");
53                        for input in function.input_types() {
54                            println!("  {input}");
55                        }
56                        println!("outputs:");
57                        for output in &function.output_types() {
58                            println!("  {output}");
59                        }
60                        println!();
61                    }
62                }
63                Ok(())
64            }
65            ProgramCommand::Imports(ProgramInfo { program, json }) => {
66                let program = program.contents()?;
67                if json {
68                    println!(
69                        "{}",
70                        serde_json::to_string(&program.imports().keys().collect::<Vec<_>>())?
71                    );
72                } else {
73                    for (id, _import) in program.imports() {
74                        println!("{id}");
75                    }
76                }
77                Ok(())
78            }
79            ProgramCommand::Cost(command) => {
80                println!("{}", command.parse()?);
81                Ok(())
82            }
83        }
84    }
85}
86
87#[derive(Debug, Args)]
88pub struct ProgramInfo<N: Network> {
89    /// Path to .aleo program to get information about, or `-` for stdin.
90    pub program: FileOrStdin<Program<N>>,
91    /// Output as JSON
92    #[clap(long, short)]
93    pub json: bool,
94}