zino_orm

Trait Transaction

Source
pub trait Transaction<K, Tx>: Schema<PrimaryKey = K>
where K: Default + Display + PartialEq,
{ // 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§

Source

async fn transaction<F, T>(tx: F) -> Result<T, Error>
where F: for<'t> FnOnce(&'t mut Tx) -> BoxFuture<'t, 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.

Source

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.

Source

async fn transactional_insert<M: Schema>( self, models: Vec<M>, ) -> Result<u64, Error>

Inserts the model and its associations inside of a transaction.

Source

async fn transactional_update<M: Schema>( queries: (&Query, &Query), mutations: (&mut Mutation, &mut Mutation), ) -> Result<u64, Error>

Updates the models inside of a transaction.

Source

async fn transactional_delete<M: Schema>( queries: (&Query, &Query), ) -> Result<u64, Error>

Deletes the models 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§

Source§

impl<'c, M, K> Transaction<K, Transaction<'c, Sqlite>> for M
where M: Schema<PrimaryKey = K>, K: Default + Display + PartialEq,

Available on crate feature orm-sqlx only.