-
Notifications
You must be signed in to change notification settings - Fork 84
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat(core): multi-pubkey DB support #2093
base: dev
Are you sure you want to change the base?
Conversation
Signed-off-by: onur-ozkan <work@onurozkan.dev>
Signed-off-by: onur-ozkan <work@onurozkan.dev>
Signed-off-by: onur-ozkan <work@onurozkan.dev>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you for the work @borngraced. We need to add test coverage on this massive change of core mm2 logic.
This PR needs to be tested very carefully.
cc @KomodoPlatform/qa
Some initial notes from my end:
@@ -219,25 +220,27 @@ impl Default for HDWalletCoinStorage { | |||
} | |||
|
|||
impl HDWalletCoinStorage { | |||
// TODO: Since hd_wallet_rmd160 is unique for a device, do we use it as db_id too? or we can just use mm2 shared_db_id and use hd_wallet_rmd160 for primary key as it's currently done |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we combine hd wallet with external wallets? I don't think it is possible, is it? @shamardy
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've previously discussed this with @borngraced via DM. The db path which stores accounts and addresses previously utilized by the user (which is hd_wallet_rmd160
) should be global for a seed. However, each address should use its own db path for orders, swaps, etc.
This approach ensures more flexibility. For instance, if the same seed is used in both Keplr and mm2, and a swap is initiated using Keplr, then the app was closed midway through the swap. Upon restarting, if the Tendermint coin is activated using mm2 seed and the address enabled for swaps is the same address that was used before in Keplr, the swap will complete successfully.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For instance, if the same seed is used in both Keplr and mm2, and a swap is initiated using Keplr, then the app was closed midway through the swap. Upon restarting, if the Tendermint coin is activated using mm2 seed and the address enabled for swaps is the same address that was used before in Keplr, the swap will complete successfully.
I guess this is one of the test cases that should be tested by QA/GUI team once this PR is ready for testing
c.c. @smk762 @naezith
pub async fn enable_account(ctx: MmArc, req: EnableAccountRequest) -> MmResult<SuccessResponse, AccountRpcError> { | ||
let account_ctx = AccountContext::from_ctx(&ctx).map_to_mm(AccountRpcError::Internal)?; | ||
// TODO db_id | ||
let account_ctx = AccountContext::from_ctx(&ctx, None).map_to_mm(AccountRpcError::Internal)?; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess there is no way for this function to figure out db_id, if I am not mistaken? If I am right, we should probably extend the function args with db_id
arg.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah there're some other rpc methods like this too.. cc @shamardy
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is part of the GUI storage methods which was done by Sergey a long time ago and we later decided to not utilize it for HD wallet. GUI storage methods can be safely removed from the codebase, if we ever need it in the future, we can get it from commits history but my implementation approach for HD wallets will not need it as far as I can see.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess just comment them out?
Currently, without making a big refactoring, this can be achieved from the coin activation functions I believe. |
yep I accomplished task 1 by implementing a db migration watcher which keeps track of new db_id and run migrations/fix shared_db_dir if needed b370bec |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yep I accomplished task 1 by implementing a db migration watcher which keeps track of new db_id and run migrations/fix shared_db_dir if needed b370bec
Q: What we call first when we are about to create new db? Can we do this migrations in the on-demand mode without running async runtime?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you add a TODO note somewhere on db id handling implementation which includes the address of #2122 issue ?
mm2src/coins_activation/src/tendermint_with_assets_activation.rs
Outdated
Show resolved
Hide resolved
mm2src/coins_activation/src/tendermint_with_assets_activation.rs
Outdated
Show resolved
Hide resolved
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think tendermint_tx_history_v2
also needs some magic in order to keep the history data separated between inner-external accounts 🫤 I hope I am wrong.. A confirmation from GUI team or QA team could be nice.
Ok(HDWalletIndexedDbStorage { db }) | ||
Ok(HDWalletIndexedDbStorage { | ||
db, | ||
db_id: db_id.map(|e| e.to_string()), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
e
may lead to confusions as it refers to error
in most cases.
db_id: db_id.map(|e| e.to_string()), | |
db_id: db_id.map(|str| str.to_string()), |
OR:
db_id: db_id.map(|e| e.to_string()), | |
db_id: db_id.map(String::from), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
/// This function is used in `hd_wallet_storage::tests`. | ||
pub(super) async fn get_all_storage_items(ctx: &MmArc) -> Vec<HDAccountStorageItem> { | ||
let coins_ctx = CoinsContext::from_ctx(ctx).unwrap(); | ||
let db = coins_ctx.hd_wallet_db.get_or_initialize().await.unwrap(); | ||
let db = coins_ctx.hd_wallet_db.get_or_initialize(None).await.unwrap(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we add conditional compilation attributes on fn get_all_storage_items
to make it accessible only from tests?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
mm2src/coins/lp_coins.rs
Outdated
if active_only && coin.is_available() { | ||
account_ids.insert(account.clone()); | ||
continue; | ||
}; | ||
|
||
if !active_only { | ||
account_ids.insert(account); | ||
continue; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: active_only && coin.is_available() || !active_only
should handle both in single block.
This pull request enables support for managing multiple public keys in mm2 databases. Initially, a single database instance is generated using the startup public key rmd160. With this update, the
mm_ctx
will manage multiple database instances by leveraging the public key fromMmCoin::account_db_id
if defined, or defaulting to the mm2 startup public key.Completed
sql_connection_pool
for managing all instances of shared and sqlite connections from one placeasync_sql_connection_pool
for managing all instances of async sqlite connections from one placeindexeddb
driver implementation to allow multi pubkey supportSwapContext
,MySwapStorage
,MakerSwapStorage
,TakerSwapStorage
NftCtx
,UtxoBlockHeaderStorage
,Zcoin storages(web only)
,lp_ordermatch
and other storage impl to support multipubkeyComplex Todos:
kick_start
unfinished swap upon new database instance creation or account activation using a custom public key.Todos