app

Local-first trade for farms and co-ops
git clone https://radroots.dev/git/app.git
Log | Files | Refs | README | LICENSE

commit 0e123a2f9f47664ec175115e10aba9785d4bf674
parent e5762fa32e6973d78415680e437a763da8cbc9f4
Author: triesap <triesap@radroots.dev>
Date:   Mon, 19 Jan 2026 19:42:41 +0000

app: persist nostr public key in app data

- add helper to read app data from datastore
- store active_key from keystore during init
- write updated app data when missing or stale
- add unit test for app data read errors

Diffstat:
Mapp/src/bootstrap.rs | 34+++++++++++++++++++++++++++++-----
Mapp/src/init.rs | 20++++++++++++++------
Mapp/src/lib.rs | 1+
3 files changed, 44 insertions(+), 11 deletions(-)

diff --git a/app/src/bootstrap.rs b/app/src/bootstrap.rs @@ -48,6 +48,17 @@ pub async fn app_datastore_write_app_data<T: RadrootsClientDatastore>( .map_err(AppInitError::Datastore) } +pub async fn app_datastore_read_app_data<T: RadrootsClientDatastore>( + datastore: &T, + key_maps: &AppKeyMapConfig, +) -> AppInitResult<AppAppData> { + let key = app_datastore_obj_key_app_data(key_maps).map_err(AppInitError::Config)?; + datastore + .get_obj::<AppAppData>(key) + .await + .map_err(AppInitError::Datastore) +} + pub async fn app_datastore_has_app_data<T: RadrootsClientDatastore>( datastore: &T, key_maps: &AppKeyMapConfig, @@ -81,11 +92,12 @@ pub async fn app_datastore_clear_bootstrap<T: RadrootsClientDatastore>( mod tests { use super::{ app_datastore_clear_bootstrap, - app_datastore_has_app_data, - app_datastore_has_config, - app_datastore_write_app_data, - app_datastore_write_config, - }; + app_datastore_has_app_data, + app_datastore_has_config, + app_datastore_read_app_data, + app_datastore_write_app_data, + app_datastore_write_config, +}; use crate::{app_key_maps_default, AppAppData, AppConfigData, AppInitError}; use radroots_app_core::datastore::{RadrootsClientDatastoreError, RadrootsClientWebDatastore}; @@ -118,6 +130,18 @@ mod tests { } #[test] + fn app_data_read_maps_idb_errors() { + let datastore = RadrootsClientWebDatastore::new(None); + let key_maps = app_key_maps_default(); + let err = futures::executor::block_on(app_datastore_read_app_data( + &datastore, + &key_maps, + )) + .expect_err("idb undefined"); + assert_eq!(err, AppInitError::Datastore(RadrootsClientDatastoreError::IdbUndefined)); + } + + #[test] fn clear_bootstrap_maps_idb_errors() { let datastore = RadrootsClientWebDatastore::new(None); let key_maps = app_key_maps_default(); diff --git a/app/src/init.rs b/app/src/init.rs @@ -23,6 +23,7 @@ use crate::{ app_datastore_has_app_data, app_datastore_has_config, app_datastore_key_nostr_key, + app_datastore_read_app_data, app_datastore_write_app_data, app_datastore_write_config, app_keystore_nostr_ensure_key, @@ -198,12 +199,6 @@ pub async fn app_init_backends(config: AppConfig) -> AppInitResult<AppBackends> app_datastore_write_config(&datastore, &config.datastore.key_maps, &config_data) .await?; } - let has_app_data = app_datastore_has_app_data(&datastore, &config.datastore.key_maps).await?; - if !has_app_data { - let app_data = AppAppData::default(); - let _ = app_datastore_write_app_data(&datastore, &config.datastore.key_maps, &app_data) - .await?; - } let nostr_keystore = RadrootsClientWebKeystoreNostr::new(Some(config.keystore.nostr_store)); let nostr_public_key = app_keystore_nostr_ensure_key(&nostr_keystore) .await @@ -229,6 +224,19 @@ pub async fn app_init_backends(config: AppConfig) -> AppInitResult<AppBackends> } Err(err) => return Err(AppInitError::Datastore(err)), } + let has_app_data = app_datastore_has_app_data(&datastore, &config.datastore.key_maps).await?; + let mut app_data = if has_app_data { + app_datastore_read_app_data(&datastore, &config.datastore.key_maps).await? + } else { + AppAppData::default() + }; + let should_write = !has_app_data || app_data.active_key != nostr_public_key; + if should_write { + app_data.active_key = nostr_public_key; + let _ = + app_datastore_write_app_data(&datastore, &config.datastore.key_maps, &app_data) + .await?; + } Ok(AppBackends { config, datastore, diff --git a/app/src/lib.rs b/app/src/lib.rs @@ -15,6 +15,7 @@ pub use bootstrap::{ app_datastore_clear_bootstrap, app_datastore_has_app_data, app_datastore_has_config, + app_datastore_read_app_data, app_datastore_write_app_data, app_datastore_write_config, };