@aztec/key-store 0.0.1-commit.d3ec352c → 0.0.1-commit.e310a4c8

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.
@@ -1,4 +1,5 @@
1
- import { Fr, GrumpkinScalar } from '@aztec/foundation/fields';
1
+ import { Fr } from '@aztec/foundation/curves/bn254';
2
+ import { GrumpkinScalar } from '@aztec/foundation/curves/grumpkin';
2
3
  import { type Bufferable } from '@aztec/foundation/serialize';
3
4
  import type { AztecAsyncKVStore } from '@aztec/kv-store';
4
5
  import { AztecAddress } from '@aztec/stdlib/aztec-address';
@@ -10,7 +11,7 @@ import { type KeyPrefix, type PublicKey } from '@aztec/stdlib/keys';
10
11
  */
11
12
  export declare class KeyStore {
12
13
  #private;
13
- static readonly SCHEMA_VERSION: number;
14
+ static readonly SCHEMA_VERSION = 1;
14
15
  constructor(database: AztecAsyncKVStore);
15
16
  /**
16
17
  * Creates a new account from a randomly generated secret key.
@@ -96,4 +97,4 @@ export declare class KeyStore {
96
97
  */
97
98
  getKeyPrefixAndAccount(value: Bufferable): Promise<[KeyPrefix, AztecAddress]>;
98
99
  }
