@metamask/accounts-controller 12.0.1 → 14.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +19 -1
- package/dist/AccountsController.js +3 -3
- package/dist/AccountsController.mjs +2 -2
- package/dist/{chunk-HD5HN6GK.mjs → chunk-E7SBT5BV.mjs} +7 -3
- package/dist/chunk-E7SBT5BV.mjs.map +1 -0
- package/dist/{chunk-GATPL76V.mjs → chunk-J77K3UMX.mjs} +71 -46
- package/dist/chunk-J77K3UMX.mjs.map +1 -0
- package/dist/{chunk-MF4BFCSU.js → chunk-KCST55AQ.js} +8 -4
- package/dist/chunk-KCST55AQ.js.map +1 -0
- package/dist/{chunk-7FX4HSTV.js → chunk-YSAAOUCM.js} +93 -68
- package/dist/chunk-YSAAOUCM.js.map +1 -0
- package/dist/index.js +3 -3
- package/dist/index.mjs +2 -2
- package/dist/tsconfig.build.tsbuildinfo +1 -1
- package/dist/types/AccountsController.d.ts +16 -16
- package/dist/types/AccountsController.d.ts.map +1 -1
- package/dist/types/utils.d.ts +7 -0
- package/dist/types/utils.d.ts.map +1 -1
- package/dist/utils.js +4 -2
- package/dist/utils.mjs +3 -1
- package/package.json +11 -11
- package/dist/chunk-7FX4HSTV.js.map +0 -1
- package/dist/chunk-GATPL76V.mjs.map +0 -1
- package/dist/chunk-HD5HN6GK.mjs.map +0 -1
- package/dist/chunk-MF4BFCSU.js.map +0 -1
    
        package/CHANGELOG.md
    CHANGED
    
    | @@ -7,6 +7,22 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 | |
| 7 7 |  | 
| 8 8 | 
             
            ## [Unreleased]
         | 
| 9 9 |  | 
| 10 | 
            +
            ## [14.0.0]
         | 
| 11 | 
            +
             | 
| 12 | 
            +
            ### Changed
         | 
| 13 | 
            +
             | 
