@aeternity/aepp-sdk 10.0.0 → 11.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (238) hide show
  1. package/README.md +15 -14
  2. package/dist/aepp-sdk.browser-script.js +1 -1
  3. package/dist/aepp-sdk.browser-script.js.LICENSE.txt +7 -27
  4. package/dist/aepp-sdk.browser-script.js.map +1 -1
  5. package/dist/aepp-sdk.browser.js +1 -1
  6. package/dist/aepp-sdk.browser.js.map +1 -1
  7. package/dist/aepp-sdk.js +1 -1
  8. package/dist/aepp-sdk.js.map +1 -1
  9. package/es/account/{base.js → base.mjs} +20 -10
  10. package/es/account/base.mjs.map +1 -0
  11. package/es/account/{memory.js → memory.mjs} +29 -14
  12. package/es/account/memory.mjs.map +1 -0
  13. package/es/account/{multiple.js → multiple.mjs} +10 -9
  14. package/es/account/multiple.mjs.map +1 -0
  15. package/es/ae/{aens.js → aens.mjs} +18 -22
  16. package/es/ae/aens.mjs.map +1 -0
  17. package/es/ae/{aepp.js → aepp.mjs} +9 -9
  18. package/es/ae/aepp.mjs.map +1 -0
  19. package/es/ae/contract.mjs +159 -0
  20. package/es/ae/contract.mjs.map +1 -0
  21. package/es/ae/{index.js → index.mjs} +8 -7
  22. package/es/ae/index.mjs.map +1 -0
  23. package/es/ae/{oracle.js → oracle.mjs} +33 -16
  24. package/es/ae/oracle.mjs.map +1 -0
  25. package/es/ae/{universal.js → universal.mjs} +10 -10
  26. package/es/ae/universal.mjs.map +1 -0
  27. package/es/ae/{wallet.js → wallet.mjs} +10 -10
  28. package/es/ae/wallet.mjs.map +1 -0
  29. package/es/aepp-wallet-communication/schema.d.ts +74 -0
  30. package/es/bignumber.d.ts +1 -7
  31. package/es/chain/{index.js → index.mjs} +20 -4
  32. package/es/chain/index.mjs.map +1 -0
  33. package/es/chain/{node.js → node.mjs} +121 -73
  34. package/es/chain/node.mjs.map +1 -0
  35. package/es/channel/{handlers.js → handlers.mjs} +18 -20
  36. package/es/channel/handlers.mjs.map +1 -0
  37. package/es/channel/{index.js → index.mjs} +7 -7
  38. package/es/channel/index.mjs.map +1 -0
  39. package/es/channel/{internal.js → internal.mjs} +49 -32
  40. package/es/channel/internal.mjs.map +1 -0
  41. package/es/contract/aci.mjs +477 -0
  42. package/es/contract/aci.mjs.map +1 -0
  43. package/es/contract/compiler.mjs +115 -0
  44. package/es/contract/compiler.mjs.map +1 -0
  45. package/es/contract/ga/helpers.mjs +30 -0
  46. package/es/contract/ga/helpers.mjs.map +1 -0
  47. package/es/contract/ga/{index.js → index.mjs} +36 -28
  48. package/es/contract/ga/index.mjs.map +1 -0
  49. package/es/errors.d.ts +284 -0
  50. package/es/index.mjs +57 -0
  51. package/es/index.mjs.map +1 -0
  52. package/es/node-pool/{index.js → index.mjs} +11 -10
  53. package/es/node-pool/index.mjs.map +1 -0
  54. package/es/{node.js → node.mjs} +9 -8
  55. package/es/node.mjs.map +1 -0
  56. package/es/tx/builder/field-types.mjs +74 -0
  57. package/es/tx/builder/field-types.mjs.map +1 -0
  58. package/es/tx/builder/{helpers.js → helpers.mjs} +114 -56
  59. package/es/tx/builder/helpers.mjs.map +1 -0
  60. package/es/tx/builder/{index.js → index.mjs} +79 -68
  61. package/es/tx/builder/index.mjs.map +1 -0
  62. package/es/tx/builder/{schema.js → schema.mjs} +11 -65
  63. package/es/tx/builder/schema.mjs.map +1 -0
  64. package/es/tx/{index.js → index.mjs} +5 -2
  65. package/es/tx/index.mjs.map +1 -0
  66. package/es/tx/{tx-object.js → tx-object.mjs} +22 -15
  67. package/es/tx/tx-object.mjs.map +1 -0
  68. package/es/tx/{tx.js → tx.mjs} +15 -14
  69. package/es/tx/tx.mjs.map +1 -0
  70. package/es/tx/{validator.js → validator.mjs} +72 -33
  71. package/es/tx/validator.mjs.map +1 -0
  72. package/es/typings/blakejs/index.d.mjs +2 -0
  73. package/es/typings/blakejs/{index.d.js.map → index.d.mjs.map} +1 -1
  74. package/es/utils/aepp-wallet-communication/connection/{browser-runtime.js → browser-runtime.mjs} +7 -6
  75. package/es/utils/aepp-wallet-communication/connection/browser-runtime.mjs.map +1 -0
  76. package/es/utils/aepp-wallet-communication/connection/{browser-window-message.js → browser-window-message.mjs} +10 -11
  77. package/es/utils/aepp-wallet-communication/connection/browser-window-message.mjs.map +1 -0
  78. package/es/utils/aepp-wallet-communication/connection/{index.js → index.mjs} +5 -2
  79. package/es/utils/aepp-wallet-communication/connection/index.mjs.map +1 -0
  80. package/es/utils/aepp-wallet-communication/{content-script-bridge.js → content-script-bridge.mjs} +6 -5
  81. package/es/utils/aepp-wallet-communication/content-script-bridge.mjs.map +1 -0
  82. package/es/utils/aepp-wallet-communication/{helpers.js → helpers.mjs} +3 -14
  83. package/es/utils/aepp-wallet-communication/helpers.mjs.map +1 -0
  84. package/es/utils/aepp-wallet-communication/rpc/{aepp-rpc.js → aepp-rpc.mjs} +113 -67
  85. package/es/utils/aepp-wallet-communication/rpc/aepp-rpc.mjs.map +1 -0
  86. package/es/utils/aepp-wallet-communication/rpc/{rpc-client.js → rpc-client.mjs} +14 -9
  87. package/es/utils/aepp-wallet-communication/rpc/rpc-client.mjs.map +1 -0
  88. package/es/utils/aepp-wallet-communication/rpc/{wallet-rpc.js → wallet-rpc.mjs} +71 -63
  89. package/es/utils/aepp-wallet-communication/rpc/wallet-rpc.mjs.map +1 -0
  90. package/es/utils/aepp-wallet-communication/schema.mjs +102 -0
  91. package/es/utils/aepp-wallet-communication/schema.mjs.map +1 -0
  92. package/es/utils/aepp-wallet-communication/{wallet-detector.js → wallet-detector.mjs} +6 -5
  93. package/es/utils/aepp-wallet-communication/wallet-detector.mjs.map +1 -0
  94. package/es/utils/{amount-formatter.js → amount-formatter.mjs} +14 -7
  95. package/es/utils/amount-formatter.mjs.map +1 -0
  96. package/es/utils/{async-init.js → async-init.mjs} +8 -11
  97. package/es/utils/async-init.mjs.map +1 -0
  98. package/es/utils/{bignumber.js → bignumber.mjs} +2 -9
  99. package/es/utils/bignumber.mjs.map +1 -0
  100. package/es/utils/{bytes.js → bytes.mjs} +16 -8
  101. package/es/utils/bytes.mjs.map +1 -0
  102. package/es/utils/{crypto-ts.js → crypto-ts.mjs} +11 -3
  103. package/es/utils/crypto-ts.mjs.map +1 -0
  104. package/es/utils/{crypto.js → crypto.mjs} +40 -105
  105. package/es/utils/crypto.mjs.map +1 -0
  106. package/es/utils/errors.mjs +689 -0
  107. package/es/utils/errors.mjs.map +1 -0
  108. package/es/utils/{hd-wallet.js → hd-wallet.mjs} +33 -34
  109. package/es/utils/hd-wallet.mjs.map +1 -0
  110. package/es/utils/{json-big.js → json-big.mjs} +1 -1
  111. package/es/utils/{json-big.js.map → json-big.mjs.map} +1 -1
  112. package/es/utils/{keystore.js → keystore.mjs} +63 -51
  113. package/es/utils/keystore.mjs.map +1 -0
  114. package/es/utils/{mptree.js → mptree.mjs} +21 -12
  115. package/es/utils/mptree.mjs.map +1 -0
  116. package/es/utils/{other.js → other.mjs} +2 -2
  117. package/es/utils/other.mjs.map +1 -0
  118. package/es/utils/{semver-satisfies.js → semver-satisfies.mjs} +1 -1
  119. package/es/utils/{semver-satisfies.js.map → semver-satisfies.mjs.map} +1 -1
  120. package/es/utils/{string.js → string.mjs} +1 -1
  121. package/es/utils/{string.js.map → string.mjs.map} +1 -1
  122. package/es/utils/{swagger.js → swagger.mjs} +46 -14
  123. package/es/utils/swagger.mjs.map +1 -0
  124. package/package.json +46 -55
  125. package/src/account/memory.js +13 -8
  126. package/src/account/multiple.js +12 -4
  127. package/src/ae/aens.js +12 -17
  128. package/src/ae/aepp.js +2 -2
  129. package/src/ae/contract.js +15 -152
  130. package/src/ae/index.js +2 -1
  131. package/src/ae/oracle.js +25 -10
  132. package/src/ae/universal.js +2 -2
  133. package/src/ae/wallet.js +2 -2
  134. package/src/chain/index.js +21 -2
  135. package/src/chain/node.js +80 -53
  136. package/src/channel/handlers.js +20 -17
  137. package/src/channel/internal.js +30 -24
  138. package/src/contract/{aci/index.js → aci.js} +152 -93
  139. package/src/contract/compiler.js +22 -117
  140. package/src/contract/ga/helpers.js +7 -5
  141. package/src/contract/ga/index.js +27 -24
  142. package/src/index.js +7 -8
  143. package/src/node-pool/index.js +9 -8
  144. package/src/node.js +5 -7
  145. package/src/tx/builder/field-types.js +61 -0
  146. package/src/tx/builder/helpers.js +113 -58
  147. package/src/tx/builder/index.js +39 -34
  148. package/src/tx/builder/schema.js +11 -25
  149. package/src/tx/tx-object.js +10 -9
  150. package/src/tx/tx.js +17 -8
  151. package/src/tx/validator.js +25 -5
  152. package/src/utils/aepp-wallet-communication/connection/browser-runtime.js +8 -3
  153. package/src/utils/aepp-wallet-communication/connection/browser-window-message.js +10 -6
  154. package/src/utils/aepp-wallet-communication/content-script-bridge.js +5 -4
  155. package/src/utils/aepp-wallet-communication/helpers.js +2 -12
  156. package/src/utils/aepp-wallet-communication/rpc/aepp-rpc.js +81 -55
  157. package/src/utils/aepp-wallet-communication/rpc/rpc-client.js +15 -6
  158. package/src/utils/aepp-wallet-communication/rpc/wallet-rpc.js +60 -49
  159. package/src/utils/aepp-wallet-communication/schema.ts +80 -0
  160. package/src/utils/aepp-wallet-communication/wallet-detector.js +3 -2
  161. package/src/utils/amount-formatter.ts +4 -3
  162. package/src/utils/async-init.js +10 -6
  163. package/src/utils/bignumber.ts +1 -9
  164. package/src/utils/bytes.ts +3 -2
  165. package/src/utils/crypto-ts.ts +2 -2
  166. package/src/utils/crypto.js +9 -92
  167. package/src/utils/errors.ts +683 -0
  168. package/src/utils/hd-wallet.js +11 -26
  169. package/src/utils/keystore.js +47 -51
  170. package/src/utils/mptree.ts +12 -6
  171. package/src/utils/swagger.js +67 -44
  172. package/CHANGELOG.md +0 -1603
  173. package/es/account/base.js.map +0 -1
  174. package/es/account/memory.js.map +0 -1
  175. package/es/account/multiple.js.map +0 -1
  176. package/es/ae/aens.js.map +0 -1
  177. package/es/ae/aepp.js.map +0 -1
  178. package/es/ae/contract.js +0 -312
  179. package/es/ae/contract.js.map +0 -1
  180. package/es/ae/index.js.map +0 -1
  181. package/es/ae/oracle.js.map +0 -1
  182. package/es/ae/universal.js.map +0 -1
  183. package/es/ae/wallet.js.map +0 -1
  184. package/es/chain/index.js.map +0 -1
  185. package/es/chain/node.js.map +0 -1
  186. package/es/channel/handlers.js.map +0 -1
  187. package/es/channel/index.js.map +0 -1
  188. package/es/channel/internal.js.map +0 -1
  189. package/es/contract/aci/helpers.js +0 -298
  190. package/es/contract/aci/helpers.js.map +0 -1
  191. package/es/contract/aci/index.js +0 -361
  192. package/es/contract/aci/index.js.map +0 -1
  193. package/es/contract/aci/transformation.js +0 -66
  194. package/es/contract/aci/transformation.js.map +0 -1
  195. package/es/contract/compiler.js +0 -244
  196. package/es/contract/compiler.js.map +0 -1
  197. package/es/contract/ga/helpers.js +0 -22
  198. package/es/contract/ga/helpers.js.map +0 -1
  199. package/es/contract/ga/index.js.map +0 -1
  200. package/es/contract/index.js +0 -162
  201. package/es/contract/index.js.map +0 -1
  202. package/es/index.js +0 -57
  203. package/es/index.js.map +0 -1
  204. package/es/node-pool/index.js.map +0 -1
  205. package/es/node.js.map +0 -1
  206. package/es/tx/builder/helpers.js.map +0 -1
  207. package/es/tx/builder/index.js.map +0 -1
  208. package/es/tx/builder/schema.js.map +0 -1
  209. package/es/tx/index.js.map +0 -1
  210. package/es/tx/tx-object.js.map +0 -1
  211. package/es/tx/tx.js.map +0 -1
  212. package/es/tx/validator.js.map +0 -1
  213. package/es/typings/blakejs/index.d.js +0 -2
  214. package/es/utils/aepp-wallet-communication/connection/browser-runtime.js.map +0 -1
  215. package/es/utils/aepp-wallet-communication/connection/browser-window-message.js.map +0 -1
  216. package/es/utils/aepp-wallet-communication/connection/index.js.map +0 -1
  217. package/es/utils/aepp-wallet-communication/content-script-bridge.js.map +0 -1
  218. package/es/utils/aepp-wallet-communication/helpers.js.map +0 -1
  219. package/es/utils/aepp-wallet-communication/rpc/aepp-rpc.js.map +0 -1
  220. package/es/utils/aepp-wallet-communication/rpc/rpc-client.js.map +0 -1
  221. package/es/utils/aepp-wallet-communication/rpc/wallet-rpc.js.map +0 -1
  222. package/es/utils/aepp-wallet-communication/schema.js +0 -107
  223. package/es/utils/aepp-wallet-communication/schema.js.map +0 -1
  224. package/es/utils/aepp-wallet-communication/wallet-detector.js.map +0 -1
  225. package/es/utils/amount-formatter.js.map +0 -1
  226. package/es/utils/async-init.js.map +0 -1
  227. package/es/utils/bignumber.js.map +0 -1
  228. package/es/utils/bytes.js.map +0 -1
  229. package/es/utils/crypto-ts.js.map +0 -1
  230. package/es/utils/crypto.js.map +0 -1
  231. package/es/utils/hd-wallet.js.map +0 -1
  232. package/es/utils/keystore.js.map +0 -1
  233. package/es/utils/mptree.js.map +0 -1
  234. package/es/utils/other.js.map +0 -1
  235. package/es/utils/swagger.js.map +0 -1
  236. package/src/contract/aci/transformation.js +0 -72
  237. package/src/contract/index.js +0 -163
  238. package/src/utils/aepp-wallet-communication/schema.js +0 -108
