use diesel::prelude::*;
use miden_node_db::DatabaseError;
use miden_node_proto::domain::account::NetworkAccountId;
use miden_protocol::account::Account;
use crate::db::models::conv as conversions;
use crate::db::schema;
#[derive(Debug, Clone, Insertable)]
#[diesel(table_name = schema::accounts)]
#[diesel(check_for_backend(diesel::sqlite::Sqlite))]
pub struct AccountInsert {
pub account_id: Vec<u8>,
pub account_data: Vec<u8>,
pub transaction_id: Option<Vec<u8>>,
}
#[derive(Debug, Clone, Queryable, Selectable)]
#[diesel(table_name = schema::accounts)]
#[diesel(check_for_backend(diesel::sqlite::Sqlite))]
pub struct AccountRow {
pub account_data: Vec<u8>,
}
pub fn upsert_committed_account(
conn: &mut SqliteConnection,
account_id: NetworkAccountId,
account: &Account,
) -> Result<(), DatabaseError> {
let account_id_bytes = conversions::network_account_id_to_bytes(account_id);
diesel::delete(
schema::accounts::table
.filter(schema::accounts::account_id.eq(&account_id_bytes))
.filter(schema::accounts::transaction_id.is_null()),
)
.execute(conn)?;
let row = AccountInsert {
account_id: account_id_bytes,
account_data: conversions::account_to_bytes(account),
transaction_id: None,
};
diesel::insert_into(schema::accounts::table).values(&row).execute(conn)?;
Ok(())
}
pub fn get_account(
conn: &mut SqliteConnection,
account_id: NetworkAccountId,
) -> Result<Option<Account>, DatabaseError> {
let account_id_bytes = conversions::network_account_id_to_bytes(account_id);
let row: Option<AccountRow> = schema::accounts::table
.filter(schema::accounts::account_id.eq(&account_id_bytes))
.order(schema::accounts::order_id.desc())
.select(AccountRow::as_select())
.first(conn)
.optional()?;
row.map(|AccountRow { account_data, .. }| conversions::account_from_bytes(&account_data))
.transpose()
}