Skip to content

Commit 4a751cb

Browse files
committed
Simplified the CREATE TABLE and CREATE INDEX builder
1 parent dcbd91f commit 4a751cb

File tree

3 files changed

+112
-269
lines changed

3 files changed

+112
-269
lines changed

src/create_index.rs

Lines changed: 49 additions & 125 deletions
Original file line numberDiff line numberDiff line change
@@ -1,195 +1,119 @@
11
use crate::error::Error;
2+
use crate::DBImpl;
23

3-
/**
4-
Representation of a CREATE INDEX builder.
5-
*/
6-
pub trait CreateIndex<'until_build> {
7-
/**
8-
Creates a unique index.
9-
10-
Null values are considered different from all other null values.
11-
*/
12-
fn unique(self) -> Self;
13-
14-
/**
15-
Creates the index only if it doesn't exist yet.
16-
*/
17-
fn if_not_exists(self) -> Self;
18-
19-
/**
20-
Adds a column to the index.
21-
22-
**Parameter**:
23-
- `column`: String representing the column to index.
24-
*/
25-
fn add_column(self, column: &'until_build str) -> Self;
26-
27-
/**
28-
Sets the condition to apply. This will build a partial index.
29-
30-
**Parameter**:
31-
- `condition`: String representing condition to apply the index to
32-
*/
33-
fn set_condition(self, condition: String) -> Self;
34-
35-
/**
36-
This method is used to build the create index operation
37-
*/
38-
fn build(self) -> Result<String, Error>;
39-
}
40-
41-
/**
42-
Representation of a create index operation
43-
*/
44-
pub struct CreateIndexData<'until_build> {
4+
/// The builder for a `CREATE INDEX` statement
5+
pub struct CreateIndexBuilder<'until_build> {
456
pub(crate) name: &'until_build str,
467
pub(crate) table_name: &'until_build str,
478
pub(crate) unique: bool,
489
pub(crate) if_not_exists: bool,
4910
pub(crate) columns: Vec<&'until_build str>,
5011
pub(crate) condition: Option<String>,
12+
pub(crate) dialect: DBImpl,
5113
}
5214

