@metamask-previews/keyring-controller 14.0.1-preview-f04be62f → 15.0.0-preview-fb52b9eb
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 +23 -1
- package/dist/KeyringController.js +3 -3
- package/dist/KeyringController.mjs +2 -2
- package/dist/{chunk-NAAWD7HX.mjs → chunk-HT7WOORD.mjs} +3 -1
- package/dist/{chunk-NAAWD7HX.mjs.map → chunk-HT7WOORD.mjs.map} +1 -1
- package/dist/{chunk-BVSGYW4D.js → chunk-ISACMNF3.js} +517 -401
- package/dist/chunk-ISACMNF3.js.map +1 -0
- package/dist/{chunk-CHLPTPMZ.js → chunk-QDPHKQON.js} +3 -1
- package/dist/chunk-QDPHKQON.js.map +1 -0
- package/dist/{chunk-6HZWCYLD.mjs → chunk-RVCG63UG.mjs} +457 -341
- package/dist/chunk-RVCG63UG.mjs.map +1 -0
- package/dist/constants.js +2 -2
- package/dist/constants.mjs +1 -1
- package/dist/index.js +3 -3
- package/dist/index.mjs +2 -2
- package/dist/tsconfig.build.tsbuildinfo +1 -1
- package/dist/types/KeyringController.d.ts +27 -33
- package/dist/types/KeyringController.d.ts.map +1 -1
- package/dist/types/constants.d.ts +3 -1
- package/dist/types/constants.d.ts.map +1 -1
- package/package.json +2 -2
- package/dist/chunk-6HZWCYLD.mjs.map +0 -1
- package/dist/chunk-BVSGYW4D.js.map +0 -1
- package/dist/chunk-CHLPTPMZ.js.map +0 -1
|
@@ -3,7 +3,7 @@ import {
|
|
|
3
3
|
__privateGet,
|
|
4
4
|
__privateMethod,
|
|
5
5
|
__privateSet
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-HT7WOORD.mjs";
|
|
7
7
|
|
|
8
8
|
// src/KeyringController.ts
|
|
9
9
|
import { isValidPrivate, toBuffer, getBinarySize } from "@ethereumjs/util";
|
|
@@ -86,7 +86,7 @@ async function displayForKeyring(keyring) {
|
|
|
86
86
|
accounts: accounts.map(normalize)
|
|
87
87
|
};
|
|
88
88
|
}
|
|
89
|
-
var _keyringBuilders, _keyrings, _unsupportedKeyrings, _password, _encryptor, _cacheEncryptionKey, _qrKeyringStateListener, _registerMessageHandlers, registerMessageHandlers_fn, _getKeyringBuilderForType, getKeyringBuilderForType_fn, _addQRKeyring, addQRKeyring_fn, _subscribeToQRKeyringEvents, subscribeToQRKeyringEvents_fn, _unsubscribeFromQRKeyringsEvents, unsubscribeFromQRKeyringsEvents_fn, _createNewVaultWithKeyring, createNewVaultWithKeyring_fn,
|
|
89
|
+
var _controllerOperationMutex, _vaultOperationMutex, _keyringBuilders, _keyrings, _unsupportedKeyrings, _password, _encryptor, _cacheEncryptionKey, _qrKeyringStateListener, _registerMessageHandlers, registerMessageHandlers_fn, _getKeyringBuilderForType, getKeyringBuilderForType_fn, _addQRKeyring, addQRKeyring_fn, _subscribeToQRKeyringEvents, subscribeToQRKeyringEvents_fn, _unsubscribeFromQRKeyringsEvents, unsubscribeFromQRKeyringsEvents_fn, _createNewVaultWithKeyring, createNewVaultWithKeyring_fn, _getUpdatedKeyrings, getUpdatedKeyrings_fn, _unlockKeyrings, unlockKeyrings_fn, _updateVault, updateVault_fn, _getAccountsFromKeyrings, getAccountsFromKeyrings_fn, _createKeyringWithFirstAccount, createKeyringWithFirstAccount_fn, _newKeyring, newKeyring_fn, _clearKeyrings, clearKeyrings_fn, _restoreKeyring, restoreKeyring_fn, _destroyKeyring, destroyKeyring_fn, _removeEmptyKeyrings, removeEmptyKeyrings_fn, _checkForDuplicate, checkForDuplicate_fn, _setUnlocked, setUnlocked_fn, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn, _withControllerLock, withControllerLock_fn, _withVaultLock, withVaultLock_fn;
|
|
90
90
|
var KeyringController = class extends BaseController {
|
|
91
91
|
/**
|
|
92
92
|
* Creates a KeyringController instance.
|
|
@@ -164,9 +164,12 @@ var KeyringController = class extends BaseController {
|
|
|
164
164
|
*/
|
|
165
165
|
__privateAdd(this, _createNewVaultWithKeyring);
|
|
166
166
|
/**
|
|
167
|
-
*
|
|
167
|
+
* Get the updated array of each keyring's type and
|
|
168
|
+
* accounts list.
|
|
169
|
+
*
|
|
170
|
+
* @returns A promise resolving to the updated keyrings array.
|
|
168
171
|
*/
|
|
169
|
-
__privateAdd(this,
|
|
172
|
+
__privateAdd(this, _getUpdatedKeyrings);
|
|
170
173
|
/**
|
|
171
174
|
* Unlock Keyrings, decrypting the vault and deserializing all
|
|
172
175
|
* keyrings contained in it, using a password or an encryption key with salt.
|
|
@@ -177,6 +180,19 @@ var KeyringController = class extends BaseController {
|
|
|
177
180
|
* @returns A promise resolving to the deserialized keyrings array.
|
|
178
181
|
*/
|
|
179
182
|
__privateAdd(this, _unlockKeyrings);
|
|
183
|
+
/**
|
|
184
|
+
* Update the vault with the current keyrings.
|
|
185
|
+
*
|
|
186
|
+
* @returns A promise resolving to `true` if the operation is successful.
|
|
187
|
+
*/
|
|
188
|
+
__privateAdd(this, _updateVault);
|
|
189
|
+
/**
|
|
190
|
+
* Retrieves all the accounts from keyrings instances
|
|
191
|
+
* that are currently in memory.
|
|
192
|
+
*
|
|
193
|
+
* @returns A promise resolving to an array of accounts.
|
|
194
|
+
*/
|
|
195
|
+
__privateAdd(this, _getAccountsFromKeyrings);
|
|
180
196
|
/**
|
|
181
197
|
* Create a new keyring, ensuring that the first account is
|
|
182
198
|
* also created.
|
|
@@ -191,14 +207,20 @@ var KeyringController = class extends BaseController {
|
|
|
191
207
|
* using the given `opts`. The keyring is built using the keyring builder
|
|
192
208
|
* registered for the given `type`.
|
|
193
209
|
*
|
|
210
|
+
*
|
|
194
211
|
* @param type - The type of keyring to add.
|
|
195
212
|
* @param data - The data to restore a previously serialized keyring.
|
|
213
|
+
* @param persist - Whether to persist the keyring to the vault.
|
|
196
214
|
* @returns The new keyring.
|
|
215
|
+
* @throws If the keyring includes duplicated accounts.
|
|
197
216
|
*/
|
|
198
217
|
__privateAdd(this, _newKeyring);
|
|
199
218
|
/**
|
|
200
219
|
* Remove all managed keyrings, destroying all their
|
|
201
220
|
* instances in memory.
|
|
221
|
+
*
|
|
222
|
+
* @param options - Operations options.
|
|
223
|
+
* @param options.skipStateUpdate - Whether to skip updating the controller state.
|
|
202
224
|
*/
|
|
203
225
|
__privateAdd(this, _clearKeyrings);
|
|
204
226
|
/**
|
|
@@ -244,8 +266,39 @@ var KeyringController = class extends BaseController {
|
|
|
244
266
|
* @fires KeyringController:unlock
|
|
245
267
|
*/
|
|
246
268
|
__privateAdd(this, _setUnlocked);
|
|
247
|
-
|
|
248
|
-
|
|
269
|
+
/**
|
|
270
|
+
* Assert that the controller mutex is locked.
|
|
271
|
+
*
|
|
272
|
+
* @throws If the controller mutex is not locked.
|
|
273
|
+
*/
|
|
274
|
+
__privateAdd(this, _assertControllerMutexIsLocked);
|
|
275
|
+
/**
|
|
276
|
+
* Lock the controller mutex before executing the given function,
|
|
277
|
+
* and release it after the function is resolved or after an
|
|
278
|
+
* error is thrown.
|
|
279
|
+
*
|
|
280
|
+
* This wrapper ensures that each mutable operation that interacts with the
|
|
281
|
+
* controller and that changes its state is executed in a mutually exclusive way,
|
|
282
|
+
* preventing unsafe concurrent access that could lead to unpredictable behavior.
|
|
283
|
+
*
|
|
284
|
+
* @param fn - The function to execute while the controller mutex is locked.
|
|
285
|
+
* @returns The result of the function.
|
|
286
|
+
*/
|
|
287
|
+
__privateAdd(this, _withControllerLock);
|
|
288
|
+
/**
|
|
289
|
+
* Lock the vault mutex before executing the given function,
|
|
290
|
+
* and release it after the function is resolved or after an
|
|
291
|
+
* error is thrown.
|
|
292
|
+
*
|
|
293
|
+
* This ensures that each operation that interacts with the vault
|
|
294
|
+
* is executed in a mutually exclusive way.
|
|
295
|
+
*
|
|
296
|
+
* @param fn - The function to execute while the vault mutex is locked.
|
|
297
|
+
* @returns The result of the function.
|
|
298
|
+
*/
|
|
299
|
+
__privateAdd(this, _withVaultLock);
|
|
300
|
+
__privateAdd(this, _controllerOperationMutex, new Mutex());
|
|
301
|
+
__privateAdd(this, _vaultOperationMutex, new Mutex());
|
|
249
302
|
__privateAdd(this, _keyringBuilders, void 0);
|
|
250
303
|
__privateAdd(this, _keyrings, void 0);
|
|
251
304
|
__privateAdd(this, _unsupportedKeyrings, void 0);
|
|
@@ -268,73 +321,74 @@ var KeyringController = class extends BaseController {
|
|
|
268
321
|
*
|
|
269
322
|
* @param accountCount - Number of accounts before adding a new one, used to
|
|
270
323
|
* make the method idempotent.
|
|
271
|
-
* @returns Promise resolving to
|
|
272
|
-
* address.
|
|
324
|
+
* @returns Promise resolving to the added account address.
|
|
273
325
|
*/
|
|
274
326
|
async addNewAccount(accountCount) {
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
const oldAccounts = await this.getAccounts();
|
|
280
|
-
if (accountCount && oldAccounts.length !== accountCount) {
|
|
281
|
-
if (accountCount > oldAccounts.length) {
|
|
282
|
-
throw new Error("Account out of sequence");
|
|
327
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
328
|
+
const primaryKeyring = this.getKeyringsByType("HD Key Tree")[0];
|
|
329
|
+
if (!primaryKeyring) {
|
|
330
|
+
throw new Error("No HD keyring found");
|
|
283
331
|
}
|
|
284
|
-
const
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
332
|
+
const oldAccounts = await primaryKeyring.getAccounts();
|
|
333
|
+
if (accountCount && oldAccounts.length !== accountCount) {
|
|
334
|
+
if (accountCount > oldAccounts.length) {
|
|
335
|
+
throw new Error("Account out of sequence");
|
|
336
|
+
}
|
|
337
|
+
const existingAccount = oldAccounts[accountCount];
|
|
338
|
+
if (!existingAccount) {
|
|
339
|
+
throw new Error(`Can't find account at index ${accountCount}`);
|
|
340
|
+
}
|
|
341
|
+
return existingAccount;
|
|
342
|
+
}
|
|
343
|
+
const [addedAccountAddress] = await primaryKeyring.addAccounts(1);
|
|
344
|
+
await this.verifySeedPhrase();
|
|
345
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
346
|
+
return addedAccountAddress;
|
|
347
|
+
});
|
|
298
348
|
}
|
|
299
349
|
/**
|
|
300
350
|
* Adds a new account to the specified keyring.
|
|
301
351
|
*
|
|
302
352
|
* @param keyring - Keyring to add the account to.
|
|
303
353
|
* @param accountCount - Number of accounts before adding a new one, used to make the method idempotent.
|
|
304
|
-
* @returns Promise resolving to
|
|
354
|
+
* @returns Promise resolving to the added account address
|
|
305
355
|
*/
|
|
306
356
|
async addNewAccountForKeyring(keyring, accountCount) {
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
if (accountCount
|
|
310
|
-
|
|
357
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
358
|
+
const oldAccounts = await __privateMethod(this, _getAccountsFromKeyrings, getAccountsFromKeyrings_fn).call(this);
|
|
359
|
+
if (accountCount && oldAccounts.length !== accountCount) {
|
|
360
|
+
if (accountCount > oldAccounts.length) {
|
|
361
|
+
throw new Error("Account out of sequence");
|
|
362
|
+
}
|
|
363
|
+
const existingAccount = oldAccounts[accountCount];
|
|
364
|
+
assertIsStrictHexString(existingAccount);
|
|
365
|
+
return existingAccount;
|
|
311
366
|
}
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
);
|
|
321
|
-
assertIsStrictHexString(addedAccountAddress);
|
|
322
|
-
return addedAccountAddress;
|
|
367
|
+
await keyring.addAccounts(1);
|
|
368
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
369
|
+
const addedAccountAddress = (await __privateMethod(this, _getAccountsFromKeyrings, getAccountsFromKeyrings_fn).call(this)).find(
|
|
370
|
+
(selectedAddress) => !oldAccounts.includes(selectedAddress)
|
|
371
|
+
);
|
|
372
|
+
assertIsStrictHexString(addedAccountAddress);
|
|
373
|
+
return addedAccountAddress;
|
|
374
|
+
});
|
|
323
375
|
}
|
|
324
376
|
/**
|
|
325
377
|
* Adds a new account to the default (first) HD seed phrase keyring without updating identities in preferences.
|
|
326
378
|
*
|
|
327
|
-
* @returns Promise resolving to
|
|
379
|
+
* @returns Promise resolving to the added account address.
|
|
328
380
|
*/
|
|
329
381
|
async addNewAccountWithoutUpdate() {
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
382
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
383
|
+
const primaryKeyring = this.getKeyringsByType("HD Key Tree")[0];
|
|
384
|
+
if (!primaryKeyring) {
|
|
385
|
+
throw new Error("No HD keyring found");
|
|
386
|
+
}
|
|
387
|
+
const [addedAccountAddress] = await primaryKeyring.addAccounts(1);
|
|
388
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
389
|
+
await this.verifySeedPhrase();
|
|
390
|
+
return addedAccountAddress;
|
|
391
|
+
});
|
|
338
392
|
}
|
|
339
393
|
/**
|
|
340
394
|
* Effectively the same as creating a new keychain then populating it
|
|
@@ -343,14 +397,13 @@ var KeyringController = class extends BaseController {
|
|
|
343
397
|
* @param password - Password to unlock keychain.
|
|
344
398
|
* @param seed - A BIP39-compliant seed phrase as Uint8Array,
|
|
345
399
|
* either as a string or an array of UTF-8 bytes that represent the string.
|
|
346
|
-
* @returns Promise resolving
|
|
400
|
+
* @returns Promise resolving when the operation ends successfully.
|
|
347
401
|
*/
|
|
348
402
|
async createNewVaultAndRestore(password, seed) {
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
try {
|
|
403
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
404
|
+
if (!password || !password.length) {
|
|
405
|
+
throw new Error("Invalid password");
|
|
406
|
+
}
|
|
354
407
|
await __privateMethod(this, _createNewVaultWithKeyring, createNewVaultWithKeyring_fn).call(this, password, {
|
|
355
408
|
type: "HD Key Tree" /* hd */,
|
|
356
409
|
opts: {
|
|
@@ -358,30 +411,23 @@ var KeyringController = class extends BaseController {
|
|
|
358
411
|
numberOfAccounts: 1
|
|
359
412
|
}
|
|
360
413
|
});
|
|
361
|
-
|
|
362
|
-
} finally {
|
|
363
|
-
releaseLock();
|
|
364
|
-
}
|
|
414
|
+
});
|
|
365
415
|
}
|
|
366
416
|
/**
|
|
367
417
|
* Create a new primary keychain and wipe any previous keychains.
|
|
368
418
|
*
|
|
369
419
|
* @param password - Password to unlock the new vault.
|
|
370
|
-
* @returns
|
|
420
|
+
* @returns Promise resolving when the operation ends successfully.
|
|
371
421
|
*/
|
|
372
422
|
async createNewVaultAndKeychain(password) {
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
const accounts = await this.getAccounts();
|
|
423
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
424
|
+
const accounts = await __privateMethod(this, _getAccountsFromKeyrings, getAccountsFromKeyrings_fn).call(this);
|
|
376
425
|
if (!accounts.length) {
|
|
377
426
|
await __privateMethod(this, _createNewVaultWithKeyring, createNewVaultWithKeyring_fn).call(this, password, {
|
|
378
427
|
type: "HD Key Tree" /* hd */
|
|
379
428
|
});
|
|
380
429
|
}
|
|
381
|
-
|
|
382
|
-
} finally {
|
|
383
|
-
releaseLock();
|
|
384
|
-
}
|
|
430
|
+
});
|
|
385
431
|
}
|
|
386
432
|
/**
|
|
387
433
|
* Adds a new keyring of the given `type`.
|
|
@@ -395,21 +441,7 @@ var KeyringController = class extends BaseController {
|
|
|
395
441
|
if (type === "QR Hardware Wallet Device" /* qr */) {
|
|
396
442
|
return this.getOrAddQRKeyring();
|
|
397
443
|
}
|
|
398
|
-
|
|
399
|
-
if (type === "HD Key Tree" /* hd */ && (!isObject(opts) || !opts.mnemonic)) {
|
|
400
|
-
if (!keyring.generateRandomMnemonic) {
|
|
401
|
-
throw new Error(
|
|
402
|
-
"KeyringController - The current keyring does not support the method generateRandomMnemonic." /* UnsupportedGenerateRandomMnemonic */
|
|
403
|
-
);
|
|
404
|
-
}
|
|
405
|
-
keyring.generateRandomMnemonic();
|
|
406
|
-
await keyring.addAccounts(1);
|
|
407
|
-
}
|
|
408
|
-
const accounts = await keyring.getAccounts();
|
|
409
|
-
await __privateMethod(this, _checkForDuplicate, checkForDuplicate_fn).call(this, type, accounts);
|
|
410
|
-
__privateGet(this, _keyrings).push(keyring);
|
|
411
|
-
await this.persistAllKeyrings();
|
|
412
|
-
return keyring;
|
|
444
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => __privateMethod(this, _newKeyring, newKeyring_fn).call(this, type, opts, true));
|
|
413
445
|
}
|
|
414
446
|
/**
|
|
415
447
|
* Method to verify a given password validity. Throws an
|
|
@@ -460,19 +492,15 @@ var KeyringController = class extends BaseController {
|
|
|
460
492
|
return await keyring.exportAccount(normalize(address));
|
|
461
493
|
}
|
|
462
494
|
/**
|
|
463
|
-
* Returns the public addresses of all accounts
|
|
495
|
+
* Returns the public addresses of all accounts from every keyring.
|
|
464
496
|
*
|
|
465
497
|
* @returns A promise resolving to an array of addresses.
|
|
466
498
|
*/
|
|
467
499
|
async getAccounts() {
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
500
|
+
return this.state.keyrings.reduce(
|
|
501
|
+
(accounts, keyring) => accounts.concat(keyring.accounts),
|
|
502
|
+
[]
|
|
471
503
|
);
|
|
472
|
-
const addresses = keyringArrays.reduce((res, arr) => {
|
|
473
|
-
return res.concat(arr);
|
|
474
|
-
}, []);
|
|
475
|
-
return addresses.map(normalize);
|
|
476
504
|
}
|
|
477
505
|
/**
|
|
478
506
|
* Get encryption public key.
|
|
@@ -565,60 +593,7 @@ var KeyringController = class extends BaseController {
|
|
|
565
593
|
* operation completes.
|
|
566
594
|
*/
|
|
567
595
|
async persistAllKeyrings() {
|
|
568
|
-
|
|
569
|
-
if (!__privateGet(this, _password) && !encryptionKey) {
|
|
570
|
-
throw new Error("KeyringController - Cannot persist vault without password and encryption key" /* MissingCredentials */);
|
|
571
|
-
}
|
|
572
|
-
const serializedKeyrings = await Promise.all(
|
|
573
|
-
__privateGet(this, _keyrings).map(async (keyring) => {
|
|
574
|
-
const [type, data] = await Promise.all([
|
|
575
|
-
keyring.type,
|
|
576
|
-
keyring.serialize()
|
|
577
|
-
]);
|
|
578
|
-
return { type, data };
|
|
579
|
-
})
|
|
580
|
-
);
|
|
581
|
-
serializedKeyrings.push(...__privateGet(this, _unsupportedKeyrings));
|
|
582
|
-
let vault;
|
|
583
|
-
let newEncryptionKey;
|
|
584
|
-
if (__privateGet(this, _cacheEncryptionKey)) {
|
|
585
|
-
assertIsExportableKeyEncryptor(__privateGet(this, _encryptor));
|
|
586
|
-
if (encryptionKey) {
|
|
587
|
-
const key = await __privateGet(this, _encryptor).importKey(encryptionKey);
|
|
588
|
-
const vaultJSON = await __privateGet(this, _encryptor).encryptWithKey(
|
|
589
|
-
key,
|
|
590
|
-
serializedKeyrings
|
|
591
|
-
);
|
|
592
|
-
vaultJSON.salt = encryptionSalt;
|
|
593
|
-
vault = JSON.stringify(vaultJSON);
|
|
594
|
-
} else if (__privateGet(this, _password)) {
|
|
595
|
-
const { vault: newVault, exportedKeyString } = await __privateGet(this, _encryptor).encryptWithDetail(
|
|
596
|
-
__privateGet(this, _password),
|
|
597
|
-
serializedKeyrings
|
|
598
|
-
);
|
|
599
|
-
vault = newVault;
|
|
600
|
-
newEncryptionKey = exportedKeyString;
|
|
601
|
-
}
|
|
602
|
-
} else {
|
|
603
|
-
if (typeof __privateGet(this, _password) !== "string") {
|
|
604
|
-
throw new TypeError("KeyringController - Password must be of type string." /* WrongPasswordType */);
|
|
605
|
-
}
|
|
606
|
-
vault = await __privateGet(this, _encryptor).encrypt(__privateGet(this, _password), serializedKeyrings);
|
|
607
|
-
}
|
|
608
|
-
if (!vault) {
|
|
609
|
-
throw new Error("KeyringController - Cannot persist vault without vault information" /* MissingVaultData */);
|
|
610
|
-
}
|
|
611
|
-
this.update((state) => {
|
|
612
|
-
state.vault = vault;
|
|
613
|
-
});
|
|
614
|
-
await __privateMethod(this, _updateKeyringsInState, updateKeyringsInState_fn).call(this);
|
|
615
|
-
if (newEncryptionKey) {
|
|
616
|
-
this.update((state) => {
|
|
617
|
-
state.encryptionKey = newEncryptionKey;
|
|
618
|
-
state.encryptionSalt = JSON.parse(vault).salt;
|
|
619
|
-
});
|
|
620
|
-
}
|
|
621
|
-
return true;
|
|
596
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => __privateMethod(this, _updateVault, updateVault_fn).call(this));
|
|
622
597
|
}
|
|
623
598
|
/**
|
|
624
599
|
* Imports an account with the specified import strategy.
|
|
@@ -626,90 +601,88 @@ var KeyringController = class extends BaseController {
|
|
|
626
601
|
* @param strategy - Import strategy name.
|
|
627
602
|
* @param args - Array of arguments to pass to the underlying stategy.
|
|
628
603
|
* @throws Will throw when passed an unrecognized strategy.
|
|
629
|
-
* @returns Promise resolving to
|
|
630
|
-
* address.
|
|
604
|
+
* @returns Promise resolving to the imported account address.
|
|
631
605
|
*/
|
|
632
606
|
async importAccountWithStrategy(strategy, args) {
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
privateKey
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
keyringState: __privateMethod(this, _getMemState, getMemState_fn).call(this),
|
|
672
|
-
importedAccountAddress: accounts[0]
|
|
673
|
-
};
|
|
607
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
608
|
+
let privateKey;
|
|
609
|
+
switch (strategy) {
|
|
610
|
+
case "privateKey":
|
|
611
|
+
const [importedKey] = args;
|
|
612
|
+
if (!importedKey) {
|
|
613
|
+
throw new Error("Cannot import an empty key.");
|
|
614
|
+
}
|
|
615
|
+
const prefixed = add0x(importedKey);
|
|
616
|
+
let bufferedPrivateKey;
|
|
617
|
+
try {
|
|
618
|
+
bufferedPrivateKey = toBuffer(prefixed);
|
|
619
|
+
} catch {
|
|
620
|
+
throw new Error("Cannot import invalid private key.");
|
|
621
|
+
}
|
|
622
|
+
if (!isValidPrivate(bufferedPrivateKey) || // ensures that the key is 64 bytes long
|
|
623
|
+
getBinarySize(prefixed) !== 64 + "0x".length) {
|
|
624
|
+
throw new Error("Cannot import invalid private key.");
|
|
625
|
+
}
|
|
626
|
+
privateKey = remove0x(prefixed);
|
|
627
|
+
break;
|
|
628
|
+
case "json":
|
|
629
|
+
let wallet;
|
|
630
|
+
const [input, password] = args;
|
|
631
|
+
try {
|
|
632
|
+
wallet = importers.fromEtherWallet(input, password);
|
|
633
|
+
} catch (e) {
|
|
634
|
+
wallet = wallet || await Wallet.fromV3(input, password, true);
|
|
635
|
+
}
|
|
636
|
+
privateKey = bytesToHex(wallet.getPrivateKey());
|
|
637
|
+
break;
|
|
638
|
+
default:
|
|
639
|
+
throw new Error(`Unexpected import strategy: '${strategy}'`);
|
|
640
|
+
}
|
|
641
|
+
const newKeyring = await __privateMethod(this, _newKeyring, newKeyring_fn).call(this, "Simple Key Pair" /* simple */, [privateKey], true);
|
|
642
|
+
const accounts = await newKeyring.getAccounts();
|
|
643
|
+
return accounts[0];
|
|
644
|
+
});
|
|
674
645
|
}
|
|
675
646
|
/**
|
|
676
647
|
* Removes an account from keyring state.
|
|
677
648
|
*
|
|
678
649
|
* @param address - Address of the account to remove.
|
|
679
650
|
* @fires KeyringController:accountRemoved
|
|
680
|
-
* @returns Promise resolving
|
|
651
|
+
* @returns Promise resolving when the account is removed.
|
|
681
652
|
*/
|
|
682
653
|
async removeAccount(address) {
|
|
683
|
-
|
|
684
|
-
|
|
685
|
-
|
|
686
|
-
|
|
687
|
-
|
|
688
|
-
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
692
|
-
|
|
693
|
-
|
|
694
|
-
|
|
654
|
+
await __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
655
|
+
const keyring = await this.getKeyringForAccount(
|
|
656
|
+
address
|
|
657
|
+
);
|
|
658
|
+
if (!keyring.removeAccount) {
|
|
659
|
+
throw new Error("`KeyringController - The keyring for the current address does not support the method removeAccount" /* UnsupportedRemoveAccount */);
|
|
660
|
+
}
|
|
661
|
+
await keyring.removeAccount(address);
|
|
662
|
+
const accounts = await keyring.getAccounts();
|
|
663
|
+
if (accounts.length === 0) {
|
|
664
|
+
await __privateMethod(this, _removeEmptyKeyrings, removeEmptyKeyrings_fn).call(this);
|
|
665
|
+
}
|
|
666
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
667
|
+
});
|
|
695
668
|
this.messagingSystem.publish(`${name}:accountRemoved`, address);
|
|
696
|
-
return __privateMethod(this, _getMemState, getMemState_fn).call(this);
|
|
697
669
|
}
|
|
698
670
|
/**
|
|
699
671
|
* Deallocates all secrets and locks the wallet.
|
|
700
672
|
*
|
|
701
|
-
* @returns Promise resolving
|
|
673
|
+
* @returns Promise resolving when the operation completes.
|
|
702
674
|
*/
|
|
703
675
|
async setLocked() {
|
|
704
|
-
__privateMethod(this,
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
state
|
|
708
|
-
|
|
676
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
677
|
+
__privateMethod(this, _unsubscribeFromQRKeyringsEvents, unsubscribeFromQRKeyringsEvents_fn).call(this);
|
|
678
|
+
__privateSet(this, _password, void 0);
|
|
679
|
+
this.update((state) => {
|
|
680
|
+
state.isUnlocked = false;
|
|
681
|
+
state.keyrings = [];
|
|
682
|
+
});
|
|
683
|
+
await __privateMethod(this, _clearKeyrings, clearKeyrings_fn).call(this);
|
|
684
|
+
this.messagingSystem.publish(`${name}:lock`);
|
|
709
685
|
});
|
|
710
|
-
await __privateMethod(this, _clearKeyrings, clearKeyrings_fn).call(this);
|
|
711
|
-
this.messagingSystem.publish(`${name}:lock`);
|
|
712
|
-
return __privateMethod(this, _getMemState, getMemState_fn).call(this);
|
|
713
686
|
}
|
|
714
687
|
/**
|
|
715
688
|
* Signs message by calling down into a specific keyring.
|
|
@@ -803,9 +776,10 @@ var KeyringController = class extends BaseController {
|
|
|
803
776
|
*
|
|
804
777
|
* @param from - Address of the sender.
|
|
805
778
|
* @param transactions - Base transactions to include in the UserOperation.
|
|
779
|
+
* @param executionContext - The execution context to use for the UserOperation.
|
|
806
780
|
* @returns A pseudo-UserOperation that can be used to construct a real.
|
|
807
781
|
*/
|
|
808
|
-
async prepareUserOperation(from, transactions) {
|
|
782
|
+
async prepareUserOperation(from, transactions, executionContext) {
|
|
809
783
|
const address = normalize(from);
|
|
810
784
|
const keyring = await this.getKeyringForAccount(
|
|
811
785
|
address
|
|
@@ -813,7 +787,11 @@ var KeyringController = class extends BaseController {
|
|
|
813
787
|
if (!keyring.prepareUserOperation) {
|
|
814
788
|
throw new Error("KeyringController - The keyring for the current address does not support the method prepareUserOperation." /* UnsupportedPrepareUserOperation */);
|
|
815
789
|
}
|
|
816
|
-
return await keyring.prepareUserOperation(
|
|
790
|
+
return await keyring.prepareUserOperation(
|
|
791
|
+
address,
|
|
792
|
+
transactions,
|
|
793
|
+
executionContext
|
|
794
|
+
);
|
|
817
795
|
}
|
|
818
796
|
/**
|
|
819
797
|
* Patches properties of a UserOperation. Currently, only the
|
|
@@ -821,9 +799,10 @@ var KeyringController = class extends BaseController {
|
|
|
821
799
|
*
|
|
822
800
|
* @param from - Address of the sender.
|
|
823
801
|
* @param userOp - UserOperation to patch.
|
|
802
|
+
* @param executionContext - The execution context to use for the UserOperation.
|
|
824
803
|
* @returns A patch to apply to the UserOperation.
|
|
825
804
|
*/
|
|
826
|
-
async patchUserOperation(from, userOp) {
|
|
805
|
+
async patchUserOperation(from, userOp, executionContext) {
|
|
827
806
|
const address = normalize(from);
|
|
828
807
|
const keyring = await this.getKeyringForAccount(
|
|
829
808
|
address
|
|
@@ -831,16 +810,17 @@ var KeyringController = class extends BaseController {
|
|
|
831
810
|
if (!keyring.patchUserOperation) {
|
|
832
811
|
throw new Error("KeyringController - The keyring for the current address does not support the method patchUserOperation." /* UnsupportedPatchUserOperation */);
|
|
833
812
|
}
|
|
834
|
-
return await keyring.patchUserOperation(address, userOp);
|
|
813
|
+
return await keyring.patchUserOperation(address, userOp, executionContext);
|
|
835
814
|
}
|
|
836
815
|
/**
|
|
837
816
|
* Signs an UserOperation.
|
|
838
817
|
*
|
|
839
818
|
* @param from - Address of the sender.
|
|
840
819
|
* @param userOp - UserOperation to sign.
|
|
820
|
+
* @param executionContext - The execution context to use for the UserOperation.
|
|
841
821
|
* @returns The signature of the UserOperation.
|
|
842
822
|
*/
|
|
843
|
-
async signUserOperation(from, userOp) {
|
|
823
|
+
async signUserOperation(from, userOp, executionContext) {
|
|
844
824
|
const address = normalize(from);
|
|
845
825
|
const keyring = await this.getKeyringForAccount(
|
|
846
826
|
address
|
|
@@ -848,7 +828,7 @@ var KeyringController = class extends BaseController {
|
|
|
848
828
|
if (!keyring.signUserOperation) {
|
|
849
829
|
throw new Error("KeyringController - The keyring for the current address does not support the method signUserOperation." /* UnsupportedSignUserOperation */);
|
|
850
830
|
}
|
|
851
|
-
return await keyring.signUserOperation(address, userOp);
|
|
831
|
+
return await keyring.signUserOperation(address, userOp, executionContext);
|
|
852
832
|
}
|
|
853
833
|
/**
|
|
854
834
|
* Attempts to decrypt the current vault and load its keyrings,
|
|
@@ -856,32 +836,34 @@ var KeyringController = class extends BaseController {
|
|
|
856
836
|
*
|
|
857
837
|
* @param encryptionKey - Key to unlock the keychain.
|
|
858
838
|
* @param encryptionSalt - Salt to unlock the keychain.
|
|
859
|
-
* @returns Promise resolving
|
|
839
|
+
* @returns Promise resolving when the operation completes.
|
|
860
840
|
*/
|
|
861
841
|
async submitEncryptionKey(encryptionKey, encryptionSalt) {
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
842
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
843
|
+
__privateSet(this, _keyrings, await __privateMethod(this, _unlockKeyrings, unlockKeyrings_fn).call(this, void 0, encryptionKey, encryptionSalt));
|
|
844
|
+
__privateMethod(this, _setUnlocked, setUnlocked_fn).call(this);
|
|
845
|
+
const qrKeyring = this.getQRKeyring();
|
|
846
|
+
if (qrKeyring) {
|
|
847
|
+
__privateMethod(this, _subscribeToQRKeyringEvents, subscribeToQRKeyringEvents_fn).call(this, qrKeyring);
|
|
848
|
+
}
|
|
849
|
+
});
|
|
869
850
|
}
|
|
870
851
|
/**
|
|
871
852
|
* Attempts to decrypt the current vault and load its keyrings,
|
|
872
853
|
* using the given password.
|
|
873
854
|
*
|
|
874
855
|
* @param password - Password to unlock the keychain.
|
|
875
|
-
* @returns Promise resolving
|
|
856
|
+
* @returns Promise resolving when the operation completes.
|
|
876
857
|
*/
|
|
877
858
|
async submitPassword(password) {
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
859
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
860
|
+
__privateSet(this, _keyrings, await __privateMethod(this, _unlockKeyrings, unlockKeyrings_fn).call(this, password));
|
|
861
|
+
__privateMethod(this, _setUnlocked, setUnlocked_fn).call(this);
|
|
862
|
+
const qrKeyring = this.getQRKeyring();
|
|
863
|
+
if (qrKeyring) {
|
|
864
|
+
__privateMethod(this, _subscribeToQRKeyringEvents, subscribeToQRKeyringEvents_fn).call(this, qrKeyring);
|
|
865
|
+
}
|
|
866
|
+
});
|
|
885
867
|
}
|
|
886
868
|
/**
|
|
887
869
|
* Verifies the that the seed phrase restores the current keychain's accounts.
|
|
@@ -931,13 +913,16 @@ var KeyringController = class extends BaseController {
|
|
|
931
913
|
* @returns The added keyring
|
|
932
914
|
*/
|
|
933
915
|
async getOrAddQRKeyring() {
|
|
934
|
-
return this.getQRKeyring() || await __privateMethod(this, _addQRKeyring, addQRKeyring_fn).call(this);
|
|
916
|
+
return this.getQRKeyring() || await __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => __privateMethod(this, _addQRKeyring, addQRKeyring_fn).call(this));
|
|
935
917
|
}
|
|
936
918
|
// TODO: Replace `any` with type
|
|
937
919
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
938
920
|
async restoreQRKeyring(serialized) {
|
|
939
|
-
(
|
|
940
|
-
|
|
921
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
922
|
+
const keyring = this.getQRKeyring() || await __privateMethod(this, _addQRKeyring, addQRKeyring_fn).call(this);
|
|
923
|
+
keyring.deserialize(serialized);
|
|
924
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
925
|
+
});
|
|
941
926
|
}
|
|
942
927
|
async resetQRKeyringState() {
|
|
943
928
|
(await this.getOrAddQRKeyring()).resetStore();
|
|
@@ -964,34 +949,38 @@ var KeyringController = class extends BaseController {
|
|
|
964
949
|
(await this.getOrAddQRKeyring()).cancelSync();
|
|
965
950
|
}
|
|
966
951
|
async connectQRHardware(page) {
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
|
|
978
|
-
|
|
952
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
953
|
+
try {
|
|
954
|
+
const keyring = this.getQRKeyring() || await __privateMethod(this, _addQRKeyring, addQRKeyring_fn).call(this);
|
|
955
|
+
let accounts;
|
|
956
|
+
switch (page) {
|
|
957
|
+
case -1:
|
|
958
|
+
accounts = await keyring.getPreviousPage();
|
|
959
|
+
break;
|
|
960
|
+
case 1:
|
|
961
|
+
accounts = await keyring.getNextPage();
|
|
962
|
+
break;
|
|
963
|
+
default:
|
|
964
|
+
accounts = await keyring.getFirstPage();
|
|
965
|
+
}
|
|
966
|
+
return accounts.map((account) => {
|
|
967
|
+
return {
|
|
968
|
+
...account,
|
|
969
|
+
balance: "0x0"
|
|
970
|
+
};
|
|
971
|
+
});
|
|
972
|
+
} catch (e) {
|
|
973
|
+
throw new Error(`Unspecified error when connect QR Hardware, ${e}`);
|
|
979
974
|
}
|
|
980
|
-
|
|
981
|
-
return {
|
|
982
|
-
...account,
|
|
983
|
-
balance: "0x0"
|
|
984
|
-
};
|
|
985
|
-
});
|
|
986
|
-
} catch (e) {
|
|
987
|
-
throw new Error(`Unspecified error when connect QR Hardware, ${e}`);
|
|
988
|
-
}
|
|
975
|
+
});
|
|
989
976
|
}
|
|
990
977
|
async unlockQRHardwareWalletAccount(index) {
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
|
|
994
|
-
|
|
978
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
979
|
+
const keyring = this.getQRKeyring() || await __privateMethod(this, _addQRKeyring, addQRKeyring_fn).call(this);
|
|
980
|
+
keyring.setAccountToUnlock(index);
|
|
981
|
+
await keyring.addAccounts(1);
|
|
982
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
983
|
+
});
|
|
995
984
|
}
|
|
996
985
|
async getAccountKeyringType(account) {
|
|
997
986
|
const keyring = await this.getKeyringForAccount(
|
|
@@ -1000,17 +989,24 @@ var KeyringController = class extends BaseController {
|
|
|
1000
989
|
return keyring.type;
|
|
1001
990
|
}
|
|
1002
991
|
async forgetQRDevice() {
|
|
1003
|
-
|
|
1004
|
-
|
|
1005
|
-
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
(
|
|
1009
|
-
|
|
1010
|
-
|
|
1011
|
-
|
|
992
|
+
return __privateMethod(this, _withControllerLock, withControllerLock_fn).call(this, async () => {
|
|
993
|
+
const keyring = this.getQRKeyring();
|
|
994
|
+
if (!keyring) {
|
|
995
|
+
return { removedAccounts: [], remainingAccounts: [] };
|
|
996
|
+
}
|
|
997
|
+
const allAccounts = await __privateMethod(this, _getAccountsFromKeyrings, getAccountsFromKeyrings_fn).call(this);
|
|
998
|
+
keyring.forgetDevice();
|
|
999
|
+
const remainingAccounts = await __privateMethod(this, _getAccountsFromKeyrings, getAccountsFromKeyrings_fn).call(this);
|
|
1000
|
+
const removedAccounts = allAccounts.filter(
|
|
1001
|
+
(address) => !remainingAccounts.includes(address)
|
|
1002
|
+
);
|
|
1003
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
1004
|
+
return { removedAccounts, remainingAccounts };
|
|
1005
|
+
});
|
|
1012
1006
|
}
|
|
1013
1007
|
};
|
|
1008
|
+
_controllerOperationMutex = new WeakMap();
|
|
1009
|
+
_vaultOperationMutex = new WeakMap();
|
|
1014
1010
|
_keyringBuilders = new WeakMap();
|
|
1015
1011
|
_keyrings = new WeakMap();
|
|
1016
1012
|
_unsupportedKeyrings = new WeakMap();
|
|
@@ -1077,13 +1073,14 @@ getKeyringBuilderForType_fn = function(type) {
|
|
|
1077
1073
|
};
|
|
1078
1074
|
_addQRKeyring = new WeakSet();
|
|
1079
1075
|
addQRKeyring_fn = async function() {
|
|
1076
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1080
1077
|
const qrKeyring = await __privateMethod(this, _newKeyring, newKeyring_fn).call(this, "QR Hardware Wallet Device" /* qr */, {
|
|
1081
1078
|
accounts: []
|
|
1082
1079
|
});
|
|
1083
1080
|
const accounts = await qrKeyring.getAccounts();
|
|
1084
1081
|
await __privateMethod(this, _checkForDuplicate, checkForDuplicate_fn).call(this, "QR Hardware Wallet Device" /* qr */, accounts);
|
|
1085
1082
|
__privateGet(this, _keyrings).push(qrKeyring);
|
|
1086
|
-
await this.
|
|
1083
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
1087
1084
|
__privateMethod(this, _subscribeToQRKeyringEvents, subscribeToQRKeyringEvents_fn).call(this, qrKeyring);
|
|
1088
1085
|
return qrKeyring;
|
|
1089
1086
|
};
|
|
@@ -1107,6 +1104,7 @@ unsubscribeFromQRKeyringsEvents_fn = function() {
|
|
|
1107
1104
|
};
|
|
1108
1105
|
_createNewVaultWithKeyring = new WeakSet();
|
|
1109
1106
|
createNewVaultWithKeyring_fn = async function(password, keyring) {
|
|
1107
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1110
1108
|
if (typeof password !== "string") {
|
|
1111
1109
|
throw new TypeError("KeyringController - Password must be of type string." /* WrongPasswordType */);
|
|
1112
1110
|
}
|
|
@@ -1114,78 +1112,160 @@ createNewVaultWithKeyring_fn = async function(password, keyring) {
|
|
|
1114
1112
|
await __privateMethod(this, _clearKeyrings, clearKeyrings_fn).call(this);
|
|
1115
1113
|
await __privateMethod(this, _createKeyringWithFirstAccount, createKeyringWithFirstAccount_fn).call(this, keyring.type, keyring.opts);
|
|
1116
1114
|
__privateMethod(this, _setUnlocked, setUnlocked_fn).call(this);
|
|
1117
|
-
return __privateMethod(this, _getMemState, getMemState_fn).call(this);
|
|
1118
1115
|
};
|
|
1119
|
-
|
|
1120
|
-
|
|
1121
|
-
|
|
1122
|
-
this.update((state) => {
|
|
1123
|
-
state.keyrings = keyrings;
|
|
1124
|
-
});
|
|
1116
|
+
_getUpdatedKeyrings = new WeakSet();
|
|
1117
|
+
getUpdatedKeyrings_fn = async function() {
|
|
1118
|
+
return Promise.all(__privateGet(this, _keyrings).map(displayForKeyring));
|
|
1125
1119
|
};
|
|
1126
1120
|
_unlockKeyrings = new WeakSet();
|
|
1127
1121
|
unlockKeyrings_fn = async function(password, encryptionKey, encryptionSalt) {
|
|
1128
|
-
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1132
|
-
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
if (
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
|
|
1122
|
+
return __privateMethod(this, _withVaultLock, withVaultLock_fn).call(this, async ({ releaseLock }) => {
|
|
1123
|
+
const encryptedVault = this.state.vault;
|
|
1124
|
+
if (!encryptedVault) {
|
|
1125
|
+
throw new Error("KeyringController - Cannot unlock without a previous vault." /* VaultError */);
|
|
1126
|
+
}
|
|
1127
|
+
await __privateMethod(this, _clearKeyrings, clearKeyrings_fn).call(this, { skipStateUpdate: true });
|
|
1128
|
+
let vault;
|
|
1129
|
+
const updatedState = {};
|
|
1130
|
+
if (__privateGet(this, _cacheEncryptionKey)) {
|
|
1131
|
+
assertIsExportableKeyEncryptor(__privateGet(this, _encryptor));
|
|
1132
|
+
if (password) {
|
|
1133
|
+
const result = await __privateGet(this, _encryptor).decryptWithDetail(
|
|
1134
|
+
password,
|
|
1135
|
+
encryptedVault
|
|
1136
|
+
);
|
|
1137
|
+
vault = result.vault;
|
|
1138
|
+
__privateSet(this, _password, password);
|
|
1139
|
+
updatedState.encryptionKey = result.exportedKeyString;
|
|
1140
|
+
updatedState.encryptionSalt = result.salt;
|
|
1141
|
+
} else {
|
|
1142
|
+
const parsedEncryptedVault = JSON.parse(encryptedVault);
|
|
1143
|
+
if (encryptionSalt !== parsedEncryptedVault.salt) {
|
|
1144
|
+
throw new Error("KeyringController - Encryption key and salt provided are expired" /* ExpiredCredentials */);
|
|
1145
|
+
}
|
|
1146
|
+
if (typeof encryptionKey !== "string") {
|
|
1147
|
+
throw new TypeError("KeyringController - Password must be of type string." /* WrongPasswordType */);
|
|
1148
|
+
}
|
|
1149
|
+
const key = await __privateGet(this, _encryptor).importKey(encryptionKey);
|
|
1150
|
+
vault = await __privateGet(this, _encryptor).decryptWithKey(
|
|
1151
|
+
key,
|
|
1152
|
+
parsedEncryptedVault
|
|
1153
|
+
);
|
|
1154
|
+
updatedState.encryptionKey = encryptionKey;
|
|
1155
|
+
updatedState.encryptionSalt = encryptionSalt;
|
|
1156
|
+
}
|
|
1147
1157
|
} else {
|
|
1148
|
-
|
|
1149
|
-
|
|
1150
|
-
throw new Error("KeyringController - Encryption key and salt provided are expired" /* ExpiredCredentials */);
|
|
1158
|
+
if (typeof password !== "string") {
|
|
1159
|
+
throw new TypeError("KeyringController - Password must be of type string." /* WrongPasswordType */);
|
|
1151
1160
|
}
|
|
1152
|
-
|
|
1161
|
+
vault = await __privateGet(this, _encryptor).decrypt(password, encryptedVault);
|
|
1162
|
+
__privateSet(this, _password, password);
|
|
1163
|
+
}
|
|
1164
|
+
if (!isSerializedKeyringsArray(vault)) {
|
|
1165
|
+
throw new Error("KeyringController - The decrypted vault has an unexpected shape." /* VaultDataError */);
|
|
1166
|
+
}
|
|
1167
|
+
await Promise.all(vault.map(__privateMethod(this, _restoreKeyring, restoreKeyring_fn).bind(this)));
|
|
1168
|
+
const updatedKeyrings = await __privateMethod(this, _getUpdatedKeyrings, getUpdatedKeyrings_fn).call(this);
|
|
1169
|
+
this.update((state) => {
|
|
1170
|
+
state.keyrings = updatedKeyrings;
|
|
1171
|
+
if (updatedState.encryptionKey || updatedState.encryptionSalt) {
|
|
1172
|
+
state.encryptionKey = updatedState.encryptionKey;
|
|
1173
|
+
state.encryptionSalt = updatedState.encryptionSalt;
|
|
1174
|
+
}
|
|
1175
|
+
});
|
|
1176
|
+
if (__privateGet(this, _password) && (!__privateGet(this, _cacheEncryptionKey) || !encryptionKey) && __privateGet(this, _encryptor).isVaultUpdated && !__privateGet(this, _encryptor).isVaultUpdated(encryptedVault)) {
|
|
1177
|
+
releaseLock();
|
|
1178
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
1179
|
+
}
|
|
1180
|
+
return __privateGet(this, _keyrings);
|
|
1181
|
+
});
|
|
1182
|
+
};
|
|
1183
|
+
_updateVault = new WeakSet();
|
|
1184
|
+
updateVault_fn = function() {
|
|
1185
|
+
return __privateMethod(this, _withVaultLock, withVaultLock_fn).call(this, async () => {
|
|
1186
|
+
const { encryptionKey, encryptionSalt } = this.state;
|
|
1187
|
+
if (!__privateGet(this, _password) && !encryptionKey) {
|
|
1188
|
+
throw new Error("KeyringController - Cannot persist vault without password and encryption key" /* MissingCredentials */);
|
|
1189
|
+
}
|
|
1190
|
+
const serializedKeyrings = await Promise.all(
|
|
1191
|
+
__privateGet(this, _keyrings).map(async (keyring) => {
|
|
1192
|
+
const [type, data] = await Promise.all([
|
|
1193
|
+
keyring.type,
|
|
1194
|
+
keyring.serialize()
|
|
1195
|
+
]);
|
|
1196
|
+
return { type, data };
|
|
1197
|
+
})
|
|
1198
|
+
);
|
|
1199
|
+
serializedKeyrings.push(...__privateGet(this, _unsupportedKeyrings));
|
|
1200
|
+
if (!serializedKeyrings.some((keyring) => keyring.type === "HD Key Tree" /* hd */)) {
|
|
1201
|
+
throw new Error("KeyringController - No HD Keyring found" /* NoHdKeyring */);
|
|
1202
|
+
}
|
|
1203
|
+
const updatedState = {};
|
|
1204
|
+
if (__privateGet(this, _cacheEncryptionKey)) {
|
|
1205
|
+
assertIsExportableKeyEncryptor(__privateGet(this, _encryptor));
|
|
1206
|
+
if (encryptionKey) {
|
|
1207
|
+
const key = await __privateGet(this, _encryptor).importKey(encryptionKey);
|
|
1208
|
+
const vaultJSON = await __privateGet(this, _encryptor).encryptWithKey(
|
|
1209
|
+
key,
|
|
1210
|
+
serializedKeyrings
|
|
1211
|
+
);
|
|
1212
|
+
vaultJSON.salt = encryptionSalt;
|
|
1213
|
+
updatedState.vault = JSON.stringify(vaultJSON);
|
|
1214
|
+
} else if (__privateGet(this, _password)) {
|
|
1215
|
+
const { vault: newVault, exportedKeyString } = await __privateGet(this, _encryptor).encryptWithDetail(
|
|
1216
|
+
__privateGet(this, _password),
|
|
1217
|
+
serializedKeyrings
|
|
1218
|
+
);
|
|
1219
|
+
updatedState.vault = newVault;
|
|
1220
|
+
updatedState.encryptionKey = exportedKeyString;
|
|
1221
|
+
}
|
|
1222
|
+
} else {
|
|
1223
|
+
if (typeof __privateGet(this, _password) !== "string") {
|
|
1153
1224
|
throw new TypeError("KeyringController - Password must be of type string." /* WrongPasswordType */);
|
|
1154
1225
|
}
|
|
1155
|
-
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
state.encryptionSalt = encryptionSalt;
|
|
1160
|
-
});
|
|
1226
|
+
updatedState.vault = await __privateGet(this, _encryptor).encrypt(
|
|
1227
|
+
__privateGet(this, _password),
|
|
1228
|
+
serializedKeyrings
|
|
1229
|
+
);
|
|
1161
1230
|
}
|
|
1162
|
-
|
|
1163
|
-
|
|
1164
|
-
throw new TypeError("KeyringController - Password must be of type string." /* WrongPasswordType */);
|
|
1231
|
+
if (!updatedState.vault) {
|
|
1232
|
+
throw new Error("KeyringController - Cannot persist vault without vault information" /* MissingVaultData */);
|
|
1165
1233
|
}
|
|
1166
|
-
|
|
1167
|
-
|
|
1168
|
-
|
|
1169
|
-
|
|
1170
|
-
|
|
1171
|
-
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
|
|
1176
|
-
}
|
|
1177
|
-
|
|
1234
|
+
const updatedKeyrings = await __privateMethod(this, _getUpdatedKeyrings, getUpdatedKeyrings_fn).call(this);
|
|
1235
|
+
this.update((state) => {
|
|
1236
|
+
state.vault = updatedState.vault;
|
|
1237
|
+
state.keyrings = updatedKeyrings;
|
|
1238
|
+
if (updatedState.encryptionKey) {
|
|
1239
|
+
state.encryptionKey = updatedState.encryptionKey;
|
|
1240
|
+
state.encryptionSalt = JSON.parse(updatedState.vault).salt;
|
|
1241
|
+
}
|
|
1242
|
+
});
|
|
1243
|
+
return true;
|
|
1244
|
+
});
|
|
1245
|
+
};
|
|
1246
|
+
_getAccountsFromKeyrings = new WeakSet();
|
|
1247
|
+
getAccountsFromKeyrings_fn = async function() {
|
|
1248
|
+
const keyrings = __privateGet(this, _keyrings);
|
|
1249
|
+
const keyringArrays = await Promise.all(
|
|
1250
|
+
keyrings.map(async (keyring) => keyring.getAccounts())
|
|
1251
|
+
);
|
|
1252
|
+
const addresses = keyringArrays.reduce((res, arr) => {
|
|
1253
|
+
return res.concat(arr);
|
|
1254
|
+
}, []);
|
|
1255
|
+
return addresses.map(normalize);
|
|
1178
1256
|
};
|
|
1179
1257
|
_createKeyringWithFirstAccount = new WeakSet();
|
|
1180
1258
|
createKeyringWithFirstAccount_fn = async function(type, opts) {
|
|
1181
|
-
|
|
1259
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1260
|
+
const keyring = await __privateMethod(this, _newKeyring, newKeyring_fn).call(this, type, opts, true);
|
|
1182
1261
|
const [firstAccount] = await keyring.getAccounts();
|
|
1183
1262
|
if (!firstAccount) {
|
|
1184
1263
|
throw new Error("KeyringController - First Account not found." /* NoFirstAccount */);
|
|
1185
1264
|
}
|
|
1186
1265
|
};
|
|
1187
1266
|
_newKeyring = new WeakSet();
|
|
1188
|
-
newKeyring_fn = async function(type, data) {
|
|
1267
|
+
newKeyring_fn = async function(type, data, persist = false) {
|
|
1268
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1189
1269
|
const keyringBuilder = __privateMethod(this, _getKeyringBuilderForType, getKeyringBuilderForType_fn).call(this, type);
|
|
1190
1270
|
if (!keyringBuilder) {
|
|
1191
1271
|
throw new Error(
|
|
@@ -1197,20 +1277,38 @@ newKeyring_fn = async function(type, data) {
|
|
|
1197
1277
|
if (keyring.init) {
|
|
1198
1278
|
await keyring.init();
|
|
1199
1279
|
}
|
|
1280
|
+
if (type === "HD Key Tree" /* hd */ && (!isObject(data) || !data.mnemonic)) {
|
|
1281
|
+
if (!keyring.generateRandomMnemonic) {
|
|
1282
|
+
throw new Error(
|
|
1283
|
+
"KeyringController - The current keyring does not support the method generateRandomMnemonic." /* UnsupportedGenerateRandomMnemonic */
|
|
1284
|
+
);
|
|
1285
|
+
}
|
|
1286
|
+
keyring.generateRandomMnemonic();
|
|
1287
|
+
await keyring.addAccounts(1);
|
|
1288
|
+
}
|
|
1289
|
+
await __privateMethod(this, _checkForDuplicate, checkForDuplicate_fn).call(this, type, await keyring.getAccounts());
|
|
1290
|
+
if (persist) {
|
|
1291
|
+
__privateGet(this, _keyrings).push(keyring);
|
|
1292
|
+
await __privateMethod(this, _updateVault, updateVault_fn).call(this);
|
|
1293
|
+
}
|
|
1200
1294
|
return keyring;
|
|
1201
1295
|
};
|
|
1202
1296
|
_clearKeyrings = new WeakSet();
|
|
1203
|
-
clearKeyrings_fn = async function() {
|
|
1297
|
+
clearKeyrings_fn = async function(options = { skipStateUpdate: false }) {
|
|
1298
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1204
1299
|
for (const keyring of __privateGet(this, _keyrings)) {
|
|
1205
1300
|
await __privateMethod(this, _destroyKeyring, destroyKeyring_fn).call(this, keyring);
|
|
1206
1301
|
}
|
|
1207
1302
|
__privateSet(this, _keyrings, []);
|
|
1208
|
-
|
|
1209
|
-
state
|
|
1210
|
-
|
|
1303
|
+
if (!options.skipStateUpdate) {
|
|
1304
|
+
this.update((state) => {
|
|
1305
|
+
state.keyrings = [];
|
|
1306
|
+
});
|
|
1307
|
+
}
|
|
1211
1308
|
};
|
|
1212
1309
|
_restoreKeyring = new WeakSet();
|
|
1213
1310
|
restoreKeyring_fn = async function(serialized) {
|
|
1311
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1214
1312
|
try {
|
|
1215
1313
|
const { type, data } = serialized;
|
|
1216
1314
|
const keyring = await __privateMethod(this, _newKeyring, newKeyring_fn).call(this, type, data);
|
|
@@ -1228,6 +1326,7 @@ destroyKeyring_fn = async function(keyring) {
|
|
|
1228
1326
|
};
|
|
1229
1327
|
_removeEmptyKeyrings = new WeakSet();
|
|
1230
1328
|
removeEmptyKeyrings_fn = async function() {
|
|
1329
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1231
1330
|
const validKeyrings = [];
|
|
1232
1331
|
await Promise.all(
|
|
1233
1332
|
__privateGet(this, _keyrings).map(async (keyring) => {
|
|
@@ -1243,7 +1342,7 @@ removeEmptyKeyrings_fn = async function() {
|
|
|
1243
1342
|
};
|
|
1244
1343
|
_checkForDuplicate = new WeakSet();
|
|
1245
1344
|
checkForDuplicate_fn = async function(type, newAccountArray) {
|
|
1246
|
-
const accounts = await this.
|
|
1345
|
+
const accounts = await __privateMethod(this, _getAccountsFromKeyrings, getAccountsFromKeyrings_fn).call(this);
|
|
1247
1346
|
switch (type) {
|
|
1248
1347
|
case "Simple Key Pair" /* simple */: {
|
|
1249
1348
|
const isIncluded = Boolean(
|
|
@@ -1263,18 +1362,35 @@ checkForDuplicate_fn = async function(type, newAccountArray) {
|
|
|
1263
1362
|
};
|
|
1264
1363
|
_setUnlocked = new WeakSet();
|
|
1265
1364
|
setUnlocked_fn = function() {
|
|
1365
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1266
1366
|
this.update((state) => {
|
|
1267
1367
|
state.isUnlocked = true;
|
|
1268
1368
|
});
|
|
1269
1369
|
this.messagingSystem.publish(`${name}:unlock`);
|
|
1270
1370
|
};
|
|
1271
|
-
|
|
1272
|
-
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1371
|
+
_assertControllerMutexIsLocked = new WeakSet();
|
|
1372
|
+
assertControllerMutexIsLocked_fn = function() {
|
|
1373
|
+
if (!__privateGet(this, _controllerOperationMutex).isLocked()) {
|
|
1374
|
+
throw new Error("KeyringController - attempt to update vault during a non mutually exclusive operation" /* ControllerLockRequired */);
|
|
1375
|
+
}
|
|
1376
|
+
};
|
|
1377
|
+
_withControllerLock = new WeakSet();
|
|
1378
|
+
withControllerLock_fn = async function(fn) {
|
|
1379
|
+
return withLock(__privateGet(this, _controllerOperationMutex), fn);
|
|
1380
|
+
};
|
|
1381
|
+
_withVaultLock = new WeakSet();
|
|
1382
|
+
withVaultLock_fn = async function(fn) {
|
|
1383
|
+
__privateMethod(this, _assertControllerMutexIsLocked, assertControllerMutexIsLocked_fn).call(this);
|
|
1384
|
+
return withLock(__privateGet(this, _vaultOperationMutex), fn);
|
|
1277
1385
|
};
|
|
1386
|
+
async function withLock(mutex, fn) {
|
|
1387
|
+
const releaseLock = await mutex.acquire();
|
|
1388
|
+
try {
|
|
1389
|
+
return await fn({ releaseLock });
|
|
1390
|
+
} finally {
|
|
1391
|
+
releaseLock();
|
|
1392
|
+
}
|
|
1393
|
+
}
|
|
1278
1394
|
var KeyringController_default = KeyringController;
|
|
1279
1395
|
|
|
1280
1396
|
export {
|
|
@@ -1287,4 +1403,4 @@ export {
|
|
|
1287
1403
|
KeyringController,
|
|
1288
1404
|
KeyringController_default
|
|
1289
1405
|
};
|
|
1290
|
-
//# sourceMappingURL=chunk-
|
|
1406
|
+
//# sourceMappingURL=chunk-RVCG63UG.mjs.map
|