react-native-quick-crypto 0.7.0-rc.9 → 0.7.1

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.
Files changed (155) hide show
  1. package/android/CMakeLists.txt +2 -0
  2. package/cpp/Cipher/MGLGenerateKeyPairInstaller.cpp +51 -14
  3. package/cpp/Cipher/MGLGenerateKeyPairSyncInstaller.cpp +25 -9
  4. package/cpp/Cipher/MGLRsa.cpp +192 -15
  5. package/cpp/Cipher/MGLRsa.h +36 -2
  6. package/cpp/JSIUtils/MGLJSIUtils.h +17 -0
  7. package/cpp/MGLKeys.cpp +210 -187
  8. package/cpp/MGLKeys.h +25 -13
  9. package/cpp/MGLQuickCryptoHostObject.cpp +6 -6
  10. package/cpp/Sig/MGLSignHostObjects.cpp +284 -421
  11. package/cpp/Sig/MGLSignHostObjects.h +40 -0
  12. package/cpp/Utils/MGLUtils.cpp +71 -42
  13. package/cpp/Utils/MGLUtils.h +81 -6
  14. package/cpp/webcrypto/MGLWebCrypto.cpp +97 -35
  15. package/cpp/webcrypto/MGLWebCrypto.h +5 -7
  16. package/cpp/webcrypto/crypto_aes.cpp +516 -0
  17. package/cpp/webcrypto/crypto_aes.h +79 -0
  18. package/cpp/webcrypto/crypto_ec.cpp +110 -20
  19. package/cpp/webcrypto/crypto_ec.h +18 -5
  20. package/cpp/webcrypto/crypto_keygen.cpp +86 -0
  21. package/cpp/webcrypto/crypto_keygen.h +38 -0
  22. package/lib/commonjs/Cipher.js +140 -95
  23. package/lib/commonjs/Cipher.js.map +1 -1
  24. package/lib/commonjs/Hashnames.js +20 -8
  25. package/lib/commonjs/Hashnames.js.map +1 -1
  26. package/lib/commonjs/NativeQuickCrypto/Cipher.js +23 -8
  27. package/lib/commonjs/NativeQuickCrypto/Cipher.js.map +1 -1
  28. package/lib/commonjs/NativeQuickCrypto/NativeQuickCrypto.js.map +1 -1
  29. package/lib/commonjs/NativeQuickCrypto/aes.js +6 -0
  30. package/lib/commonjs/NativeQuickCrypto/aes.js.map +1 -0
  31. package/lib/commonjs/NativeQuickCrypto/keygen.js +6 -0
  32. package/lib/commonjs/NativeQuickCrypto/keygen.js.map +1 -0
  33. package/lib/commonjs/NativeQuickCrypto/rsa.js +6 -0
  34. package/lib/commonjs/NativeQuickCrypto/rsa.js.map +1 -0
  35. package/lib/commonjs/NativeQuickCrypto/sig.js +17 -0
  36. package/lib/commonjs/NativeQuickCrypto/sig.js.map +1 -1
  37. package/lib/commonjs/Utils.js +45 -7
  38. package/lib/commonjs/Utils.js.map +1 -1
  39. package/lib/commonjs/aes.js +184 -227
  40. package/lib/commonjs/aes.js.map +1 -1
  41. package/lib/commonjs/ec.js +79 -91
  42. package/lib/commonjs/ec.js.map +1 -1
  43. package/lib/commonjs/index.js +12 -2
  44. package/lib/commonjs/index.js.map +1 -1
  45. package/lib/commonjs/keygen.js +56 -0
  46. package/lib/commonjs/keygen.js.map +1 -0
  47. package/lib/commonjs/keys.js +84 -29
  48. package/lib/commonjs/keys.js.map +1 -1
  49. package/lib/commonjs/random.js +6 -0
  50. package/lib/commonjs/random.js.map +1 -1
  51. package/lib/commonjs/rsa.js +115 -196
  52. package/lib/commonjs/rsa.js.map +1 -1
  53. package/lib/commonjs/sig.js.map +1 -1
  54. package/lib/commonjs/subtle.js +205 -29
  55. package/lib/commonjs/subtle.js.map +1 -1
  56. package/lib/commonjs/webcrypto.js +14 -0
  57. package/lib/commonjs/webcrypto.js.map +1 -0
  58. package/lib/module/Cipher.js +138 -93
  59. package/lib/module/Cipher.js.map +1 -1
  60. package/lib/module/Hashnames.js +20 -8
  61. package/lib/module/Hashnames.js.map +1 -1
  62. package/lib/module/NativeQuickCrypto/Cipher.js +22 -7
  63. package/lib/module/NativeQuickCrypto/Cipher.js.map +1 -1
  64. package/lib/module/NativeQuickCrypto/NativeQuickCrypto.js.map +1 -1
  65. package/lib/module/NativeQuickCrypto/aes.js +2 -0
  66. package/lib/module/NativeQuickCrypto/aes.js.map +1 -0
  67. package/lib/module/NativeQuickCrypto/keygen.js +2 -0
  68. package/lib/module/NativeQuickCrypto/keygen.js.map +1 -0
  69. package/lib/module/NativeQuickCrypto/rsa.js +2 -0
  70. package/lib/module/NativeQuickCrypto/rsa.js.map +1 -0
  71. package/lib/module/NativeQuickCrypto/sig.js +13 -0
  72. package/lib/module/NativeQuickCrypto/sig.js.map +1 -1
  73. package/lib/module/Utils.js +38 -5
  74. package/lib/module/Utils.js.map +1 -1
  75. package/lib/module/aes.js +183 -228
  76. package/lib/module/aes.js.map +1 -1
  77. package/lib/module/ec.js +76 -93
  78. package/lib/module/ec.js.map +1 -1
  79. package/lib/module/index.js +11 -2
  80. package/lib/module/index.js.map +1 -1
  81. package/lib/module/keygen.js +47 -0
  82. package/lib/module/keygen.js.map +1 -0
  83. package/lib/module/keys.js +76 -28
  84. package/lib/module/keys.js.map +1 -1
  85. package/lib/module/random.js +6 -0
  86. package/lib/module/random.js.map +1 -1
  87. package/lib/module/rsa.js +115 -198
  88. package/lib/module/rsa.js.map +1 -1
  89. package/lib/module/sig.js.map +1 -1
  90. package/lib/module/subtle.js +209 -34
  91. package/lib/module/subtle.js.map +1 -1
  92. package/lib/module/webcrypto.js +8 -0
  93. package/lib/module/webcrypto.js.map +1 -0
  94. package/lib/typescript/Cipher.d.ts +23 -14
  95. package/lib/typescript/Cipher.d.ts.map +1 -1
  96. package/lib/typescript/Hash.d.ts.map +1 -1
  97. package/lib/typescript/Hashnames.d.ts +2 -2
  98. package/lib/typescript/Hashnames.d.ts.map +1 -1
  99. package/lib/typescript/NativeQuickCrypto/Cipher.d.ts +16 -6
  100. package/lib/typescript/NativeQuickCrypto/Cipher.d.ts.map +1 -1
  101. package/lib/typescript/NativeQuickCrypto/NativeQuickCrypto.d.ts +4 -1
  102. package/lib/typescript/NativeQuickCrypto/NativeQuickCrypto.d.ts.map +1 -1
  103. package/lib/typescript/NativeQuickCrypto/aes.d.ts +5 -0
  104. package/lib/typescript/NativeQuickCrypto/aes.d.ts.map +1 -0
  105. package/lib/typescript/NativeQuickCrypto/keygen.d.ts +4 -0
  106. package/lib/typescript/NativeQuickCrypto/keygen.d.ts.map +1 -0
  107. package/lib/typescript/NativeQuickCrypto/rsa.d.ts +5 -0
  108. package/lib/typescript/NativeQuickCrypto/rsa.d.ts.map +1 -0
  109. package/lib/typescript/NativeQuickCrypto/sig.d.ts +10 -0
  110. package/lib/typescript/NativeQuickCrypto/sig.d.ts.map +1 -1
  111. package/lib/typescript/NativeQuickCrypto/webcrypto.d.ts +14 -2
  112. package/lib/typescript/NativeQuickCrypto/webcrypto.d.ts.map +1 -1
  113. package/lib/typescript/Utils.d.ts +5 -4
  114. package/lib/typescript/Utils.d.ts.map +1 -1
  115. package/lib/typescript/aes.d.ts +18 -1
  116. package/lib/typescript/aes.d.ts.map +1 -1
  117. package/lib/typescript/ec.d.ts +3 -1
  118. package/lib/typescript/ec.d.ts.map +1 -1
  119. package/lib/typescript/index.d.ts +30 -24
  120. package/lib/typescript/index.d.ts.map +1 -1
  121. package/lib/typescript/keygen.d.ts +6 -0
  122. package/lib/typescript/keygen.d.ts.map +1 -0
  123. package/lib/typescript/keys.d.ts +67 -18
  124. package/lib/typescript/keys.d.ts.map +1 -1
  125. package/lib/typescript/random.d.ts +2 -1
  126. package/lib/typescript/random.d.ts.map +1 -1
  127. package/lib/typescript/rsa.d.ts +9 -1
  128. package/lib/typescript/rsa.d.ts.map +1 -1
  129. package/lib/typescript/sig.d.ts +3 -17
  130. package/lib/typescript/sig.d.ts.map +1 -1
  131. package/lib/typescript/subtle.d.ts +8 -4
  132. package/lib/typescript/subtle.d.ts.map +1 -1
  133. package/lib/typescript/webcrypto.d.ts +9 -0
  134. package/lib/typescript/webcrypto.d.ts.map +1 -0
  135. package/package.json +2 -2
  136. package/src/Cipher.ts +139 -75
  137. package/src/Hashnames.ts +23 -21
  138. package/src/NativeQuickCrypto/Cipher.ts +46 -14
  139. package/src/NativeQuickCrypto/NativeQuickCrypto.ts +6 -0
  140. package/src/NativeQuickCrypto/aes.ts +14 -0
  141. package/src/NativeQuickCrypto/keygen.ts +7 -0
  142. package/src/NativeQuickCrypto/rsa.ts +12 -0
  143. package/src/NativeQuickCrypto/sig.ts +27 -0
  144. package/src/NativeQuickCrypto/webcrypto.ts +28 -2
  145. package/src/Utils.ts +49 -8
  146. package/src/aes.ts +259 -222
  147. package/src/ec.ts +114 -90
  148. package/src/index.ts +10 -1
  149. package/src/keygen.ts +80 -0
  150. package/src/keys.ts +165 -61
  151. package/src/random.ts +12 -1
  152. package/src/rsa.ts +161 -187
  153. package/src/sig.ts +7 -23
  154. package/src/subtle.ts +309 -35
  155. package/src/webcrypto.ts +8 -0