@@ -1,8 +1,11 @@
1
1
  import nacl from 'tweetnacl'
2
2
  import { full as hmac } from 'tweetnacl-auth'
3
3
  import { fromString } from 'bip32-path'
4
- import { validateMnemonic, mnemonicToSeed, generateMnemonic as genMnemonic } from '@aeternity/bip39'
5
- import { decryptKey, encodeBase58Check, encryptKey } from './crypto'
4
+ import { decryptKey, encryptKey } from './crypto'
5
+ import { encode } from '../tx/builder/helpers'
6
+ import {
7
+ InvalidDerivationPathError, NotHardenedSegmentError, UnsupportedChildIndexError
8
+ } from './errors'
6
9
 
7
10
  const ED25519_CURVE = Buffer.from('ed25519 seed')
8
11
  const HARDENED_OFFSET = 0x80000000
@@ -13,7 +16,7 @@ export function derivePathFromKey (path, key) {
13
16
  const segments = path === '' ? [] : fromString(path).toPathArray()
14
17
  segments.forEach((segment, i) => {
15
18
  if (segment < HARDENED_OFFSET) {
16
- throw new Error(`Segment #${i + 1} is not hardened`)
19
+ throw new NotHardenedSegmentError(`Segment #${i + 1} is not hardened`)
17
20
  }
18
21
  })
19
22
 
@@ -22,7 +25,7 @@ export function derivePathFromKey (path, key) {
22
25
 
23
26
  export function derivePathFromSeed (path, seed) {
24
27
  if (!['m', 'm/'].includes(path.slice(0, 2))) {
25
- throw new Error('Invalid path')
28
+ throw new InvalidDerivationPathError()
26
29
  }
27
30
  const masterKey = getMasterKeyFromSeed(seed)
28
31
  return derivePathFromKey(path.slice(2), masterKey)
@@ -32,7 +35,7 @@ function formatAccount (keys) {
32
35
  const { secretKey, publicKey } = keys
33
36
  return {
34
37
  secretKey: toHex(secretKey),
35
- publicKey: `ak_${encodeBase58Check(publicKey)}`
38
+ publicKey: encode(publicKey, 'ak')
36
39
  }
37
40
  }
38
41
 
@@ -40,10 +43,6 @@ export function getKeyPair (secretKey) {
40
43
  return nacl.sign.keyPair.fromSeed(secretKey)
41
44
  }
42
45
 
43
- export function generateMnemonic () {
44
- return genMnemonic()
45
- }
46
-
47
46
  export function getMasterKeyFromSeed (seed) {
48
47
  const I = hmac(seed, ED25519_CURVE)
49
48
  const IL = I.slice(0, 32)
@@ -56,7 +55,7 @@ export function getMasterKeyFromSeed (seed) {
56
55
 
57
56
  export function deriveChild ({ secretKey, chainCode }, index) {
58
57
  if (index < HARDENED_OFFSET) {
59
- throw new Error(`Child index #${index} is not supported`)
58
+ throw new UnsupportedChildIndexError(index)
60
59
  }
61
60
  const indexBuffer = Buffer.allocUnsafe(4)
62
61
  indexBuffer.writeUInt32BE(index, 0)
@@ -72,11 +71,7 @@ export function deriveChild ({ secretKey, chainCode }, index) {
72
71
  }
73
72
  }
74
73
 
75
- export function generateSaveHDWallet (mnemonic, password) {
76
- if (!validateMnemonic(mnemonic)) {
77
- throw new Error('Invalid mnemonic')
78
- }
79
- const seed = mnemonicToSeed(mnemonic)
74
+ export function generateSaveHDWalletFromSeed (seed, password) {
80
75
  const walletKey = derivePathFromSeed('m/44h/457h', seed)
81
76
  return {
82
77
  secretKey: toHex(encryptKey(password, walletKey.secretKey)),
@@ -94,8 +89,7 @@ export function getSaveHDWalletAccounts (saveHDWallet, password, accountCount) {
94
89
  formatAccount(getKeyPair(derivePathFromKey(`${idx}h/0h/0h`, walletKey).secretKey)))
95
90
  }
96
91
 
97
- export const getHdWalletAccountFromMnemonic = (mnemonic, accountIdx) => {
98
- const seed = mnemonicToSeed(mnemonic)
92
+ export const getHdWalletAccountFromSeed = (seed, accountIdx) => {
99
93
  const walletKey = derivePathFromSeed('m/44h/457h', seed)
100
94
  const derived = derivePathFromKey(`${accountIdx}h/0h/0h`, walletKey)
101
95
  const keyPair = getKeyPair(derived.secretKey)
@@ -104,12 +98,3 @@ export const getHdWalletAccountFromMnemonic = (mnemonic, accountIdx) => {
104
98
  idx: accountIdx
105
99
  }
106
100
  }
107
-
108
- export default {
109
- getHdWalletAccountFromMnemonic,
110
- getSaveHDWalletAccounts,
111
- generateSaveHDWallet,
112
- generateMnemonic,
113
- deriveChild,
114
- getMasterKeyFromSeed
115
- }
@@ -1,10 +1,11 @@
1
1
  import nacl from 'tweetnacl'
2
- import { v4 as uuid } from 'uuid'
3
-
4
- import { encodeBase58Check } from './crypto'
2
+ import { v4 as uuid } from '@aeternity/uuid'
3
+ import { ArgonType, hash } from '@aeternity/argon2-browser/dist/argon2-bundled.min.js'
4
+ import { encode } from '../tx/builder/helpers'
5
5
  import { str2buf } from './bytes'
6
-
7
- const _sodium = require('libsodium-wrappers-sumo')
6
+ import {
7
+ ArgumentError, InvalidKeyError, UnsupportedAlgorithmError, InvalidPasswordError
8
+ } from './errors'
8
9
 
9
10
  /**
10
11
  * KeyStore module
@@ -31,24 +32,18 @@ const DERIVED_KEY_FUNCTIONS = {
31
32
  argon2id: deriveKeyUsingArgon2id
32
33
  }
33
34
 
34
- export async function deriveKeyUsingArgon2id (password, salt, options) {
35
- const { memlimit_kib: memoryCost, opslimit: timeCost } = options.kdf_params
36
- // const isBrowser = !(typeof module !== 'undefined' && module.exports)
37
-
38
- return _sodium.ready.then(async () => {
39
- // tslint:disable-next-line:typedef
40
- const sodium = _sodium
41
-
42
- const result = sodium.crypto_pwhash(
43
- 32,
44
- password,
45
- salt,
46
- timeCost,
47
- memoryCost * 1024,
48
- sodium.crypto_pwhash_ALG_ARGON2ID13
49
- )
50
- return Buffer.from(result)
51
- })
35
+ export async function deriveKeyUsingArgon2id (pass, salt, options) {
36
+ const { memlimit_kib: mem, opslimit: time } = options.kdf_params
37
+
38
+ const result = (await hash({
39
+ hashLen: 32,
40
+ pass,
41
+ salt,
42
+ time,
43
+ mem,
44
+ type: ArgonType.Argon2id
45
+ })).hash
46
+ return Buffer.from(result)
52
47
  }
53
48
 
54
49
  // CRYPTO PART
@@ -62,65 +57,66 @@ function encryptXsalsa20Poly1305 ({ plaintext, key, nonce }) {
62
57
 
63
58
  function decryptXsalsa20Poly1305 ({ ciphertext, key, nonce }) {
64
59
  const res = nacl.secretbox.open(ciphertext, nonce, key)
65
- if (!res) throw new Error('Invalid password or nonce')
60
+ if (!res) throw new InvalidPasswordError('Invalid password or nonce')
66
61
  return res
67
62
  }
68
63
 
69
64
  /**
70
65
  * Symmetric private key encryption using secret (derived) key.
71
- * @param {buffer|string} plaintext Data to be encrypted.
72
- * @param {buffer|string} key Secret key.
73
- * @param {buffer|string} nonce Randomly generated nonce.
66
+ * @param {Buffer|string} plaintext Data to be encrypted.
67
+ * @param {Buffer|string} key Secret key.
68
+ * @param {Buffer|string} nonce Randomly generated nonce.
74
69
  * @param {string=} algo Encryption algorithm (default: DEFAULTS.crypto.symmetric_alg).
75
- * @return {buffer} Encrypted data.
70
+ * @return {Buffer} Encrypted data.
76
71
  */
77
72
  function encrypt (plaintext, key, nonce, algo = DEFAULTS.crypto.symmetric_alg) {
78
- if (!CRYPTO_FUNCTIONS[algo]) throw new Error(algo + ' is not available')
73
+ if (!CRYPTO_FUNCTIONS[algo]) throw new UnsupportedAlgorithmError(algo)
79
74
  return CRYPTO_FUNCTIONS[algo].encrypt({ plaintext, nonce, key })
80
75
  }
81
76
 
82
77
  /**
83
78
  * Symmetric private key decryption using secret (derived) key.
84
- * @param {buffer|Uint8Array} ciphertext Data to be decrypted.
85
- * @param {buffer|Uint8Array} key Secret key.
86
- * @param {buffer|Uint8Array} nonce Nonce from key-object.
79
+ * @param {Buffer|Uint8Array} ciphertext Data to be decrypted.
80
+ * @param {Buffer|Uint8Array} key Secret key.
81
+ * @param {Buffer|Uint8Array} nonce Nonce from key-object.
87
82
  * @param {string=} algo Encryption algorithm.
88
- * @return {buffer} Decrypted data.
83
+ * @return {Buffer} Decrypted data.
89
84
  */
90
85
  function decrypt (ciphertext, key, nonce, algo) {
91
- if (!CRYPTO_FUNCTIONS[algo]) throw new Error(algo + ' is not available')
86
+ if (!CRYPTO_FUNCTIONS[algo]) throw new UnsupportedAlgorithmError(algo)
92
87
  return CRYPTO_FUNCTIONS[algo].decrypt({ ciphertext, nonce, key })
93
88
  }
94
89
 
95
90
  /**
96
91
  * Derive secret key from password with key derivation function.
97
92
  * @param {string} password User-supplied password.
98
- * @param {buffer|Uint8Array} nonce Randomly generated nonce.
93
+ * @param {Buffer|Uint8Array} nonce Randomly generated nonce.
99
94
  * @param {Object=} options Encryption parameters.
100
95
  * @param {string=} options.kdf Key derivation function (default: DEFAULTS.crypto.kdf).
101
96
  * @param {Object=} options.kdf_params KDF parameters (default: DEFAULTS.crypto.kdf_params).
102
- * @return {buffer} Secret key derived from password.
97
+ * @return {Buffer} Secret key derived from password.
103
98
  */
104
99
  async function deriveKey (password, nonce, options = {
105
100
  kdf_params: DEFAULTS.crypto.kdf_params,
106
101
  kdf: DEFAULTS.crypto.kdf
107
102
  }) {
108
- if (typeof password === 'undefined' || password === null || !nonce) {
109
- throw new Error('Must provide password and nonce to derive a key')
110
- }
103
+ if (!nonce) throw new ArgumentError('nonce', 'provided', nonce)
104
+ if (password == null) throw new ArgumentError('password', 'provided', password)
111
105
 
112
- if (!Object.prototype.hasOwnProperty.call(DERIVED_KEY_FUNCTIONS, options.kdf)) throw new Error('Unsupported kdf type')
106
+ if (!Object.prototype.hasOwnProperty.call(DERIVED_KEY_FUNCTIONS, options.kdf)) {
107
+ throw new UnsupportedAlgorithmError(options.kdf)
108
+ }
113
109
 
114
110
  return DERIVED_KEY_FUNCTIONS[options.kdf](password, nonce, options)
115
111
  }
116
112
 
117
113
  /**
118
114
  * Assemble key data object in secret-storage format.
119
- * @param {buffer} name Key name.
120
- * @param {buffer} derivedKey Password-derived secret key.
121
- * @param {buffer} privateKey Private key.
122
- * @param {buffer} nonce Randomly generated 24byte nonce.
123
- * @param {buffer} salt Randomly generated 16byte salt.
115
+ * @param {Buffer} name Key name.
116
+ * @param {Buffer} derivedKey Password-derived secret key.
117
+ * @param {Buffer} privateKey Private key.
118
+ * @param {Buffer} nonce Randomly generated 24byte nonce.
119
+ * @param {Buffer} salt Randomly generated 16byte salt.
124
120
  * @param {Object=} options Encryption parameters.
125
121
  * @param {string=} options.kdf Key derivation function (default: argon2id).
126
122
  * @param {string=} options.cipher Symmetric cipher (default: constants.cipher).
@@ -148,7 +144,7 @@ function marshal (name, derivedKey, privateKey, nonce, salt, options = {}) {
148
144
  export function getAddressFromPriv (secret) {
149
145
  const keys = nacl.sign.keyPair.fromSecretKey(str2buf(secret))
150
146
  const publicBuffer = Buffer.from(keys.publicKey)
151
- return `ak_${encodeBase58Check(publicBuffer)}`
147
+ return encode(publicBuffer, 'ak')
152
148
  }
153
149
 
154
150
  /**
@@ -170,7 +166,7 @@ export async function recover (password, keyObject) {
170
166
  nonce,
171
167
  keyObject.crypto.symmetric_alg
172
168
  )
173
- if (!key) throw new Error('Invalid password')
169
+ if (!key) throw new InvalidPasswordError('Invalid password')
174
170
 
175
171
  if (Buffer.from(key).length === 64) return Buffer.from(key).toString('hex')
176
172
  return Buffer.from(key).toString('utf-8')
@@ -180,7 +176,7 @@ export async function recover (password, keyObject) {
180
176
  * Export private key to keystore secret-storage format.
181
177
  * @param {String} name Key name.
182
178
  * @param {String} password User-supplied password.
183
- * @param {String} privateKey Private key.
179
+ * @param {String|Buffer} privateKey Private key as hex-string or a Buffer.
184
180
  * @param {Buffer} nonce Randomly generated 24byte nonce.
185
181
  * @param {Buffer} salt Randomly generated 16byte salt.
186
182
  * @param {Object=} options Encryption parameters.
@@ -201,7 +197,7 @@ export async function dump (
201
197
  return marshal(
202
198
  name,
203
199
  await deriveKey(password, salt, opt),
204
- privateKey,
200
+ typeof privateKey === 'string' ? Buffer.from(privateKey, 'hex') : privateKey,
205
201
  nonce,
206
202
  salt,
207
203
  opt
@@ -213,11 +209,11 @@ export function validateKeyObj (obj) {
213
209
  const cryptoKeys = ['cipher_params', 'ciphertext', 'symmetric_alg', 'kdf', 'kdf_params']
214
210
 
215
211
  const missingRootKeys = root.filter(key => !Object.prototype.hasOwnProperty.call(obj, key))
216
- if (missingRootKeys.length) throw new Error(`Invalid key file format. Require properties: ${missingRootKeys}`)
212
+ if (missingRootKeys.length) throw new InvalidKeyError(`Invalid key file format. Require properties: ${missingRootKeys}`)
217
213
 
218
214
  const missingCryptoKeys = cryptoKeys
219
215
  .filter(key => !Object.prototype.hasOwnProperty.call(obj.crypto, key))
220
- if (missingCryptoKeys.length) throw new Error(`Invalid key file format. Require properties: ${missingCryptoKeys}`)
216
+ if (missingCryptoKeys.length) throw new InvalidKeyError(`Invalid key file format. Require properties: ${missingCryptoKeys}`)
221
217
 
222
218
  return true
223
219
  }
@@ -18,6 +18,12 @@
18
18
  import { encode as rlpEncode } from 'rlp'
19
19
  import type { Input } from 'rlp'
20
20
  import { hash } from './crypto-ts'
21
+ import {
22
+ MerkleTreeHashMismatchError,
23
+ MissingNodeInTreeError,
24
+ UnknownPathNibbleError,
25
+ UnknownNodeLengthError
26
+ } from './errors'
21
27
 
22
28
  enum NodeType {
23
29
  Branch,
@@ -47,9 +53,9 @@ export default class MPTree {
47
53
  binary[1].map((node) => [node[0].toString('hex'), node[1]])
48
54
  )
49
55
 
50
- if (this.nodes[this.rootHash] === undefined) throw new Error('Can\'t find a node by root hash')
56
+ if (this.nodes[this.rootHash] === undefined) throw new MissingNodeInTreeError('Can\'t find a node by root hash')
51
57
  Object.entries(this.nodes).forEach(([key, node]) => {
52
- if (MPTree.nodeHash(node) !== key) throw new Error('Node hash is not equal to provided one')
58
+ if (MPTree.nodeHash(node) !== key) throw new MerkleTreeHashMismatchError()
53
59
  const { type, payload } = MPTree.parseNode(node)
54
60
  switch (type) {
55
61
  case NodeType.Branch:
@@ -58,13 +64,13 @@ export default class MPTree {
58
64
  .filter(n => n.length)
59
65
  .forEach((n) => {
60
66
  if (this.nodes[n.toString('hex')] === undefined) {
61
- throw new Error('Can\'t find a node by hash in branch node')
67
+ throw new MissingNodeInTreeError('Can\'t find a node by hash in branch node')
62
68
  }
63
69
  })
64
70
  break
65
71
  case NodeType.Extension:
66
72
  if (this.nodes[payload[0].toString('hex')] === undefined) {
67
- throw new Error('Can\'t find a node by hash in extension node')
73
+ throw new MissingNodeInTreeError('Can\'t find a node by hash in extension node')
68
74
  }
69
75
  }
70
76
  })
@@ -81,13 +87,13 @@ export default class MPTree {
81
87
  case 2: {
82
88
  const path = node[0].toString('hex')
83
89
  const nibble = parseInt(path[0], 16)
84
- if (nibble > 3) throw new Error(`Unknown path nibble: ${nibble}`)
90
+ if (nibble > 3) throw new UnknownPathNibbleError(nibble)
85
91
  const type = nibble <= 1 ? NodeType.Extension : NodeType.Leaf
86
92
  const slice = [0, 2].includes(nibble) ? 2 : 1
87
93
  return { type, payload: [node[1]], path: path.slice(slice) }
88
94
  }
89
95
  default:
90
- throw new Error(`Unknown node length: ${node.length}`)
96
+ throw new UnknownNodeLengthError(node.length)
91
97
  }
92
98
  }
93
99
 
@@ -25,6 +25,8 @@ import SwaggerClient from 'swagger-client'
25
25
  import fetch from 'cross-fetch'
26
26
  import JsonBig from './json-big'
27
27
  import { snakizeKeys, pascalizeKeys, mapObject, filterObject } from './other'
28
+ import { ArgumentCountMismatchError } from './errors'
29
+ import { snakeToPascal } from './string'
28
30
 
29
31
  let warnedAboutInternalApiUsage = false
30
32
 
@@ -50,21 +52,27 @@ export default async (
50
52
  spec = spec || await (await fetch(specUrl)).json()
51
53
  const jsonImp = disableBigNumbers ? JSON : JsonBig
52
54
 
53
- if (
54
- [
55
- 'https://compiler.aepps.com',
56
- 'https://latest.compiler.aepps.com'
57
- ].includes(new URL(specUrl).origin) ||
58
- new URL(specUrl).origin.includes('https://')
59
- ) {
60
- spec.schemes = ['https']
61
- }
62
-
63
55
  const [external, internal] = await Promise.all([specUrl, internalUrl].map((url) => {
64
56
  if (!url) return null
57
+ const pendingGetRequests = {}
65
58
  return SwaggerClient({
66
59
  url,
67
60
  spec,
61
+ requestInterceptor: request => {
62
+ if (request.method !== 'GET') return
63
+ return {
64
+ ...request,
65
+ userFetch: async (url, request) => {
66
+ const key = JSON.stringify({ ...request, url })
67
+ pendingGetRequests[key] ??= fetch(url, request)
68
+ try {
69
+ return (await pendingGetRequests[key]).clone()
70
+ } finally {
71
+ delete pendingGetRequests[key]
72
+ }
73
+ }
74
+ }
75
+ },
68
76
  responseInterceptor: response => {
69
77
  if (response.text === '' || response.text?.size === 0) return response
70
78
  const body = jsonImp.parse(response.text)
@@ -76,8 +84,9 @@ export default async (
76
84
  })
77
85
  }))
78
86
 
79
- const combinedApi = [
80
- ...Object.values(external.apis),
87
+ const combinedApi = Object.assign(
88
+ {},
89
+ ...external.apis.external ? [external.apis.external] : Object.values(external.apis),
81
90
  mapObject(internal?.apis.internal || {}, ([key, handler]) => [key, (...args) => {
82
91
  if (!warnedAboutInternalApiUsage) {
83
92
  console.warn(
@@ -89,45 +98,59 @@ export default async (
89
98
  }
90
99
  return handler(...args)
91
100
  }])
92
- ].reduce((acc, n) => ({ ...acc, ...n }))
101
+ )
93
102
 
94
103
  const opSpecs = Object.values(spec.paths)
95
104
  .map(paths => Object.values(paths))
96
105
  .flat()
97
106
  .reduce((acc, n) => ({ ...acc, [n.operationId]: n }), {})
98
107
 
99
- const api = mapObject(combinedApi, ([opId, handler]) => [
100
- opId.slice(0, 1).toLowerCase() + opId.slice(1),
101
- async (...args) => {
102
- const opSpec = opSpecs[opId]
103
- const parameters = [
104
- ...opSpec.parameters,
105
- ...opSpec.requestBody
106
- ? [{
107
- required: opSpec.requestBody.required,
108
- schema: Object.values(opSpec.requestBody.content)[0].schema,
109
- name: '__requestBody'
110
- }]
111
- : []
112
- ]
113
- const required = parameters.filter(param => param.required).map(p => p.name)
114
- if (args.length < required.length) throw new Error('swagger: Not enough arguments')
115
- const values = required.reduce(
116
- (acc, req, idx) => ({ ...acc, [req]: args[idx] }),
117
- args[required.length] || {}
118
- )
119
- const { __requestBody, ...stringified } = mapObject(values, ([param, value]) => {
120
- if (typeof value !== 'object') return [param, value]
121
- const rootKeys = Object.keys(parameters.find(p => p.name === param).schema.properties)
122
- const filteredValue = filterObject(
123
- disableCaseConversion ? value : snakizeKeys(value),
124
- ([key]) => rootKeys.includes(key)
108
+ const requestQueues = {}
109
+ const api = mapObject(combinedApi, ([opId, handler]) => {
110
+ const functionName = opId.slice(0, 1).toLowerCase() + snakeToPascal(opId.slice(1))
111
+ return [
112
+ functionName,
113
+ async (...args) => {
114
+ const opSpec = opSpecs[opId]
115
+ const parameters = [
116
+ ...opSpec.parameters,
117
+ ...opSpec.requestBody
118
+ ? [{
119
+ required: opSpec.requestBody.required,
120
+ schema: Object.values(opSpec.requestBody.content)[0].schema,
121
+ name: '__requestBody'
122
+ }]
123
+ : []
124
+ ]
125
+ const required = parameters.filter(param => param.required).map(p => p.name)
126
+ if (![0, 1].includes(args.length - required.length)) {
127
+ throw new ArgumentCountMismatchError(functionName, required.length, args.length)
128
+ }
129
+ const values = required.reduce(
130
+ (acc, req, idx) => ({ ...acc, [req]: args[idx] }),
131
+ args[required.length] || {}
125
132
  )
126
- return [param, jsonImp.stringify(filteredValue)]
127
- })
128
- return (await handler(stringified, { requestBody: __requestBody })).body
129
- }
130
- ])
133
+ const { __requestBody, __queue, ...stringified } = mapObject(values, ([param, value]) => {
134
+ if (typeof value !== 'object') return [param, value]
135
+ const rootKeys = Object.keys(parameters.find(p => p.name === param).schema.properties)
136
+ const filteredValue = filterObject(
137
+ disableCaseConversion ? value : snakizeKeys(value),
138
+ ([key]) => rootKeys.includes(key)
139
+ )
140
+ return [param, jsonImp.stringify(filteredValue)]
141
+ })
142
+
143
+ const request = async () => (await handler(stringified, { requestBody: __requestBody }))
144
+ .body
145
+ if (!__queue) return request()
146
+ const res = (requestQueues[__queue] ?? Promise.resolve()).then(request, request)
147
+ // TODO: remove after fixing https://github.com/aeternity/aeternity/issues/3803
148
+ // gap to ensure that node won't reject the nonce
149
+ requestQueues[__queue] = res.then(() => new Promise(resolve => setTimeout(resolve, 750)))
150
+ return res
151
+ }
152
+ ]
153
+ })
131
154
 
132
155
  return Object.assign(external, { api })
133
156
  }