53-
/**
54-
Implementation of database specific implementations of the [CreateIndex] trait.
55-
56-
Should only be constructed via [crate::DBImpl::create_index].
57-
*/
58-
pub enum CreateIndexImpl<'until_build> {
59-
/**
60-
SQLite representation of the CREATE INDEX operation.
61-
*/
62-
#[cfg(feature = "sqlite")]
63-
Sqlite(CreateIndexData<'until_build>),
64-
/**
65-
MySQL representation of the CREATE INDEX operation.
66-
*/
67-
#[cfg(feature = "mysql")]
68-
MySQL(CreateIndexData<'until_build>),
69-
/**
70-
Postgres representation of the CREATE INDEX operation.
71-
*/
72-
#[cfg(feature = "postgres")]
73-
Postgres(CreateIndexData<'until_build>),
74-
}
75-
76-
impl<'until_build> CreateIndex<'until_build> for CreateIndexImpl<'until_build> {
15+
impl<'until_build> CreateIndexBuilder<'until_build> {
16+
/// Creates a unique index.
17+
///
18+
/// Null values are considered different from all other null values.
7719
fn unique(mut self) -> Self {
78-
match self {
79-
#[cfg(feature = "sqlite")]
80-
CreateIndexImpl::Sqlite(ref mut d) => d.unique = true,
81-
#[cfg(feature = "mysql")]
82-
CreateIndexImpl::MySQL(ref mut d) => d.unique = true,
83-
#[cfg(feature = "postgres")]
84-
CreateIndexImpl::Postgres(ref mut d) => d.unique = true,
85-
};
20+
self.unique = true;
8621
self
8722
}
8823

24+
/// Creates the index only if it doesn't exist yet.
8925
fn if_not_exists(mut self) -> Self {
90-
match self {
91-
#[cfg(feature = "sqlite")]
92-
CreateIndexImpl::Sqlite(ref mut d) => d.if_not_exists = true,
93-
#[cfg(feature = "mysql")]
94-
CreateIndexImpl::MySQL(ref mut d) => d.if_not_exists = true,
95-
#[cfg(feature = "postgres")]
96-
CreateIndexImpl::Postgres(ref mut d) => d.if_not_exists = true,
97-
};
26+
self.if_not_exists = true;
9827
self
9928
}
10029

30+
/// Adds a column to the index.
31+
///
32+
/// **Parameter**:
33+
/// - `column`: String representing the column to index.
10134
fn add_column(mut self, column: &'until_build str) -> Self {
102-
match self {
103-
#[cfg(feature = "sqlite")]
104-
CreateIndexImpl::Sqlite(ref mut d) => d.columns.push(column),
105-
#[cfg(feature = "mysql")]
106-
CreateIndexImpl::MySQL(ref mut d) => d.columns.push(column),
107-
#[cfg(feature = "postgres")]
108-
CreateIndexImpl::Postgres(ref mut d) => d.columns.push(column),
109-
}
35+
self.columns.push(column);
11036
self
11137
}
11238

39+
/// Sets the condition to apply. This will build a partial index.
40+
///
41+
/// **Parameter**:
42+
/// - `condition`: String representing condition to apply the index to
11343
fn set_condition(mut self, condition: String) -> Self {
114-
match self {
115-
#[cfg(feature = "sqlite")]
116-
CreateIndexImpl::Sqlite(ref mut d) => d.condition = Some(condition),
117-
#[cfg(feature = "mysql")]
118-
CreateIndexImpl::MySQL(ref mut d) => d.condition = Some(condition),
119-
#[cfg(feature = "postgres")]
120-
CreateIndexImpl::Postgres(ref mut d) => d.condition = Some(condition),
121-
}
44+
self.condition = Some(condition);
12245
self
12346
}
12447

48+
/// This method is used to build the create index operation.
12549
fn build(self) -> Result<String, Error> {
126-
match self {
50+
match self.dialect {
12751
#[cfg(feature = "sqlite")]
128-
CreateIndexImpl::Sqlite(d) => {
129-
if d.columns.is_empty() {
52+
DBImpl::SQLite => {
53+
if self.columns.is_empty() {
13054
return Err(Error::SQLBuildError(format!(
13155
"Couldn't create index on {}: Missing column(s) to create the index on",
132-
d.table_name
56+
self.table_name
13357
)));
13458
}
13559

13660
Ok(format!(
13761
"CREATE {} INDEX{} {} ON {} ({}) {};",
138-
if d.unique { "UNIQUE" } else { "" },
139-
if d.if_not_exists {
62+
if self.unique { "UNIQUE" } else { "" },
63+
if self.if_not_exists {
14064
" IF NOT EXISTS"
14165
} else {
14266
""
14367
},
144-
d.name,
145-
d.table_name,
146-
d.columns.join(", "),
147-
d.condition.as_ref().map_or("", |x| x.as_str()),
68+
self.name,
69+
self.table_name,
70+
self.columns.join(", "),
71+
self.condition.as_ref().map_or("", |x| x.as_str()),
14872
))
14973
}
15074
#[cfg(feature = "mysql")]
151-
CreateIndexImpl::MySQL(d) => {
152-
if d.columns.is_empty() {
75+
DBImpl::MySQL => {
76+
if self.columns.is_empty() {
15377
return Err(Error::SQLBuildError(format!(
15478
"Couldn't create index on {}: Missing column(s) to create the index on",
155-
d.table_name
79+
self.table_name
15680
)));
15781
}
15882

15983
Ok(format!(
16084
"CREATE {} INDEX{} {} ON {} ({});",
161-
if d.unique { "UNIQUE" } else { "" },
162-
if d.if_not_exists {
85+
if self.unique { "UNIQUE" } else { "" },
86+
if self.if_not_exists {
16387
" IF NOT EXISTS"
16488
} else {
16589
""
16690
},
167-
d.name,
168-
d.table_name,
169-
d.columns.join(", "),
91+
self.name,
92+
self.table_name,
93+
self.columns.join(", "),
17094
))
17195
}
17296
#[cfg(feature = "postgres")]
173-
CreateIndexImpl::Postgres(d) => {
174-
if d.columns.is_empty() {
97+
DBImpl::Postgres => {
98+
if self.columns.is_empty() {
17599
return Err(Error::SQLBuildError(format!(
176100
"Couldn't create index on {}: Missing column(s) to create the index on",
177-
d.table_name
101+
self.table_name
178102
)));
179103
}
180104

181105
Ok(format!(
182106
"CREATE{} INDEX{} {} ON {} ({}){};",
183-
if d.unique { " UNIQUE" } else { "" },
184-
if d.if_not_exists {
107+
if self.unique { " UNIQUE" } else { "" },
108+
if self.if_not_exists {
185109
" IF NOT EXISTS"
186110
} else {
187111
""
188112
},
189-
d.name,
190-
d.table_name,
191-
d.columns.join(", "),
192-
match d.condition {
113+
self.name,
114+
self.table_name,
115+
self.columns.join(", "),
116+
match self.condition {
193117
None => String::from(""),
194118
Some(cond) => format!(" WHERE {}", cond.as_str()),
195119
}

0 commit comments

Comments
 (0)