package/src/ec.ts CHANGED
@@ -1,4 +1,6 @@
1
+ import { generateKeyPairPromise, type GenerateKeyPairOptions } from './Cipher';
1
2
  import { NativeQuickCrypto } from './NativeQuickCrypto/NativeQuickCrypto';
3
+ import { DSASigEnc, SignMode } from './NativeQuickCrypto/sig';
2
4
  import {
3
5
  bufferLikeToArrayBuffer,
4
6
  type BufferLike,
@@ -8,6 +10,8 @@ import {
8
10
  validateKeyOps,
9
11
  hasAnyNotIn,
10
12
  ab2str,
13
+ getUsagesUnion,
14
+ normalizeHashName,
11
15
  } from './Utils';
12
16
  import {
13
17
  type ImportFormat,
@@ -22,7 +26,9 @@ import {
22
26
  type AnyAlgorithm,
23
27
  PrivateKeyObject,
24
28
  KeyType,
29
+ type CryptoKeyPair,
25
30
  } from './keys';
31
+ import type { KeyObjectHandle } from './NativeQuickCrypto/webcrypto';
26
32
 
27
33
  // const {
28
34
  // ArrayPrototypeIncludes,
@@ -114,71 +120,6 @@ function createECPublicKeyRaw(
114
120
  return new PublicKeyObject(handle);
115
121
  }
116
122
 
117
- // async function ecGenerateKey(algorithm, extractable, keyUsages) {
118
- // const { name, namedCurve } = algorithm;
119
-
120
- // if (!ArrayPrototypeIncludes(ObjectKeys(kNamedCurveAliases), namedCurve)) {
121
- // throw lazyDOMException(
122
- // 'Unrecognized namedCurve',
123
- // 'NotSupportedError');
124
- // }
125
-
126
- // const usageSet = new SafeSet(keyUsages);
127
- // switch (name) {
128
- // case 'ECDSA':
129
- // if (hasAnyNotIn(usageSet, ['sign', 'verify'])) {
130
- // throw lazyDOMException(
131
- // 'Unsupported key usage for an ECDSA key',
132
- // 'SyntaxError');
133
- // }
134
- // break;
135
- // case 'ECDH':
136
- // if (hasAnyNotIn(usageSet, ['deriveKey', 'deriveBits'])) {
137
- // throw lazyDOMException(
138
- // 'Unsupported key usage for an ECDH key',
139
- // 'SyntaxError');
140
- // }
141
- // // Fall through
142
- // }
143
-
144
- // const keypair = await generateKeyPair('ec', { namedCurve }).catch((err) => {
145
- // throw lazyDOMException(
146
- // 'The operation failed for an operation-specific reason',
147
- // { name: 'OperationError', cause: err });
148
- // });
149
-
150
- // let publicUsages;
151
- // let privateUsages;
152
- // switch (name) {
153
- // case 'ECDSA':
154
- // publicUsages = getUsagesUnion(usageSet, 'verify');
155
- // privateUsages = getUsagesUnion(usageSet, 'sign');
156
- // break;
157
- // case 'ECDH':
158
- // publicUsages = [];
159
- // privateUsages = getUsagesUnion(usageSet, 'deriveKey', 'deriveBits');
160
- // break;
161
- // }
162
-
163
- // const keyAlgorithm = { name, namedCurve };
164
-
165
- // const publicKey =
166
- // new InternalCryptoKey(
167
- // keypair.publicKey,
168
- // keyAlgorithm,
169
- // publicUsages,
170
- // true);
171
-
172
- // const privateKey =
173
- // new InternalCryptoKey(
174
- // keypair.privateKey,
175
- // keyAlgorithm,
176
- // privateUsages,
177
- // extractable);
178
-
179
- // return { __proto__: null, publicKey, privateKey };
180
- // }
181
-
182
123
  export function ecExportKey(
183
124
  key: CryptoKey,
184
125
  format: KWebCryptoKeyFormat
@@ -310,8 +251,8 @@ export function ecImportKey(
310
251
  case 'ECDSA':
311
252
  // Fall through
312
253
  case 'ECDH':
313
- // if (keyObject.asymmetricKeyType !== 'ec')
314
- // throw new Error('Invalid key type');
254
+ if (keyObject.asymmetricKeyType !== 'ec')
255
+ throw new Error('Invalid key type');
315
256
  break;
316
257
  }
317
258
 
@@ -326,26 +267,109 @@ export function ecImportKey(
326
267
  return new CryptoKey(keyObject, { name, namedCurve }, keyUsages, extractable);
327
268
  }
328
269
 
329
- // function ecdsaSignVerify(key, data, { name, hash }, signature) {
330
- // const mode = signature === undefined ? kSignJobModeSign : kSignJobModeVerify;
331
- // const type = mode === kSignJobModeSign ? 'private' : 'public';
332
-
333
- // if (key.type !== type)
334
- // throw lazyDOMException(`Key must be a ${type} key`, 'InvalidAccessError');
335
-
336
- // const hashname = normalizeHashName(hash.name);
337
-
338
- // return jobPromise(() => new SignJob(
339
- // kCryptoJobAsync,
340
- // mode,
341
- // key[kKeyObject][kHandle],
342
- // undefined,
343
- // undefined,
344
- // undefined,
345
- // data,
346
- // hashname,
347
- // undefined, // Salt length, not used with ECDSA
348
- // undefined, // PSS Padding, not used with ECDSA
349
- // kSigEncP1363,
350
- // signature));
351
- // }
270
+ export const ecdsaSignVerify = (
271
+ key: CryptoKey,
272
+ data: BufferLike,
273
+ { hash }: SubtleAlgorithm,
274
+ signature?: BufferLike
275
+ ) => {
276
+ const mode: SignMode =
277
+ signature === undefined
278
+ ? SignMode.kSignJobModeSign
279
+ : SignMode.kSignJobModeVerify;
280
+ const type = mode === SignMode.kSignJobModeSign ? 'private' : 'public';
281
+
282
+ if (key.type !== type)
283
+ throw lazyDOMException(`Key must be a ${type} key`, 'InvalidAccessError');
284
+
285
+ const hashname = normalizeHashName(hash);
286
+
287
+ return NativeQuickCrypto.webcrypto.signVerify(
288
+ mode,
289
+ key.keyObject.handle,
290
+ // three undefined args because C++ uses `GetPublicOrPrivateKeyFromJs` & friends
291
+ undefined,
292
+ undefined,
293
+ undefined,
294
+ bufferLikeToArrayBuffer(data),
295
+ hashname,
296
+ undefined, // salt length, not used with ECDSA
297
+ undefined, // pss padding, not used with ECDSA
298
+ DSASigEnc.kSigEncP1363,
299
+ bufferLikeToArrayBuffer(signature || new ArrayBuffer(0))
300
+ );
301
+ };
302
+
303
+ export const ecGenerateKey = async (
304
+ algorithm: SubtleAlgorithm,
305
+ extractable: boolean,
306
+ keyUsages: KeyUsage[]
307
+ ): Promise<CryptoKeyPair> => {
308
+ const { name, namedCurve } = algorithm;
309
+
310
+ if (!Object.keys(kNamedCurveAliases).includes(namedCurve || '')) {
311
+ throw lazyDOMException(
312
+ `Unrecognized namedCurve '${namedCurve}'`,
313
+ 'NotSupportedError'
314
+ );
315
+ }
316
+
317
+ // const usageSet = new SafeSet(keyUsages);
318
+ switch (name) {
319
+ case 'ECDSA':
320
+ const checkUsages = ['sign', 'verify'];
321
+ if (hasAnyNotIn(keyUsages, checkUsages)) {
322
+ throw lazyDOMException(
323
+ 'Unsupported key usage for an ECDSA key',
324
+ 'SyntaxError'
325
+ );
326
+ }
327
+ break;
328
+ case 'ECDH':
329
+ if (hasAnyNotIn(keyUsages, ['deriveKey', 'deriveBits'])) {
330
+ throw lazyDOMException(
331
+ 'Unsupported key usage for an ECDH key',
332
+ 'SyntaxError'
333
+ );
334
+ }
335
+ // Fall through
336
+ }
337
+
338
+ const options: GenerateKeyPairOptions = { namedCurve };
339
+ const [err, keypair] = await generateKeyPairPromise('ec', options);
340
+
341
+ if (err) {
342
+ throw lazyDOMException('ecGenerateKey (generateKeyPairPromise) failed', {
343
+ name: 'OperationError',
344
+ cause: err,
345
+ });
346
+ }
347
+
348
+ let publicUsages: KeyUsage[] = [];
349
+ let privateUsages: KeyUsage[] = [];
350
+ switch (name) {
351
+ case 'ECDSA':
352
+ publicUsages = getUsagesUnion(keyUsages, 'verify');
353
+ privateUsages = getUsagesUnion(keyUsages, 'sign');
354
+ break;
355
+ case 'ECDH':
356
+ publicUsages = [];
357
+ privateUsages = getUsagesUnion(keyUsages, 'deriveKey', 'deriveBits');
358
+ break;
359
+ }
360
+
361
+ const keyAlgorithm = { name, namedCurve };
362
+
363
+ const pub = new PublicKeyObject(keypair?.publicKey as KeyObjectHandle);
364
+ const publicKey = new CryptoKey(pub, keyAlgorithm, publicUsages, true);
365
+
366
+ const priv = new PrivateKeyObject(keypair?.privateKey as KeyObjectHandle);
367
+ const privateKey = new CryptoKey(
368
+ priv,
369
+ keyAlgorithm,
370
+ privateUsages,
371
+ extractable
372
+ );
373
+
374
+ return { publicKey, privateKey };
375
+ };
package/src/index.ts CHANGED
@@ -12,15 +12,18 @@ import {
12
12
  generateKeyPair,
13
13
  generateKeyPairSync,
14
14
  } from './Cipher';
15
+ import { generateKey, generateKeySync } from './keygen';
15
16
  import { createSign, createVerify } from './sig';
16
17
  import { createHmac } from './Hmac';
17
18
  import { createHash } from './Hash';
18
19
  import { constants } from './constants';
19
20
  import { subtle } from './subtle';
20
21
  import { getCiphers, getHashes } from './Utils';
22
+ import webcrypto from './webcrypto';
23
+ import { createPrivateKey, createPublicKey, createSecretKey } from './keys';
21
24
 
22
25
  /**
23
- * Loosesly matches Node.js {crypto} with some unimplemented functionality
26
+ * Loosely matches Node.js {crypto} with some unimplemented functionality
24
27
  */
25
28
  const QuickCrypto = {
26
29
  createHmac,
@@ -31,11 +34,16 @@ const QuickCrypto = {
31
34
  createCipheriv,
32
35
  createDecipher,
33
36
  createDecipheriv,
37
+ createPublicKey,
38
+ createPrivateKey,
39
+ createSecretKey,
34
40
  publicEncrypt,
35
41
  publicDecrypt,
36
42
  privateDecrypt,
43
+ generateKey,
37
44
  generateKeyPair,
38
45
  generateKeyPairSync,
46
+ generateKeySync,
39
47
  createSign,
40
48
  createVerify,
41
49
  subtle,
@@ -44,6 +52,7 @@ const QuickCrypto = {
44
52
  ...random,
45
53
  getCiphers,
46
54
  getHashes,
55
+ webcrypto,
47
56
  };
48
57
 
49
58
  /**
package/src/keygen.ts ADDED
@@ -0,0 +1,80 @@
1
+ import { NativeQuickCrypto } from './NativeQuickCrypto/NativeQuickCrypto';
2
+ import { lazyDOMException, validateFunction } from './Utils';
3
+ import { kAesKeyLengths } from './aes';
4
+ import {
5
+ SecretKeyObject,
6
+ type SecretKeyType,
7
+ type AesKeyGenParams,
8
+ } from './keys';
9
+
10
+ export type KeyGenCallback = (
11
+ err: Error | undefined,
12
+ key?: SecretKeyObject
13
+ ) => void;
14
+
15
+ export const generateKeyPromise = (
16
+ type: SecretKeyType,
17
+ options: AesKeyGenParams // | HmacKeyGenParams
18
+ ): Promise<[Error | undefined, SecretKeyObject | undefined]> => {
19
+ return new Promise((resolve, reject) => {
20
+ generateKey(type, options, (err, key) => {
21
+ if (err) {
22
+ reject([err, undefined]);
23
+ }
24
+ resolve([undefined, key]);
25
+ });
26
+ });
27
+ };
28
+
29
+ export const generateKey = (
30
+ type: SecretKeyType,
31
+ options: AesKeyGenParams, // | HmacKeyGenParams,
32
+ callback: KeyGenCallback
33
+ ): void => {
34
+ validateLength(type, options.length);
35
+ if (!validateFunction(callback)) {
36
+ throw lazyDOMException('Callback is not a function', 'SyntaxError');
37
+ }
38
+ NativeQuickCrypto.webcrypto
39
+ .generateSecretKey(options.length)
40
+ .then((handle) => {
41
+ callback(undefined, new SecretKeyObject(handle));
42
+ })
43
+ .catch((err) => {
44
+ callback(err, undefined);
45
+ });
46
+ };
47
+
48
+ export const generateKeySync = (
49
+ type: SecretKeyType,
50
+ options: AesKeyGenParams // | HmacKeyGenParams,
51
+ ): SecretKeyObject => {
52
+ validateLength(type, options.length);
53
+ const handle = NativeQuickCrypto.webcrypto.generateSecretKeySync(
54
+ options.length
55
+ );
56
+ return new SecretKeyObject(handle);
57
+ };
58
+
59
+ const validateLength = (type: SecretKeyType, length: number) => {
60
+ switch (type) {
61
+ case 'aes':
62
+ if (!kAesKeyLengths.includes(length)) {
63
+ throw lazyDOMException(
64
+ 'AES key length must be 128, 192, or 256 bits',
65
+ 'OperationError'
66
+ );
67
+ }
68
+ break;
69
+ case 'hmac':
70
+ if (length < 8 || length > 2 ** 31 - 1) {
71
+ throw lazyDOMException(
72
+ 'HMAC key length must be between 8 and 2^31 - 1',
73
+ 'OperationError'
74
+ );
75
+ }
76
+ break;
77
+ default:
78
+ throw new Error(`Unsupported key type '${type}' for generateKey()`);
79
+ }
80
+ };