Test ActiveModelBehavior

This commit is contained in:
Billy Chan 2021-10-15 17:42:50 +08:00
parent aa5ccb9216
commit cc96bb783c
No known key found for this signature in database
GPG Key ID: A2D690CAC7DF3CC7
2 changed files with 170 additions and 3 deletions

View File

@ -49,4 +49,76 @@ impl Related<super::lineitem::Entity> for Entity {
} }
} }
impl ActiveModelBehavior for ActiveModel {} impl ActiveModelBehavior for ActiveModel {
fn new() -> Self {
use sea_orm::Set;
Self {
serial: Set(Uuid::new_v4()),
..ActiveModelTrait::default()
}
}
fn before_save(self, insert: bool) -> Result<Self, DbErr> {
use rust_decimal_macros::dec;
if let Some(price) = self.price.clone().take() {
if price == dec!(0) {
Err(DbErr::Custom(format!(
"[before_save] Invalid Price, insert: {}",
insert
)))
} else {
Ok(self)
}
} else {
Err(DbErr::Custom(format!(
"[before_save] Price must be set, insert: {}",
insert
)))
}
}
fn after_save(self, insert: bool) -> Result<Self, DbErr> {
use rust_decimal_macros::dec;
if let Some(price) = dbg!(self.price.clone()).take() {
if price < dec!(0) {
Err(DbErr::Custom(format!(
"[after_save] Invalid Price, insert: {}",
insert
)))
} else {
Ok(self)
}
} else {
Err(DbErr::Custom(format!(
"[after_save] Price must be set, insert: {}",
insert
)))
}
}
fn before_delete(self) -> Result<Self, DbErr> {
if let Some(name) = self.name.clone().take() {
if name.contains("(err_on_before_delete)") {
Err(DbErr::Custom(
"[before_delete] Cannot be deleted".to_owned(),
))
} else {
Ok(self)
}
} else {
Err(DbErr::Custom("[before_delete] Name must be set".to_owned()))
}
}
fn after_delete(self) -> Result<Self, DbErr> {
if let Some(name) = self.name.clone().take() {
if name.contains("(err_on_after_delete)") {
Err(DbErr::Custom("[after_delete] Cannot be deleted".to_owned()))
} else {
Ok(self)
}
} else {
Err(DbErr::Custom("[after_delete] Name must be set".to_owned()))
}
}
}

View File

@ -1,9 +1,9 @@
pub mod common; pub mod common;
pub use common::{bakery_chain::*, setup::*, TestContext}; pub use common::{bakery_chain::*, setup::*, TestContext};
use pretty_assertions::assert_eq;
pub use sea_orm::entity::*; pub use sea_orm::entity::*;
pub use sea_orm::{ConnectionTrait, QueryFilter}; pub use sea_orm::*;
use sea_orm::{DatabaseTransaction, DbErr};
#[sea_orm_macros::test] #[sea_orm_macros::test]
#[cfg(any( #[cfg(any(
@ -105,6 +105,101 @@ fn _transaction_with_reference<'a>(
}) })
} }
#[sea_orm_macros::test]
#[cfg(any(
feature = "sqlx-mysql",
feature = "sqlx-sqlite",
feature = "sqlx-postgres"
))]
#[sea_orm_macros::test]
#[cfg(any(
feature = "sqlx-mysql",
feature = "sqlx-sqlite",
feature = "sqlx-postgres"
))]
pub async fn transaction_with_active_model_behaviour() -> Result<(), DbErr> {
use rust_decimal_macros::dec;
let ctx = TestContext::new("transaction_with_active_model_behaviour_test").await;
if let Ok(txn) = ctx.db.begin().await {
assert_eq!(
cake::ActiveModel {
name: Set("Cake with invalid price".to_owned()),
price: Set(dec!(0)),
gluten_free: Set(false),
..Default::default()
}
.save(&txn)
.await,
Err(DbErr::Custom(
"[before_save] Invalid Price, insert: true".to_owned()
))
);
assert_eq!(cake::Entity::find().all(&txn).await?.len(), 0);
assert_eq!(
cake::ActiveModel {
name: Set("Cake with invalid price".to_owned()),
price: Set(dec!(-10)),
gluten_free: Set(false),
..Default::default()
}
.save(&txn)
.await,
Err(DbErr::Custom(
"[after_save] Invalid Price, insert: true".to_owned()
))
);
assert_eq!(cake::Entity::find().all(&txn).await?.len(), 1);
let readonly_cake_1 = cake::ActiveModel {
name: Set("Readonly cake (err_on_before_delete)".to_owned()),
price: Set(dec!(10)),
gluten_free: Set(true),
..Default::default()
}
.save(&txn)
.await?;
assert_eq!(cake::Entity::find().all(&txn).await?.len(), 2);
assert_eq!(
readonly_cake_1.delete(&txn).await.err(),
Some(DbErr::Custom(
"[before_delete] Cannot be deleted".to_owned()
))
);
assert_eq!(cake::Entity::find().all(&txn).await?.len(), 2);
let readonly_cake_2 = cake::ActiveModel {
name: Set("Readonly cake (err_on_after_delete)".to_owned()),
price: Set(dec!(10)),
gluten_free: Set(true),
..Default::default()
}
.save(&txn)
.await?;
assert_eq!(cake::Entity::find().all(&txn).await?.len(), 3);
assert_eq!(
readonly_cake_2.delete(&txn).await.err(),
Some(DbErr::Custom("[after_delete] Cannot be deleted".to_owned()))
);
assert_eq!(cake::Entity::find().all(&txn).await?.len(), 2);
}
assert_eq!(cake::Entity::find().all(&ctx.db).await?.len(), 0);
ctx.delete().await;
Ok(())
}
#[sea_orm_macros::test] #[sea_orm_macros::test]
#[cfg(any( #[cfg(any(
feature = "sqlx-mysql", feature = "sqlx-mysql",