99
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoia2V5X3N0b3JlLmQudHMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi9zcmMva2V5X3N0b3JlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUVBLE9BQU8sRUFBRSxFQUFFLEVBQUUsY0FBYyxFQUFTLE1BQU0sMEJBQTBCLENBQUM7QUFFckUsT0FBTyxFQUFFLEtBQUssVUFBVSxFQUFxQixNQUFNLDZCQUE2QixDQUFDO0FBQ2pGLE9BQU8sS0FBSyxFQUFFLGlCQUFpQixFQUFpQixNQUFNLGlCQUFpQixDQUFDO0FBQ3hFLE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSw2QkFBNkIsQ0FBQztBQUMzRCxPQUFPLEVBQUUsZUFBZSxFQUFFLEtBQUssY0FBYyxFQUFFLE1BQU0sd0JBQXdCLENBQUM7QUFDOUUsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0sc0JBQXNCLENBQUM7QUFDNUQsT0FBTyxFQUVMLEtBQUssU0FBUyxFQUNkLEtBQUssU0FBUyxFQUlmLE1BQU0sb0JBQW9CLENBQUM7QUFFNUI7O0dBRUc7QUFDSCxxQkFBYSxRQUFROztJQUNuQixnQkFBdUIsY0FBYyxTQUFLO0lBRzFDLFlBQVksUUFBUSxFQUFFLGlCQUFpQixFQUV0QztJQUVEOzs7T0FHRztJQUNJLGFBQWEsSUFBSSxPQUFPLENBQUMsZUFBZSxDQUFDLENBSS9DO0lBRUQ7Ozs7O09BS0c7SUFDVSxVQUFVLENBQUMsRUFBRSxFQUFFLEVBQUUsRUFBRSxjQUFjLEVBQUUsY0FBYyxHQUFHLE9BQU8sQ0FBQyxlQUFlLENBQUMsQ0FvQ3hGO0lBRUQ7OztPQUdHO0lBQ1UsV0FBVyxJQUFJLE9BQU8sQ0FBQyxZQUFZLEVBQUUsQ0FBQyxDQUtsRDtJQUVEOzs7Ozs7T0FNRztJQUNVLHVCQUF1QixDQUFDLE9BQU8sRUFBRSxFQUFFLEVBQUUsZUFBZSxFQUFFLFlBQVksR0FBRyxPQUFPLENBQUMsb0JBQW9CLENBQUMsQ0FxQzlHO0lBRUQ7Ozs7O09BS0c7SUFDVSwyQkFBMkIsQ0FBQyxPQUFPLEVBQUUsWUFBWSxHQUFHLE9BQU8sQ0FBQyxTQUFTLENBQUMsQ0FRbEY7SUFFRDs7Ozs7T0FLRztJQUNVLGlDQUFpQyxDQUFDLE9BQU8sRUFBRSxZQUFZLEdBQUcsT0FBTyxDQUFDLFNBQVMsQ0FBQyxDQVF4RjtJQUVEOzs7OztPQUtHO0lBQ1UsaUNBQWlDLENBQUMsT0FBTyxFQUFFLFlBQVksR0FBRyxPQUFPLENBQUMsU0FBUyxDQUFDLENBUXhGO0lBRUQ7Ozs7O09BS0c7SUFDVSx5QkFBeUIsQ0FBQyxPQUFPLEVBQUUsWUFBWSxHQUFHLE9BQU8sQ0FBQyxTQUFTLENBQUMsQ0FRaEY7SUFFRDs7Ozs7T0FLRztJQUNVLGlDQUFpQyxDQUFDLE9BQU8sRUFBRSxZQUFZLEdBQUcsT0FBTyxDQUFDLGNBQWMsQ0FBQyxDQVE3RjtJQUVEOzs7Ozs7T0FNRztJQUNVLDhCQUE4QixDQUFDLE9BQU8sRUFBRSxZQUFZLEVBQUUsR0FBRyxFQUFFLFlBQVksR0FBRyxPQUFPLENBQUMsRUFBRSxDQUFDLENBYWpHO0lBRUQ7Ozs7OztPQU1HO0lBQ1Usa0JBQWtCLENBQUMsR0FBRyxFQUFFLFNBQVMsR0FBRyxPQUFPLENBQUMsY0FBYyxDQUFDLENBaUJ2RTtJQUVEOzs7OztPQUtHO0lBQ1Usc0JBQXNCLENBQUMsS0FBSyxFQUFFLFVBQVUsR0FBRyxPQUFPLENBQUMsQ0FBQyxTQUFTLEVBQUUsWUFBWSxDQUFDLENBQUMsQ0FjekY7Q0FDRiJ9
100
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoia2V5X3N0b3JlLmQudHMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi9zcmMva2V5X3N0b3JlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUVBLE9BQU8sRUFBRSxFQUFFLEVBQUUsTUFBTSxnQ0FBZ0MsQ0FBQztBQUNwRCxPQUFPLEVBQUUsY0FBYyxFQUFTLE1BQU0sbUNBQW1DLENBQUM7QUFFMUUsT0FBTyxFQUFFLEtBQUssVUFBVSxFQUFxQixNQUFNLDZCQUE2QixDQUFDO0FBQ2pGLE9BQU8sS0FBSyxFQUFFLGlCQUFpQixFQUFpQixNQUFNLGlCQUFpQixDQUFDO0FBQ3hFLE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSw2QkFBNkIsQ0FBQztBQUMzRCxPQUFPLEVBQUUsZUFBZSxFQUFFLEtBQUssY0FBYyxFQUFFLE1BQU0sd0JBQXdCLENBQUM7QUFDOUUsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0sc0JBQXNCLENBQUM7QUFDNUQsT0FBTyxFQUVMLEtBQUssU0FBUyxFQUNkLEtBQUssU0FBUyxFQUlmLE1BQU0sb0JBQW9CLENBQUM7QUFPNUI7O0dBRUc7QUFDSCxxQkFBYSxRQUFROztJQUNuQixnQkFBdUIsY0FBYyxLQUFLO0lBSTFDLFlBQVksUUFBUSxFQUFFLGlCQUFpQixFQUd0QztJQUVEOzs7T0FHRztJQUNJLGFBQWEsSUFBSSxPQUFPLENBQUMsZUFBZSxDQUFDLENBSS9DO0lBRUQ7Ozs7O09BS0c7SUFDVSxVQUFVLENBQUMsRUFBRSxFQUFFLEVBQUUsRUFBRSxjQUFjLEVBQUUsY0FBYyxHQUFHLE9BQU8sQ0FBQyxlQUFlLENBQUMsQ0F3Q3hGO0lBRUQ7OztPQUdHO0lBQ1UsV0FBVyxJQUFJLE9BQU8sQ0FBQyxZQUFZLEVBQUUsQ0FBQyxDQUtsRDtJQUVEOzs7Ozs7T0FNRztJQUNVLHVCQUF1QixDQUFDLE9BQU8sRUFBRSxFQUFFLEVBQUUsZUFBZSxFQUFFLFlBQVksR0FBRyxPQUFPLENBQUMsb0JBQW9CLENBQUMsQ0FzQzlHO0lBRUQ7Ozs7O09BS0c7SUFDVSwyQkFBMkIsQ0FBQyxPQUFPLEVBQUUsWUFBWSxHQUFHLE9BQU8sQ0FBQyxTQUFTLENBQUMsQ0FRbEY7SUFFRDs7Ozs7T0FLRztJQUNVLGlDQUFpQyxDQUFDLE9BQU8sRUFBRSxZQUFZLEdBQUcsT0FBTyxDQUFDLFNBQVMsQ0FBQyxDQVF4RjtJQUVEOzs7OztPQUtHO0lBQ1UsaUNBQWlDLENBQUMsT0FBTyxFQUFFLFlBQVksR0FBRyxPQUFPLENBQUMsU0FBUyxDQUFDLENBUXhGO0lBRUQ7Ozs7O09BS0c7SUFDVSx5QkFBeUIsQ0FBQyxPQUFPLEVBQUUsWUFBWSxHQUFHLE9BQU8sQ0FBQyxTQUFTLENBQUMsQ0FRaEY7SUFFRDs7Ozs7T0FLRztJQUNVLGlDQUFpQyxDQUFDLE9BQU8sRUFBRSxZQUFZLEdBQUcsT0FBTyxDQUFDLGNBQWMsQ0FBQyxDQVE3RjtJQUVEOzs7Ozs7T0FNRztJQUNVLDhCQUE4QixDQUFDLE9BQU8sRUFBRSxZQUFZLEVBQUUsR0FBRyxFQUFFLFlBQVksR0FBRyxPQUFPLENBQUMsRUFBRSxDQUFDLENBYWpHO0lBRUQ7Ozs7OztPQU1HO0lBQ1Usa0JBQWtCLENBQUMsR0FBRyxFQUFFLFNBQVMsR0FBRyxPQUFPLENBQUMsY0FBYyxDQUFDLENBa0J2RTtJQUVEOzs7OztPQUtHO0lBQ1Usc0JBQXNCLENBQUMsS0FBSyxFQUFFLFVBQVUsR0FBRyxPQUFPLENBQUMsQ0FBQyxTQUFTLEVBQUUsWUFBWSxDQUFDLENBQUMsQ0FjekY7Q0FDRiJ9
@@ -1 +1 @@
1
- {"version":3,"file":"key_store.d.ts","sourceRoot":"","sources":["../src/key_store.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,EAAE,EAAE,cAAc,EAAS,MAAM,0BAA0B,CAAC;AAErE,OAAO,EAAE,KAAK,UAAU,EAAqB,MAAM,6BAA6B,CAAC;AACjF,OAAO,KAAK,EAAE,iBAAiB,EAAiB,MAAM,iBAAiB,CAAC;AACxE,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAC3D,OAAO,EAAE,eAAe,EAAE,KAAK,cAAc,EAAE,MAAM,wBAAwB,CAAC;AAC9E,OAAO,EAAE,oBAAoB,EAAE,MAAM,sBAAsB,CAAC;AAC5D,OAAO,EAEL,KAAK,SAAS,EACd,KAAK,SAAS,EAIf,MAAM,oBAAoB,CAAC;AAE5B;;GAEG;AACH,qBAAa,QAAQ;;IACnB,gBAAuB,cAAc,SAAK;IAG1C,YAAY,QAAQ,EAAE,iBAAiB,EAEtC;IAED;;;OAGG;IACI,aAAa,IAAI,OAAO,CAAC,eAAe,CAAC,CAI/C;IAED;;;;;OAKG;IACU,UAAU,CAAC,EAAE,EAAE,EAAE,EAAE,cAAc,EAAE,cAAc,GAAG,OAAO,CAAC,eAAe,CAAC,CAoCxF;IAED;;;OAGG;IACU,WAAW,IAAI,OAAO,CAAC,YAAY,EAAE,CAAC,CAKlD;IAED;;;;;;OAMG;IACU,uBAAuB,CAAC,OAAO,EAAE,EAAE,EAAE,eAAe,EAAE,YAAY,GAAG,OAAO,CAAC,oBAAoB,CAAC,CAqC9G;IAED;;;;;OAKG;IACU,2BAA2B,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,SAAS,CAAC,CAQlF;IAED;;;;;OAKG;IACU,iCAAiC,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,SAAS,CAAC,CAQxF;IAED;;;;;OAKG;IACU,iCAAiC,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,SAAS,CAAC,CAQxF;IAED;;;;;OAKG;IACU,yBAAyB,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,SAAS,CAAC,CAQhF;IAED;;;;;OAKG;IACU,iCAAiC,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,cAAc,CAAC,CAQ7F;IAED;;;;;;OAMG;IACU,8BAA8B,CAAC,OAAO,EAAE,YAAY,EAAE,GAAG,EAAE,YAAY,GAAG,OAAO,CAAC,EAAE,CAAC,CAajG;IAED;;;;;;OAMG;IACU,kBAAkB,CAAC,GAAG,EAAE,SAAS,GAAG,OAAO,CAAC,cAAc,CAAC,CAiBvE;IAED;;;;;OAKG;IACU,sBAAsB,CAAC,KAAK,EAAE,UAAU,GAAG,OAAO,CAAC,CAAC,SAAS,EAAE,YAAY,CAAC,CAAC,CAczF;CACF"}
1
+ {"version":3,"file":"key_store.d.ts","sourceRoot":"","sources":["../src/key_store.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,EAAE,EAAE,MAAM,gCAAgC,CAAC;AACpD,OAAO,EAAE,cAAc,EAAS,MAAM,mCAAmC,CAAC;AAE1E,OAAO,EAAE,KAAK,UAAU,EAAqB,MAAM,6BAA6B,CAAC;AACjF,OAAO,KAAK,EAAE,iBAAiB,EAAiB,MAAM,iBAAiB,CAAC;AACxE,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAC3D,OAAO,EAAE,eAAe,EAAE,KAAK,cAAc,EAAE,MAAM,wBAAwB,CAAC;AAC9E,OAAO,EAAE,oBAAoB,EAAE,MAAM,sBAAsB,CAAC;AAC5D,OAAO,EAEL,KAAK,SAAS,EACd,KAAK,SAAS,EAIf,MAAM,oBAAoB,CAAC;AAO5B;;GAEG;AACH,qBAAa,QAAQ;;IACnB,gBAAuB,cAAc,KAAK;IAI1C,YAAY,QAAQ,EAAE,iBAAiB,EAGtC;IAED;;;OAGG;IACI,aAAa,IAAI,OAAO,CAAC,eAAe,CAAC,CAI/C;IAED;;;;;OAKG;IACU,UAAU,CAAC,EAAE,EAAE,EAAE,EAAE,cAAc,EAAE,cAAc,GAAG,OAAO,CAAC,eAAe,CAAC,CAwCxF;IAED;;;OAGG;IACU,WAAW,IAAI,OAAO,CAAC,YAAY,EAAE,CAAC,CAKlD;IAED;;;;;;OAMG;IACU,uBAAuB,CAAC,OAAO,EAAE,EAAE,EAAE,eAAe,EAAE,YAAY,GAAG,OAAO,CAAC,oBAAoB,CAAC,CAsC9G;IAED;;;;;OAKG;IACU,2BAA2B,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,SAAS,CAAC,CAQlF;IAED;;;;;OAKG;IACU,iCAAiC,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,SAAS,CAAC,CAQxF;IAED;;;;;OAKG;IACU,iCAAiC,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,SAAS,CAAC,CAQxF;IAED;;;;;OAKG;IACU,yBAAyB,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,SAAS,CAAC,CAQhF;IAED;;;;;OAKG;IACU,iCAAiC,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,cAAc,CAAC,CAQ7F;IAED;;;;;;OAMG;IACU,8BAA8B,CAAC,OAAO,EAAE,YAAY,EAAE,GAAG,EAAE,YAAY,GAAG,OAAO,CAAC,EAAE,CAAC,CAajG;IAED;;;;;;OAMG;IACU,kBAAkB,CAAC,GAAG,EAAE,SAAS,GAAG,OAAO,CAAC,cAAc,CAAC,CAkBvE;IAED;;;;;OAKG;IACU,sBAAsB,CAAC,KAAK,EAAE,UAAU,GAAG,OAAO,CAAC,CAAC,SAAS,EAAE,YAAY,CAAC,CAAC,CAczF;CACF"}
package/dest/key_store.js CHANGED
@@ -1,18 +1,24 @@
1
1
  import { GeneratorIndex } from '@aztec/constants';
2
- import { poseidon2HashWithSeparator } from '@aztec/foundation/crypto';
3
- import { Fr, GrumpkinScalar, Point } from '@aztec/foundation/fields';
2
+ import { poseidon2HashWithSeparator } from '@aztec/foundation/crypto/poseidon';
3
+ import { Fr } from '@aztec/foundation/curves/bn254';
4
+ import { GrumpkinScalar, Point } from '@aztec/foundation/curves/grumpkin';
4
5
  import { toArray } from '@aztec/foundation/iterable';
5
6
  import { serializeToBuffer } from '@aztec/foundation/serialize';
6
7
  import { AztecAddress } from '@aztec/stdlib/aztec-address';
7
8
  import { CompleteAddress } from '@aztec/stdlib/contract';
8
9
  import { KeyValidationRequest } from '@aztec/stdlib/kernel';
9
10
  import { KEY_PREFIXES, computeAppSecretKey, deriveKeys, derivePublicKeyFromSecretKey } from '@aztec/stdlib/keys';
11
+ /** Maps a key prefix to the storage suffix for the corresponding master secret key. */ function secretKeyStorageSuffix(prefix) {
12
+ return prefix === 'n' ? 'nhk_m' : `${prefix}sk_m`;
13
+ }
10
14
  /**
11
15
  * Used for managing keys. Can hold keys of multiple accounts.
12
16
  */ export class KeyStore {
13
17
  static SCHEMA_VERSION = 1;
18
+ #db;
14
19
  #keys;
15
20
  constructor(database){
21
+ this.#db = database;
16
22
  this.#keys = database.openMap('key_store');
17
23
  }
18
24
  /**
@@ -29,28 +35,31 @@ import { KEY_PREFIXES, computeAppSecretKey, deriveKeys, derivePublicKeyFromSecre
29
35
  * @param partialAddress - The partial address of the account.
30
36
  * @returns The account's complete address.
31
37
  */ async addAccount(sk, partialAddress) {
32
- const { masterNullifierSecretKey, masterIncomingViewingSecretKey, masterOutgoingViewingSecretKey, masterTaggingSecretKey, publicKeys } = await deriveKeys(sk);
38
+ const { masterNullifierHidingKey, masterIncomingViewingSecretKey, masterOutgoingViewingSecretKey, masterTaggingSecretKey, publicKeys } = await deriveKeys(sk);
33
39
  const completeAddress = await CompleteAddress.fromSecretKeyAndPartialAddress(sk, partialAddress);
34
40
  const { address: account } = completeAddress;
35
- // Naming of keys is as follows ${account}-${n/iv/ov/t}${sk/pk}_m
36
- await this.#keys.set(`${account.toString()}-ivsk_m`, masterIncomingViewingSecretKey.toBuffer());
37
- await this.#keys.set(`${account.toString()}-ovsk_m`, masterOutgoingViewingSecretKey.toBuffer());
38
- await this.#keys.set(`${account.toString()}-tsk_m`, masterTaggingSecretKey.toBuffer());
39
- await this.#keys.set(`${account.toString()}-nsk_m`, masterNullifierSecretKey.toBuffer());
40
- await this.#keys.set(`${account.toString()}-npk_m`, publicKeys.masterNullifierPublicKey.toBuffer());
41
- await this.#keys.set(`${account.toString()}-ivpk_m`, publicKeys.masterIncomingViewingPublicKey.toBuffer());
42
- await this.#keys.set(`${account.toString()}-ovpk_m`, publicKeys.masterOutgoingViewingPublicKey.toBuffer());
43
- await this.#keys.set(`${account.toString()}-tpk_m`, publicKeys.masterTaggingPublicKey.toBuffer());
44
- // We store pk_m_hash under `account-{n/iv/ov/t}pk_m_hash` key to be able to obtain address and key prefix
45
- // using the #getKeyPrefixAndAccount function later on
41
+ // Compute hashes before transaction
46
42
  const masterNullifierPublicKeyHash = await publicKeys.masterNullifierPublicKey.hash();
47
- await this.#keys.set(`${account.toString()}-npk_m_hash`, masterNullifierPublicKeyHash.toBuffer());
48
43
  const masterIncomingViewingPublicKeyHash = await publicKeys.masterIncomingViewingPublicKey.hash();
49
- await this.#keys.set(`${account.toString()}-ivpk_m_hash`, masterIncomingViewingPublicKeyHash.toBuffer());
50
44
  const masterOutgoingViewingPublicKeyHash = await publicKeys.masterOutgoingViewingPublicKey.hash();
51
- await this.#keys.set(`${account.toString()}-ovpk_m_hash`, masterOutgoingViewingPublicKeyHash.toBuffer());
52
45
  const masterTaggingPublicKeyHash = await publicKeys.masterTaggingPublicKey.hash();
53
- await this.#keys.set(`${account.toString()}-tpk_m_hash`, masterTaggingPublicKeyHash.toBuffer());
46
+ await this.#db.transactionAsync(async ()=>{
47
+ // Naming of keys is as follows ${account}-${n/iv/ov/t}${sk/pk}_m
48
+ await this.#keys.set(`${account.toString()}-ivsk_m`, masterIncomingViewingSecretKey.toBuffer());
49
+ await this.#keys.set(`${account.toString()}-ovsk_m`, masterOutgoingViewingSecretKey.toBuffer());
50
+ await this.#keys.set(`${account.toString()}-tsk_m`, masterTaggingSecretKey.toBuffer());
51
+ await this.#keys.set(`${account.toString()}-nhk_m`, masterNullifierHidingKey.toBuffer());
52
+ await this.#keys.set(`${account.toString()}-npk_m`, publicKeys.masterNullifierPublicKey.toBuffer());
53
+ await this.#keys.set(`${account.toString()}-ivpk_m`, publicKeys.masterIncomingViewingPublicKey.toBuffer());
54
+ await this.#keys.set(`${account.toString()}-ovpk_m`, publicKeys.masterOutgoingViewingPublicKey.toBuffer());
55
+ await this.#keys.set(`${account.toString()}-tpk_m`, publicKeys.masterTaggingPublicKey.toBuffer());
56
+ // We store pk_m_hash under `account-{n/iv/ov/t}pk_m_hash` key to be able to obtain address and key prefix
57
+ // using the #getKeyPrefixAndAccount function later on
58
+ await this.#keys.set(`${account.toString()}-npk_m_hash`, masterNullifierPublicKeyHash.toBuffer());
59
+ await this.#keys.set(`${account.toString()}-ivpk_m_hash`, masterIncomingViewingPublicKeyHash.toBuffer());
60
+ await this.#keys.set(`${account.toString()}-ovpk_m_hash`, masterOutgoingViewingPublicKeyHash.toBuffer());
61
+ await this.#keys.set(`${account.toString()}-tpk_m_hash`, masterTaggingPublicKeyHash.toBuffer());
62
+ });
54
63
  // At last, we return the newly derived account address
55
64
  return completeAddress;
56
65
  }
@@ -82,9 +91,10 @@ import { KEY_PREFIXES, computeAppSecretKey, deriveKeys, derivePublicKeyFromSecre
82
91
  throw new Error(`Could not find ${keyPrefix}pkM for ${keyPrefix}pk_m_hash ${pkMHash.toString()}.`);
83
92
  }
84
93
  // Now we find the secret key for the public key
85
- const skMBuffer = await this.#keys.getAsync(`${account.toString()}-${keyPrefix}sk_m`);
94
+ const skStorageSuffix = secretKeyStorageSuffix(keyPrefix);
95
+ const skMBuffer = await this.#keys.getAsync(`${account.toString()}-${skStorageSuffix}`);
86
96
  if (!skMBuffer) {
87
- throw new Error(`Could not find ${keyPrefix}sk_m for account ${account.toString()} whose address was successfully obtained with ${keyPrefix}pk_m_hash ${pkMHash.toString()}.`);
97
+ throw new Error(`Could not find ${skStorageSuffix} for account ${account.toString()} whose address was successfully obtained with ${keyPrefix}pk_m_hash ${pkMHash.toString()}.`);
88
98
  }
89
99
  const skM = GrumpkinScalar.fromBuffer(skMBuffer);
90
100
  // We sanity check that it's possible to derive the public key from the secret key
@@ -182,14 +192,15 @@ import { KEY_PREFIXES, computeAppSecretKey, deriveKeys, derivePublicKeyFromSecre
182
192
  * @dev Used when feeding the sk_m to the kernel circuit for keys verification.
183
193
  */ async getMasterSecretKey(pkM) {
184
194
  const [keyPrefix, account] = await this.getKeyPrefixAndAccount(pkM);
185
- const secretKeyBuffer = await this.#keys.getAsync(`${account.toString()}-${keyPrefix}sk_m`);
195
+ const skStorageSuffix = secretKeyStorageSuffix(keyPrefix);
196
+ const secretKeyBuffer = await this.#keys.getAsync(`${account.toString()}-${skStorageSuffix}`);
186
197
  if (!secretKeyBuffer) {
187
- throw new Error(`Could not find ${keyPrefix}sk_m for ${keyPrefix}pk_m ${pkM.toString()}. This should not happen.`);
198
+ throw new Error(`Could not find ${skStorageSuffix} for ${keyPrefix}pk_m ${pkM.toString()}. This should not happen.`);
188
199
  }
189
200
  const skM = GrumpkinScalar.fromBuffer(secretKeyBuffer);
190
201
  const derivedpkM = await derivePublicKeyFromSecretKey(skM);
191
202
  if (!derivedpkM.equals(pkM)) {
192
- throw new Error(`Could not find ${keyPrefix}skM for ${keyPrefix}pkM ${pkM.toString()} in secret keys buffer.`);
203
+ throw new Error(`Could not find ${skStorageSuffix} for ${keyPrefix}pkM ${pkM.toString()} in secret keys buffer.`);
193
204
  }
194
205
  return Promise.resolve(skM);
195
206
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aztec/key-store",
3
- "version": "0.0.1-commit.d3ec352c",
3
+ "version": "0.0.1-commit.e310a4c8",
4
4
  "type": "module",
5
5
  "exports": "./dest/index.js",
6
6
  "typedocOptions": {
@@ -57,17 +57,17 @@
57
57
  ]
58
58
  },
59
59
  "dependencies": {
60
- "@aztec/constants": "0.0.1-commit.d3ec352c",
61
- "@aztec/foundation": "0.0.1-commit.d3ec352c",
62
- "@aztec/kv-store": "0.0.1-commit.d3ec352c",
63
- "@aztec/stdlib": "0.0.1-commit.d3ec352c",
60
+ "@aztec/constants": "0.0.1-commit.e310a4c8",
61
+ "@aztec/foundation": "0.0.1-commit.e310a4c8",
62
+ "@aztec/kv-store": "0.0.1-commit.e310a4c8",
63
+ "@aztec/stdlib": "0.0.1-commit.e310a4c8",
64
64
  "tslib": "^2.4.0"
65
65
  },
66
66
  "devDependencies": {
67
67
  "@jest/globals": "^30.0.0",
68
68
  "@types/jest": "^30.0.0",
69
69
  "@types/node": "^22.15.17",
70
- "@typescript/native-preview": "7.0.0-dev.20251126.1",
70
+ "@typescript/native-preview": "7.0.0-dev.20260113.1",
71
71
  "jest": "^30.0.0",
72
72
  "ts-node": "^10.9.1",
73
73
  "typescript": "^5.3.3"
package/src/key_store.ts CHANGED
@@ -1,6 +1,7 @@
1
1
  import { GeneratorIndex } from '@aztec/constants';
2
- import { poseidon2HashWithSeparator } from '@aztec/foundation/crypto';
3
- import { Fr, GrumpkinScalar, Point } from '@aztec/foundation/fields';
2
+ import { poseidon2HashWithSeparator } from '@aztec/foundation/crypto/poseidon';
3
+ import { Fr } from '@aztec/foundation/curves/bn254';
4
+ import { GrumpkinScalar, Point } from '@aztec/foundation/curves/grumpkin';
4
5
  import { toArray } from '@aztec/foundation/iterable';
5
6
  import { type Bufferable, serializeToBuffer } from '@aztec/foundation/serialize';
6
7
  import type { AztecAsyncKVStore, AztecAsyncMap } from '@aztec/kv-store';
@@ -16,14 +17,21 @@ import {
16
17
  derivePublicKeyFromSecretKey,
17
18
  } from '@aztec/stdlib/keys';
18
19
 
20
+ /** Maps a key prefix to the storage suffix for the corresponding master secret key. */
21
+ function secretKeyStorageSuffix(prefix: KeyPrefix): string {
22
+ return prefix === 'n' ? 'nhk_m' : `${prefix}sk_m`;
23
+ }
24
+
19
25
  /**
20
26
  * Used for managing keys. Can hold keys of multiple accounts.
21
27
  */
22
28
  export class KeyStore {
23
29
  public static readonly SCHEMA_VERSION = 1;
30
+ #db: AztecAsyncKVStore;
24
31
  #keys: AztecAsyncMap<string, Buffer>;
25
32
 
26
33
  constructor(database: AztecAsyncKVStore) {
34
+ this.#db = database;
27
35
  this.#keys = database.openMap('key_store');
28
36
  }
29
37
 
@@ -45,7 +53,7 @@ export class KeyStore {
45
53
  */
46
54
  public async addAccount(sk: Fr, partialAddress: PartialAddress): Promise<CompleteAddress> {
47
55
  const {
48
- masterNullifierSecretKey,
56
+ masterNullifierHidingKey,
49
57
  masterIncomingViewingSecretKey,
50
58
  masterOutgoingViewingSecretKey,
51
59
  masterTaggingSecretKey,
@@ -55,27 +63,31 @@ export class KeyStore {
55
63
  const completeAddress = await CompleteAddress.fromSecretKeyAndPartialAddress(sk, partialAddress);
56
64
  const { address: account } = completeAddress;
57
65
 
58
- // Naming of keys is as follows ${account}-${n/iv/ov/t}${sk/pk}_m
59
- await this.#keys.set(`${account.toString()}-ivsk_m`, masterIncomingViewingSecretKey.toBuffer());
60
- await this.#keys.set(`${account.toString()}-ovsk_m`, masterOutgoingViewingSecretKey.toBuffer());
61
- await this.#keys.set(`${account.toString()}-tsk_m`, masterTaggingSecretKey.toBuffer());
62
- await this.#keys.set(`${account.toString()}-nsk_m`, masterNullifierSecretKey.toBuffer());
63
-
64
- await this.#keys.set(`${account.toString()}-npk_m`, publicKeys.masterNullifierPublicKey.toBuffer());
65
- await this.#keys.set(`${account.toString()}-ivpk_m`, publicKeys.masterIncomingViewingPublicKey.toBuffer());
66
- await this.#keys.set(`${account.toString()}-ovpk_m`, publicKeys.masterOutgoingViewingPublicKey.toBuffer());
67
- await this.#keys.set(`${account.toString()}-tpk_m`, publicKeys.masterTaggingPublicKey.toBuffer());
68
-
69
- // We store pk_m_hash under `account-{n/iv/ov/t}pk_m_hash` key to be able to obtain address and key prefix
70
- // using the #getKeyPrefixAndAccount function later on
66
+ // Compute hashes before transaction
71
67
  const masterNullifierPublicKeyHash = await publicKeys.masterNullifierPublicKey.hash();
72
- await this.#keys.set(`${account.toString()}-npk_m_hash`, masterNullifierPublicKeyHash.toBuffer());
73
68
  const masterIncomingViewingPublicKeyHash = await publicKeys.masterIncomingViewingPublicKey.hash();
74
- await this.#keys.set(`${account.toString()}-ivpk_m_hash`, masterIncomingViewingPublicKeyHash.toBuffer());
75
69
  const masterOutgoingViewingPublicKeyHash = await publicKeys.masterOutgoingViewingPublicKey.hash();
76
- await this.#keys.set(`${account.toString()}-ovpk_m_hash`, masterOutgoingViewingPublicKeyHash.toBuffer());
77
70
  const masterTaggingPublicKeyHash = await publicKeys.masterTaggingPublicKey.hash();
78
- await this.#keys.set(`${account.toString()}-tpk_m_hash`, masterTaggingPublicKeyHash.toBuffer());
71
+
72
+ await this.#db.transactionAsync(async () => {
73
+ // Naming of keys is as follows ${account}-${n/iv/ov/t}${sk/pk}_m
74
+ await this.#keys.set(`${account.toString()}-ivsk_m`, masterIncomingViewingSecretKey.toBuffer());
75
+ await this.#keys.set(`${account.toString()}-ovsk_m`, masterOutgoingViewingSecretKey.toBuffer());
76
+ await this.#keys.set(`${account.toString()}-tsk_m`, masterTaggingSecretKey.toBuffer());
77
+ await this.#keys.set(`${account.toString()}-nhk_m`, masterNullifierHidingKey.toBuffer());
78
+
79
+ await this.#keys.set(`${account.toString()}-npk_m`, publicKeys.masterNullifierPublicKey.toBuffer());
80
+ await this.#keys.set(`${account.toString()}-ivpk_m`, publicKeys.masterIncomingViewingPublicKey.toBuffer());
81
+ await this.#keys.set(`${account.toString()}-ovpk_m`, publicKeys.masterOutgoingViewingPublicKey.toBuffer());
82
+ await this.#keys.set(`${account.toString()}-tpk_m`, publicKeys.masterTaggingPublicKey.toBuffer());
83
+
84
+ // We store pk_m_hash under `account-{n/iv/ov/t}pk_m_hash` key to be able to obtain address and key prefix
85
+ // using the #getKeyPrefixAndAccount function later on
86
+ await this.#keys.set(`${account.toString()}-npk_m_hash`, masterNullifierPublicKeyHash.toBuffer());
87
+ await this.#keys.set(`${account.toString()}-ivpk_m_hash`, masterIncomingViewingPublicKeyHash.toBuffer());
88
+ await this.#keys.set(`${account.toString()}-ovpk_m_hash`, masterOutgoingViewingPublicKeyHash.toBuffer());
89
+ await this.#keys.set(`${account.toString()}-tpk_m_hash`, masterTaggingPublicKeyHash.toBuffer());
90
+ });
79
91
 
80
92
  // At last, we return the newly derived account address
81
93
  return completeAddress;
@@ -117,10 +129,11 @@ export class KeyStore {
117
129
  }
118
130
 
119
131
  // Now we find the secret key for the public key
120
- const skMBuffer = await this.#keys.getAsync(`${account.toString()}-${keyPrefix}sk_m`);
132
+ const skStorageSuffix = secretKeyStorageSuffix(keyPrefix);
133
+ const skMBuffer = await this.#keys.getAsync(`${account.toString()}-${skStorageSuffix}`);
121
134
  if (!skMBuffer) {
122
135
  throw new Error(
123
- `Could not find ${keyPrefix}sk_m for account ${account.toString()} whose address was successfully obtained with ${keyPrefix}pk_m_hash ${pkMHash.toString()}.`,
136
+ `Could not find ${skStorageSuffix} for account ${account.toString()} whose address was successfully obtained with ${keyPrefix}pk_m_hash ${pkMHash.toString()}.`,
124
137
  );
125
138
  }
126
139
 
@@ -250,17 +263,18 @@ export class KeyStore {
250
263
  public async getMasterSecretKey(pkM: PublicKey): Promise<GrumpkinScalar> {
251
264
  const [keyPrefix, account] = await this.getKeyPrefixAndAccount(pkM);
252
265
 
253
- const secretKeyBuffer = await this.#keys.getAsync(`${account.toString()}-${keyPrefix}sk_m`);
266
+ const skStorageSuffix = secretKeyStorageSuffix(keyPrefix);
267
+ const secretKeyBuffer = await this.#keys.getAsync(`${account.toString()}-${skStorageSuffix}`);
254
268
  if (!secretKeyBuffer) {
255
269
  throw new Error(
256
- `Could not find ${keyPrefix}sk_m for ${keyPrefix}pk_m ${pkM.toString()}. This should not happen.`,
270
+ `Could not find ${skStorageSuffix} for ${keyPrefix}pk_m ${pkM.toString()}. This should not happen.`,
257
271
  );
258
272
  }
259
273
 
260
274
  const skM = GrumpkinScalar.fromBuffer(secretKeyBuffer);
261
275
  const derivedpkM = await derivePublicKeyFromSecretKey(skM);
262
276
  if (!derivedpkM.equals(pkM)) {
263
- throw new Error(`Could not find ${keyPrefix}skM for ${keyPrefix}pkM ${pkM.toString()} in secret keys buffer.`);
277
+ throw new Error(`Could not find ${skStorageSuffix} for ${keyPrefix}pkM ${pkM.toString()} in secret keys buffer.`);
264
278
  }
265
279
 
266
280
  return Promise.resolve(skM);