canic_utils/case/
mod.rs

1use derive_more::Display;
2
3mod constant;
4mod snake;
5mod title;
6
7//
8// utils/case
9//
10// all case operations come through here as we have to include
11// multiple crates to get the desired behaviour
12//
13
14// Case
15#[derive(Clone, Copy, Debug, Display)]
16pub enum Case {
17    Camel,
18    Constant, // adheres to rust constant rules, more strict than UPPER_SNAKE
19    Kebab,
20    Lower,
21    Sentence,
22    Snake,
23    Title,
24    Upper,
25    UpperCamel, // or PascalCase
26    UpperSnake, // or SCREAMING_SNAKE
27    UpperKebab, // or TRAIN-CASE
28}
29
30//
31// Casing
32//
33
34pub trait Casing<T: std::fmt::Display> {
35    fn to_case(&self, case: Case) -> String;
36    fn is_case(&self, case: Case) -> bool;
37}
38
39impl<T: std::fmt::Display> Casing<T> for T
40where
41    String: PartialEq<T>,
42{
43    // to_case
44    // don't use convert_case:: Lower and Upper because they add spaces, and other
45    // unexpected behaviour
46    fn to_case(&self, case: Case) -> String {
47        use convert_case as cc;
48        let s = &self.to_string();
49
50        match case {
51            // rust
52            Case::Lower => s.to_lowercase(),
53            Case::Upper => s.to_uppercase(),
54
55            // custom
56            Case::Title => title::to_title_case(s),
57            Case::Snake => snake::to_snake_case(s),
58            Case::UpperSnake => snake::to_snake_case(s).to_uppercase(),
59            Case::Constant => constant::to_constant_case(s).to_uppercase(),
60
61            // convert_case
62            Case::Camel => cc::Casing::to_case(s, cc::Case::Camel),
63            Case::Kebab => cc::Casing::to_case(s, cc::Case::Kebab),
64            Case::Sentence => cc::Casing::to_case(s, cc::Case::Sentence),
65            Case::UpperCamel => cc::Casing::to_case(s, cc::Case::UpperCamel),
66            Case::UpperKebab => cc::Casing::to_case(s, cc::Case::Kebab).to_uppercase(),
67        }
68    }
69
70    // is_case
71    fn is_case(&self, case: Case) -> bool {
72        &self.to_case(case) == self
73    }
74}