Unilateral-exit readiness
Breez's default mobile persistence does not retain the needed exit tree
The reviewed Breez mobile configuration stores ordinary wallet data in SQLite but supplies no persistent tree store, falling back to an in-memory tree store. The lower-level exit service requires tree nodes that this default mobile path does not durably retain. 123
What the evidence shows
Technical and product details
- Documented behavior
The default Breez SQLite backend returns tree_store: None. 1
Supporting material shown on this page
SQLite backendPinned source code · github.com · checked 2026-07-14 Relevant lines from the pinned source · open raw file 33 PublicKey::from_slice(&identity).map_err(|e| SdkError::Generic(e.to_string()))?; 34 let db_path = crate::default_storage_path(&self.storage_dir, &network, &identity)?; 35 let storage = Arc::new(SqliteStorage::new(&db_path)?); 36 Ok(Arc::new(ResolvedStores { 37 storage, 38 tree_store: None, 39 token_output_store: None, - Technical details
WalletBuilder replaces a missing store with InMemoryTreeStore; normal leaf refresh uses include_parents=false; process death therefore does not preserve the ancestor graph through that default tree-store path. 23
Supporting material shown on this page
WalletBuilder fallbackPinned source code · github.com · checked 2026-07-14 Relevant lines from the pinned source · open raw file 120 self.config, 121 self.spark_signer, 122 self.session_store 123 .unwrap_or(Arc::new(InMemorySessionStore::default())), 124 self.tree_store 125 .unwrap_or(Arc::new(InMemoryTreeStore::default())), 126 self.token_output_storenormal leaf queryPinned source code · github.com · checked 2026-07-14 Relevant lines from the pinned source · open raw file 199 .get_non_coordinator_operators() 200 .map(|op| (op.id, op.client.clone())) 201 .collect(); 202 203 let coord_fut = 204 self.query_nodes(&coordinator_client, false, None, available_leaf_statuses()); 205 let op_futs = operators.iter().map(|(id, client)| async move { - Product consequence
Durable operator-outage state is an additional integration feature, not a property supplied by the ordinary seed/SQLite setup. 123
Supporting material shown on this page
SQLite backendPinned source code · github.com · checked 2026-07-14 Relevant lines from the pinned source · open raw file 33 PublicKey::from_slice(&identity).map_err(|e| SdkError::Generic(e.to_string()))?; 34 let db_path = crate::default_storage_path(&self.storage_dir, &network, &identity)?; 35 let storage = Arc::new(SqliteStorage::new(&db_path)?); 36 Ok(Arc::new(ResolvedStores { 37 storage, 38 tree_store: None, 39 token_output_store: None,WalletBuilder fallbackPinned source code · github.com · checked 2026-07-14 Relevant lines from the pinned source · open raw file 120 self.config, 121 self.spark_signer, 122 self.session_store 123 .unwrap_or(Arc::new(InMemorySessionStore::default())), 124 self.tree_store 125 .unwrap_or(Arc::new(InMemoryTreeStore::default())), 126 self.token_output_storenormal leaf queryPinned source code · github.com · checked 2026-07-14 Relevant lines from the pinned source · open raw file 199 .get_non_coordinator_operators() 200 .map(|op| (op.id, op.client.clone())) 201 .collect(); 202 203 let coord_fut = 204 self.query_nodes(&coordinator_client, false, None, available_leaf_statuses()); 205 let op_futs = operators.iter().map(|(id, client)| async move {
Scope control
What this does not establish
Sources and excerpts
Primary sources
The relevant details and available source-code excerpts appear alongside the claims above. This list preserves the complete original-source trail for independent verification.
SQLite backend
Pinned source code · github.com · Pinned or archival · checked 2026-07-14
WalletBuilder fallback
Pinned source code · github.com · Pinned or archival · checked 2026-07-14
normal leaf query
Pinned source code · github.com · Pinned or archival · checked 2026-07-14
How sources, absence findings, and limitations were evaluated