tidy_browser/
args.rs

1use std::path::PathBuf;
2
3use clap::{
4    builder::{IntoResettable, OsStr, Resettable},
5    ArgAction, ValueHint,
6};
7
8#[derive(Clone)]
9#[derive(Debug)]
10#[derive(clap::Parser)]
11pub struct Args {
12    #[command(subcommand)]
13    pub cmd: Option<SubCmd>,
14
15    #[arg(
16        short,
17        long,
18        default_value("results"),
19        verbatim_doc_comment,
20        value_hint(ValueHint::DirPath)
21    )]
22    /// Specify output dir
23    /// binary-cookies ignore the arg
24    pub output_dir: PathBuf,
25
26    #[arg(short, long)]
27    /// All browsers data
28    pub all_browsers: bool,
29
30    #[arg(long, default_value(","), value_hint(ValueHint::Other))]
31    /// Csv separator
32    pub sep: String,
33
34    #[arg(long, id("domain"), value_hint(ValueHint::Url))]
35    /// Filter by host/domain
36    pub host: Option<String>,
37
38    #[arg(long, default_value(Format::Csv))]
39    /// Out format
40    pub out_format: Format,
41}
42
43#[derive(Clone, Copy)]
44#[derive(Debug)]
45#[derive(Default)]
46pub enum Format {
47    #[default]
48    Csv,
49    Json,
50    JsonLines,
51}
52
53impl clap::ValueEnum for Format {
54    fn value_variants<'a>() -> &'a [Self] {
55        &[Self::Csv, Self::Json, Self::JsonLines]
56    }
57    fn to_possible_value<'a>(&self) -> ::std::option::Option<clap::builder::PossibleValue> {
58        match self {
59            Self::Csv => Some(clap::builder::PossibleValue::new("csv")),
60            Self::Json => Some(clap::builder::PossibleValue::new("json")),
61            Self::JsonLines => Some(clap::builder::PossibleValue::new("jsonl")),
62        }
63    }
64}
65
66impl IntoResettable<OsStr> for Format {
67    fn into_resettable(self) -> clap::builder::Resettable<OsStr> {
68        Resettable::Value(match self {
69            Format::Csv => "csv".into(),
70            Format::Json => "json".into(),
71            Format::JsonLines => "jsonl".into(),
72        })
73    }
74}
75
76#[derive(Clone)]
77#[derive(Debug)]
78#[derive(clap::Subcommand)]
79pub enum SubCmd {
80    /// Chromium based
81    Chromium(ChromiumArgs),
82    /// Firefox based
83    Firefox(FirefoxArgs),
84    /// Parse BinaryCookies
85    BinaryCookies(BinaryCookiesArgs),
86    #[cfg(target_os = "macos")]
87    /// Safari
88    Safari(SafariArgs),
89    /// Generates completions for the specified SHELL, sends them to `stdout` and exits.
90    Completions {
91        shell: clap_complete_command::Shell,
92    },
93}
94
95#[derive(Clone, Copy)]
96#[derive(Debug)]
97#[derive(Default)]
98#[derive(PartialEq, Eq, PartialOrd, Ord)]
99#[derive(clap::ValueEnum)]
100#[derive(Hash)]
101#[derive(strum::EnumIter)]
102pub enum Value {
103    #[default]
104    Cookie,
105    Login,
106}
107
108#[derive(Clone)]
109#[derive(Debug)]
110#[derive(PartialEq, Eq, PartialOrd, Ord)]
111#[derive(clap::Args)]
112pub struct SafariArgs {
113    #[arg(short, long, value_delimiter(','), action(ArgAction::Append))]
114    /// Only support cookie
115    pub values: Vec<Value>,
116
117    #[arg(long, value_hint(ValueHint::FilePath))]
118    pub cookies_path: Option<PathBuf>,
119}
120
121#[derive(Clone)]
122#[derive(Debug)]
123#[derive(PartialEq, Eq, PartialOrd, Ord)]
124#[derive(clap::Args)]
125pub struct ChromiumArgs {
126    #[arg(short, long)]
127    pub name: ChromiumName,
128
129    #[arg(long, id("DIR"), verbatim_doc_comment, value_hint(ValueHint::DirPath))]
130    /// When browser is started with `--user-data-dir=DIR   Specify the directory that user data (your "profile") is kept in.`
131    #[cfg_attr(target_os = "linux", doc = "[example value: ~/.config/google-chrome]")]
132    #[cfg_attr(
133        target_os = "macos",
134        doc = "[example value: ~/Library/Application Support/Google/Chrome]"
135    )]
136    #[cfg_attr(
137        target_os = "windows",
138        doc = r"[example value: ~\AppData\Local\Google\Chrome\User Data]"
139    )]
140    pub user_data_dir: Option<PathBuf>,
141
142    #[arg(short, long, value_delimiter(','), action(ArgAction::Append))]
143    pub values: Vec<Value>,
144}
145
146#[derive(Clone, Copy)]
147#[derive(Debug)]
148#[derive(PartialEq, Eq, PartialOrd, Ord)]
149#[derive(clap::ValueEnum)]
150#[clap(rename_all = "PascalCase")]
151#[derive(strum::EnumIter)]
152pub enum ChromiumName {
153    Chrome,
154    Edge,
155    Chromium,
156    Brave,
157    Vivaldi,
158    Yandex,
159    Opera,
160    #[cfg(not(target_os = "linux"))]
161    Arc,
162    #[cfg(not(target_os = "linux"))]
163    OperaGX,
164    #[cfg(not(target_os = "linux"))]
165    CocCoc,
166}
167
168#[derive(Clone)]
169#[derive(Debug)]
170#[derive(PartialEq, Eq, PartialOrd, Ord)]
171#[derive(clap::Args)]
172pub struct FirefoxArgs {
173    #[arg(short, long)]
174    pub name: FirefoxName,
175
176    #[arg(long, id("DIR"), value_hint(ValueHint::DirPath))]
177    /// Browser data dir.
178    #[cfg_attr(target_os = "linux", doc = "[example value: ~/.mozilla/firefox]")]
179    #[cfg_attr(
180        target_os = "macos",
181        doc = "[example value: ~/Library/Application Support/Firefox]"
182    )]
183    #[cfg_attr(
184        target_os = "windows",
185        doc = r"[example value: ~\AppData\Roaming\Mozilla\Firefox]"
186    )]
187    pub base: Option<PathBuf>,
188
189    #[arg(short('P'), id("profile"), value_hint(ValueHint::Other))]
190    /// When browser is started with `-P <profile>       Start with <profile>.`
191    pub profile: Option<String>,
192
193    #[arg(long("profile"), id("path"))]
194    #[arg(verbatim_doc_comment)]
195    /// When browser is started with `--profile <path>   Start with profile at <path>.`
196    /// When the arg is used, other args (such as `--base`, `-P`) are ignore.
197    pub profile_path: Option<PathBuf>,
198
199    #[arg(short, long, value_delimiter(','), action(ArgAction::Append))]
200    /// Only support cookie
201    pub values: Vec<Value>,
202}
203
204#[derive(Clone, Copy)]
205#[derive(Debug)]
206#[derive(PartialEq, Eq, PartialOrd, Ord)]
207#[derive(clap::ValueEnum)]
208#[clap(rename_all = "PascalCase")]
209#[derive(strum::EnumIter)]
210pub enum FirefoxName {
211    Firefox,
212    Librewolf,
213    Floorp,
214}
215
216#[derive(Clone)]
217#[derive(Debug)]
218#[derive(PartialEq, Eq, PartialOrd, Ord)]
219#[derive(clap::Args)]
220pub struct BinaryCookiesArgs {
221    #[arg(short('i'), long, value_hint(ValueHint::FilePath))]
222    pub cookies_path: PathBuf,
223    #[arg(short, long, value_hint(ValueHint::FilePath))]
224    pub out_file: Option<PathBuf>,
225}