diff --git a/src/databases/database.rs b/src/databases/database.rs index 0d6e8c3e..18b2a56a 100644 --- a/src/databases/database.rs +++ b/src/databases/database.rs @@ -81,7 +81,6 @@ pub enum Error { UsernameTaken, EmailTaken, UserNotFound, - CategoryAlreadyExists, CategoryNotFound, TagAlreadyExists, TagNotFound, diff --git a/src/databases/mysql.rs b/src/databases/mysql.rs index dae509d0..8fb0ce12 100644 --- a/src/databases/mysql.rs +++ b/src/databases/mysql.rs @@ -249,17 +249,7 @@ impl Database for Mysql { .execute(&self.pool) .await .map(|v| i64::try_from(v.last_insert_id()).expect("last ID is larger than i64")) - .map_err(|e| match e { - sqlx::Error::Database(err) => { - log::error!("DB error: {:?}", err); - if err.message().contains("Duplicate entry") && err.message().contains("name") { - database::Error::CategoryAlreadyExists - } else { - database::Error::Error - } - } - _ => database::Error::Error, - }) + .map_err(|_| database::Error::Error) } async fn get_category_from_id(&self, category_id: i64) -> Result { diff --git a/src/databases/sqlite.rs b/src/databases/sqlite.rs index 434a9048..4e955151 100644 --- a/src/databases/sqlite.rs +++ b/src/databases/sqlite.rs @@ -239,17 +239,7 @@ impl Database for Sqlite { .execute(&self.pool) .await .map(|v| v.last_insert_rowid()) - .map_err(|e| match e { - sqlx::Error::Database(err) => { - log::error!("DB error: {:?}", err); - if err.message().contains("UNIQUE") && err.message().contains("name") { - database::Error::CategoryAlreadyExists - } else { - database::Error::Error - } - } - _ => database::Error::Error, - }) + .map_err(|_| database::Error::Error) } async fn get_category_from_id(&self, category_id: i64) -> Result { diff --git a/src/errors.rs b/src/errors.rs index c92a0361..24a9661e 100644 --- a/src/errors.rs +++ b/src/errors.rs @@ -288,7 +288,6 @@ pub fn map_database_error_to_service_error(error: &database::Error) -> ServiceEr database::Error::UsernameTaken => ServiceError::UsernameTaken, database::Error::EmailTaken => ServiceError::EmailTaken, database::Error::UserNotFound => ServiceError::UserNotFound, - database::Error::CategoryAlreadyExists => ServiceError::CategoryAlreadyExists, database::Error::CategoryNotFound => ServiceError::InvalidCategory, database::Error::TagAlreadyExists => ServiceError::TagAlreadyExists, database::Error::TagNotFound => ServiceError::InvalidTag, diff --git a/src/services/category.rs b/src/services/category.rs index 5abe8aa6..ec3e5ca2 100644 --- a/src/services/category.rs +++ b/src/services/category.rs @@ -28,6 +28,8 @@ impl Service { /// It returns an error if: /// /// * The user does not have the required permissions. + /// * The category name is empty. + /// * The category already exists. /// * There is a database error. pub async fn add_category(&self, category_name: &str, user_id: &UserId) -> Result { let user = self.user_repository.get_compact(user_id).await?; @@ -44,10 +46,16 @@ impl Service { return Err(ServiceError::CategoryNameEmpty); } - match self.category_repository.add(trimmed_name).await { - Ok(id) => Ok(id), + // Try to get the category by name to check if it already exists + match self.category_repository.get_by_name(trimmed_name).await { + // Return ServiceError::CategoryAlreadyExists if the category exists + Ok(_) => Err(ServiceError::CategoryAlreadyExists), Err(e) => match e { - DatabaseError::CategoryAlreadyExists => Err(ServiceError::CategoryAlreadyExists), + // Otherwise try to create it + DatabaseError::CategoryNotFound => match self.category_repository.add(trimmed_name).await { + Ok(id) => Ok(id), + Err(_) => Err(ServiceError::DatabaseError), + }, _ => Err(ServiceError::DatabaseError), }, } diff --git a/src/upgrades/from_v1_0_0_to_v2_0_0/databases/sqlite_v2_0_0.rs b/src/upgrades/from_v1_0_0_to_v2_0_0/databases/sqlite_v2_0_0.rs index 37a06d5e..cbaed29f 100644 --- a/src/upgrades/from_v1_0_0_to_v2_0_0/databases/sqlite_v2_0_0.rs +++ b/src/upgrades/from_v1_0_0_to_v2_0_0/databases/sqlite_v2_0_0.rs @@ -116,16 +116,7 @@ impl SqliteDatabaseV2_0_0 { .execute(&self.pool) .await .map(|v| v.last_insert_rowid()) - .map_err(|e| match e { - sqlx::Error::Database(err) => { - if err.message().contains("UNIQUE") && err.message().contains("name") { - database::Error::CategoryAlreadyExists - } else { - database::Error::Error - } - } - _ => database::Error::Error, - }) + .map_err(|_| database::Error::Error) } pub async fn insert_category(&self, category: &CategoryRecordV2) -> Result {