Skip to main content

SqlStore

Struct SqlStore 

Source
pub struct SqlStore { /* private fields */ }
Expand description

SQL-backed Store implementation.

Implementations§

Source§

impl SqlStore

Source

pub fn new(pool: Pool<Any>) -> Self

Create a new SQL store wrapping an existing connection pool.

Source

pub async fn migrate(&self) -> Result<(), StoreError>

Run database migrations. Idempotent: a _migrations ledger records what has been applied, so re-running is a no-op. The DDL is selected per backend (SQLite uses BLOB, PostgreSQL uses BYTEA).

Trait Implementations§

Source§

impl AccountStore for SqlStore

Source§

fn get_account<'life0, 'life1, 'async_trait>( &'life0 self, id: &'life1 AccountId, ) -> Pin<Box<dyn Future<Output = Result<Account, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Fetch a single account by id.
Source§

fn get_accounts<'life0, 'life1, 'async_trait>( &'life0 self, ids: &'life1 [AccountId], ) -> Pin<Box<dyn Future<Output = Result<Vec<Account>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Fetch multiple accounts by id.
Source§

fn create_account<'life0, 'async_trait>( &'life0 self, account: Account, ) -> Pin<Box<dyn Future<Output = Result<(), StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait,

Persist a new account (version 1).
Source§

fn append_account_version<'life0, 'async_trait>( &'life0 self, account: Account, ) -> Pin<Box<dyn Future<Output = Result<(), StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait,

Append a new version to an existing account.
Source§

fn get_account_history<'life0, 'life1, 'async_trait>( &'life0 self, id: &'life1 AccountId, ) -> Pin<Box<dyn Future<Output = Result<Vec<Account>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Return the full version history for an account.
Source§

fn list_accounts<'life0, 'async_trait>( &'life0 self, ) -> Pin<Box<dyn Future<Output = Result<Vec<Account>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait,

List all accounts (latest version of each).
Source§

impl BookStore for SqlStore

Source§

fn create_book<'life0, 'async_trait>( &'life0 self, book: Book, ) -> Pin<Box<dyn Future<Output = Result<(), StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait,

Create a new book.
Source§

fn get_book<'life0, 'life1, 'async_trait>( &'life0 self, id: &'life1 BookId, ) -> Pin<Box<dyn Future<Output = Result<Book, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Fetch a book by id.
Source§

fn list_books<'life0, 'async_trait>( &'life0 self, ) -> Pin<Box<dyn Future<Output = Result<Vec<Book>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait,

List all books.
Source§

impl EventStore for SqlStore

Source§

fn append_event<'life0, 'life1, 'async_trait>( &'life0 self, event: &'life1 LedgerEvent, ) -> Pin<Box<dyn Future<Output = Result<u64, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Append an event and return its sequence number. Idempotent on the event’s event_dedup_key: appending an event whose key already exists does not insert a duplicate and returns the existing seq. The seq field on the input is ignored – the store assigns it.
Source§

fn get_events_since<'life0, 'async_trait>( &'life0 self, after_seq: u64, limit: u32, ) -> Pin<Box<dyn Future<Output = Result<Vec<LedgerEvent>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait,

Return events with sequence numbers greater than after_seq, up to limit.
Source§

impl PostingStore for SqlStore

Source§

fn get_postings<'life0, 'life1, 'async_trait>( &'life0 self, ids: &'life1 [PostingId], ) -> Pin<Box<dyn Future<Output = Result<Vec<Posting>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Fetch postings by their ids.
Source§

fn get_postings_by_account<'life0, 'life1, 'life2, 'async_trait>( &'life0 self, account: &'life1 AccountId, asset: Option<&'life2 AssetId>, status: Option<PostingStatus>, ) -> Pin<Box<dyn Future<Output = Result<Vec<Posting>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait, 'life2: 'async_trait,

Return postings owned by an account, optionally filtered by asset and/or status.
Source§

fn query_postings<'life0, 'life1, 'async_trait>( &'life0 self, query: &'life1 PostingQuery, ) -> Pin<Box<dyn Future<Output = Result<Page<Posting>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Query postings with filtering and pagination.
Source§

fn reserve_postings<'life0, 'life1, 'async_trait>( &'life0 self, ids: &'life1 [PostingId], reservation: ReservationId, ) -> Pin<Box<dyn Future<Output = Result<u64, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Reserve postings: Active → PendingInactive, stamping reservation as the owner token. A dumb instruction — each id flips only if still Active; returns the number of rows reserved (0 ≤ n ≤ ids.len()). It does not error on a short count; the caller (saga) interprets it.
Source§

fn release_postings<'life0, 'life1, 'async_trait>( &'life0 self, ids: &'life1 [PostingId], reservation: ReservationId, ) -> Pin<Box<dyn Future<Output = Result<u64, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Release postings: PendingInactive owned by reservationActive, clearing the owner. A dumb instruction — only postings reserved by this reservation flip; returns the number of rows released. Releasing an Active (already released) or differently-owned posting simply does not count. The caller interprets the result.
Source§

fn deactivate_postings<'life0, 'life1, 'async_trait>( &'life0 self, ids: &'life1 [PostingId], reservation: Option<ReservationId>, ) -> Pin<Box<dyn Future<Output = Result<u64, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Deactivate postings: flip to Inactive. A dumb instruction — it applies the conditional update and returns the number of rows changed; it does not decide whether that count is correct. The caller (saga) interprets it. Read more
Source§

fn insert_postings<'life0, 'life1, 'async_trait>( &'life0 self, postings: &'life1 [Posting], ) -> Pin<Box<dyn Future<Output = Result<u64, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Insert postings if absent (idempotent). A dumb instruction — inserts each posting unless one with the same id already exists, and returns the number of rows inserted (already-present postings contribute 0). The caller decides what a short count means.
Source§

impl SagaStore for SqlStore

Source§

fn save_saga<'life0, 'life1, 'async_trait>( &'life0 self, id: &'life1 i64, data: Vec<u8>, ) -> Pin<Box<dyn Future<Output = Result<(), StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Persist a saga execution state.
Source§

fn list_pending_sagas<'life0, 'async_trait>( &'life0 self, ) -> Pin<Box<dyn Future<Output = Result<Vec<(i64, Vec<u8>)>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait,

Load all pending (incomplete) saga states.
Source§

fn delete_saga<'life0, 'life1, 'async_trait>( &'life0 self, id: &'life1 i64, ) -> Pin<Box<dyn Future<Output = Result<(), StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Delete a completed saga state.
Source§

impl TransferStore for SqlStore

Source§

fn get_transfer<'life0, 'life1, 'async_trait>( &'life0 self, id: &'life1 EnvelopeId, ) -> Pin<Box<dyn Future<Output = Result<Option<EnvelopeRecord>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Fetch a transfer record by its content-addressed id.
Source§

fn store_transfer<'life0, 'life1, 'async_trait>( &'life0 self, record: EnvelopeRecord, involved: &'life1 [AccountId], ) -> Pin<Box<dyn Future<Output = Result<u64, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Persist a transfer record if absent (idempotent) and index it under every account in involved (both created and consumed owners — the caller supplies the set so storage computes nothing). A dumb instruction: returns 1 if the transfer row was newly inserted, 0 if it already existed. The caller decides what 0 means.
Source§

fn get_transfers_for_account<'life0, 'life1, 'async_trait>( &'life0 self, account: &'life1 AccountId, ) -> Pin<Box<dyn Future<Output = Result<Vec<EnvelopeRecord>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Return all transfers involving the given account.
Source§

fn query_transfers<'life0, 'life1, 'async_trait>( &'life0 self, query: &'life1 TransferQuery, ) -> Pin<Box<dyn Future<Output = Result<Page<EnvelopeRecord>, StoreError>> + Send + 'async_trait>>
where Self: 'async_trait, 'life0: 'async_trait, 'life1: 'async_trait,

Query transfers with filtering and pagination.

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self>

Converts self into a Left variant of Either<Self, Self> if into_left is true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
where F: FnOnce(&Self) -> bool,

Converts self into a Left variant of Either<Self, Self> if into_left(&self) returns true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<T> Store for T

Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more