sea_query/index/
common.rs

1use crate::expr::Expr;
2use crate::{FunctionCall, types::*};
3
4/// Specification of a table index
5#[derive(Default, Debug, Clone)]
6pub struct TableIndex {
7    pub(crate) name: Option<String>,
8    pub(crate) columns: Vec<IndexColumn>,
9}
10
11#[derive(Debug, Clone)]
12#[non_exhaustive]
13pub enum IndexColumn {
14    TableColumn(IndexColumnTableColumn),
15    Expr(IndexColumnExpr),
16}
17
18#[derive(Debug, Clone)]
19pub struct IndexColumnTableColumn {
20    pub(crate) name: DynIden,
21    pub(crate) prefix: Option<u32>,
22    pub(crate) order: Option<IndexOrder>,
23}
24
25#[derive(Debug, Clone)]
26pub struct IndexColumnExpr {
27    pub(crate) expr: Expr,
28    pub(crate) order: Option<IndexOrder>,
29}
30
31impl IndexColumn {
32    pub(crate) fn name(&self) -> Option<&DynIden> {
33        match self {
34            IndexColumn::TableColumn(IndexColumnTableColumn { name, .. }) => Some(name),
35            IndexColumn::Expr(_) => None,
36        }
37    }
38}
39
40#[derive(Debug, Clone)]
41#[non_exhaustive]
42pub enum IndexOrder {
43    Asc,
44    Desc,
45}
46
47pub trait IntoIndexColumn: Into<IndexColumn> {
48    fn into_index_column(self) -> IndexColumn;
49}
50
51impl<T> IntoIndexColumn for T
52where
53    T: Into<IndexColumn>,
54{
55    fn into_index_column(self) -> IndexColumn {
56        self.into()
57    }
58}
59
60impl<I> From<I> for IndexColumn
61where
62    I: IntoIden,
63{
64    fn from(value: I) -> Self {
65        IndexColumn::TableColumn(IndexColumnTableColumn {
66            name: value.into_iden(),
67            prefix: None,
68            order: None,
69        })
70    }
71}
72
73impl<I> From<(I, u32)> for IndexColumn
74where
75    I: IntoIden,
76{
77    fn from(value: (I, u32)) -> Self {
78        IndexColumn::TableColumn(IndexColumnTableColumn {
79            name: value.0.into_iden(),
80            prefix: Some(value.1),
81            order: None,
82        })
83    }
84}
85
86impl<I> From<(I, IndexOrder)> for IndexColumn
87where
88    I: IntoIden,
89{
90    fn from(value: (I, IndexOrder)) -> Self {
91        IndexColumn::TableColumn(IndexColumnTableColumn {
92            name: value.0.into_iden(),
93            prefix: None,
94            order: Some(value.1),
95        })
96    }
97}
98
99impl<I> From<(I, u32, IndexOrder)> for IndexColumn
100where
101    I: IntoIden,
102{
103    fn from(value: (I, u32, IndexOrder)) -> Self {
104        IndexColumn::TableColumn(IndexColumnTableColumn {
105            name: value.0.into_iden(),
106            prefix: Some(value.1),
107            order: Some(value.2),
108        })
109    }
110}
111
112impl From<FunctionCall> for IndexColumn {
113    fn from(value: FunctionCall) -> Self {
114        IndexColumn::Expr(IndexColumnExpr {
115            expr: value.into(),
116            order: None,
117        })
118    }
119}
120
121impl From<(FunctionCall, IndexOrder)> for IndexColumn {
122    fn from(value: (FunctionCall, IndexOrder)) -> Self {
123        IndexColumn::Expr(IndexColumnExpr {
124            expr: value.0.into(),
125            order: Some(value.1),
126        })
127    }
128}
129
130impl From<Expr> for IndexColumn {
131    fn from(value: Expr) -> Self {
132        IndexColumn::Expr(IndexColumnExpr {
133            expr: value,
134            order: None,
135        })
136    }
137}
138
139impl From<(Expr, IndexOrder)> for IndexColumn {
140    fn from(value: (Expr, IndexOrder)) -> Self {
141        IndexColumn::Expr(IndexColumnExpr {
142            expr: value.0,
143            order: Some(value.1),
144        })
145    }
146}
147
148impl TableIndex {
149    /// Construct a new table index
150    pub fn new() -> Self {
151        Self::default()
152    }
153
154    /// Set index name
155    pub fn name<T>(&mut self, name: T) -> &mut Self
156    where
157        T: Into<String>,
158    {
159        self.name = Some(name.into());
160        self
161    }
162
163    /// Set index column
164    pub fn col(&mut self, col: IndexColumn) -> &mut Self {
165        self.columns.push(col);
166        self
167    }
168
169    pub fn get_column_names(&self) -> Vec<String> {
170        self.columns
171            .iter()
172            .filter_map(|col| col.name().map(|name| name.to_string()))
173            .collect()
174    }
175
176    pub fn take(&mut self) -> Self {
177        Self {
178            name: self.name.take(),
179            columns: std::mem::take(&mut self.columns),
180        }
181    }
182}