@metamask-previews/seedless-onboarding-controller 0.0.0-preview-ddbcf048
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 +20 -0
- package/LICENSE +20 -0
- package/README.md +15 -0
- package/dist/SeedPhraseMetadata.cjs +146 -0
- package/dist/SeedPhraseMetadata.cjs.map +1 -0
- package/dist/SeedPhraseMetadata.d.cts +82 -0
- package/dist/SeedPhraseMetadata.d.cts.map +1 -0
- package/dist/SeedPhraseMetadata.d.mts +82 -0
- package/dist/SeedPhraseMetadata.d.mts.map +1 -0
- package/dist/SeedPhraseMetadata.mjs +142 -0
- package/dist/SeedPhraseMetadata.mjs.map +1 -0
- package/dist/SeedlessOnboardingController.cjs +578 -0
- package/dist/SeedlessOnboardingController.cjs.map +1 -0
- package/dist/SeedlessOnboardingController.d.cts +87 -0
- package/dist/SeedlessOnboardingController.d.cts.map +1 -0
- package/dist/SeedlessOnboardingController.d.mts +87 -0
- package/dist/SeedlessOnboardingController.d.mts.map +1 -0
- package/dist/SeedlessOnboardingController.mjs +573 -0
- package/dist/SeedlessOnboardingController.mjs.map +1 -0
- package/dist/constants.cjs +29 -0
- package/dist/constants.cjs.map +1 -0
- package/dist/constants.d.cts +24 -0
- package/dist/constants.d.cts.map +1 -0
- package/dist/constants.d.mts +24 -0
- package/dist/constants.d.mts.map +1 -0
- package/dist/constants.mjs +26 -0
- package/dist/constants.mjs.map +1 -0
- package/dist/errors.cjs +76 -0
- package/dist/errors.cjs.map +1 -0
- package/dist/errors.d.cts +26 -0
- package/dist/errors.d.cts.map +1 -0
- package/dist/errors.d.mts +26 -0
- package/dist/errors.d.mts.map +1 -0
- package/dist/errors.mjs +72 -0
- package/dist/errors.mjs.map +1 -0
- package/dist/index.cjs +24 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +5 -0
- package/dist/index.d.cts.map +1 -0
- package/dist/index.d.mts +5 -0
- package/dist/index.d.mts.map +1 -0
- package/dist/index.mjs +4 -0
- package/dist/index.mjs.map +1 -0
- package/dist/logger.cjs +8 -0
- package/dist/logger.cjs.map +1 -0
- package/dist/logger.d.cts +5 -0
- package/dist/logger.d.cts.map +1 -0
- package/dist/logger.d.mts +5 -0
- package/dist/logger.d.mts.map +1 -0
- package/dist/logger.mjs +5 -0
- package/dist/logger.mjs.map +1 -0
- package/dist/types.cjs +3 -0
- package/dist/types.cjs.map +1 -0
- package/dist/types.d.cts +120 -0
- package/dist/types.d.cts.map +1 -0
- package/dist/types.d.mts +120 -0
- package/dist/types.d.mts.map +1 -0
- package/dist/types.mjs +2 -0
- package/dist/types.mjs.map +1 -0
- package/package.json +80 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SeedlessOnboardingController.cjs","sourceRoot":"","sources":["../src/SeedlessOnboardingController.ts"],"names":[],"mappings":"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","sourcesContent":["import { keccak256AndHexify } from '@metamask/auth-network-utils';\nimport type { StateMetadata } from '@metamask/base-controller';\nimport { BaseController } from '@metamask/base-controller';\nimport { encrypt, decrypt } from '@metamask/browser-passworder';\nimport type {\n KeyPair,\n NodeAuthTokens,\n SEC1EncodedPublicKey,\n} from '@metamask/toprf-secure-backup';\nimport { ToprfSecureBackup } from '@metamask/toprf-secure-backup';\nimport {\n base64ToBytes,\n bytesToBase64,\n stringToBytes,\n remove0x,\n bigIntToHex,\n} from '@metamask/utils';\nimport { Mutex } from 'async-mutex';\n\nimport {\n controllerName,\n SeedlessOnboardingControllerError,\n Web3AuthNetwork,\n} from './constants';\nimport { RecoveryError } from './errors';\nimport { projectLogger, createModuleLogger } from './logger';\nimport { SeedPhraseMetadata } from './SeedPhraseMetadata';\nimport type {\n VaultEncryptor,\n MutuallyExclusiveCallback,\n SeedlessOnboardingControllerMessenger,\n SeedlessOnboardingControllerOptions,\n SeedlessOnboardingControllerState,\n VaultData,\n AuthenticatedUserDetails,\n} from './types';\n\nconst log = createModuleLogger(projectLogger, controllerName);\n\n/**\n * Get the default state for the Seedless Onboarding Controller.\n *\n * @returns The default state for the Seedless Onboarding Controller.\n */\nexport function getDefaultSeedlessOnboardingControllerState(): SeedlessOnboardingControllerState {\n return {\n backupHashes: [],\n };\n}\n\n/**\n * Seedless Onboarding Controller State Metadata.\n *\n * This allows us to choose if fields of the state should be persisted or not\n * using the `persist` flag; and if they can be sent to Sentry or not, using\n * the `anonymous` flag.\n */\nconst seedlessOnboardingMetadata: StateMetadata<SeedlessOnboardingControllerState> =\n {\n vault: {\n persist: true,\n anonymous: false,\n },\n backupHashes: {\n persist: true,\n anonymous: true,\n },\n nodeAuthTokens: {\n persist: false,\n anonymous: true,\n },\n authConnectionId: {\n persist: true,\n anonymous: true,\n },\n groupedAuthConnectionId: {\n persist: true,\n anonymous: true,\n },\n userId: {\n persist: true,\n anonymous: true,\n },\n };\n\nexport class SeedlessOnboardingController extends BaseController<\n typeof controllerName,\n SeedlessOnboardingControllerState,\n SeedlessOnboardingControllerMessenger\n> {\n readonly #vaultEncryptor: VaultEncryptor;\n\n readonly #vaultOperationMutex = new Mutex();\n\n readonly toprfClient: ToprfSecureBackup;\n\n /**\n * Creates a new SeedlessOnboardingController instance.\n *\n * @param options - The options for the SeedlessOnboardingController.\n * @param options.messenger - A restricted messenger.\n * @param options.state - Initial state to set on this controller.\n * @param options.encryptor - An optional encryptor to use for encrypting and decrypting seedless onboarding vault.\n * @param options.network - The network to be used for the Seedless Onboarding flow.\n */\n constructor({\n messenger,\n state,\n encryptor = { encrypt, decrypt }, // default to `encrypt` and `decrypt` from `@metamask/browser-passworder`\n network = Web3AuthNetwork.Mainnet,\n }: SeedlessOnboardingControllerOptions) {\n super({\n name: controllerName,\n metadata: seedlessOnboardingMetadata,\n state: {\n ...getDefaultSeedlessOnboardingControllerState(),\n ...state,\n },\n messenger,\n });\n\n this.#vaultEncryptor = encryptor;\n this.toprfClient = new ToprfSecureBackup({\n network,\n });\n }\n\n /**\n * Authenticate OAuth user using the seedless onboarding flow\n * and determine if the user is already registered or not.\n *\n * @param params - The parameters for authenticate OAuth user.\n * @param params.idTokens - The ID token(s) issued by OAuth verification service. Currently this array only contains a single idToken which is verified by all the nodes, in future we are considering to issue a unique idToken for each node.\n * @param params.authConnectionId - OAuth authConnectionId from dashboard\n * @param params.userId - user email or id from Social login\n * @param params.groupedAuthConnectionId - Optional grouped authConnectionId to be used for the authenticate request.\n * You can pass this to use aggregate multiple OAuth connections. Useful when you want user to have same account while using different OAuth connections.\n * @returns A promise that resolves to the authentication result.\n */\n async authenticate(params: {\n idTokens: string[];\n authConnectionId: string;\n userId: string;\n groupedAuthConnectionId?: string;\n }) {\n try {\n const { idTokens, authConnectionId, groupedAuthConnectionId, userId } =\n params;\n const hashedIdTokenHexes = idTokens.map((idToken) => {\n return remove0x(keccak256AndHexify(stringToBytes(idToken)));\n });\n const authenticationResult = await this.toprfClient.authenticate({\n verifier: groupedAuthConnectionId || authConnectionId,\n verifierId: userId,\n idTokens: hashedIdTokenHexes,\n singleIdVerifierParams: {\n subVerifier: authConnectionId,\n subVerifierIdTokens: idTokens,\n },\n });\n // update the state with the authenticated user info\n this.update((state) => {\n state.nodeAuthTokens = authenticationResult.nodeAuthTokens;\n state.authConnectionId = authConnectionId;\n state.groupedAuthConnectionId = groupedAuthConnectionId;\n state.userId = userId;\n });\n return authenticationResult;\n } catch (error) {\n log('Error authenticating user', error);\n throw new Error(SeedlessOnboardingControllerError.AuthenticationError);\n }\n }\n\n /**\n * Create a new TOPRF encryption key using given password and backups the provided seed phrase.\n *\n * @param password - The password used to create new wallet and seedphrase\n * @param seedPhrase - The seed phrase to backup\n * @returns A promise that resolves to the encrypted seed phrase and the encryption key.\n */\n async createToprfKeyAndBackupSeedPhrase(\n password: string,\n seedPhrase: Uint8Array,\n ): Promise<void> {\n // to make sure that fail fast,\n // assert that the user is authenticated before creating the TOPRF key and backing up the seed phrase\n this.#assertIsAuthenticatedUser(this.state);\n\n // locally evaluate the encryption key from the password\n const { encKey, authKeyPair, oprfKey } = this.toprfClient.createLocalKey({\n password,\n });\n\n // encrypt and store the seed phrase backup\n await this.#encryptAndStoreSeedPhraseBackup(\n seedPhrase,\n encKey,\n authKeyPair,\n );\n\n // store/persist the encryption key shares\n // We store the seed phrase metadata in the metadata store first. If this operation fails,\n // we avoid persisting the encryption key shares to prevent a situation where a user appears\n // to have an account but with no associated data.\n await this.#persistOprfKey(oprfKey, authKeyPair.pk);\n // create a new vault with the resulting authentication data\n await this.#createNewVaultWithAuthData({\n password,\n rawToprfEncryptionKey: encKey,\n rawToprfAuthKeyPair: authKeyPair,\n });\n }\n\n /**\n * Add a new seed phrase backup to the metadata store.\n *\n * @param seedPhrase - The seed phrase to backup.\n * @param password - The password used to create new wallet and seedphrase\n * @returns A promise that resolves to the success of the operation.\n */\n async addNewSeedPhraseBackup(\n seedPhrase: Uint8Array,\n password: string, // TODO: to verify whether we need the password here, check how multi-srp is handled in the keyring first.\n ): Promise<void> {\n // verify the password and unlock the vault\n const { toprfEncryptionKey, toprfAuthKeyPair } =\n await this.#unlockVaultWithPassword(password);\n\n // encrypt and store the seed phrase backup\n await this.#encryptAndStoreSeedPhraseBackup(\n seedPhrase,\n toprfEncryptionKey,\n toprfAuthKeyPair,\n );\n }\n\n /**\n * Fetches all encrypted seed phrases and metadata for user's account from the metadata store.\n *\n * Decrypts the seed phrases and returns the decrypted seed phrases using the recovered encryption key from the password.\n *\n * @param password - The password used to create new wallet and seedphrase\n * @returns A promise that resolves to the seed phrase metadata.\n */\n async fetchAllSeedPhrases(password: string): Promise<Uint8Array[]> {\n // assert that the user is authenticated before fetching the seed phrases\n this.#assertIsAuthenticatedUser(this.state);\n\n const { encKey, authKeyPair } = await this.#recoverEncKey(password);\n\n try {\n const secretData = await this.toprfClient.fetchAllSecretDataItems({\n decKey: encKey,\n authKeyPair,\n });\n\n if (secretData?.length > 0) {\n await this.#createNewVaultWithAuthData({\n password,\n rawToprfEncryptionKey: encKey,\n rawToprfAuthKeyPair: authKeyPair,\n });\n }\n\n return this.#withPersistedSeedPhraseBackupsState<Uint8Array[]>(() =>\n Promise.resolve(\n SeedPhraseMetadata.parseSeedPhraseFromMetadataStore(secretData),\n ),\n );\n } catch (error) {\n log('Error fetching seed phrase metadata', error);\n throw new Error(\n SeedlessOnboardingControllerError.FailedToFetchSeedPhraseMetadata,\n );\n }\n }\n\n /**\n * Update the password of the seedless onboarding flow.\n *\n * Changing password will also update the encryption key, metadata store and the vault with new encrypted values.\n *\n * @param newPassword - The new password to update.\n * @param oldPassword - The old password to verify.\n */\n async changePassword(newPassword: string, oldPassword: string) {\n // verify the old password of the encrypted vault\n await this.#unlockVaultWithPassword(oldPassword);\n\n try {\n // update the encryption key with new password and update the Metadata Store\n const { encKey: newEncKey, authKeyPair: newAuthKeyPair } =\n await this.#changeEncryptionKey(newPassword, oldPassword);\n\n // update and encrypt the vault with new password\n await this.#createNewVaultWithAuthData({\n password: newPassword,\n rawToprfEncryptionKey: newEncKey,\n rawToprfAuthKeyPair: newAuthKeyPair,\n });\n } catch (error) {\n log('Error changing password', error);\n throw new Error(SeedlessOnboardingControllerError.FailedToChangePassword);\n }\n }\n\n /**\n * Get the hash of the seed phrase backup for the given seed phrase, from the state.\n *\n * If the given seed phrase is not backed up and not found in the state, it will return `undefined`.\n *\n * @param seedPhrase - The seed phrase to get the hash of.\n * @returns A promise that resolves to the hash of the seed phrase backup.\n */\n getSeedPhraseBackupHash(seedPhrase: Uint8Array): string | undefined {\n const seedPhraseHash = keccak256AndHexify(seedPhrase);\n return this.state.backupHashes.find((hash) => hash === seedPhraseHash);\n }\n\n /**\n * Persist the encryption key for the seedless onboarding flow.\n *\n * @param oprfKey - The OPRF key to be splited and persisted.\n * @param authPubKey - The authentication public key.\n * @returns A promise that resolves to the success of the operation.\n */\n async #persistOprfKey(oprfKey: bigint, authPubKey: SEC1EncodedPublicKey) {\n this.#assertIsAuthenticatedUser(this.state);\n const verifier =\n this.state.groupedAuthConnectionId || this.state.authConnectionId;\n\n try {\n await this.toprfClient.persistLocalKey({\n nodeAuthTokens: this.state.nodeAuthTokens,\n verifier,\n verifierId: this.state.userId,\n oprfKey,\n authPubKey,\n });\n } catch (error) {\n log('Error persisting local encryption key', error);\n throw new Error(SeedlessOnboardingControllerError.FailedToPersistOprfKey);\n }\n }\n\n /**\n * Recover the encryption key from password.\n *\n * @param password - The password used to derive/recover the encryption key.\n * @returns A promise that resolves to the encryption key and authentication key pair.\n * @throws RecoveryError - If failed to recover the encryption key.\n */\n async #recoverEncKey(password: string) {\n this.#assertIsAuthenticatedUser(this.state);\n const verifier =\n this.state.groupedAuthConnectionId || this.state.authConnectionId;\n\n try {\n const recoverEncKeyResult = await this.toprfClient.recoverEncKey({\n nodeAuthTokens: this.state.nodeAuthTokens,\n password,\n verifier,\n verifierId: this.state.userId,\n });\n return recoverEncKeyResult;\n } catch (error) {\n throw RecoveryError.getInstance(error);\n }\n }\n\n /**\n * Update the encryption key with new password and update the Metadata Store with new encryption key.\n *\n * @param newPassword - The new password to update.\n * @param oldPassword - The old password to verify.\n * @returns A promise that resolves to new encryption key and authentication key pair.\n */\n async #changeEncryptionKey(newPassword: string, oldPassword: string) {\n this.#assertIsAuthenticatedUser(this.state);\n const verifier =\n this.state.groupedAuthConnectionId || this.state.authConnectionId;\n\n const {\n encKey,\n authKeyPair,\n keyShareIndex: newKeyShareIndex,\n } = await this.#recoverEncKey(oldPassword);\n\n return await this.toprfClient.changeEncKey({\n nodeAuthTokens: this.state.nodeAuthTokens,\n verifier,\n verifierId: this.state.userId,\n oldEncKey: encKey,\n oldAuthKeyPair: authKeyPair,\n newKeyShareIndex,\n newPassword,\n });\n }\n\n /**\n * Encrypt and store the seed phrase backup in the metadata store.\n *\n * @param seedPhrase - The seed phrase to store.\n * @param encKey - The encryption key to store.\n * @param authKeyPair - The authentication key pair to store.\n *\n * @returns A promise that resolves to the success of the operation.\n */\n async #encryptAndStoreSeedPhraseBackup(\n seedPhrase: Uint8Array,\n encKey: Uint8Array,\n authKeyPair: KeyPair,\n ): Promise<void> {\n try {\n const seedPhraseMetadata = new SeedPhraseMetadata(seedPhrase);\n const secretData = seedPhraseMetadata.toBytes();\n await this.#withPersistedSeedPhraseBackupsState(async () => {\n await this.toprfClient.addSecretDataItem({\n encKey,\n secretData,\n authKeyPair,\n });\n return seedPhrase;\n });\n } catch (error) {\n log('Error encrypting and storing seed phrase backup', error);\n throw new Error(\n SeedlessOnboardingControllerError.FailedToEncryptAndStoreSeedPhraseBackup,\n );\n }\n }\n\n /**\n * Unlocks the encrypted vault using the provided password and returns the decrypted vault data.\n * This method ensures thread-safety by using a mutex lock when accessing the vault.\n *\n * @param password - The password to decrypt the vault.\n * @returns A promise that resolves to an object containing:\n * - nodeAuthTokens: Authentication tokens to communicate with the TOPRF service\n * - toprfEncryptionKey: The decrypted TOPRF encryption key\n * - toprfAuthKeyPair: The decrypted TOPRF authentication key pair\n * @throws {Error} If:\n * - The password is invalid or empty\n * - The vault is not initialized\n * - The password is incorrect (from encryptor.decrypt)\n * - The decrypted vault data is malformed\n */\n async #unlockVaultWithPassword(password: string): Promise<{\n nodeAuthTokens: NodeAuthTokens;\n toprfEncryptionKey: Uint8Array;\n toprfAuthKeyPair: KeyPair;\n }> {\n return this.#withVaultLock(async () => {\n assertIsValidPassword(password);\n\n const encryptedVault = this.state.vault;\n if (!encryptedVault) {\n throw new Error(SeedlessOnboardingControllerError.VaultError);\n }\n // Note that vault decryption using the password is a very costly operation as it involves deriving the encryption key\n // from the password using an intentionally slow key derivation function.\n // We should make sure that we only call it very intentionally.\n const decryptedVaultData = await this.#vaultEncryptor.decrypt(\n password,\n encryptedVault,\n );\n\n const { nodeAuthTokens, toprfEncryptionKey, toprfAuthKeyPair } =\n this.#parseVaultData(decryptedVaultData);\n\n // update the state with the restored nodeAuthTokens\n this.update((state) => {\n state.nodeAuthTokens = nodeAuthTokens;\n });\n\n return { nodeAuthTokens, toprfEncryptionKey, toprfAuthKeyPair };\n });\n }\n\n /**\n * Executes a callback function that creates or restores seed phrases and persists their hashes in the controller state.\n *\n * This method:\n * 1. Executes the provided callback to create/restore seed phrases\n * 2. Generates keccak256 hashes of the seed phrases\n * 3. Merges new hashes with existing ones in the state, ensuring uniqueness\n * 4. Updates the controller state with the combined hashes\n *\n * This is a wrapper method that should be used around any operation that creates\n * or restores seed phrases to ensure their hashes are properly tracked.\n *\n * @param createOrRestoreSeedPhraseBackupCallback - function that returns either a single seed phrase\n * or an array of seed phrases as Uint8Array(s)\n * @returns The original seed phrase(s) returned by the callback\n * @throws Rethrows any errors from the callback with additional logging\n */\n async #withPersistedSeedPhraseBackupsState<\n Result extends Uint8Array | Uint8Array[],\n >(\n createOrRestoreSeedPhraseBackupCallback: () => Promise<Result>,\n ): Promise<Result> {\n try {\n const backedUpSeedPhrases =\n await createOrRestoreSeedPhraseBackupCallback();\n let backedUpHashB64Strings: string[] = [];\n\n if (Array.isArray(backedUpSeedPhrases)) {\n backedUpHashB64Strings = backedUpSeedPhrases.map((seedPhrase) =>\n keccak256AndHexify(seedPhrase),\n );\n } else {\n backedUpHashB64Strings = [keccak256AndHexify(backedUpSeedPhrases)];\n }\n\n const existingBackedUpHashes = this.state.backupHashes;\n const uniqueHashesSet = new Set([\n ...existingBackedUpHashes,\n ...backedUpHashB64Strings,\n ]);\n\n this.update((state) => {\n state.backupHashes = Array.from(uniqueHashesSet);\n });\n\n return backedUpSeedPhrases;\n } catch (error) {\n log('Error persisting seed phrase backups', error);\n throw error;\n }\n }\n\n /**\n * Create a new vault with the given authentication data.\n *\n * Serialize the authentication and key data which will be stored in the vault.\n *\n * @param params - The parameters for creating a new vault.\n * @param params.password - The password to encrypt the vault.\n * @param params.rawToprfEncryptionKey - The encryption key to encrypt the vault.\n * @param params.rawToprfAuthKeyPair - The authentication key pair to encrypt the vault.\n */\n async #createNewVaultWithAuthData({\n password,\n rawToprfEncryptionKey,\n rawToprfAuthKeyPair,\n }: {\n password: string;\n rawToprfEncryptionKey: Uint8Array;\n rawToprfAuthKeyPair: KeyPair;\n }): Promise<void> {\n this.#assertIsAuthenticatedUser(this.state);\n\n const { toprfEncryptionKey, toprfAuthKeyPair } = this.#serializeKeyData(\n rawToprfEncryptionKey,\n rawToprfAuthKeyPair,\n );\n\n const serializedVaultData = JSON.stringify({\n authTokens: this.state.nodeAuthTokens,\n toprfEncryptionKey,\n toprfAuthKeyPair,\n });\n\n await this.#updateVault({\n password,\n serializedVaultData,\n });\n }\n\n /**\n * Encrypt and update the vault with the given authentication data.\n *\n * @param params - The parameters for updating the vault.\n * @param params.password - The password to encrypt the vault.\n * @param params.serializedVaultData - The serialized authentication data to update the vault with.\n * @returns A promise that resolves to the updated vault.\n */\n async #updateVault({\n password,\n serializedVaultData,\n }: {\n password: string;\n serializedVaultData: string;\n }): Promise<void> {\n await this.#withVaultLock(async () => {\n assertIsValidPassword(password);\n\n const updatedState: Partial<SeedlessOnboardingControllerState> = {};\n\n // Note that vault encryption using the password is a very costly operation as it involves deriving the encryption key\n // from the password using an intentionally slow key derivation function.\n // We should make sure that we only call it very intentionally.\n updatedState.vault = await this.#vaultEncryptor.encrypt(\n password,\n serializedVaultData,\n );\n\n this.update((state) => {\n state.vault = updatedState.vault;\n });\n });\n }\n\n /**\n * Lock the vault mutex before executing the given function,\n * and release it after the function is resolved or after an\n * error is thrown.\n *\n * This ensures that each operation that interacts with the vault\n * is executed in a mutually exclusive way.\n *\n * @param callback - The function to execute while the vault mutex is locked.\n * @returns The result of the function.\n */\n async #withVaultLock<Result>(\n callback: MutuallyExclusiveCallback<Result>,\n ): Promise<Result> {\n return await withLock(this.#vaultOperationMutex, callback);\n }\n\n /**\n * Serialize the encryption key and authentication key pair.\n *\n * @param encKey - The encryption key to serialize.\n * @param authKeyPair - The authentication key pair to serialize.\n * @returns The serialized encryption key and authentication key pair.\n */\n #serializeKeyData(\n encKey: Uint8Array,\n authKeyPair: KeyPair,\n ): {\n toprfEncryptionKey: string;\n toprfAuthKeyPair: string;\n } {\n const b64EncodedEncKey = bytesToBase64(encKey);\n const b64EncodedAuthKeyPair = JSON.stringify({\n sk: bigIntToHex(authKeyPair.sk), // Convert BigInt to hex string\n pk: bytesToBase64(authKeyPair.pk),\n });\n\n return {\n toprfEncryptionKey: b64EncodedEncKey,\n toprfAuthKeyPair: b64EncodedAuthKeyPair,\n };\n }\n\n /**\n * Parse and deserialize the authentication data from the vault.\n *\n * @param data - The decrypted vault data.\n * @returns The parsed authentication data.\n * @throws If the vault data is not valid.\n */\n #parseVaultData(data: unknown): {\n nodeAuthTokens: NodeAuthTokens;\n toprfEncryptionKey: Uint8Array;\n toprfAuthKeyPair: KeyPair;\n } {\n if (typeof data !== 'string') {\n throw new Error(SeedlessOnboardingControllerError.InvalidVaultData);\n }\n\n let parsedVaultData: unknown;\n try {\n parsedVaultData = JSON.parse(data);\n } catch {\n throw new Error(SeedlessOnboardingControllerError.InvalidVaultData);\n }\n\n this.#assertIsValidVaultData(parsedVaultData);\n\n const rawToprfEncryptionKey = base64ToBytes(\n parsedVaultData.toprfEncryptionKey,\n );\n const parsedToprfAuthKeyPair = JSON.parse(parsedVaultData.toprfAuthKeyPair);\n const rawToprfAuthKeyPair = {\n sk: BigInt(parsedToprfAuthKeyPair.sk),\n pk: base64ToBytes(parsedToprfAuthKeyPair.pk),\n };\n\n return {\n nodeAuthTokens: parsedVaultData.authTokens,\n toprfEncryptionKey: rawToprfEncryptionKey,\n toprfAuthKeyPair: rawToprfAuthKeyPair,\n };\n }\n\n /**\n * Assert that the provided value contains valid authenticated user information.\n *\n * This method checks that the value is an object containing:\n * - nodeAuthTokens: A non-empty array of authentication tokens\n * - authConnectionId: A string identifier for the OAuth connection\n * - groupedAuthConnectionId: A string identifier for grouped OAuth connections\n * - userId: A string identifier for the authenticated user\n *\n * @param value - The value to validate.\n * @throws {Error} If the value does not contain valid authenticated user information.\n */\n #assertIsAuthenticatedUser(\n value: unknown,\n ): asserts value is AuthenticatedUserDetails {\n if (\n !value ||\n typeof value !== 'object' ||\n !('authConnectionId' in value) ||\n typeof value.authConnectionId !== 'string' ||\n !('userId' in value) ||\n typeof value.userId !== 'string'\n ) {\n throw new Error(SeedlessOnboardingControllerError.MissingAuthUserInfo);\n }\n\n if (\n !('nodeAuthTokens' in value) ||\n typeof value.nodeAuthTokens !== 'object' ||\n !Array.isArray(value.nodeAuthTokens) ||\n value.nodeAuthTokens.length < 3 // At least 3 auth tokens are required for Threshold OPRF service\n ) {\n throw new Error(SeedlessOnboardingControllerError.InsufficientAuthToken);\n }\n }\n\n /**\n * Check if the provided value is a valid vault data.\n *\n * @param value - The value to check.\n * @throws If the value is not a valid vault data.\n */\n #assertIsValidVaultData(value: unknown): asserts value is VaultData {\n // value is not valid vault data if any of the following conditions are true:\n if (\n !value || // value is not defined\n typeof value !== 'object' || // value is not an object\n !('authTokens' in value) || // authTokens is not defined\n typeof value.authTokens !== 'object' || // authTokens is not an object\n !('toprfEncryptionKey' in value) || // toprfEncryptionKey is not defined\n typeof value.toprfEncryptionKey !== 'string' || // toprfEncryptionKey is not a string\n !('toprfAuthKeyPair' in value) || // toprfAuthKeyPair is not defined\n typeof value.toprfAuthKeyPair !== 'string' // toprfAuthKeyPair is not a string\n ) {\n throw new Error(SeedlessOnboardingControllerError.VaultDataError);\n }\n }\n}\n\n/**\n * Assert that the provided password is a valid non-empty string.\n *\n * @param password - The password to check.\n * @throws If the password is not a valid string.\n */\nfunction assertIsValidPassword(password: unknown): asserts password is string {\n if (typeof password !== 'string') {\n throw new Error(SeedlessOnboardingControllerError.WrongPasswordType);\n }\n\n if (!password || !password.length) {\n throw new Error(SeedlessOnboardingControllerError.InvalidEmptyPassword);\n }\n}\n\n/**\n * Lock the given mutex before executing the given function,\n * and release it after the function is resolved or after an\n * error is thrown.\n *\n * @param mutex - The mutex to lock.\n * @param callback - The function to execute while the mutex is locked.\n * @returns The result of the function.\n */\nasync function withLock<Result>(\n mutex: Mutex,\n callback: MutuallyExclusiveCallback<Result>,\n): Promise<Result> {\n const releaseLock = await mutex.acquire();\n\n try {\n return await callback({ releaseLock });\n } finally {\n releaseLock();\n }\n}\n"]}
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
import { BaseController } from "@metamask/base-controller";
|
|
2
|
+
import { ToprfSecureBackup } from "@metamask/toprf-secure-backup";
|
|
3
|
+
import { controllerName } from "./constants.cjs";
|
|
4
|
+
import type { SeedlessOnboardingControllerMessenger, SeedlessOnboardingControllerOptions, SeedlessOnboardingControllerState } from "./types.cjs";
|
|
5
|
+
/**
|
|
6
|
+
* Get the default state for the Seedless Onboarding Controller.
|
|
7
|
+
*
|
|
8
|
+
* @returns The default state for the Seedless Onboarding Controller.
|
|
9
|
+
*/
|
|
10
|
+
export declare function getDefaultSeedlessOnboardingControllerState(): SeedlessOnboardingControllerState;
|
|
11
|
+
export declare class SeedlessOnboardingController extends BaseController<typeof controllerName, SeedlessOnboardingControllerState, SeedlessOnboardingControllerMessenger> {
|
|
12
|
+
#private;
|
|
13
|
+
readonly toprfClient: ToprfSecureBackup;
|
|
14
|
+
/**
|
|
15
|
+
* Creates a new SeedlessOnboardingController instance.
|
|
16
|
+
*
|
|
17
|
+
* @param options - The options for the SeedlessOnboardingController.
|
|
18
|
+
* @param options.messenger - A restricted messenger.
|
|
19
|
+
* @param options.state - Initial state to set on this controller.
|
|
20
|
+
* @param options.encryptor - An optional encryptor to use for encrypting and decrypting seedless onboarding vault.
|
|
21
|
+
* @param options.network - The network to be used for the Seedless Onboarding flow.
|
|
22
|
+
*/
|
|
23
|
+
constructor({ messenger, state, encryptor, // default to `encrypt` and `decrypt` from `@metamask/browser-passworder`
|
|
24
|
+
network, }: SeedlessOnboardingControllerOptions);
|
|
25
|
+
/**
|
|
26
|
+
* Authenticate OAuth user using the seedless onboarding flow
|
|
27
|
+
* and determine if the user is already registered or not.
|
|
28
|
+
*
|
|
29
|
+
* @param params - The parameters for authenticate OAuth user.
|
|
30
|
+
* @param params.idTokens - The ID token(s) issued by OAuth verification service. Currently this array only contains a single idToken which is verified by all the nodes, in future we are considering to issue a unique idToken for each node.
|
|
31
|
+
* @param params.authConnectionId - OAuth authConnectionId from dashboard
|
|
32
|
+
* @param params.userId - user email or id from Social login
|
|
33
|
+
* @param params.groupedAuthConnectionId - Optional grouped authConnectionId to be used for the authenticate request.
|
|
34
|
+
* You can pass this to use aggregate multiple OAuth connections. Useful when you want user to have same account while using different OAuth connections.
|
|
35
|
+
* @returns A promise that resolves to the authentication result.
|
|
36
|
+
*/
|
|
37
|
+
authenticate(params: {
|
|
38
|
+
idTokens: string[];
|
|
39
|
+
authConnectionId: string;
|
|
40
|
+
userId: string;
|
|
41
|
+
groupedAuthConnectionId?: string;
|
|
42
|
+
}): Promise<import("@metamask/toprf-secure-backup").AuthenticateResult>;
|
|
43
|
+
/**
|
|
44
|
+
* Create a new TOPRF encryption key using given password and backups the provided seed phrase.
|
|
45
|
+
*
|
|
46
|
+
* @param password - The password used to create new wallet and seedphrase
|
|
47
|
+
* @param seedPhrase - The seed phrase to backup
|
|
48
|
+
* @returns A promise that resolves to the encrypted seed phrase and the encryption key.
|
|
49
|
+
*/
|
|
50
|
+
createToprfKeyAndBackupSeedPhrase(password: string, seedPhrase: Uint8Array): Promise<void>;
|
|
51
|
+
/**
|
|
52
|
+
* Add a new seed phrase backup to the metadata store.
|
|
53
|
+
*
|
|
54
|
+
* @param seedPhrase - The seed phrase to backup.
|
|
55
|
+
* @param password - The password used to create new wallet and seedphrase
|
|
56
|
+
* @returns A promise that resolves to the success of the operation.
|
|
57
|
+
*/
|
|
58
|
+
addNewSeedPhraseBackup(seedPhrase: Uint8Array, password: string): Promise<void>;
|
|
59
|
+
/**
|
|
60
|
+
* Fetches all encrypted seed phrases and metadata for user's account from the metadata store.
|
|
61
|
+
*
|
|
62
|
+
* Decrypts the seed phrases and returns the decrypted seed phrases using the recovered encryption key from the password.
|
|
63
|
+
*
|
|
64
|
+
* @param password - The password used to create new wallet and seedphrase
|
|
65
|
+
* @returns A promise that resolves to the seed phrase metadata.
|
|
66
|
+
*/
|
|
67
|
+
fetchAllSeedPhrases(password: string): Promise<Uint8Array[]>;
|
|
68
|
+
/**
|
|
69
|
+
* Update the password of the seedless onboarding flow.
|
|
70
|
+
*
|
|
71
|
+
* Changing password will also update the encryption key, metadata store and the vault with new encrypted values.
|
|
72
|
+
*
|
|
73
|
+
* @param newPassword - The new password to update.
|
|
74
|
+
* @param oldPassword - The old password to verify.
|
|
75
|
+
*/
|
|
76
|
+
changePassword(newPassword: string, oldPassword: string): Promise<void>;
|
|
77
|
+
/**
|
|
78
|
+
* Get the hash of the seed phrase backup for the given seed phrase, from the state.
|
|
79
|
+
*
|
|
80
|
+
* If the given seed phrase is not backed up and not found in the state, it will return `undefined`.
|
|
81
|
+
*
|
|
82
|
+
* @param seedPhrase - The seed phrase to get the hash of.
|
|
83
|
+
* @returns A promise that resolves to the hash of the seed phrase backup.
|
|
84
|
+
*/
|
|
85
|
+
getSeedPhraseBackupHash(seedPhrase: Uint8Array): string | undefined;
|
|
86
|
+
}
|
|
87
|
+
//# sourceMappingURL=SeedlessOnboardingController.d.cts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SeedlessOnboardingController.d.cts","sourceRoot":"","sources":["../src/SeedlessOnboardingController.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,cAAc,EAAE,kCAAkC;AAO3D,OAAO,EAAE,iBAAiB,EAAE,sCAAsC;AAUlE,OAAO,EACL,cAAc,EAGf,wBAAoB;AAIrB,OAAO,KAAK,EAGV,qCAAqC,EACrC,mCAAmC,EACnC,iCAAiC,EAGlC,oBAAgB;AAIjB;;;;GAIG;AACH,wBAAgB,2CAA2C,IAAI,iCAAiC,CAI/F;AAqCD,qBAAa,4BAA6B,SAAQ,cAAc,CAC9D,OAAO,cAAc,EACrB,iCAAiC,EACjC,qCAAqC,CACtC;;IAKC,QAAQ,CAAC,WAAW,EAAE,iBAAiB,CAAC;IAExC;;;;;;;;OAQG;gBACS,EACV,SAAS,EACT,KAAK,EACL,SAAgC,EAAE,yEAAyE;IAC3G,OAAiC,GAClC,EAAE,mCAAmC;IAiBtC;;;;;;;;;;;OAWG;IACG,YAAY,CAAC,MAAM,EAAE;QACzB,QAAQ,EAAE,MAAM,EAAE,CAAC;QACnB,gBAAgB,EAAE,MAAM,CAAC;QACzB,MAAM,EAAE,MAAM,CAAC;QACf,uBAAuB,CAAC,EAAE,MAAM,CAAC;KAClC;IA8BD;;;;;;OAMG;IACG,iCAAiC,CACrC,QAAQ,EAAE,MAAM,EAChB,UAAU,EAAE,UAAU,GACrB,OAAO,CAAC,IAAI,CAAC;IA8BhB;;;;;;OAMG;IACG,sBAAsB,CAC1B,UAAU,EAAE,UAAU,EACtB,QAAQ,EAAE,MAAM,GACf,OAAO,CAAC,IAAI,CAAC;IAahB;;;;;;;OAOG;IACG,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,EAAE,CAAC;IAiClE;;;;;;;OAOG;IACG,cAAc,CAAC,WAAW,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM;IAqB7D;;;;;;;OAOG;IACH,uBAAuB,CAAC,UAAU,EAAE,UAAU,GAAG,MAAM,GAAG,SAAS;CA8apE"}
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
import { BaseController } from "@metamask/base-controller";
|
|
2
|
+
import { ToprfSecureBackup } from "@metamask/toprf-secure-backup";
|
|
3
|
+
import { controllerName } from "./constants.mjs";
|
|
4
|
+
import type { SeedlessOnboardingControllerMessenger, SeedlessOnboardingControllerOptions, SeedlessOnboardingControllerState } from "./types.mjs";
|
|
5
|
+
/**
|
|
6
|
+
* Get the default state for the Seedless Onboarding Controller.
|
|
7
|
+
*
|
|
8
|
+
* @returns The default state for the Seedless Onboarding Controller.
|
|
9
|
+
*/
|
|
10
|
+
export declare function getDefaultSeedlessOnboardingControllerState(): SeedlessOnboardingControllerState;
|
|
11
|
+
export declare class SeedlessOnboardingController extends BaseController<typeof controllerName, SeedlessOnboardingControllerState, SeedlessOnboardingControllerMessenger> {
|
|
12
|
+
#private;
|
|
13
|
+
readonly toprfClient: ToprfSecureBackup;
|
|
14
|
+
/**
|
|
15
|
+
* Creates a new SeedlessOnboardingController instance.
|
|
16
|
+
*
|
|
17
|
+
* @param options - The options for the SeedlessOnboardingController.
|
|
18
|
+
* @param options.messenger - A restricted messenger.
|
|
19
|
+
* @param options.state - Initial state to set on this controller.
|
|
20
|
+
* @param options.encryptor - An optional encryptor to use for encrypting and decrypting seedless onboarding vault.
|
|
21
|
+
* @param options.network - The network to be used for the Seedless Onboarding flow.
|
|
22
|
+
*/
|
|
23
|
+
constructor({ messenger, state, encryptor, // default to `encrypt` and `decrypt` from `@metamask/browser-passworder`
|
|
24
|
+
network, }: SeedlessOnboardingControllerOptions);
|
|
25
|
+
/**
|
|
26
|
+
* Authenticate OAuth user using the seedless onboarding flow
|
|
27
|
+
* and determine if the user is already registered or not.
|
|
28
|
+
*
|
|
29
|
+
* @param params - The parameters for authenticate OAuth user.
|
|
30
|
+
* @param params.idTokens - The ID token(s) issued by OAuth verification service. Currently this array only contains a single idToken which is verified by all the nodes, in future we are considering to issue a unique idToken for each node.
|
|
31
|
+
* @param params.authConnectionId - OAuth authConnectionId from dashboard
|
|
32
|
+
* @param params.userId - user email or id from Social login
|
|
33
|
+
* @param params.groupedAuthConnectionId - Optional grouped authConnectionId to be used for the authenticate request.
|
|
34
|
+
* You can pass this to use aggregate multiple OAuth connections. Useful when you want user to have same account while using different OAuth connections.
|
|
35
|
+
* @returns A promise that resolves to the authentication result.
|
|
36
|
+
*/
|
|
37
|
+
authenticate(params: {
|
|
38
|
+
idTokens: string[];
|
|
39
|
+
authConnectionId: string;
|
|
40
|
+
userId: string;
|
|
41
|
+
groupedAuthConnectionId?: string;
|
|
42
|
+
}): Promise<import("@metamask/toprf-secure-backup").AuthenticateResult>;
|
|
43
|
+
/**
|
|
44
|
+
* Create a new TOPRF encryption key using given password and backups the provided seed phrase.
|
|
45
|
+
*
|
|
46
|
+
* @param password - The password used to create new wallet and seedphrase
|
|
47
|
+
* @param seedPhrase - The seed phrase to backup
|
|
48
|
+
* @returns A promise that resolves to the encrypted seed phrase and the encryption key.
|
|
49
|
+
*/
|
|
50
|
+
createToprfKeyAndBackupSeedPhrase(password: string, seedPhrase: Uint8Array): Promise<void>;
|
|
51
|
+
/**
|
|
52
|
+
* Add a new seed phrase backup to the metadata store.
|
|
53
|
+
*
|
|
54
|
+
* @param seedPhrase - The seed phrase to backup.
|
|
55
|
+
* @param password - The password used to create new wallet and seedphrase
|
|
56
|
+
* @returns A promise that resolves to the success of the operation.
|
|
57
|
+
*/
|
|
58
|
+
addNewSeedPhraseBackup(seedPhrase: Uint8Array, password: string): Promise<void>;
|
|
59
|
+
/**
|
|
60
|
+
* Fetches all encrypted seed phrases and metadata for user's account from the metadata store.
|
|
61
|
+
*
|
|
62
|
+
* Decrypts the seed phrases and returns the decrypted seed phrases using the recovered encryption key from the password.
|
|
63
|
+
*
|
|
64
|
+
* @param password - The password used to create new wallet and seedphrase
|
|
65
|
+
* @returns A promise that resolves to the seed phrase metadata.
|
|
66
|
+
*/
|
|
67
|
+
fetchAllSeedPhrases(password: string): Promise<Uint8Array[]>;
|
|
68
|
+
/**
|
|
69
|
+
* Update the password of the seedless onboarding flow.
|
|
70
|
+
*
|
|
71
|
+
* Changing password will also update the encryption key, metadata store and the vault with new encrypted values.
|
|
72
|
+
*
|
|
73
|
+
* @param newPassword - The new password to update.
|
|
74
|
+
* @param oldPassword - The old password to verify.
|
|
75
|
+
*/
|
|
76
|
+
changePassword(newPassword: string, oldPassword: string): Promise<void>;
|
|
77
|
+
/**
|
|
78
|
+
* Get the hash of the seed phrase backup for the given seed phrase, from the state.
|
|
79
|
+
*
|
|
80
|
+
* If the given seed phrase is not backed up and not found in the state, it will return `undefined`.
|
|
81
|
+
*
|
|
82
|
+
* @param seedPhrase - The seed phrase to get the hash of.
|
|
83
|
+
* @returns A promise that resolves to the hash of the seed phrase backup.
|
|
84
|
+
*/
|
|
85
|
+
getSeedPhraseBackupHash(seedPhrase: Uint8Array): string | undefined;
|
|
86
|
+
}
|
|
87
|
+
//# sourceMappingURL=SeedlessOnboardingController.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SeedlessOnboardingController.d.mts","sourceRoot":"","sources":["../src/SeedlessOnboardingController.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,cAAc,EAAE,kCAAkC;AAO3D,OAAO,EAAE,iBAAiB,EAAE,sCAAsC;AAUlE,OAAO,EACL,cAAc,EAGf,wBAAoB;AAIrB,OAAO,KAAK,EAGV,qCAAqC,EACrC,mCAAmC,EACnC,iCAAiC,EAGlC,oBAAgB;AAIjB;;;;GAIG;AACH,wBAAgB,2CAA2C,IAAI,iCAAiC,CAI/F;AAqCD,qBAAa,4BAA6B,SAAQ,cAAc,CAC9D,OAAO,cAAc,EACrB,iCAAiC,EACjC,qCAAqC,CACtC;;IAKC,QAAQ,CAAC,WAAW,EAAE,iBAAiB,CAAC;IAExC;;;;;;;;OAQG;gBACS,EACV,SAAS,EACT,KAAK,EACL,SAAgC,EAAE,yEAAyE;IAC3G,OAAiC,GAClC,EAAE,mCAAmC;IAiBtC;;;;;;;;;;;OAWG;IACG,YAAY,CAAC,MAAM,EAAE;QACzB,QAAQ,EAAE,MAAM,EAAE,CAAC;QACnB,gBAAgB,EAAE,MAAM,CAAC;QACzB,MAAM,EAAE,MAAM,CAAC;QACf,uBAAuB,CAAC,EAAE,MAAM,CAAC;KAClC;IA8BD;;;;;;OAMG;IACG,iCAAiC,CACrC,QAAQ,EAAE,MAAM,EAChB,UAAU,EAAE,UAAU,GACrB,OAAO,CAAC,IAAI,CAAC;IA8BhB;;;;;;OAMG;IACG,sBAAsB,CAC1B,UAAU,EAAE,UAAU,EACtB,QAAQ,EAAE,MAAM,GACf,OAAO,CAAC,IAAI,CAAC;IAahB;;;;;;;OAOG;IACG,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,EAAE,CAAC;IAiClE;;;;;;;OAOG;IACG,cAAc,CAAC,WAAW,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM;IAqB7D;;;;;;;OAOG;IACH,uBAAuB,CAAC,UAAU,EAAE,UAAU,GAAG,MAAM,GAAG,SAAS;CA8apE"}
|