miden_client/store/
account.rs

1// ACCOUNT RECORD
2// ================================================================================================
3use alloc::vec::Vec;
4use core::fmt::Display;
5
6use miden_objects::Word;
7use miden_objects::account::{Account, AccountId};
8
9/// Represents a stored account state along with its status.
10///
11/// The account should be stored in the database with its parts normalized. Meaning that the
12/// account header, vault, storage and code are stored separately. This is done to avoid data
13/// duplication as the header can reference the same elements if they have equal roots.
14#[derive(Debug)]
15pub struct AccountRecord {
16    /// Full account object.
17    account: Account,
18    /// Status of the tracked account.
19    status: AccountStatus,
20}
21
22impl AccountRecord {
23    pub fn new(account: Account, status: AccountStatus) -> Self {
24        Self { account, status }
25    }
26
27    pub fn account(&self) -> &Account {
28        &self.account
29    }
30
31    pub fn status(&self) -> &AccountStatus {
32        &self.status
33    }
34
35    pub fn is_locked(&self) -> bool {
36        self.status.is_locked()
37    }
38
39    pub fn seed(&self) -> Option<&Word> {
40        self.status.seed()
41    }
42}
43
44impl From<AccountRecord> for Account {
45    fn from(record: AccountRecord) -> Self {
46        record.account
47    }
48}
49
50// ACCOUNT STATUS
51// ================================================================================================
52
53/// Represents the status of an account tracked by the client.
54///
55/// The status of an account may change by local or external factors.
56#[derive(Debug)]
57pub enum AccountStatus {
58    /// The account is new and hasn't been used yet. The seed used to create the account is
59    /// stored in this state.
60    New { seed: Word },
61    /// The account is tracked by the node and was used at least once.
62    Tracked,
63    /// The local account state doesn't match the node's state, rendering it unusable. Only used
64    /// for private accounts.
65    Locked,
66}
67
68impl AccountStatus {
69    pub fn is_locked(&self) -> bool {
70        matches!(self, AccountStatus::Locked)
71    }
72
73    pub fn seed(&self) -> Option<&Word> {
74        match self {
75            AccountStatus::New { seed } => Some(seed),
76            _ => None,
77        }
78    }
79}
80
81impl Display for AccountStatus {
82    fn fmt(&self, f: &mut core::fmt::Formatter) -> core::fmt::Result {
83        match self {
84            AccountStatus::New { .. } => write!(f, "New"),
85            AccountStatus::Tracked => write!(f, "Tracked"),
86            AccountStatus::Locked => write!(f, "Locked"),
87        }
88    }
89}
90
91// ACCOUNT UPDATES
92// ================================================================================================
93
94/// Contains account changes to apply to the store.
95pub struct AccountUpdates {
96    /// Updated public accounts.
97    updated_public_accounts: Vec<Account>,
98    /// Network account commitments that don't match the current tracked state for private
99    /// accounts.
100    mismatched_private_accounts: Vec<(AccountId, Word)>,
101}
102
103impl AccountUpdates {
104    /// Creates a new instance of `AccountUpdates`.
105    pub fn new(
106        updated_public_accounts: Vec<Account>,
107        mismatched_private_accounts: Vec<(AccountId, Word)>,
108    ) -> Self {
109        Self {
110            updated_public_accounts,
111            mismatched_private_accounts,
112        }
113    }
114
115    /// Returns the updated public accounts.
116    pub fn updated_public_accounts(&self) -> &[Account] {
117        &self.updated_public_accounts
118    }
119
120    /// Returns the mismatched private accounts.
121    pub fn mismatched_private_accounts(&self) -> &[(AccountId, Word)] {
122        &self.mismatched_private_accounts
123    }
124}