Skip to main content

contract_cli/
output.rs

1use std::io::IsTerminal;
2
3use crate::error::AppError;
4
5#[derive(Clone, Copy, Debug)]
6pub enum Format {
7    Json,
8    Human,
9}
10
11impl Format {
12    pub fn detect(json_flag: bool) -> Self {
13        if json_flag || !std::io::stdout().is_terminal() {
14            Format::Json
15        } else {
16            Format::Human
17        }
18    }
19}
20
21#[derive(Clone, Copy)]
22pub struct Ctx {
23    pub format: Format,
24    pub quiet: bool,
25}
26
27impl Ctx {
28    pub fn new(json_flag: bool, quiet: bool) -> Self {
29        Self {
30            format: Format::detect(json_flag),
31            quiet,
32        }
33    }
34}
35
36pub fn print_success<T, F>(ctx: Ctx, data: &T, human: F)
37where
38    T: serde::Serialize,
39    F: FnOnce(&T),
40{
41    match ctx.format {
42        Format::Json => {
43            let envelope = serde_json::json!({
44                "version": "1",
45                "status": "success",
46                "data": data,
47            });
48            println!("{}", serde_json::to_string_pretty(&envelope).unwrap());
49        }
50        Format::Human if !ctx.quiet => human(data),
51        Format::Human => {}
52    }
53}
54
55pub fn print_error(format: Format, err: &AppError) {
56    match format {
57        Format::Json => {
58            let envelope = serde_json::json!({
59                "version": "1",
60                "status": "error",
61                "error": {
62                    "code": err.error_code(),
63                    "message": err.to_string(),
64                    "suggestion": err.suggestion(),
65                },
66            });
67            eprintln!("{}", serde_json::to_string_pretty(&envelope).unwrap());
68        }
69        Format::Human => {
70            eprintln!("error: {}", err);
71            let hint = err.suggestion();
72            if !hint.is_empty() {
73                eprintln!("  hint: {}", hint);
74            }
75        }
76    }
77}
78
79pub fn print_raw<T: serde::Serialize>(value: &T) {
80    println!("{}", serde_json::to_string_pretty(value).unwrap());
81}