Skip to main content

ex_cli/cli/
order.rs

1use crate::error::{MyError, MyResult};
2use indexmap::IndexSet;
3
4#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq)]
5pub enum DirKind {
6    Asc,
7    Desc,
8}
9
10#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq)]
11pub enum OrderKind {
12    Dir,
13    Group,
14    Name,
15    Ext,
16    Size(DirKind),
17    Time(DirKind),
18}
19
20impl OrderKind {
21    fn from_char(ch: char) -> Option<Self> {
22        match ch {
23            'd' => Some(Self::Dir),
24            'n' => Some(Self::Name),
25            'e' => Some(Self::Ext),
26            's' => Some(Self::Size(DirKind::Asc)),
27            't' => Some(Self::Time(DirKind::Asc)),
28            _ => None,
29        }
30    }
31
32    pub fn ascending(self: Self) -> Self {
33        match self {
34            Self::Size(_) => Self::Size(DirKind::Asc),
35            Self::Time(_) => Self::Time(DirKind::Asc),
36            any => any,
37        }
38    }
39
40    pub fn descending(self: Self) -> Self {
41        match self {
42            Self::Size(_) => Self::Size(DirKind::Desc),
43            Self::Time(_) => Self::Time(DirKind::Desc),
44            any => any,
45        }
46    }
47}
48
49#[derive(Clone)]
50pub struct OrderVec {
51    pub inner: Vec<OrderKind>,
52}
53
54impl OrderVec {
55    pub fn from_str(value: &str) -> MyResult<Self> {
56        let mut results = IndexSet::new();
57        let mut result = None;
58        for ch in value.chars() {
59            if ch.is_alphabetic() {
60                if let Some(result) = result {
61                    results.insert(result);
62                }
63                result = OrderKind::from_char(ch);
64                if result == None {
65                    return Err(MyError::create_clap("order", value));
66                }
67            } else if ch == '+' {
68                result = result.map(|x| x.ascending());
69            } else if ch == '-' {
70                result = result.map(|x| x.descending());
71            } else {
72                return Err(MyError::create_clap("order", value));
73            }
74        }
75        if let Some(result) = result {
76            results.insert(result);
77        }
78        let results = Self { inner: results.into_iter().collect() };
79        Ok(results)
80    }
81}