| 14 | 
            +
            - **BREAKING** Bump `@metamask/keyring-controller` peer dependency to ^16.0.0 ([#4234](https://github.com/MetaMask/core/pull/4234))
         | 
| 15 | 
            +
            - Bump `@metamask/keyring-api` to 6.0.0, `@metamask/eth-snap-keyring` to 4.0.0 and snap dependencies ([#4193](https://github.com/MetaMask/core/pull/4193))
         | 
| 16 | 
            +
            - Bump `@metamask/base-controller` to `^5.0.2` ([#4232](https://github.com/MetaMask/core/pull/4232))
         | 
| 17 | 
            +
             | 
| 18 | 
            +
            ## [13.0.0]
         | 
| 19 | 
            +
             | 
| 20 | 
            +
            ### Changed
         | 
| 21 | 
            +
             | 
| 22 | 
            +
            - Fix update setSelectedAccount to throw if the id is not found ([#4167](https://github.com/MetaMask/core/pull/4167))
         | 
| 23 | 
            +
            - Fix normal account indexing naming with index gap ([#4089](https://github.com/MetaMask/core/pull/4089))
         | 
| 24 | 
            +
            - **BREAKING** Bump peer dependency `@metamask/snaps-controllers` to `^6.0.3` and dependencies `@metamask/snaps-sdk` to `^3.1.1`, `@metamask/eth-snap-keyring` to `^3.0.0`([#4090](https://github.com/MetaMask/core/pull/4090))
         | 
| 25 | 
            +
             | 
| 10 26 | 
             
            ## [12.0.1]
         | 
| 11 27 |  | 
| 12 28 | 
             
            ### Fixed
         | 
| @@ -155,7 +171,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 | |
| 155 171 |  | 
| 156 172 | 
             
            - Initial release ([#1637](https://github.com/MetaMask/core/pull/1637))
         | 
| 157 173 |  | 
| 158 | 
            -
            [Unreleased]: https://github.com/MetaMask/core/compare/@metamask/accounts-controller@ | 
| 174 | 
            +
            [Unreleased]: https://github.com/MetaMask/core/compare/@metamask/accounts-controller@14.0.0...HEAD
         | 
| 175 | 
            +
            [14.0.0]: https://github.com/MetaMask/core/compare/@metamask/accounts-controller@13.0.0...@metamask/accounts-controller@14.0.0
         | 
| 176 | 
            +
            [13.0.0]: https://github.com/MetaMask/core/compare/@metamask/accounts-controller@12.0.1...@metamask/accounts-controller@13.0.0
         | 
| 159 177 | 
             
            [12.0.1]: https://github.com/MetaMask/core/compare/@metamask/accounts-controller@12.0.0...@metamask/accounts-controller@12.0.1
         | 
| 160 178 | 
             
            [12.0.0]: https://github.com/MetaMask/core/compare/@metamask/accounts-controller@11.0.0...@metamask/accounts-controller@12.0.0
         | 
| 161 179 | 
             
            [11.0.0]: https://github.com/MetaMask/core/compare/@metamask/accounts-controller@10.0.0...@metamask/accounts-controller@11.0.0
         | 
| @@ -1,8 +1,8 @@ | |
| 1 1 | 
             
            "use strict";Object.defineProperty(exports, "__esModule", {value: true});
         | 
| 2 2 |  | 
| 3 | 
            -
            var  | 
| 4 | 
            -
            require('./chunk- | 
| 3 | 
            +
            var _chunkYSAAOUCMjs = require('./chunk-YSAAOUCM.js');
         | 
| 4 | 
            +
            require('./chunk-KCST55AQ.js');
         | 
| 5 5 |  | 
| 6 6 |  | 
| 7 | 
            -
            exports.AccountsController =  | 
| 7 | 
            +
            exports.AccountsController = _chunkYSAAOUCMjs.AccountsController;
         | 
| 8 8 | 
             
            //# sourceMappingURL=AccountsController.js.map
         | 
| @@ -48,17 +48,21 @@ function keyringTypeToName(keyringType) { | |
| 48 48 | 
             
                }
         | 
| 49 49 | 
             
              }
         | 
| 50 50 | 
             
            }
         | 
| 51 | 
            -
            function  | 
| 51 | 
            +
            function getUUIDOptionsFromAddressOfNormalAccount(address) {
         | 
| 52 52 | 
             
              const v4options = {
         | 
| 53 53 | 
             
                random: sha256(toBuffer(address)).slice(0, 16)
         | 
| 54 54 | 
             
              };
         | 
| 55 | 
            -
              return  | 
| 55 | 
            +
              return v4options;
         | 
| 56 | 
            +
            }
         | 
| 57 | 
            +
            function getUUIDFromAddressOfNormalAccount(address) {
         | 
| 58 | 
            +
              return uuid(getUUIDOptionsFromAddressOfNormalAccount(address));
         | 
| 56 59 | 
             
            }
         | 
| 57 60 |  | 
| 58 61 | 
             
            export {
         | 
| 59 62 | 
             
              __privateAdd,
         | 
| 60 63 | 
             
              __privateMethod,
         | 
| 61 64 | 
             
              keyringTypeToName,
         | 
| 65 | 
            +
              getUUIDOptionsFromAddressOfNormalAccount,
         | 
| 62 66 | 
             
              getUUIDFromAddressOfNormalAccount
         | 
| 63 67 | 
             
            };
         | 
| 64 | 
            -
            //# sourceMappingURL=chunk- | 
| 68 | 
            +
            //# sourceMappingURL=chunk-E7SBT5BV.mjs.map
         | 
| @@ -0,0 +1 @@ | |
| 1 | 
            +
            {"version":3,"sources":["../src/utils.ts"],"sourcesContent":["import { toBuffer } from '@ethereumjs/util';\nimport { isCustodyKeyring, KeyringTypes } from '@metamask/keyring-controller';\nimport { sha256 } from 'ethereum-cryptography/sha256';\nimport type { V4Options } from 'uuid';\nimport { v4 as uuid } from 'uuid';\n\n/**\n * Returns the name of the keyring type.\n *\n * @param keyringType - The type of the keyring.\n * @returns The name of the keyring type.\n */\nexport function keyringTypeToName(keyringType: string): string {\n  // Custody keyrings are a special case, as they are not a single type\n  // they just start with the prefix `Custody`\n  if (isCustodyKeyring(keyringType)) {\n    return 'Custody';\n  }\n\n  switch (keyringType) {\n    case KeyringTypes.simple: {\n      return 'Account';\n    }\n    case KeyringTypes.hd: {\n      return 'Account';\n    }\n    case KeyringTypes.trezor: {\n      return 'Trezor';\n    }\n    case KeyringTypes.ledger: {\n      return 'Ledger';\n    }\n    case KeyringTypes.lattice: {\n      return 'Lattice';\n    }\n    case KeyringTypes.qr: {\n      return 'QR';\n    }\n    case KeyringTypes.snap: {\n      return 'Snap Account';\n    }\n    default: {\n      throw new Error(`Unknown keyring ${keyringType}`);\n    }\n  }\n}\n\n/**\n * Generates a UUID v4 options from a given Ethereum address.\n * @param address - The Ethereum address to generate the UUID from.\n * @returns The UUID v4 options.\n */\nexport function getUUIDOptionsFromAddressOfNormalAccount(\n  address: string,\n): V4Options {\n  const v4options = {\n    random: sha256(toBuffer(address)).slice(0, 16),\n  };\n\n  return v4options;\n}\n\n/**\n * Generates a UUID from a given Ethereum address.\n * @param address - The Ethereum address to generate the UUID from.\n * @returns The generated UUID.\n */\nexport function getUUIDFromAddressOfNormalAccount(address: string): string {\n  return uuid(getUUIDOptionsFromAddressOfNormalAccount(address));\n}\n"],"mappings":";;;;;;;;;;;;;;;AAAA,SAAS,gBAAgB;AACzB,SAAS,kBAAkB,oBAAoB;AAC/C,SAAS,cAAc;AAEvB,SAAS,MAAM,YAAY;AAQpB,SAAS,kBAAkB,aAA6B;AAG7D,MAAI,iBAAiB,WAAW,GAAG;AACjC,WAAO;AAAA,EACT;AAEA,UAAQ,aAAa;AAAA,IACnB,KAAK,aAAa,QAAQ;AACxB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,IAAI;AACpB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,QAAQ;AACxB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,QAAQ;AACxB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,SAAS;AACzB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,IAAI;AACpB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,MAAM;AACtB,aAAO;AAAA,IACT;AAAA,IACA,SAAS;AACP,YAAM,IAAI,MAAM,mBAAmB,WAAW,EAAE;AAAA,IAClD;AAAA,EACF;AACF;AAOO,SAAS,yCACd,SACW;AACX,QAAM,YAAY;AAAA,IAChB,QAAQ,OAAO,SAAS,OAAO,CAAC,EAAE,MAAM,GAAG,EAAE;AAAA,EAC/C;AAEA,SAAO;AACT;AAOO,SAAS,kCAAkC,SAAyB;AACzE,SAAO,KAAK,yCAAyC,OAAO,CAAC;AAC/D;","names":[]}
         | 
| @@ -3,16 +3,13 @@ import { | |
| 3 3 | 
             
              __privateMethod,
         | 
| 4 4 | 
             
              getUUIDFromAddressOfNormalAccount,
         | 
| 5 5 | 
             
              keyringTypeToName
         | 
| 6 | 
            -
            } from "./chunk- | 
| 6 | 
            +
            } from "./chunk-E7SBT5BV.mjs";
         | 
| 7 7 |  | 
| 8 8 | 
             
            // src/AccountsController.ts
         | 
| 9 | 
            -
            import { toBuffer } from "@ethereumjs/util";
         | 
| 10 9 | 
             
            import { BaseController } from "@metamask/base-controller";
         | 
| 11 10 | 
             
            import { SnapKeyring } from "@metamask/eth-snap-keyring";
         | 
| 12 11 | 
             
            import { EthAccountType, EthMethod } from "@metamask/keyring-api";
         | 
| 13 12 | 
             
            import { KeyringTypes } from "@metamask/keyring-controller";
         | 
| 14 | 
            -
            import { sha256 } from "ethereum-cryptography/sha256";
         | 
| 15 | 
            -
            import { v4 as uuid } from "uuid";
         | 
| 16 13 | 
             
            var controllerName = "AccountsController";
         | 
| 17 14 | 
             
            var accountsControllerMetadata = {
         | 
| 18 15 | 
             
              internalAccounts: {
         | 
| @@ -26,7 +23,7 @@ var defaultState = { | |
| 26 23 | 
             
                selectedAccount: ""
         | 
| 27 24 | 
             
              }
         | 
| 28 25 | 
             
            };
         | 
| 29 | 
            -
            var _generateInternalAccountForNonSnapAccount, generateInternalAccountForNonSnapAccount_fn, _listSnapAccounts, listSnapAccounts_fn, _listNormalAccounts, listNormalAccounts_fn, _handleOnKeyringStateChange, handleOnKeyringStateChange_fn, _handleOnSnapStateChange, handleOnSnapStateChange_fn, _getNextAccountNumber, getNextAccountNumber_fn, _handleNewAccountAdded, handleNewAccountAdded_fn, _handleAccountRemoved, handleAccountRemoved_fn, _registerMessageHandlers, registerMessageHandlers_fn;
         | 
| 26 | 
            +
            var _generateInternalAccountForNonSnapAccount, generateInternalAccountForNonSnapAccount_fn, _listSnapAccounts, listSnapAccounts_fn, _listNormalAccounts, listNormalAccounts_fn, _handleOnKeyringStateChange, handleOnKeyringStateChange_fn, _handleOnSnapStateChange, handleOnSnapStateChange_fn, _getAccountsByKeyringType, getAccountsByKeyringType_fn, _getNextAccountNumber, getNextAccountNumber_fn, _handleNewAccountAdded, handleNewAccountAdded_fn, _handleAccountRemoved, handleAccountRemoved_fn, _populateExistingMetadata, populateExistingMetadata_fn, _registerMessageHandlers, registerMessageHandlers_fn;
         | 
| 30 27 | 
             
            var AccountsController = class extends BaseController {
         | 
| 31 28 | 
             
              /**
         | 
| 32 29 | 
             
               * Constructor for AccountsController.
         | 
| @@ -81,6 +78,12 @@ var AccountsController = class extends BaseController { | |
| 81 78 | 
             
                 * @param snapState - The new SnapControllerState.
         | 
| 82 79 | 
             
                 */
         | 
| 83 80 | 
             
                __privateAdd(this, _handleOnSnapStateChange);
         | 
| 81 | 
            +
                /**
         | 
| 82 | 
            +
                 * Returns the list of accounts for a given keyring type.
         | 
| 83 | 
            +
                 * @param keyringType - The type of keyring.
         | 
| 84 | 
            +
                 * @returns The list of accounts associcated with this keyring type.
         | 
| 85 | 
            +
                 */
         | 
| 86 | 
            +
                __privateAdd(this, _getAccountsByKeyringType);
         | 
| 84 87 | 
             
                /**
         | 
| 85 88 | 
             
                 * Returns the next account number for a given keyring type.
         | 
| 86 89 | 
             
                 * @param keyringType - The type of keyring.
         | 
| @@ -99,6 +102,13 @@ var AccountsController = class extends BaseController { | |
| 99 102 | 
             
                 * @param accountId - The ID of the account to be removed.
         | 
| 100 103 | 
             
                 */
         | 
| 101 104 | 
             
                __privateAdd(this, _handleAccountRemoved);
         | 
| 105 | 
            +
                /**
         | 
| 106 | 
            +
                 * Retrieves the value of a specific metadata key for an existing account.
         | 
| 107 | 
            +
                 * @param accountId - The ID of the account.
         | 
| 108 | 
            +
                 * @param metadataKey - The key of the metadata to retrieve.
         | 
| 109 | 
            +
                 * @returns The value of the specified metadata key, or undefined if the account or metadata key does not exist.
         | 
| 110 | 
            +
                 */
         | 
| 111 | 
            +
                __privateAdd(this, _populateExistingMetadata);
         | 
| 102 112 | 
             
                /**
         | 
| 103 113 | 
             
                 * Registers message handlers for the AccountsController.
         | 
| 104 114 | 
             
                 * @private
         | 
| @@ -150,13 +160,14 @@ var AccountsController = class extends BaseController { | |
| 150 160 | 
             
                      name: "",
         | 
| 151 161 | 
             
                      keyring: {
         | 
| 152 162 | 
             
                        type: ""
         | 
| 153 | 
            -
                      }
         | 
| 163 | 
            +
                      },
         | 
| 164 | 
            +
                      importTime: 0
         | 
| 154 165 | 
             
                    }
         | 
| 155 166 | 
             
                  };
         | 
| 156 167 | 
             
                }
         | 
| 157 168 | 
             
                const account = this.getAccount(accountId);
         | 
| 158 169 | 
             
                if (account === void 0) {
         | 
| 159 | 
            -
                  throw new Error(`Account Id ${accountId} not found`);
         | 
| 170 | 
            +
                  throw new Error(`Account Id "${accountId}" not found`);
         | 
| 160 171 | 
             
                }
         | 
| 161 172 | 
             
                return account;
         | 
| 162 173 | 
             
              }
         | 
| @@ -185,21 +196,15 @@ var AccountsController = class extends BaseController { | |
| 185 196 | 
             
               * @param accountId - The ID of the account to be selected.
         | 
| 186 197 | 
             
               */
         | 
| 187 198 | 
             
              setSelectedAccount(accountId) {
         | 
| 188 | 
            -
                const account = this. | 
| 199 | 
            +
                const account = this.getAccountExpect(accountId);
         | 
| 189 200 | 
             
                this.update((currentState) => {
         | 
| 190 | 
            -
                   | 
| 191 | 
            -
             | 
| 192 | 
            -
                    currentState.internalAccounts.selectedAccount = account.id;
         | 
| 193 | 
            -
                  } else {
         | 
| 194 | 
            -
                    currentState.internalAccounts.selectedAccount = "";
         | 
| 195 | 
            -
                  }
         | 
| 201 | 
            +
                  currentState.internalAccounts.accounts[account.id].metadata.lastSelected = Date.now();
         | 
| 202 | 
            +
                  currentState.internalAccounts.selectedAccount = account.id;
         | 
| 196 203 | 
             
                });
         | 
| 197 | 
            -
                 | 
| 198 | 
            -
                   | 
| 199 | 
            -
             | 
| 200 | 
            -
             | 
| 201 | 
            -
                  );
         | 
| 202 | 
            -
                }
         | 
| 204 | 
            +
                this.messagingSystem.publish(
         | 
| 205 | 
            +
                  "AccountsController:selectedAccountChange",
         | 
| 206 | 
            +
                  account
         | 
| 207 | 
            +
                );
         | 
| 203 208 | 
             
              }
         | 
| 204 209 | 
             
              /**
         | 
| 205 210 | 
             
               * Sets the name of the account with the given ID.
         | 
| @@ -220,8 +225,7 @@ var AccountsController = class extends BaseController { | |
| 220 225 | 
             
                    ...account,
         | 
| 221 226 | 
             
                    metadata: { ...account.metadata, name: accountName }
         | 
| 222 227 | 
             
                  };
         | 
| 223 | 
            -
                  currentState.internalAccounts.accounts[accountId] =  | 
| 224 | 
            -
                  internalAccount;
         | 
| 228 | 
            +
                  currentState.internalAccounts.accounts[accountId] = internalAccount;
         | 
| 225 229 | 
             
                });
         | 
| 226 230 | 
             
              }
         | 
| 227 231 | 
             
              /**
         | 
| @@ -257,8 +261,9 @@ var AccountsController = class extends BaseController { | |
| 257 261 | 
             
                    ...internalAccount,
         | 
| 258 262 | 
             
                    metadata: {
         | 
| 259 263 | 
             
                      ...internalAccount.metadata,
         | 
| 260 | 
            -
                      name:  | 
| 261 | 
            -
                       | 
| 264 | 
            +
                      name: __privateMethod(this, _populateExistingMetadata, populateExistingMetadata_fn).call(this, existingAccount?.id, "name") ?? `${keyringTypeName} ${keyringAccountIndex + 1}`,
         | 
| 265 | 
            +
                      importTime: __privateMethod(this, _populateExistingMetadata, populateExistingMetadata_fn).call(this, existingAccount?.id, "importTime") ?? Date.now(),
         | 
| 266 | 
            +
                      lastSelected: __privateMethod(this, _populateExistingMetadata, populateExistingMetadata_fn).call(this, existingAccount?.id, "lastSelected")
         | 
| 262 267 | 
             
                    }
         | 
| 263 268 | 
             
                  };
         | 
| 264 269 | 
             
                  return internalAccountMap;
         | 
| @@ -297,6 +302,7 @@ generateInternalAccountForNonSnapAccount_fn = function(address, type) { | |
| 297 302 | 
             
                type: EthAccountType.Eoa,
         | 
| 298 303 | 
             
                metadata: {
         | 
| 299 304 | 
             
                  name: "",
         | 
| 305 | 
            +
                  importTime: Date.now(),
         | 
| 300 306 | 
             
                  keyring: {
         | 
| 301 307 | 
             
                    type
         | 
| 302 308 | 
             
                  }
         | 
| @@ -326,11 +332,9 @@ listNormalAccounts_fn = async function() { | |
| 326 332 | 
             
                  "KeyringController:getKeyringForAccount",
         | 
| 327 333 | 
             
                  address
         | 
| 328 334 | 
             
                );
         | 
| 329 | 
            -
                const  | 
| 330 | 
            -
                  random: sha256(toBuffer(address)).slice(0, 16)
         | 
| 331 | 
            -
                };
         | 
| 335 | 
            +
                const id = getUUIDFromAddressOfNormalAccount(address);
         | 
| 332 336 | 
             
                internalAccounts.push({
         | 
| 333 | 
            -
                  id | 
| 337 | 
            +
                  id,
         | 
| 334 338 | 
             
                  address,
         | 
| 335 339 | 
             
                  options: {},
         | 
| 336 340 | 
             
                  methods: [
         | 
| @@ -343,7 +347,9 @@ listNormalAccounts_fn = async function() { | |
| 343 347 | 
             
                  ],
         | 
| 344 348 | 
             
                  type: EthAccountType.Eoa,
         | 
| 345 349 | 
             
                  metadata: {
         | 
| 346 | 
            -
                    name: "",
         | 
| 350 | 
            +
                    name: __privateMethod(this, _populateExistingMetadata, populateExistingMetadata_fn).call(this, id, "name") ?? "",
         | 
| 351 | 
            +
                    importTime: __privateMethod(this, _populateExistingMetadata, populateExistingMetadata_fn).call(this, id, "importTime") ?? Date.now(),
         | 
| 352 | 
            +
                    lastSelected: __privateMethod(this, _populateExistingMetadata, populateExistingMetadata_fn).call(this, id, "lastSelected"),
         | 
| 347 353 | 
             
                    keyring: {
         | 
| 348 354 | 
             
                      type: keyring.type
         | 
| 349 355 | 
             
                    }
         | 
| @@ -438,7 +444,13 @@ handleOnKeyringStateChange_fn = function(keyringState) { | |
| 438 444 | 
             
                      return (accountB.metadata.lastSelected ?? 0) - (accountA.metadata.lastSelected ?? 0);
         | 
| 439 445 | 
             
                    }
         | 
| 440 446 | 
             
                  );
         | 
| 441 | 
            -
                   | 
| 447 | 
            +
                  if (!accountToSelect) {
         | 
| 448 | 
            +
                    this.update((currentState) => {
         | 
| 449 | 
            +
                      currentState.internalAccounts.selectedAccount = "";
         | 
| 450 | 
            +
                    });
         | 
| 451 | 
            +
                    return;
         | 
| 452 | 
            +
                  }
         | 
| 453 | 
            +
                  this.setSelectedAccount(accountToSelect.id);
         | 
| 442 454 | 
             
                }
         | 
| 443 455 | 
             
              }
         | 
| 444 456 | 
             
            };
         | 
| @@ -461,27 +473,34 @@ handleOnSnapStateChange_fn = function(snapState) { | |
| 461 473 | 
             
                });
         | 
| 462 474 | 
             
              });
         | 
| 463 475 | 
             
            };
         | 
| 476 | 
            +
            _getAccountsByKeyringType = new WeakSet();
         | 
| 477 | 
            +
            getAccountsByKeyringType_fn = function(keyringType) {
         | 
| 478 | 
            +
              return this.listAccounts().filter((internalAccount) => {
         | 
| 479 | 
            +
                if (keyringType === KeyringTypes.hd || keyringType === KeyringTypes.simple) {
         | 
| 480 | 
            +
                  return internalAccount.metadata.keyring.type === KeyringTypes.hd || internalAccount.metadata.keyring.type === KeyringTypes.simple;
         | 
| 481 | 
            +
                }
         | 
| 482 | 
            +
                return internalAccount.metadata.keyring.type === keyringType;
         | 
| 483 | 
            +
              });
         | 
| 484 | 
            +
            };
         | 
| 464 485 | 
             
            _getNextAccountNumber = new WeakSet();
         | 
| 465 486 | 
             
            getNextAccountNumber_fn = function(keyringType) {
         | 
| 466 487 | 
             
              const keyringName = keyringTypeToName(keyringType);
         | 
| 467 | 
            -
              const  | 
| 468 | 
            -
             | 
| 469 | 
            -
             | 
| 470 | 
            -
             | 
| 488 | 
            +
              const keyringAccounts = __privateMethod(this, _getAccountsByKeyringType, getAccountsByKeyringType_fn).call(this, keyringType);
         | 
| 489 | 
            +
              const lastDefaultIndexUsedForKeyringType = keyringAccounts.reduce(
         | 
| 490 | 
            +
                (maxInternalAccountIndex, internalAccount) => {
         | 
| 491 | 
            +
                  const match = new RegExp(`${keyringName} ([0-9]+)$`, "u").exec(
         | 
| 492 | 
            +
                    internalAccount.metadata.name
         | 
| 493 | 
            +
                  );
         | 
| 494 | 
            +
                  if (match) {
         | 
| 495 | 
            +
                    const internalAccountIndex = parseInt(match[1], 10);
         | 
| 496 | 
            +
                    return Math.max(maxInternalAccountIndex, internalAccountIndex);
         | 
| 471 497 | 
             
                  }
         | 
| 472 | 
            -
                  return  | 
| 473 | 
            -
                }
         | 
| 498 | 
            +
                  return maxInternalAccountIndex;
         | 
| 499 | 
            +
                },
         | 
| 500 | 
            +
                0
         | 
| 474 501 | 
             
              );
         | 
| 475 | 
            -
              const lastDefaultIndexUsedForKeyringType = previousKeyringAccounts.filter(
         | 
| 476 | 
            -
                (internalAccount) => new RegExp(`${keyringName} \\d+$`, "u").test(
         | 
| 477 | 
            -
                  internalAccount.metadata.name
         | 
| 478 | 
            -
                )
         | 
| 479 | 
            -
              ).map((internalAccount) => {
         | 
| 480 | 
            -
                const nameToWords = internalAccount.metadata.name.split(" ");
         | 
| 481 | 
            -
                return parseInt(nameToWords[nameToWords.length], 10);
         | 
| 482 | 
            -
              }).sort((a, b) => b - a)[0] || 0;
         | 
| 483 502 | 
             
              const indexToUse = Math.max(
         | 
| 484 | 
            -
                 | 
| 503 | 
            +
                keyringAccounts.length + 1,
         | 
| 485 504 | 
             
                lastDefaultIndexUsedForKeyringType + 1
         | 
| 486 505 | 
             
              );
         | 
| 487 506 | 
             
              return { accountPrefix: keyringName, indexToUse };
         | 
| @@ -511,6 +530,7 @@ handleNewAccountAdded_fn = function(account) { | |
| 511 530 | 
             
                  metadata: {
         | 
| 512 531 | 
             
                    ...newAccount.metadata,
         | 
| 513 532 | 
             
                    name: accountName,
         | 
| 533 | 
            +
                    importTime: Date.now(),
         | 
| 514 534 | 
             
                    lastSelected: Date.now()
         | 
| 515 535 | 
             
                  }
         | 
| 516 536 | 
             
                };
         | 
| @@ -523,6 +543,11 @@ handleAccountRemoved_fn = function(accountId) { | |
| 523 543 | 
             
                delete currentState.internalAccounts.accounts[accountId];
         | 
| 524 544 | 
             
              });
         | 
| 525 545 | 
             
            };
         | 
| 546 | 
            +
            _populateExistingMetadata = new WeakSet();
         | 
| 547 | 
            +
            populateExistingMetadata_fn = function(accountId, metadataKey) {
         | 
| 548 | 
            +
              const internalAccount = this.getAccount(accountId);
         | 
| 549 | 
            +
              return internalAccount ? internalAccount.metadata[metadataKey] : void 0;
         | 
| 550 | 
            +
            };
         | 
| 526 551 | 
             
            _registerMessageHandlers = new WeakSet();
         | 
| 527 552 | 
             
            registerMessageHandlers_fn = function() {
         | 
| 528 553 | 
             
              this.messagingSystem.registerActionHandler(
         | 
| @@ -558,4 +583,4 @@ registerMessageHandlers_fn = function() { | |
| 558 583 | 
             
            export {
         | 
| 559 584 | 
             
              AccountsController
         | 
| 560 585 | 
             
            };
         | 
| 561 | 
            -
            //# sourceMappingURL=chunk- | 
| 586 | 
            +
            //# sourceMappingURL=chunk-J77K3UMX.mjs.map
         | 
| @@ -0,0 +1 @@ | |
| 1 | 
            +
            {"version":3,"sources":["../src/AccountsController.ts"],"sourcesContent":["import type {\n  ControllerGetStateAction,\n  ControllerStateChangeEvent,\n  RestrictedControllerMessenger,\n} from '@metamask/base-controller';\nimport { BaseController } from '@metamask/base-controller';\nimport { SnapKeyring } from '@metamask/eth-snap-keyring';\nimport type { InternalAccount } from '@metamask/keyring-api';\nimport { EthAccountType, EthMethod } from '@metamask/keyring-api';\nimport { KeyringTypes } from '@metamask/keyring-controller';\nimport type {\n  KeyringControllerState,\n  KeyringControllerGetKeyringForAccountAction,\n  KeyringControllerGetKeyringsByTypeAction,\n  KeyringControllerGetAccountsAction,\n  KeyringControllerStateChangeEvent,\n} from '@metamask/keyring-controller';\nimport type {\n  SnapControllerState,\n  SnapStateChange,\n} from '@metamask/snaps-controllers';\nimport type { SnapId } from '@metamask/snaps-sdk';\nimport type { Snap } from '@metamask/snaps-utils';\nimport type { Keyring, Json } from '@metamask/utils';\nimport type { Draft } from 'immer';\n\nimport { getUUIDFromAddressOfNormalAccount, keyringTypeToName } from './utils';\n\nconst controllerName = 'AccountsController';\n\nexport type AccountsControllerState = {\n  internalAccounts: {\n    accounts: Record<string, InternalAccount>;\n    selectedAccount: string; // id of the selected account\n  };\n};\n\nexport type AccountsControllerGetStateAction = ControllerGetStateAction<\n  typeof controllerName,\n  AccountsControllerState\n>;\n\nexport type AccountsControllerSetSelectedAccountAction = {\n  type: `${typeof controllerName}:setSelectedAccount`;\n  handler: AccountsController['setSelectedAccount'];\n};\n\nexport type AccountsControllerSetAccountNameAction = {\n  type: `${typeof controllerName}:setAccountName`;\n  handler: AccountsController['setAccountName'];\n};\n\nexport type AccountsControllerListAccountsAction = {\n  type: `${typeof controllerName}:listAccounts`;\n  handler: AccountsController['listAccounts'];\n};\n\nexport type AccountsControllerUpdateAccountsAction = {\n  type: `${typeof controllerName}:updateAccounts`;\n  handler: AccountsController['updateAccounts'];\n};\n\nexport type AccountsControllerGetSelectedAccountAction = {\n  type: `${typeof controllerName}:getSelectedAccount`;\n  handler: AccountsController['getSelectedAccount'];\n};\n\nexport type AccountsControllerGetAccountByAddressAction = {\n  type: `${typeof controllerName}:getAccountByAddress`;\n  handler: AccountsController['getAccountByAddress'];\n};\n\nexport type AccountsControllerGetAccountAction = {\n  type: `${typeof controllerName}:getAccount`;\n  handler: AccountsController['getAccount'];\n};\n\nexport type AllowedActions =\n  | KeyringControllerGetKeyringForAccountAction\n  | KeyringControllerGetKeyringsByTypeAction\n  | KeyringControllerGetAccountsAction;\n\nexport type AccountsControllerActions =\n  | AccountsControllerGetStateAction\n  | AccountsControllerSetSelectedAccountAction\n  | AccountsControllerListAccountsAction\n  | AccountsControllerSetAccountNameAction\n  | AccountsControllerUpdateAccountsAction\n  | AccountsControllerGetAccountByAddressAction\n  | AccountsControllerGetSelectedAccountAction\n  | AccountsControllerGetAccountAction;\n\nexport type AccountsControllerChangeEvent = ControllerStateChangeEvent<\n  typeof controllerName,\n  AccountsControllerState\n>;\n\nexport type AccountsControllerSelectedAccountChangeEvent = {\n  type: `${typeof controllerName}:selectedAccountChange`;\n  payload: [InternalAccount];\n};\n\nexport type AllowedEvents = SnapStateChange | KeyringControllerStateChangeEvent;\n\nexport type AccountsControllerEvents =\n  | AccountsControllerChangeEvent\n  | AccountsControllerSelectedAccountChangeEvent;\n\nexport type AccountsControllerMessenger = RestrictedControllerMessenger<\n  typeof controllerName,\n  AccountsControllerActions | AllowedActions,\n  AccountsControllerEvents | AllowedEvents,\n  AllowedActions['type'],\n  AllowedEvents['type']\n>;\n\ntype AddressAndKeyringTypeObject = {\n  address: string;\n  type: string;\n};\n\nconst accountsControllerMetadata = {\n  internalAccounts: {\n    persist: true,\n    anonymous: false,\n  },\n};\n\nconst defaultState: AccountsControllerState = {\n  internalAccounts: {\n    accounts: {},\n    selectedAccount: '',\n  },\n};\n\n/**\n * Controller that manages internal accounts.\n * The accounts controller is responsible for creating and managing internal accounts.\n * It also provides convenience methods for accessing and updating the internal accounts.\n * The accounts controller also listens for keyring state changes and updates the internal accounts accordingly.\n * The accounts controller also listens for snap state changes and updates the internal accounts accordingly.\n *\n */\nexport class AccountsController extends BaseController<\n  typeof controllerName,\n  AccountsControllerState,\n  AccountsControllerMessenger\n> {\n  /**\n   * Constructor for AccountsController.\n   *\n   * @param options - The controller options.\n   * @param options.messenger - The messenger object.\n   * @param options.state - Initial state to set on this controller\n   */\n  constructor({\n    messenger,\n    state,\n  }: {\n    messenger: AccountsControllerMessenger;\n    state: AccountsControllerState;\n  }) {\n    super({\n      messenger,\n      name: controllerName,\n      metadata: accountsControllerMetadata,\n      state: {\n        ...defaultState,\n        ...state,\n      },\n    });\n\n    this.messagingSystem.subscribe(\n      'SnapController:stateChange',\n      (snapStateState) => this.#handleOnSnapStateChange(snapStateState),\n    );\n\n    this.messagingSystem.subscribe(\n      'KeyringController:stateChange',\n      (keyringState) => this.#handleOnKeyringStateChange(keyringState),\n    );\n\n    this.#registerMessageHandlers();\n  }\n\n  /**\n   * Returns the internal account object for the given account ID, if it exists.\n   *\n   * @param accountId - The ID of the account to retrieve.\n   * @returns The internal account object, or undefined if the account does not exist.\n   */\n  getAccount(accountId: string): InternalAccount | undefined {\n    return this.state.internalAccounts.accounts[accountId];\n  }\n\n  /**\n   * Returns an array of all internal accounts.\n   *\n   * @returns An array of InternalAccount objects.\n   */\n  listAccounts(): InternalAccount[] {\n    return Object.values(this.state.internalAccounts.accounts);\n  }\n\n  /**\n   * Returns the internal account object for the given account ID.\n   *\n   * @param accountId - The ID of the account to retrieve.\n   * @returns The internal account object.\n   * @throws An error if the account ID is not found.\n   */\n  getAccountExpect(accountId: string): InternalAccount {\n    // Edge case where the extension is setup but the srp is not yet created\n    // certain ui elements will query the selected address before any accounts are created.\n    if (!accountId) {\n      return {\n        id: '',\n        address: '',\n        options: {},\n        methods: [],\n        type: EthAccountType.Eoa,\n        metadata: {\n          name: '',\n          keyring: {\n            type: '',\n          },\n          importTime: 0,\n        },\n      };\n    }\n\n    const account = this.getAccount(accountId);\n    if (account === undefined) {\n      throw new Error(`Account Id \"${accountId}\" not found`);\n    }\n    return account;\n  }\n\n  /**\n   * Returns the selected internal account.\n   *\n   * @returns The selected internal account.\n   */\n  getSelectedAccount(): InternalAccount {\n    return this.getAccountExpect(this.state.internalAccounts.selectedAccount);\n  }\n\n  /**\n   * Returns the account with the specified address.\n   * ! This method will only return the first account that matches the address\n   * @param address - The address of the account to retrieve.\n   * @returns The account with the specified address, or undefined if not found.\n   */\n  getAccountByAddress(address: string): InternalAccount | undefined {\n    return this.listAccounts().find(\n      (account) => account.address.toLowerCase() === address.toLowerCase(),\n    );\n  }\n\n  /**\n   * Sets the selected account by its ID.\n   *\n   * @param accountId - The ID of the account to be selected.\n   */\n  setSelectedAccount(accountId: string): void {\n    const account = this.getAccountExpect(accountId);\n\n    this.update((currentState: Draft<AccountsControllerState>) => {\n      currentState.internalAccounts.accounts[account.id].metadata.lastSelected =\n        Date.now();\n      currentState.internalAccounts.selectedAccount = account.id;\n    });\n\n    this.messagingSystem.publish(\n      'AccountsController:selectedAccountChange',\n      account,\n    );\n  }\n\n  /**\n   * Sets the name of the account with the given ID.\n   *\n   * @param accountId - The ID of the account to set the name for.\n   * @param accountName - The new name for the account.\n   * @throws An error if an account with the same name already exists.\n   */\n  setAccountName(accountId: string, accountName: string): void {\n    const account = this.getAccountExpect(accountId);\n\n    if (\n      this.listAccounts().find(\n        (internalAccount) =>\n          internalAccount.metadata.name === accountName &&\n          internalAccount.id !== accountId,\n      )\n    ) {\n      throw new Error('Account name already exists');\n    }\n\n    this.update((currentState: Draft<AccountsControllerState>) => {\n      const internalAccount = {\n        ...account,\n        metadata: { ...account.metadata, name: accountName },\n      };\n      currentState.internalAccounts.accounts[accountId] = internalAccount;\n    });\n  }\n\n  /**\n   * Updates the internal accounts list by retrieving normal and snap accounts,\n   * removing duplicates, and updating the metadata of each account.\n   *\n   * @returns A Promise that resolves when the accounts have been updated.\n   */\n  async updateAccounts(): Promise<void> {\n    const snapAccounts: InternalAccount[] = await this.#listSnapAccounts();\n    const normalAccounts = (await this.#listNormalAccounts()).filter(\n      (account) =>\n        !snapAccounts.find(\n          (snapAccount) => snapAccount.address === account.address,\n        ),\n    );\n\n    // keyring type map.\n    const keyringTypes = new Map<string, number>();\n    const previousAccounts = this.state.internalAccounts.accounts;\n\n    const accounts: Record<string, InternalAccount> = [\n      ...normalAccounts,\n      ...snapAccounts,\n    ].reduce((internalAccountMap, internalAccount) => {\n      const keyringTypeName = keyringTypeToName(\n        internalAccount.metadata.keyring.type,\n      );\n      const keyringAccountIndex = keyringTypes.get(keyringTypeName) ?? 0;\n      if (keyringAccountIndex) {\n        keyringTypes.set(keyringTypeName, keyringAccountIndex + 1);\n      } else {\n        keyringTypes.set(keyringTypeName, 1);\n      }\n\n      const existingAccount = previousAccounts[internalAccount.id];\n\n      internalAccountMap[internalAccount.id] = {\n        ...internalAccount,\n\n        metadata: {\n          ...internalAccount.metadata,\n          name:\n            this.#populateExistingMetadata(existingAccount?.id, 'name') ??\n            `${keyringTypeName} ${keyringAccountIndex + 1}`,\n          importTime:\n            this.#populateExistingMetadata(existingAccount?.id, 'importTime') ??\n            Date.now(),\n          lastSelected: this.#populateExistingMetadata(\n            existingAccount?.id,\n            'lastSelected',\n          ),\n        },\n      };\n\n      return internalAccountMap;\n    }, {} as Record<string, InternalAccount>);\n\n    this.update((currentState: Draft<AccountsControllerState>) => {\n      (currentState as AccountsControllerState).internalAccounts.accounts =\n        accounts;\n    });\n  }\n\n  /**\n   * Loads the backup state of the accounts controller.\n   *\n   * @param backup - The backup state to load.\n   */\n  loadBackup(backup: AccountsControllerState): void {\n    if (backup.internalAccounts) {\n      this.update((currentState: Draft<AccountsControllerState>) => {\n        (currentState as AccountsControllerState).internalAccounts =\n          backup.internalAccounts;\n      });\n    }\n  }\n\n  /**\n   * Generates an internal account for a non-Snap account.\n   * @param address - The address of the account.\n   * @param type - The type of the account.\n   * @returns The generated internal account.\n   */\n  #generateInternalAccountForNonSnapAccount(\n    address: string,\n    type: string,\n  ): InternalAccount {\n    return {\n      id: getUUIDFromAddressOfNormalAccount(address),\n      address,\n      options: {},\n      methods: [\n        EthMethod.PersonalSign,\n        EthMethod.Sign,\n        EthMethod.SignTransaction,\n        EthMethod.SignTypedDataV1,\n        EthMethod.SignTypedDataV3,\n        EthMethod.SignTypedDataV4,\n      ],\n      type: EthAccountType.Eoa,\n      metadata: {\n        name: '',\n        importTime: Date.now(),\n        keyring: {\n          type,\n        },\n      },\n    };\n  }\n\n  /**\n   * Returns a list of internal accounts created using the SnapKeyring.\n   *\n   * @returns A promise that resolves to an array of InternalAccount objects.\n   */\n  async #listSnapAccounts(): Promise<InternalAccount[]> {\n    const [snapKeyring] = this.messagingSystem.call(\n      'KeyringController:getKeyringsByType',\n      SnapKeyring.type,\n    );\n    // snap keyring is not available until the first account is created in the keyring controller\n    if (!snapKeyring) {\n      return [];\n    }\n\n    const snapAccounts = (snapKeyring as SnapKeyring).listAccounts();\n\n    return snapAccounts;\n  }\n\n  /**\n   * Returns a list of normal accounts.\n   * Note: listNormalAccounts is a temporary method until the keyrings all implement the InternalAccount interface.\n   * Once all keyrings implement the InternalAccount interface, this method can be removed and getAccounts can be used instead.\n   *\n   * @returns A Promise that resolves to an array of InternalAccount objects.\n   */\n  async #listNormalAccounts(): Promise<InternalAccount[]> {\n    const addresses = await this.messagingSystem.call(\n      'KeyringController:getAccounts',\n    );\n    const internalAccounts: InternalAccount[] = [];\n    for (const address of addresses) {\n      const keyring = await this.messagingSystem.call(\n        'KeyringController:getKeyringForAccount',\n        address,\n      );\n\n      const id = getUUIDFromAddressOfNormalAccount(address);\n\n      internalAccounts.push({\n        id,\n        address,\n        options: {},\n        methods: [\n          EthMethod.PersonalSign,\n          EthMethod.Sign,\n          EthMethod.SignTransaction,\n          EthMethod.SignTypedDataV1,\n          EthMethod.SignTypedDataV3,\n          EthMethod.SignTypedDataV4,\n        ],\n        type: EthAccountType.Eoa,\n        metadata: {\n          name: this.#populateExistingMetadata(id, 'name') ?? '',\n          importTime:\n            this.#populateExistingMetadata(id, 'importTime') ?? Date.now(),\n          lastSelected: this.#populateExistingMetadata(id, 'lastSelected'),\n          keyring: {\n            type: (keyring as Keyring<Json>).type,\n          },\n        },\n      });\n    }\n\n    return internalAccounts.filter(\n      (account) => account.metadata.keyring.type !== KeyringTypes.snap,\n    );\n  }\n\n  /**\n   * Handles changes in the keyring state, specifically when new accounts are added or removed.\n   *\n   * @param keyringState - The new state of the keyring controller.\n   */\n  #handleOnKeyringStateChange(keyringState: KeyringControllerState): void {\n    // check if there are any new accounts added\n    // TODO: change when accountAdded event is added to the keyring controller\n\n    // We check for keyrings length to be greater than 0 because the extension client may try execute\n    // submit password twice and clear the keyring state.\n    // https://github.com/MetaMask/KeyringController/blob/2d73a4deed8d013913f6ef0c9f5c0bb7c614f7d3/src/KeyringController.ts#L910\n    if (keyringState.isUnlocked && keyringState.keyrings.length > 0) {\n      const updatedNormalKeyringAddresses: AddressAndKeyringTypeObject[] = [];\n      const updatedSnapKeyringAddresses: AddressAndKeyringTypeObject[] = [];\n\n      for (const keyring of keyringState.keyrings) {\n        if (keyring.type === KeyringTypes.snap) {\n          updatedSnapKeyringAddresses.push(\n            ...keyring.accounts.map((address) => {\n              return {\n                address,\n                type: keyring.type,\n              };\n            }),\n          );\n        } else {\n          updatedNormalKeyringAddresses.push(\n            ...keyring.accounts.map((address) => {\n              return {\n                address,\n                type: keyring.type,\n              };\n            }),\n          );\n        }\n      }\n\n      const { previousNormalInternalAccounts, previousSnapInternalAccounts } =\n        this.listAccounts().reduce(\n          (accumulator, account) => {\n            if (account.metadata.keyring.type === KeyringTypes.snap) {\n              accumulator.previousSnapInternalAccounts.push(account);\n            } else {\n              accumulator.previousNormalInternalAccounts.push(account);\n            }\n            return accumulator;\n          },\n          {\n            previousNormalInternalAccounts: [] as InternalAccount[],\n            previousSnapInternalAccounts: [] as InternalAccount[],\n          },\n        );\n\n      const addedAccounts: AddressAndKeyringTypeObject[] = [];\n      const deletedAccounts: InternalAccount[] = [];\n\n      // snap account ids are random uuid while normal accounts\n      // are determininistic based on the address\n\n      // ^NOTE: This will be removed when normal accounts also implement internal accounts\n      // finding all the normal accounts that were added\n      for (const account of updatedNormalKeyringAddresses) {\n        if (\n          !this.state.internalAccounts.accounts[\n            getUUIDFromAddressOfNormalAccount(account.address)\n          ]\n        ) {\n          addedAccounts.push(account);\n        }\n      }\n\n      // finding all the snap accounts that were added\n      for (const account of updatedSnapKeyringAddresses) {\n        if (\n          !previousSnapInternalAccounts.find(\n            (internalAccount: InternalAccount) =>\n              internalAccount.address.toLowerCase() ===\n              account.address.toLowerCase(),\n          )\n        ) {\n          addedAccounts.push(account);\n        }\n      }\n\n      // finding all the normal accounts that were deleted\n      for (const account of previousNormalInternalAccounts) {\n        if (\n          !updatedNormalKeyringAddresses.find(\n            ({ address }) =>\n              address.toLowerCase() === account.address.toLowerCase(),\n          )\n        ) {\n          deletedAccounts.push(account);\n        }\n      }\n\n      // finding all the snap accounts that were deleted\n      for (const account of previousSnapInternalAccounts) {\n        if (\n          !updatedSnapKeyringAddresses.find(\n            ({ address }) =>\n              address.toLowerCase() === account.address.toLowerCase(),\n          )\n        ) {\n          deletedAccounts.push(account);\n        }\n      }\n\n      if (deletedAccounts.length > 0) {\n        for (const account of deletedAccounts) {\n          this.#handleAccountRemoved(account.id);\n        }\n      }\n\n      if (addedAccounts.length > 0) {\n        for (const account of addedAccounts) {\n          this.#handleNewAccountAdded(account);\n        }\n      }\n\n      // handle if the selected account was deleted\n      if (!this.getAccount(this.state.internalAccounts.selectedAccount)) {\n        const [accountToSelect] = this.listAccounts().sort(\n          (accountA, accountB) => {\n            // sort by lastSelected descending\n            return (\n              (accountB.metadata.lastSelected ?? 0) -\n              (accountA.metadata.lastSelected ?? 0)\n            );\n          },\n        );\n\n        // if the accountToSelect is undefined, then there are no accounts\n        // it mean the keyring was reinitialized.\n        if (!accountToSelect) {\n          this.update((currentState: Draft<AccountsControllerState>) => {\n            currentState.internalAccounts.selectedAccount = '';\n          });\n          return;\n        }\n\n        this.setSelectedAccount(accountToSelect.id);\n      }\n    }\n  }\n\n  /**\n   * Handles the change in SnapControllerState by updating the metadata of accounts that have a snap enabled.\n   *\n   * @param snapState - The new SnapControllerState.\n   */\n  #handleOnSnapStateChange(snapState: SnapControllerState) {\n    // only check if snaps changed in status\n    const { snaps } = snapState;\n    const accounts = this.listAccounts().filter(\n      (account) => account.metadata.snap,\n    );\n\n    this.update((currentState: Draft<AccountsControllerState>) => {\n      accounts.forEach((account) => {\n        const currentAccount =\n          currentState.internalAccounts.accounts[account.id];\n        if (currentAccount.metadata.snap) {\n          const snapId = currentAccount.metadata.snap.id;\n          const storedSnap: Snap = snaps[snapId as SnapId];\n          if (storedSnap) {\n            currentAccount.metadata.snap.enabled =\n              storedSnap.enabled && !storedSnap.blocked;\n          }\n        }\n      });\n    });\n  }\n\n  /**\n   * Returns the list of accounts for a given keyring type.\n   * @param keyringType - The type of keyring.\n   * @returns The list of accounts associcated with this keyring type.\n   */\n  #getAccountsByKeyringType(keyringType: string) {\n    return this.listAccounts().filter((internalAccount) => {\n      // We do consider `hd` and `simple` keyrings to be of same type. So we check those 2 types\n      // to group those accounts together!\n      if (\n        keyringType === KeyringTypes.hd ||\n        keyringType === KeyringTypes.simple\n      ) {\n        return (\n          internalAccount.metadata.keyring.type === KeyringTypes.hd ||\n          internalAccount.metadata.keyring.type === KeyringTypes.simple\n        );\n      }\n\n      return internalAccount.metadata.keyring.type === keyringType;\n    });\n  }\n\n  /**\n   * Returns the next account number for a given keyring type.\n   * @param keyringType - The type of keyring.\n   * @returns An object containing the account prefix and index to use.\n   */\n  #getNextAccountNumber(keyringType: string): {\n    accountPrefix: string;\n    indexToUse: number;\n  } {\n    const keyringName = keyringTypeToName(keyringType);\n    const keyringAccounts = this.#getAccountsByKeyringType(keyringType);\n    const lastDefaultIndexUsedForKeyringType = keyringAccounts.reduce(\n      (maxInternalAccountIndex, internalAccount) => {\n        // We **DO NOT USE** `\\d+` here to only consider valid \"human\"\n        // number (rounded decimal number)\n        const match = new RegExp(`${keyringName} ([0-9]+)$`, 'u').exec(\n          internalAccount.metadata.name,\n        );\n\n        if (match) {\n          // Quoting `RegExp.exec` documentation:\n          // > The returned array has the matched text as the first item, and then one item for\n          // > each capturing group of the matched text.\n          // So use `match[1]` to get the captured value\n          const internalAccountIndex = parseInt(match[1], 10);\n          return Math.max(maxInternalAccountIndex, internalAccountIndex);\n        }\n\n        return maxInternalAccountIndex;\n      },\n      0,\n    );\n\n    const indexToUse = Math.max(\n      keyringAccounts.length + 1,\n      lastDefaultIndexUsedForKeyringType + 1,\n    );\n\n    return { accountPrefix: keyringName, indexToUse };\n  }\n\n  /**\n   * Handles the addition of a new account to the controller.\n   * If the account is not a Snap Keyring account, generates an internal account for it and adds it to the controller.\n   * If the account is a Snap Keyring account, retrieves the account from the keyring and adds it to the controller.\n   * @param account - The address and keyring type object of the new account.\n   */\n  #handleNewAccountAdded(account: AddressAndKeyringTypeObject) {\n    let newAccount: InternalAccount;\n    if (account.type !== KeyringTypes.snap) {\n      newAccount = this.#generateInternalAccountForNonSnapAccount(\n        account.address,\n        account.type,\n      );\n    } else {\n      const [snapKeyring] = this.messagingSystem.call(\n        'KeyringController:getKeyringsByType',\n        SnapKeyring.type,\n      );\n\n      newAccount = (snapKeyring as SnapKeyring).getAccountByAddress(\n        account.address,\n      ) as InternalAccount;\n\n      // The snap deleted the account before the keyring controller could add it\n      if (!newAccount) {\n        return;\n      }\n    }\n\n    // get next index number for the keyring type\n    const { accountPrefix, indexToUse } = this.#getNextAccountNumber(\n      newAccount.metadata.keyring.type,\n    );\n\n    const accountName = `${accountPrefix} ${indexToUse}`;\n\n    this.update((currentState: Draft<AccountsControllerState>) => {\n      (currentState as AccountsControllerState).internalAccounts.accounts[\n        newAccount.id\n      ] = {\n        ...newAccount,\n        metadata: {\n          ...newAccount.metadata,\n          name: accountName,\n          importTime: Date.now(),\n          lastSelected: Date.now(),\n        },\n      };\n    });\n\n    this.setSelectedAccount(newAccount.id);\n  }\n\n  /**\n   * Handles the removal of an account from the internal accounts list.\n   * @param accountId - The ID of the account to be removed.\n   */\n  #handleAccountRemoved(accountId: string) {\n    this.update((currentState: Draft<AccountsControllerState>) => {\n      delete currentState.internalAccounts.accounts[accountId];\n    });\n  }\n\n  /**\n   * Retrieves the value of a specific metadata key for an existing account.\n   * @param accountId - The ID of the account.\n   * @param metadataKey - The key of the metadata to retrieve.\n   * @returns The value of the specified metadata key, or undefined if the account or metadata key does not exist.\n   */\n  #populateExistingMetadata<T extends keyof InternalAccount['metadata']>(\n    accountId: string,\n    metadataKey: T,\n  ): InternalAccount['metadata'][T] | undefined {\n    const internalAccount = this.getAccount(accountId);\n    return internalAccount ? internalAccount.metadata[metadataKey] : undefined;\n  }\n\n  /**\n   * Registers message handlers for the AccountsController.\n   * @private\n   */\n  #registerMessageHandlers() {\n    this.messagingSystem.registerActionHandler(\n      `${controllerName}:setSelectedAccount`,\n      this.setSelectedAccount.bind(this),\n    );\n\n    this.messagingSystem.registerActionHandler(\n      `${controllerName}:listAccounts`,\n      this.listAccounts.bind(this),\n    );\n\n    this.messagingSystem.registerActionHandler(\n      `${controllerName}:setAccountName`,\n      this.setAccountName.bind(this),\n    );\n\n    this.messagingSystem.registerActionHandler(\n      `${controllerName}:updateAccounts`,\n      this.updateAccounts.bind(this),\n    );\n\n    this.messagingSystem.registerActionHandler(\n      `${controllerName}:getSelectedAccount`,\n      this.getSelectedAccount.bind(this),\n    );\n\n    this.messagingSystem.registerActionHandler(\n      `${controllerName}:getAccountByAddress`,\n      this.getAccountByAddress.bind(this),\n    );\n\n    this.messagingSystem.registerActionHandler(\n      `AccountsController:getAccount`,\n      this.getAccount.bind(this),\n    );\n  }\n}\n"],"mappings":"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","names":[]}
         | 
| @@ -48,11 +48,14 @@ function keyringTypeToName(keyringType) { | |
| 48 48 | 
             
                }
         | 
| 49 49 | 
             
              }
         | 
| 50 50 | 
             
            }
         | 
| 51 | 
            -
            function  | 
| 51 | 
            +
            function getUUIDOptionsFromAddressOfNormalAccount(address) {
         | 
| 52 52 | 
             
              const v4options = {
         | 
| 53 53 | 
             
                random: _sha256.sha256.call(void 0, _util.toBuffer.call(void 0, address)).slice(0, 16)
         | 
| 54 54 | 
             
              };
         | 
| 55 | 
            -
              return  | 
| 55 | 
            +
              return v4options;
         | 
| 56 | 
            +
            }
         | 
| 57 | 
            +
            function getUUIDFromAddressOfNormalAccount(address) {
         | 
| 58 | 
            +
              return _uuid.v4.call(void 0, getUUIDOptionsFromAddressOfNormalAccount(address));
         | 
| 56 59 | 
             
            }
         | 
| 57 60 |  | 
| 58 61 |  | 
| @@ -60,5 +63,6 @@ function getUUIDFromAddressOfNormalAccount(address) { | |
| 60 63 |  | 
| 61 64 |  | 
| 62 65 |  | 
| 63 | 
            -
             | 
| 64 | 
            -
             | 
| 66 | 
            +
             | 
| 67 | 
            +
            exports.__privateAdd = __privateAdd; exports.__privateMethod = __privateMethod; exports.keyringTypeToName = keyringTypeToName; exports.getUUIDOptionsFromAddressOfNormalAccount = getUUIDOptionsFromAddressOfNormalAccount; exports.getUUIDFromAddressOfNormalAccount = getUUIDFromAddressOfNormalAccount;
         | 
| 68 | 
            +
            //# sourceMappingURL=chunk-KCST55AQ.js.map
         | 
| @@ -0,0 +1 @@ | |
| 1 | 
            +
            {"version":3,"sources":["../src/utils.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;AAAA,SAAS,gBAAgB;AACzB,SAAS,kBAAkB,oBAAoB;AAC/C,SAAS,cAAc;AAEvB,SAAS,MAAM,YAAY;AAQpB,SAAS,kBAAkB,aAA6B;AAG7D,MAAI,iBAAiB,WAAW,GAAG;AACjC,WAAO;AAAA,EACT;AAEA,UAAQ,aAAa;AAAA,IACnB,KAAK,aAAa,QAAQ;AACxB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,IAAI;AACpB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,QAAQ;AACxB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,QAAQ;AACxB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,SAAS;AACzB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,IAAI;AACpB,aAAO;AAAA,IACT;AAAA,IACA,KAAK,aAAa,MAAM;AACtB,aAAO;AAAA,IACT;AAAA,IACA,SAAS;AACP,YAAM,IAAI,MAAM,mBAAmB,WAAW,EAAE;AAAA,IAClD;AAAA,EACF;AACF;AAOO,SAAS,yCACd,SACW;AACX,QAAM,YAAY;AAAA,IAChB,QAAQ,OAAO,SAAS,OAAO,CAAC,EAAE,MAAM,GAAG,EAAE;AAAA,EAC/C;AAEA,SAAO;AACT;AAOO,SAAS,kCAAkC,SAAyB;AACzE,SAAO,KAAK,yCAAyC,OAAO,CAAC;AAC/D","sourcesContent":["import { toBuffer } from '@ethereumjs/util';\nimport { isCustodyKeyring, KeyringTypes } from '@metamask/keyring-controller';\nimport { sha256 } from 'ethereum-cryptography/sha256';\nimport type { V4Options } from 'uuid';\nimport { v4 as uuid } from 'uuid';\n\n/**\n * Returns the name of the keyring type.\n *\n * @param keyringType - The type of the keyring.\n * @returns The name of the keyring type.\n */\nexport function keyringTypeToName(keyringType: string): string {\n  // Custody keyrings are a special case, as they are not a single type\n  // they just start with the prefix `Custody`\n  if (isCustodyKeyring(keyringType)) {\n    return 'Custody';\n  }\n\n  switch (keyringType) {\n    case KeyringTypes.simple: {\n      return 'Account';\n    }\n    case KeyringTypes.hd: {\n      return 'Account';\n    }\n    case KeyringTypes.trezor: {\n      return 'Trezor';\n    }\n    case KeyringTypes.ledger: {\n      return 'Ledger';\n    }\n    case KeyringTypes.lattice: {\n      return 'Lattice';\n    }\n    case KeyringTypes.qr: {\n      return 'QR';\n    }\n    case KeyringTypes.snap: {\n      return 'Snap Account';\n    }\n    default: {\n      throw new Error(`Unknown keyring ${keyringType}`);\n    }\n  }\n}\n\n/**\n * Generates a UUID v4 options from a given Ethereum address.\n * @param address - The Ethereum address to generate the UUID from.\n * @returns The UUID v4 options.\n */\nexport function getUUIDOptionsFromAddressOfNormalAccount(\n  address: string,\n): V4Options {\n  const v4options = {\n    random: sha256(toBuffer(address)).slice(0, 16),\n  };\n\n  return v4options;\n}\n\n/**\n * Generates a UUID from a given Ethereum address.\n * @param address - The Ethereum address to generate the UUID from.\n * @returns The generated UUID.\n */\nexport function getUUIDFromAddressOfNormalAccount(address: string): string {\n  return uuid(getUUIDOptionsFromAddressOfNormalAccount(address));\n}\n"]}
         |