Skip to content

feat: make MoneyAccountUpgradeController own its bootstrap - #10072

Open
Jwhiles wants to merge 9 commits into
mainfrom
money-account-upgrade-controller-owned-bootstrap
Open

feat: make MoneyAccountUpgradeController own its bootstrap#10072
Jwhiles wants to merge 9 commits into
mainfrom
money-account-upgrade-controller-owned-bootstrap

Conversation

@Jwhiles

@Jwhiles Jwhiles commented Sep 2, 2026

Copy link
Copy Markdown
Contributor

Explanation

This updates the money account upgrade controller to make it better able to handle its own initialisation. At the moment clients have to manage initialising the controller, leading to a lot of shared code. This PR tries to move that logic into the controller itself as much as possible

Key changes:

  • The controller subscribes to RemoteFeatureFlagController:stateChanged and KeyringController:stateChanged and uses this information to bootstrap itself.
  • BREAKING: init() now takes no arguments, and merely sets up subscriptions to to some messenger events.
  • BREAKING: the constructor requires a hooks option for the parts of the upgrade flow that can only be determined in the client.
  • upgradeAccount() waits for an in-flight bootstrap instead of throwing (replacing mobile's module-level whenMoneyAccountUpgradeReady promise), and is disarmed when isEnabled flips off so it cannot run against a stale config.
  • A public sync() lets clients re-trigger the bootstraps checks from client-only signals - for example onboarding being completed.
  • Vault-config parsing/validation and comparison move to @metamask/money-account-utils (getMoneyAccountVaultConfig, parseMoneyAccountVaultConfig, areMoneyAccountVaultConfigsEqual, MoneyAccountVaultConfig), shared by the controller and both clients.

References

Checklist

  • I've updated the test suite for new or updated code as appropriate
  • I've updated documentation (JSDoc, Markdown, etc.) for new or updated code as appropriate
  • I've communicated my changes to consumers by updating changelogs for packages I've changed, highlighting breaking changes as necessary
  • I've prepared draft pull requests for clients and consumer packages to resolve any breaking changes

Note

High Risk
Breaking controller API and bootstrap timing affect wallet upgrade flows that sign EIP-7702 authorizations and delegations; incorrect gating or config supersession logic could block upgrades or sign against wrong vault parameters.

Overview
MoneyAccountUpgradeController now bootstraps itself instead of relying on clients to call init({ chainId, boringVaultAddress }). After a no-arg init(), it listens to remote feature flags and keyring state, gates on client hooks (isEnabled, optional isEligible / ensureChainConfigured / onBootstrapError), parses moneyAccountVaultConfig, then fetches CHOMP service details to arm the upgrade config.

Breaking API: constructor requires hooks; messenger must allow RemoteFeatureFlagController and KeyringController getState + stateChange. upgradeAccount() waits for in-flight bootstrap, refuses when disarmed (feature off, failed bootstrap, locked wallet), and aborts mid-sequence if the vault config is superseded so nothing signs against a stale vault. Public sync() re-runs gates for client-only signals (e.g. onboarding).

Vault parsing moves to @metamask/money-account-utils (getMoneyAccountVaultConfig, parseMoneyAccountVaultConfig, areMoneyAccountVaultConfigsEqual, MissingMoneyAccountVaultConfigError in the upgrade package). Tests and changelogs document serialization, re-bootstrap on config change, and error reporting.

Reviewed by Cursor Bugbot for commit 5f5d356. Bugbot is set up for automated code reviews on this repo. Configure here.

@Jwhiles

Jwhiles commented Sep 2, 2026

Copy link
Copy Markdown
Contributor Author

@metamaskbot publish-preview

1 similar comment
@Jwhiles

Jwhiles commented Sep 2, 2026

Copy link
Copy Markdown
Contributor Author

@metamaskbot publish-preview

@github-actions

github-actions Bot commented Sep 2, 2026

Copy link
Copy Markdown
Contributor

Preview builds have been published. Learn how to use preview builds in other projects.

Expand for full list of packages and versions.
@metamask-previews/account-tree-controller@8.0.0-preview-7e951bf
@metamask-previews/accounts-controller@39.1.1-preview-7e951bf
@metamask-previews/address-book-controller@7.1.2-preview-7e951bf
@metamask-previews/ai-controllers@1.0.0-preview-7e951bf
@metamask-previews/analytics-controller@2.0.0-preview-7e951bf
@metamask-previews/analytics-data-regulation-controller@0.0.0-preview-7e951bf
@metamask-previews/announcement-controller@8.1.0-preview-7e951bf
@metamask-previews/app-metadata-controller@2.0.1-preview-7e951bf
@metamask-previews/approval-controller@9.0.2-preview-7e951bf
@metamask-previews/assets-controller@14.0.3-preview-7e951bf
@metamask-previews/assets-controllers@111.1.3-preview-7e951bf
@metamask-previews/authenticated-user-storage@3.0.2-preview-7e951bf
@metamask-previews/base-controller@9.1.0-preview-7e951bf
@metamask-previews/base-data-service@1.0.0-preview-7e951bf
@metamask-previews/bitcoin-regtest-up@1.0.0-preview-7e951bf
@metamask-previews/bridge-controller@80.1.1-preview-7e951bf
@metamask-previews/bridge-status-controller@75.4.0-preview-7e951bf
@metamask-previews/build-utils@3.0.4-preview-7e951bf
@metamask-previews/chain-agnostic-permission@1.7.0-preview-7e951bf
@metamask-previews/chomp-api-service@4.0.1-preview-7e951bf
@metamask-previews/claims-controller@0.6.1-preview-7e951bf
@metamask-previews/client-controller@1.0.1-preview-7e951bf
@metamask-previews/client-utils@2.1.1-preview-7e951bf
@metamask-previews/compliance-controller@2.1.0-preview-7e951bf
@metamask-previews/composable-controller@12.0.1-preview-7e951bf
@metamask-previews/config-registry-controller@3.1.0-preview-7e951bf
@metamask-previews/connectivity-controller@0.3.0-preview-7e951bf
@metamask-previews/controller-utils@12.3.0-preview-7e951bf
@metamask-previews/core-backend@9.0.0-preview-7e951bf
@metamask-previews/delegation-controller@3.0.2-preview-7e951bf
@metamask-previews/earn-controller@12.2.6-preview-7e951bf
@metamask-previews/eip-5792-middleware@3.0.5-preview-7e951bf
@metamask-previews/eip-7702-internal-rpc-middleware@0.1.1-preview-7e951bf
@metamask-previews/eip1193-permission-middleware@2.0.1-preview-7e951bf
@metamask-previews/eth-block-tracker@15.0.1-preview-7e951bf
@metamask-previews/eth-json-rpc-middleware@24.0.2-preview-7e951bf
@metamask-previews/eth-json-rpc-provider@6.0.1-preview-7e951bf
@metamask-previews/foundryup@1.0.1-preview-7e951bf
@metamask-previews/gas-fee-controller@26.3.2-preview-7e951bf
@metamask-previews/gator-permissions-controller@5.0.2-preview-7e951bf
@metamask-previews/geolocation-controller@1.0.0-preview-7e951bf
@metamask-previews/java-tron-up@1.0.0-preview-7e951bf
@metamask-previews/json-rpc-engine@10.5.0-preview-7e951bf
@metamask-previews/json-rpc-middleware-stream@8.0.8-preview-7e951bf
@metamask-previews/keyring-controller@27.1.1-preview-7e951bf
@metamask-previews/kyc-controller@0.0.0-preview-7e951bf
@metamask-previews/local-node-utils@1.0.0-preview-7e951bf
@metamask-previews/logging-controller@9.0.0-preview-7e951bf
@metamask-previews/message-manager@14.1.2-preview-7e951bf
@metamask-previews/messenger@2.0.0-preview-7e951bf
@metamask-previews/messenger-cli@0.2.0-preview-7e951bf
@metamask-previews/money-account-api-data-service@0.4.1-preview-7e951bf
@metamask-previews/money-account-balance-service@2.4.3-preview-7e951bf
@metamask-previews/money-account-controller@1.0.0-preview-7e951bf
@metamask-previews/money-account-upgrade-controller@3.0.2-preview-7e951bf
@metamask-previews/money-account-utils@1.1.0-preview-7e951bf
@metamask-previews/multichain-account-service@13.0.2-preview-7e951bf
@metamask-previews/multichain-api-middleware@4.0.3-preview-7e951bf
@metamask-previews/multichain-network-controller@3.2.4-preview-7e951bf
@metamask-previews/multichain-transactions-controller@7.1.2-preview-7e951bf
@metamask-previews/name-controller@9.1.2-preview-7e951bf
@metamask-previews/network-connection-banner-controller@0.2.1-preview-7e951bf
@metamask-previews/network-controller@36.0.0-preview-7e951bf
@metamask-previews/network-enablement-controller@6.0.5-preview-7e951bf
@metamask-previews/notification-services-controller@26.0.1-preview-7e951bf
@metamask-previews/passkey-controller@3.1.0-preview-7e951bf
@metamask-previews/permission-controller@13.1.1-preview-7e951bf
@metamask-previews/permission-log-controller@5.1.0-preview-7e951bf
@metamask-previews/perps-controller@15.1.0-preview-7e951bf
@metamask-previews/phishing-controller@17.4.0-preview-7e951bf
@metamask-previews/platform-api-docs@0.1.0-preview-7e951bf
@metamask-previews/polling-controller@16.0.9-preview-7e951bf
@metamask-previews/preferences-controller@23.1.0-preview-7e951bf
@metamask-previews/profile-metrics-controller@4.0.3-preview-7e951bf
@metamask-previews/profile-sync-controller@29.0.0-preview-7e951bf
@metamask-previews/ramps-controller@20.2.0-preview-7e951bf
@metamask-previews/rate-limit-controller@7.0.1-preview-7e951bf
@metamask-previews/react-data-query@1.0.0-preview-7e951bf
@metamask-previews/remote-feature-flag-controller@6.1.0-preview-7e951bf
@metamask-previews/sample-controllers@5.0.6-preview-7e951bf
@metamask-previews/seedless-onboarding-controller@10.1.1-preview-7e951bf
@metamask-previews/selected-network-controller@26.1.7-preview-7e951bf
@metamask-previews/sentinel-api-service@1.0.1-preview-7e951bf
@metamask-previews/shield-controller@6.0.1-preview-7e951bf
@metamask-previews/signature-controller@39.2.10-preview-7e951bf
@metamask-previews/smart-transactions-controller@26.0.0-preview-7e951bf
@metamask-previews/snap-account-service@2.1.2-preview-7e951bf
@metamask-previews/social-controllers@2.8.0-preview-7e951bf
@metamask-previews/solana-test-validator-up@1.0.0-preview-7e951bf
@metamask-previews/stellar-quickstart-up@0.0.0-preview-7e951bf
@metamask-previews/storage-service@1.0.2-preview-7e951bf
@metamask-previews/subscription-controller@8.0.1-preview-7e951bf
@metamask-previews/transaction-controller@69.7.0-preview-7e951bf
@metamask-previews/transaction-pay-controller@27.1.1-preview-7e951bf
@metamask-previews/user-operation-controller@41.2.9-preview-7e951bf
@metamask-previews/wallet@12.0.2-preview-7e951bf
@metamask-previews/wallet-cli@0.0.0-preview-7e951bf

@github-actions

github-actions Bot commented Sep 2, 2026

Copy link
Copy Markdown
Contributor

Preview builds have been published. Learn how to use preview builds in other projects.

Expand for full list of packages and versions.
@metamask-previews/account-tree-controller@8.0.0-preview-6b7c25c
@metamask-previews/accounts-controller@39.1.1-preview-6b7c25c
@metamask-previews/address-book-controller@7.1.2-preview-6b7c25c
@metamask-previews/ai-controllers@1.0.0-preview-6b7c25c
@metamask-previews/analytics-controller@2.0.0-preview-6b7c25c
@metamask-previews/analytics-data-regulation-controller@0.0.0-preview-6b7c25c
@metamask-previews/announcement-controller@8.1.0-preview-6b7c25c
@metamask-previews/app-metadata-controller@2.0.1-preview-6b7c25c
@metamask-previews/approval-controller@9.0.2-preview-6b7c25c
@metamask-previews/assets-controller@14.0.3-preview-6b7c25c
@metamask-previews/assets-controllers@111.1.3-preview-6b7c25c
@metamask-previews/authenticated-user-storage@3.0.2-preview-6b7c25c
@metamask-previews/base-controller@9.1.0-preview-6b7c25c
@metamask-previews/base-data-service@1.0.0-preview-6b7c25c
@metamask-previews/bitcoin-regtest-up@1.0.0-preview-6b7c25c
@metamask-previews/bridge-controller@80.1.1-preview-6b7c25c
@metamask-previews/bridge-status-controller@75.4.0-preview-6b7c25c
@metamask-previews/build-utils@3.0.4-preview-6b7c25c
@metamask-previews/chain-agnostic-permission@1.7.0-preview-6b7c25c
@metamask-previews/chomp-api-service@4.0.1-preview-6b7c25c
@metamask-previews/claims-controller@0.6.1-preview-6b7c25c
@metamask-previews/client-controller@1.0.1-preview-6b7c25c
@metamask-previews/client-utils@2.1.1-preview-6b7c25c
@metamask-previews/compliance-controller@2.1.0-preview-6b7c25c
@metamask-previews/composable-controller@12.0.1-preview-6b7c25c
@metamask-previews/config-registry-controller@3.1.0-preview-6b7c25c
@metamask-previews/connectivity-controller@0.3.0-preview-6b7c25c
@metamask-previews/controller-utils@12.3.0-preview-6b7c25c
@metamask-previews/core-backend@9.0.0-preview-6b7c25c
@metamask-previews/delegation-controller@3.0.2-preview-6b7c25c
@metamask-previews/earn-controller@12.2.6-preview-6b7c25c
@metamask-previews/eip-5792-middleware@3.0.5-preview-6b7c25c
@metamask-previews/eip-7702-internal-rpc-middleware@0.1.1-preview-6b7c25c
@metamask-previews/eip1193-permission-middleware@2.0.1-preview-6b7c25c
@metamask-previews/eth-block-tracker@15.0.1-preview-6b7c25c
@metamask-previews/eth-json-rpc-middleware@24.0.2-preview-6b7c25c
@metamask-previews/eth-json-rpc-provider@6.0.1-preview-6b7c25c
@metamask-previews/foundryup@1.0.1-preview-6b7c25c
@metamask-previews/gas-fee-controller@26.3.2-preview-6b7c25c
@metamask-previews/gator-permissions-controller@5.0.2-preview-6b7c25c
@metamask-previews/geolocation-controller@1.0.0-preview-6b7c25c
@metamask-previews/java-tron-up@1.0.0-preview-6b7c25c
@metamask-previews/json-rpc-engine@10.5.0-preview-6b7c25c
@metamask-previews/json-rpc-middleware-stream@8.0.8-preview-6b7c25c
@metamask-previews/keyring-controller@27.1.1-preview-6b7c25c
@metamask-previews/kyc-controller@0.0.0-preview-6b7c25c
@metamask-previews/local-node-utils@1.0.0-preview-6b7c25c
@metamask-previews/logging-controller@9.0.0-preview-6b7c25c
@metamask-previews/message-manager@14.1.2-preview-6b7c25c
@metamask-previews/messenger@2.0.0-preview-6b7c25c
@metamask-previews/messenger-cli@0.2.0-preview-6b7c25c
@metamask-previews/money-account-api-data-service@0.4.1-preview-6b7c25c
@metamask-previews/money-account-balance-service@2.4.3-preview-6b7c25c
@metamask-previews/money-account-controller@1.0.0-preview-6b7c25c
@metamask-previews/money-account-upgrade-controller@3.0.2-preview-6b7c25c
@metamask-previews/money-account-utils@1.1.0-preview-6b7c25c
@metamask-previews/multichain-account-service@13.0.2-preview-6b7c25c
@metamask-previews/multichain-api-middleware@4.0.3-preview-6b7c25c
@metamask-previews/multichain-network-controller@3.2.4-preview-6b7c25c
@metamask-previews/multichain-transactions-controller@7.1.2-preview-6b7c25c
@metamask-previews/name-controller@9.1.2-preview-6b7c25c
@metamask-previews/network-connection-banner-controller@0.2.1-preview-6b7c25c
@metamask-previews/network-controller@36.0.0-preview-6b7c25c
@metamask-previews/network-enablement-controller@6.0.5-preview-6b7c25c
@metamask-previews/notification-services-controller@26.0.1-preview-6b7c25c
@metamask-previews/passkey-controller@3.1.0-preview-6b7c25c
@metamask-previews/permission-controller@13.1.1-preview-6b7c25c
@metamask-previews/permission-log-controller@5.1.0-preview-6b7c25c
@metamask-previews/perps-controller@15.1.0-preview-6b7c25c
@metamask-previews/phishing-controller@17.4.0-preview-6b7c25c
@metamask-previews/platform-api-docs@0.1.0-preview-6b7c25c
@metamask-previews/polling-controller@16.0.9-preview-6b7c25c
@metamask-previews/preferences-controller@23.1.0-preview-6b7c25c
@metamask-previews/profile-metrics-controller@4.0.3-preview-6b7c25c
@metamask-previews/profile-sync-controller@29.0.0-preview-6b7c25c
@metamask-previews/ramps-controller@20.2.0-preview-6b7c25c
@metamask-previews/rate-limit-controller@7.0.1-preview-6b7c25c
@metamask-previews/react-data-query@1.0.0-preview-6b7c25c
@metamask-previews/remote-feature-flag-controller@6.1.0-preview-6b7c25c
@metamask-previews/sample-controllers@5.0.6-preview-6b7c25c
@metamask-previews/seedless-onboarding-controller@10.1.1-preview-6b7c25c
@metamask-previews/selected-network-controller@26.1.7-preview-6b7c25c
@metamask-previews/sentinel-api-service@1.0.1-preview-6b7c25c
@metamask-previews/shield-controller@6.0.1-preview-6b7c25c
@metamask-previews/signature-controller@39.2.10-preview-6b7c25c
@metamask-previews/smart-transactions-controller@26.0.0-preview-6b7c25c
@metamask-previews/snap-account-service@2.1.2-preview-6b7c25c
@metamask-previews/social-controllers@2.8.0-preview-6b7c25c
@metamask-previews/solana-test-validator-up@1.0.0-preview-6b7c25c
@metamask-previews/stellar-quickstart-up@0.0.0-preview-6b7c25c
@metamask-previews/storage-service@1.0.2-preview-6b7c25c
@metamask-previews/subscription-controller@8.0.1-preview-6b7c25c
@metamask-previews/transaction-controller@69.7.0-preview-6b7c25c
@metamask-previews/transaction-pay-controller@27.1.1-preview-6b7c25c
@metamask-previews/user-operation-controller@41.2.9-preview-6b7c25c
@metamask-previews/wallet@12.0.2-preview-6b7c25c
@metamask-previews/wallet-cli@0.0.0-preview-6b7c25c

@Jwhiles

Jwhiles commented Sep 2, 2026

Copy link
Copy Markdown
Contributor Author

@metamaskbot publish-preview

@github-actions

github-actions Bot commented Sep 2, 2026

Copy link
Copy Markdown
Contributor

Preview builds have been published. Learn how to use preview builds in other projects.

Expand for full list of packages and versions.
@metamask-previews/account-tree-controller@8.0.0-preview-1ee21f9e0
@metamask-previews/accounts-controller@39.1.1-preview-1ee21f9e0
@metamask-previews/address-book-controller@7.1.2-preview-1ee21f9e0
@metamask-previews/ai-controllers@1.0.0-preview-1ee21f9e0
@metamask-previews/analytics-controller@2.0.0-preview-1ee21f9e0
@metamask-previews/analytics-data-regulation-controller@0.0.0-preview-1ee21f9e0
@metamask-previews/announcement-controller@8.1.0-preview-1ee21f9e0
@metamask-previews/app-metadata-controller@2.0.1-preview-1ee21f9e0
@metamask-previews/approval-controller@9.0.2-preview-1ee21f9e0
@metamask-previews/assets-controller@14.0.3-preview-1ee21f9e0
@metamask-previews/assets-controllers@111.1.3-preview-1ee21f9e0
@metamask-previews/authenticated-user-storage@3.0.2-preview-1ee21f9e0
@metamask-previews/base-controller@9.1.0-preview-1ee21f9e0
@metamask-previews/base-data-service@1.0.0-preview-1ee21f9e0
@metamask-previews/bitcoin-regtest-up@1.0.0-preview-1ee21f9e0
@metamask-previews/bridge-controller@80.1.1-preview-1ee21f9e0
@metamask-previews/bridge-status-controller@75.4.0-preview-1ee21f9e0
@metamask-previews/build-utils@3.0.4-preview-1ee21f9e0
@metamask-previews/chain-agnostic-permission@1.7.0-preview-1ee21f9e0
@metamask-previews/chomp-api-service@4.0.1-preview-1ee21f9e0
@metamask-previews/claims-controller@0.6.1-preview-1ee21f9e0
@metamask-previews/client-controller@1.0.1-preview-1ee21f9e0
@metamask-previews/client-utils@2.1.1-preview-1ee21f9e0
@metamask-previews/compliance-controller@2.1.0-preview-1ee21f9e0
@metamask-previews/composable-controller@12.0.1-preview-1ee21f9e0
@metamask-previews/config-registry-controller@3.1.0-preview-1ee21f9e0
@metamask-previews/connectivity-controller@0.3.0-preview-1ee21f9e0
@metamask-previews/controller-utils@12.3.0-preview-1ee21f9e0
@metamask-previews/core-backend@9.0.0-preview-1ee21f9e0
@metamask-previews/delegation-controller@3.0.2-preview-1ee21f9e0
@metamask-previews/earn-controller@12.2.6-preview-1ee21f9e0
@metamask-previews/eip-5792-middleware@3.0.5-preview-1ee21f9e0
@metamask-previews/eip-7702-internal-rpc-middleware@0.1.1-preview-1ee21f9e0
@metamask-previews/eip1193-permission-middleware@2.0.1-preview-1ee21f9e0
@metamask-previews/eth-block-tracker@15.0.1-preview-1ee21f9e0
@metamask-previews/eth-json-rpc-middleware@24.0.2-preview-1ee21f9e0
@metamask-previews/eth-json-rpc-provider@6.0.1-preview-1ee21f9e0
@metamask-previews/foundryup@1.0.1-preview-1ee21f9e0
@metamask-previews/gas-fee-controller@26.3.2-preview-1ee21f9e0
@metamask-previews/gator-permissions-controller@5.0.2-preview-1ee21f9e0
@metamask-previews/geolocation-controller@1.0.0-preview-1ee21f9e0
@metamask-previews/java-tron-up@1.0.0-preview-1ee21f9e0
@metamask-previews/json-rpc-engine@10.5.0-preview-1ee21f9e0
@metamask-previews/json-rpc-middleware-stream@8.0.8-preview-1ee21f9e0
@metamask-previews/keyring-controller@27.1.1-preview-1ee21f9e0
@metamask-previews/kyc-controller@0.0.0-preview-1ee21f9e0
@metamask-previews/local-node-utils@1.0.0-preview-1ee21f9e0
@metamask-previews/logging-controller@9.0.0-preview-1ee21f9e0
@metamask-previews/message-manager@14.1.2-preview-1ee21f9e0
@metamask-previews/messenger@2.0.0-preview-1ee21f9e0
@metamask-previews/messenger-cli@0.2.0-preview-1ee21f9e0
@metamask-previews/money-account-api-data-service@0.4.1-preview-1ee21f9e0
@metamask-previews/money-account-balance-service@2.4.3-preview-1ee21f9e0
@metamask-previews/money-account-controller@1.0.0-preview-1ee21f9e0
@metamask-previews/money-account-upgrade-controller@3.0.2-preview-1ee21f9e0
@metamask-previews/money-account-utils@1.1.0-preview-1ee21f9e0
@metamask-previews/multichain-account-service@13.0.2-preview-1ee21f9e0
@metamask-previews/multichain-api-middleware@4.0.3-preview-1ee21f9e0
@metamask-previews/multichain-network-controller@3.2.4-preview-1ee21f9e0
@metamask-previews/multichain-transactions-controller@7.1.2-preview-1ee21f9e0
@metamask-previews/name-controller@9.1.2-preview-1ee21f9e0
@metamask-previews/network-connection-banner-controller@0.2.1-preview-1ee21f9e0
@metamask-previews/network-controller@36.0.0-preview-1ee21f9e0
@metamask-previews/network-enablement-controller@6.0.5-preview-1ee21f9e0
@metamask-previews/notification-services-controller@26.0.1-preview-1ee21f9e0
@metamask-previews/passkey-controller@3.1.0-preview-1ee21f9e0
@metamask-previews/permission-controller@13.1.1-preview-1ee21f9e0
@metamask-previews/permission-log-controller@5.1.0-preview-1ee21f9e0
@metamask-previews/perps-controller@15.1.0-preview-1ee21f9e0
@metamask-previews/phishing-controller@17.4.0-preview-1ee21f9e0
@metamask-previews/platform-api-docs@0.1.0-preview-1ee21f9e0
@metamask-previews/polling-controller@16.0.9-preview-1ee21f9e0
@metamask-previews/preferences-controller@23.1.0-preview-1ee21f9e0
@metamask-previews/profile-metrics-controller@4.0.3-preview-1ee21f9e0
@metamask-previews/profile-sync-controller@29.0.0-preview-1ee21f9e0
@metamask-previews/ramps-controller@20.2.0-preview-1ee21f9e0
@metamask-previews/rate-limit-controller@7.0.1-preview-1ee21f9e0
@metamask-previews/react-data-query@1.0.0-preview-1ee21f9e0
@metamask-previews/remote-feature-flag-controller@6.1.0-preview-1ee21f9e0
@metamask-previews/sample-controllers@5.0.6-preview-1ee21f9e0
@metamask-previews/seedless-onboarding-controller@10.1.1-preview-1ee21f9e0
@metamask-previews/selected-network-controller@26.1.7-preview-1ee21f9e0
@metamask-previews/sentinel-api-service@1.0.1-preview-1ee21f9e0
@metamask-previews/shield-controller@6.0.1-preview-1ee21f9e0
@metamask-previews/signature-controller@39.2.10-preview-1ee21f9e0
@metamask-previews/smart-transactions-controller@26.0.0-preview-1ee21f9e0
@metamask-previews/snap-account-service@2.1.2-preview-1ee21f9e0
@metamask-previews/social-controllers@2.8.0-preview-1ee21f9e0
@metamask-previews/solana-test-validator-up@1.0.0-preview-1ee21f9e0
@metamask-previews/stellar-quickstart-up@0.0.0-preview-1ee21f9e0
@metamask-previews/storage-service@1.0.2-preview-1ee21f9e0
@metamask-previews/subscription-controller@8.0.1-preview-1ee21f9e0
@metamask-previews/transaction-controller@69.7.0-preview-1ee21f9e0
@metamask-previews/transaction-pay-controller@27.1.1-preview-1ee21f9e0
@metamask-previews/user-operation-controller@41.2.9-preview-1ee21f9e0
@metamask-previews/wallet@12.0.2-preview-1ee21f9e0
@metamask-previews/wallet-cli@0.0.0-preview-1ee21f9e0

Jwhiles added a commit to MetaMask/metamask-extension that referenced this pull request Sep 2, 2026
MoneyAccountUpgradeController (core PR MetaMask/core#10072) now owns its
bootstrap: it watches the feature-flag and keyring state, parses the vault
config, and serializes its own re-inits. The extension supplies only the
client-specific parts as hooks — the basic-functionality gate inside
isEnabled, the fail-closed geo check as isEligible, the shared Money chain
configurator, and Sentry reporting for a missing vault config — and
MoneyAccountUpgradeService is deleted.

Per review feedback, no messenger calls happen at construction:
metamask-controller calls controller.init() once everything is built,
alongside the other post-construction init() calls, so the init map no
longer carries ordering constraints. Onboarding and preferences changes
re-trigger the controller's gating through its public sync().

The package is pinned to a preview build until core releases
@metamask/money-account-upgrade-controller@4.0.0 and
@metamask/money-account-utils@1.2.0; the resolutions entries and the
^3.0.2 dependency swap to ^4.0.0 / ^1.2.0 then.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@Jwhiles
Jwhiles force-pushed the money-account-upgrade-controller-owned-bootstrap branch from 1ee21f9 to 4258cb1 Compare September 2, 2026 12:25
@Jwhiles
Jwhiles marked this pull request as ready for review September 2, 2026 12:28
@Jwhiles
Jwhiles requested review from a team as code owners September 2, 2026 12:28
@Jwhiles Jwhiles changed the title feat!: make MoneyAccountUpgradeController own its bootstrap feat: make MoneyAccountUpgradeController own its bootstrap Sep 2, 2026
@Jwhiles
Jwhiles force-pushed the money-account-upgrade-controller-owned-bootstrap branch from 4258cb1 to 81700ed Compare September 2, 2026 12:30

@cursor cursor Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes and found 1 potential issue.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, have a team admin enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit 81700ed. Configure here.

ffmcgee725
ffmcgee725 previously approved these changes Sep 2, 2026
@Jwhiles

Jwhiles commented Sep 2, 2026

Copy link
Copy Markdown
Contributor Author

@metamaskbot publish-preview

2 similar comments
@Jwhiles

Jwhiles commented Sep 2, 2026

Copy link
Copy Markdown
Contributor Author

@metamaskbot publish-preview

@Jwhiles

Jwhiles commented Sep 2, 2026

Copy link
Copy Markdown
Contributor Author

@metamaskbot publish-preview

@Jwhiles
Jwhiles force-pushed the money-account-upgrade-controller-owned-bootstrap branch from a302de5 to 6ec257f Compare September 2, 2026 14:08
@Jwhiles

Jwhiles commented Sep 2, 2026

Copy link
Copy Markdown
Contributor Author

@metamaskbot publish-preview

Jwhiles and others added 2 commits September 3, 2026 14:07
The controller now subscribes to RemoteFeatureFlagController and
KeyringController state, parses the moneyAccountVaultConfig flag, and runs
its own serialized bootstrap, replacing the client-side services that
previously drove init() externally. Client-specific concerns (version-gated
enable flag, eligibility checks, adding the vault chain, error reporting)
are supplied as constructor hooks.

- BREAKING: init() is now the no-argument lifecycle entry point (subscribe
  and sync); the config-arming routine is internal and driven by the
  moneyAccountVaultConfig remote feature flag
- BREAKING: the constructor requires a hooks option with an isEnabled hook
- upgradeAccount() now waits for an in-flight bootstrap instead of
  throwing, and refuses to run against a stale config after the feature is
  disabled
- Add vault-config parsing and comparison helpers to
  @metamask/money-account-utils, shared by the controller and both clients

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Jwhiles and others added 6 commits September 3, 2026 14:07
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
A disarm (isEnabled flipping off) or a newer scheduled config during the
CHOMP service-details call now supersedes the in-flight run instead of the
run arming a config the controller had already dropped.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Scheduling a bootstrap for a changed vault config now disarms the armed
config, so upgradeAccount waits for the re-bootstrap (or refuses if it
failed) instead of signing delegations against the old vault. The wait also
follows runs chained onto the bootstrap while waiting, so a call that
captured a superseded run no longer throws while its successor is still
running.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
- Make `underlyingToken` optional in the shared vault-config parser so
  flags that predate the field still parse, matching the balance service
- Re-check the armed config before every upgrade step and abort if it is
  disarmed or superseded mid-sequence
- Refuse `upgradeAccount` while the wallet is locked
- Contain a throwing `onBootstrapError` hook so the failed bootstrap is
  still retried and nothing escapes `init()` or `sync()`

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
@Jwhiles
Jwhiles force-pushed the money-account-upgrade-controller-owned-bootstrap branch from ad38c64 to ce71f7e Compare September 3, 2026 13:08

@mcmire mcmire left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have one comment below, but everything else seems good to me.

Comment on lines +153 to +157
| ControllerStateChangedEvent<'KeyringController', KeyringControllerState>
| ControllerStateChangedEvent<
'RemoteFeatureFlagController',
RemoteFeatureFlagControllerState
>;

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Types already exist for these events, is it possible to use those?

Suggested change
| ControllerStateChangedEvent<'KeyringController', KeyringControllerState>
| ControllerStateChangedEvent<
'RemoteFeatureFlagController',
RemoteFeatureFlagControllerState
>;
type AllowedEvents =
| KeyringControllerStateChangeEvent
| RemoteFeatureFlagControllerStateChangeEvent

(You have may encountered a lint rule prohibiting use of :stateChange events but I plan on removing that.)

@mcmire mcmire left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

@Jwhiles
Jwhiles enabled auto-merge September 3, 2026 15:34
@Jwhiles
Jwhiles added this pull request to the merge queue Sep 3, 2026
@github-merge-queue
github-merge-queue Bot removed this pull request from the merge queue due to failed status checks Sep 3, 2026
@Jwhiles
Jwhiles added this pull request to the merge queue Sep 3, 2026
@github-merge-queue
github-merge-queue Bot removed this pull request from the merge queue due to failed status checks Sep 3, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants