cat_gateway/
cli.rs

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
//! CLI interpreter for the service
use std::io::Write;

use clap::Parser;
use tracing::{error, info};

use crate::{
    cardano::start_followers,
    db::{self, index::session::CassandraSession},
    service::{self, started},
    settings::{DocsSettings, ServiceSettings, Settings},
};

#[derive(Parser)]
#[clap(rename_all = "kebab-case")]
/// Simple service CLI options
pub(crate) enum Cli {
    /// Run the service
    Run(ServiceSettings),
    /// Build API docs of the service in the JSON format
    Docs(DocsSettings),
}

impl Cli {
    /// Execute the specified operation.
    ///
    /// This method is asynchronous and returns a `Result` indicating whether the
    /// operation was successful or if an error occurred.
    ///
    /// # Errors
    ///
    /// This method can return an error if:
    ///
    /// - Failed to initialize the logger with the specified log level.
    /// - Failed to create a new `State` with the provided database URL.
    /// - Failed to run the service on the specified address.
    pub(crate) async fn exec(self) -> anyhow::Result<()> {
        match self {
            Self::Run(settings) => {
                Settings::init(settings)?;

                let mut tasks = Vec::new();

                info!("Catalyst Gateway - Starting");

                // Start the DB's
                CassandraSession::init();
                db::event::establish_connection();

                // Start the chain indexing follower.
                start_followers().await?;

                let handle = tokio::spawn(async move {
                    match service::run().await {
                        Ok(()) => info!("Endpoints started ok"),
                        Err(err) => {
                            error!("Error starting endpoints {err}");
                        },
                    }
                });
                tasks.push(handle);

                started();

                for task in tasks {
                    task.await?;
                }

                info!("Catalyst Gateway - Shut Down");
            },
            Self::Docs(settings) => {
                let docs = service::get_app_docs();
                match settings.output {
                    Some(path) => {
                        let mut docs_file = std::fs::File::create(path)?;
                        docs_file.write_all(docs.as_bytes())?;
                    },
                    None => println!("{docs}"),
                }
            },
        }

        Ok(())
    }
}