pub trait Transaction<K, Tx>: Schema<PrimaryKey = K>{
// Required methods
async fn transaction<F, T>(tx: F) -> Result<T, Error>
where F: for<'t> FnOnce(&'t mut Tx) -> BoxFuture<'t, Result<T, Error>>;
async fn transactional_execute(
queries: &[&str],
params: Option<&Map>,
) -> Result<u64, Error>;
async fn transactional_insert<M: Schema>(
self,
models: Vec<M>,
) -> Result<u64, Error>;
async fn transactional_update<M: Schema>(
queries: (&Query, &Query),
mutations: (&mut Mutation, &mut Mutation),
) -> Result<u64, Error>;
async fn transactional_delete<M: Schema>(
queries: (&Query, &Query),
) -> Result<u64, Error>;
}
Expand description
An in-progress database transaction.
§Examples
ⓘ
use crate::model::{Account, AccountColumn, Order, Stock, StockColumn};
use zino_orm::{MutationBuilder, QueryBuilder, Schema, Transaction};
let user_id = "0193d8e6-2970-7b52-bc06-80a981212aa9";
let product_id = "0193c06d-bee6-7070-a5e7-9659161bddb5";
let order = Order::from_customer(user_id, product_id);
let quantity = order.quantity();
let total_price = order.total_price();
let order_ctx = order.prepare_insert()?;
let stock_query = QueryBuilder::<Stock>::new()
.and_eq(StockColumn::ProductId, product_id)
.and_ge(StockColumn::Quantity, quantity)
.build();
let mut stock_mutation = MutationBuilder::<Stock>::new()
.inc(StockColumn::Quantity, -quantity)
.build();
let stock_ctx = Stock::prepare_update_one(&stock_query, &mut stock_mutation).await?;
let account_query = QueryBuilder::<Account>::new()
.and_eq(AccountColumn::UserId, user_id)
.and_ge(AccountColumn::Balance, total_price)
.build();
let mut account_mutation = MutationBuilder::<Account>::new()
.inc(AccountColumn::Balance, -total_price)
.build();
let account_ctx = Account::prepare_update_one(&account_query, &mut account_mutation).await?;
Order::transaction(move |tx| Box::pin(async move {
let connection = tx.acquire().await?;
connection.execute(order_ctx.query()).await?;
connection.execute(stock_ctx.query()).await?;
connection.execute(account_ctx.query()).await?;
Ok(())
})).await?;
Required Methods§
Sourceasync fn transaction<F, T>(tx: F) -> Result<T, Error>
async fn transaction<F, T>(tx: F) -> Result<T, Error>
Executes the specific operations inside of a transaction. If the operations return an error, the transaction will be rolled back; if not, the transaction will be committed.
Sourceasync fn transactional_execute(
queries: &[&str],
params: Option<&Map>,
) -> Result<u64, Error>
async fn transactional_execute( queries: &[&str], params: Option<&Map>, ) -> Result<u64, Error>
Executes the queries sequentially inside of a transaction. If it returns an error, the transaction will be rolled back; if not, the transaction will be committed.
Sourceasync fn transactional_insert<M: Schema>(
self,
models: Vec<M>,
) -> Result<u64, Error>
async fn transactional_insert<M: Schema>( self, models: Vec<M>, ) -> Result<u64, Error>
Inserts the model and its associations inside of a transaction.
Dyn Compatibility§
This trait is not dyn compatible.
In older versions of Rust, dyn compatibility was called "object safety", so this trait is not object safe.
Implementors§
impl<'c, M, K> Transaction<K, Transaction<'c, Sqlite>> for M
Available on crate feature
orm-sqlx
only.