stellar_xdr/cli/generate/
default.rs1use clap::{Args, ValueEnum};
2use std::{
3 io::{stdout, Write},
4 str::FromStr,
5};
6
7use crate::cli::util;
8
9#[derive(thiserror::Error, Debug)]
10pub enum Error {
11 #[error("unknown type {0}, choose one of {1:?}")]
12 UnknownType(String, &'static [&'static str]),
13 #[error("error reading file: {0}")]
14 ReadFile(#[from] std::io::Error),
15 #[error("error generating XDR: {0}")]
16 WriteXdr(#[from] crate::Error),
17 #[error("error generating JSON: {0}")]
18 GenerateJson(#[from] serde_json::Error),
19 #[error("type doesn't have a text representation, use 'json' as output")]
20 TextUnsupported,
21}
22
23#[derive(Args, Debug, Clone)]
25#[command()]
26pub struct Cmd {
27 #[arg(long)]
29 pub r#type: String,
30
31 #[arg(long = "output", value_enum, default_value_t)]
33 pub output_format: OutputFormat,
34}
35
36#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq, ValueEnum)]
37pub enum OutputFormat {
38 Single,
39 SingleBase64,
40 Json,
44 JsonFormatted,
45 Text,
46}
47
48impl Default for OutputFormat {
49 fn default() -> Self {
50 Self::SingleBase64
51 }
52}
53
54macro_rules! run_x {
57 ($f:ident) => {
58 fn $f(&self) -> Result<(), Error> {
59 use crate::WriteXdr;
60 let r#type = crate::TypeVariant::from_str(&self.r#type).map_err(|_| {
61 Error::UnknownType(self.r#type.clone(), &crate::TypeVariant::VARIANTS_STR)
62 })?;
63 let v = crate::Type::default(r#type);
64 match self.output_format {
65 OutputFormat::Single => {
66 let l = crate::Limits::none();
67 stdout().write_all(&v.to_xdr(l)?)?
68 }
69 OutputFormat::SingleBase64 => {
70 let l = crate::Limits::none();
71 println!("{}", v.to_xdr_base64(l)?)
72 }
73 OutputFormat::Json => {
74 println!("{}", serde_json::to_string(&v)?);
75 }
76 OutputFormat::JsonFormatted => {
77 println!("{}", serde_json::to_string_pretty(&v)?);
78 }
79 OutputFormat::Text => {
80 let v = serde_json::to_value(v)?;
81 let text = util::serde_json_value_to_text(v).ok_or(Error::TextUnsupported)?;
82 println!("{text}")
83 }
84 }
85 Ok(())
86 }
87 };
88}
89
90impl Cmd {
91 pub fn run(&self) -> Result<(), Error> {
97 self.run_inner()
98 }
99
100 run_x!(run_inner);
101}