rustic_rs/commands/
cat.rs

1//! `cat` subcommand
2
3use crate::{status_err, Application, RUSTIC_APP};
4
5use abscissa_core::{Command, Runnable, Shutdown};
6
7use anyhow::Result;
8
9use rustic_core::repofile::{BlobType, FileType};
10
11/// `cat` subcommand
12///
13/// Output the contents of a file or blob
14#[derive(clap::Parser, Command, Debug)]
15pub(crate) struct CatCmd {
16    #[clap(subcommand)]
17    cmd: CatSubCmd,
18}
19
20/// `cat` subcommands
21#[derive(clap::Subcommand, Debug)]
22enum CatSubCmd {
23    /// Display a tree blob
24    TreeBlob(IdOpt),
25    /// Display a data blob
26    DataBlob(IdOpt),
27    /// Display the config file
28    Config,
29    /// Display an index file
30    Index(IdOpt),
31    /// Display a snapshot file
32    Snapshot(IdOpt),
33    /// Display a tree within a snapshot
34    Tree(TreeOpts),
35}
36
37#[derive(Default, clap::Parser, Debug)]
38struct IdOpt {
39    /// Id to display
40    id: String,
41}
42
43#[derive(clap::Parser, Debug)]
44struct TreeOpts {
45    /// Snapshot/path of the tree to display
46    #[clap(value_name = "SNAPSHOT[:PATH]")]
47    snap: String,
48}
49
50impl Runnable for CatCmd {
51    fn run(&self) {
52        if let Err(err) = self.inner_run() {
53            status_err!("{}", err);
54            RUSTIC_APP.shutdown(Shutdown::Crash);
55        };
56    }
57}
58
59impl CatCmd {
60    fn inner_run(&self) -> Result<()> {
61        let config = RUSTIC_APP.config();
62        let data = match &self.cmd {
63            CatSubCmd::Config => config
64                .repository
65                .run_open(|repo| Ok(repo.cat_file(FileType::Config, "")?))?,
66            CatSubCmd::Index(opt) => config
67                .repository
68                .run_open(|repo| Ok(repo.cat_file(FileType::Index, &opt.id)?))?,
69            CatSubCmd::Snapshot(opt) => config
70                .repository
71                .run_open(|repo| Ok(repo.cat_file(FileType::Snapshot, &opt.id)?))?,
72            CatSubCmd::TreeBlob(opt) => config
73                .repository
74                .run_indexed(|repo| Ok(repo.cat_blob(BlobType::Tree, &opt.id)?))?,
75            CatSubCmd::DataBlob(opt) => config
76                .repository
77                .run_indexed(|repo| Ok(repo.cat_blob(BlobType::Data, &opt.id)?))?,
78            CatSubCmd::Tree(opt) => config.repository.run_indexed(|repo| {
79                Ok(repo.cat_tree(&opt.snap, |sn| config.snapshot_filter.matches(sn))?)
80            })?,
81        };
82        println!("{}", String::from_utf8(data.to_vec())?);
83
84        Ok(())
85    }
86}