@opcat-labs/opcat 1.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 (138) hide show
  1. package/.mocharc.yaml +3 -0
  2. package/index.d.ts +1541 -0
  3. package/index.js +74 -0
  4. package/lib/address.js +478 -0
  5. package/lib/block/block.js +277 -0
  6. package/lib/block/blockheader.js +295 -0
  7. package/lib/block/index.js +4 -0
  8. package/lib/block/merkleblock.js +323 -0
  9. package/lib/bn.js +3423 -0
  10. package/lib/crypto/bn.js +278 -0
  11. package/lib/crypto/ecdsa.js +339 -0
  12. package/lib/crypto/hash.browser.js +171 -0
  13. package/lib/crypto/hash.js +2 -0
  14. package/lib/crypto/hash.node.js +171 -0
  15. package/lib/crypto/point.js +221 -0
  16. package/lib/crypto/random.browser.js +28 -0
  17. package/lib/crypto/random.js +2 -0
  18. package/lib/crypto/random.node.js +11 -0
  19. package/lib/crypto/signature.js +325 -0
  20. package/lib/encoding/base58.js +111 -0
  21. package/lib/encoding/base58check.js +121 -0
  22. package/lib/encoding/bufferreader.js +212 -0
  23. package/lib/encoding/bufferwriter.js +140 -0
  24. package/lib/encoding/decode-asm.js +24 -0
  25. package/lib/encoding/decode-hex.js +32 -0
  26. package/lib/encoding/decode-script-chunks.js +43 -0
  27. package/lib/encoding/encode-hex.js +284 -0
  28. package/lib/encoding/is-hex.js +7 -0
  29. package/lib/encoding/varint.js +75 -0
  30. package/lib/errors/index.js +54 -0
  31. package/lib/errors/spec.js +314 -0
  32. package/lib/hash-cache.js +50 -0
  33. package/lib/hdprivatekey.js +678 -0
  34. package/lib/hdpublickey.js +525 -0
  35. package/lib/message/message.js +191 -0
  36. package/lib/mnemonic/mnemonic.js +303 -0
  37. package/lib/mnemonic/pbkdf2.browser.js +68 -0
  38. package/lib/mnemonic/pbkdf2.js +2 -0
  39. package/lib/mnemonic/pbkdf2.node.js +68 -0
  40. package/lib/mnemonic/words/chinese.js +2054 -0
  41. package/lib/mnemonic/words/english.js +2054 -0
  42. package/lib/mnemonic/words/french.js +2054 -0
  43. package/lib/mnemonic/words/index.js +8 -0
  44. package/lib/mnemonic/words/italian.js +2054 -0
  45. package/lib/mnemonic/words/japanese.js +2054 -0
  46. package/lib/mnemonic/words/spanish.js +2054 -0
  47. package/lib/networks.js +379 -0
  48. package/lib/opcode.js +255 -0
  49. package/lib/privatekey.js +374 -0
  50. package/lib/publickey.js +386 -0
  51. package/lib/script/index.js +5 -0
  52. package/lib/script/interpreter.js +1834 -0
  53. package/lib/script/script.js +1074 -0
  54. package/lib/script/stack.js +109 -0
  55. package/lib/script/write-i32-le.js +17 -0
  56. package/lib/script/write-push-data.js +35 -0
  57. package/lib/script/write-u16-le.js +12 -0
  58. package/lib/script/write-u32-le.js +16 -0
  59. package/lib/script/write-u64-le.js +24 -0
  60. package/lib/script/write-u8-le.js +8 -0
  61. package/lib/script/write-varint.js +46 -0
  62. package/lib/transaction/index.js +7 -0
  63. package/lib/transaction/input/index.js +5 -0
  64. package/lib/transaction/input/input.js +354 -0
  65. package/lib/transaction/input/multisig.js +242 -0
  66. package/lib/transaction/input/publickey.js +100 -0
  67. package/lib/transaction/input/publickeyhash.js +118 -0
  68. package/lib/transaction/output.js +231 -0
  69. package/lib/transaction/sighash.js +167 -0
  70. package/lib/transaction/signature.js +97 -0
  71. package/lib/transaction/transaction.js +1639 -0
  72. package/lib/transaction/unspentoutput.js +113 -0
  73. package/lib/util/_.js +47 -0
  74. package/lib/util/js.js +90 -0
  75. package/lib/util/preconditions.js +33 -0
  76. package/package.json +26 -0
  77. package/test/address.js +509 -0
  78. package/test/block/block.js +251 -0
  79. package/test/block/blockheader.js +275 -0
  80. package/test/block/merklebloack.js +211 -0
  81. package/test/crypto/bn.js +177 -0
  82. package/test/crypto/ecdsa.js +391 -0
  83. package/test/crypto/hash.browser.js +135 -0
  84. package/test/crypto/hash.js +136 -0
  85. package/test/crypto/point.js +224 -0
  86. package/test/crypto/random.js +32 -0
  87. package/test/crypto/signature.js +409 -0
  88. package/test/data/bip69.json +215 -0
  89. package/test/data/bitcoind/base58_keys_invalid.json +52 -0
  90. package/test/data/bitcoind/base58_keys_valid.json +335 -0
  91. package/test/data/bitcoind/blocks.json +22 -0
  92. package/test/data/bitcoind/script_tests.json +3822 -0
  93. package/test/data/bitcoind/sig_canonical.json +7 -0
  94. package/test/data/bitcoind/sig_noncanonical.json +36 -0
  95. package/test/data/bitcoind/tx_invalid.json +445 -0
  96. package/test/data/bitcoind/tx_valid.json +44 -0
  97. package/test/data/blk86756-testnet.dat +0 -0
  98. package/test/data/blk86756-testnet.js +14 -0
  99. package/test/data/blk86756-testnet.json +684 -0
  100. package/test/data/block.hex +1 -0
  101. package/test/data/ecdsa.json +230 -0
  102. package/test/data/merkleblocks.js +488 -0
  103. package/test/data/messages.json +22 -0
  104. package/test/data/sighash.json +12 -0
  105. package/test/data/tx_creation.json +95 -0
  106. package/test/encoding/base58.js +131 -0
  107. package/test/encoding/base58check.js +136 -0
  108. package/test/encoding/bufferreader.js +337 -0
  109. package/test/encoding/bufferwriter.js +172 -0
  110. package/test/encoding/varint.js +104 -0
  111. package/test/hashCache.js +67 -0
  112. package/test/hdkeys.js +445 -0
  113. package/test/hdprivatekey.js +332 -0
  114. package/test/hdpublickey.js +304 -0
  115. package/test/index.js +16 -0
  116. package/test/message/message.js +204 -0
  117. package/test/mnemonic/data/fixtures.json +300 -0
  118. package/test/mnemonic/mnemonic.js +259 -0
  119. package/test/mnemonic/mocha.opts +1 -0
  120. package/test/mnemonic/pbkdf2.test.js +59 -0
  121. package/test/networks.js +159 -0
  122. package/test/opcode.js +161 -0
  123. package/test/privatekey.js +439 -0
  124. package/test/publickey.js +554 -0
  125. package/test/script/interpreter.js +734 -0
  126. package/test/script/script.js +1437 -0
  127. package/test/transaction/deserialize.js +34 -0
  128. package/test/transaction/input/input.js +90 -0
  129. package/test/transaction/input/multisig.js +90 -0
  130. package/test/transaction/input/publickey.js +68 -0
  131. package/test/transaction/input/publickeyhash.js +51 -0
  132. package/test/transaction/output.js +185 -0
  133. package/test/transaction/sighash.js +65 -0
  134. package/test/transaction/signature.js +114 -0
  135. package/test/transaction/transaction.js +1109 -0
  136. package/test/transaction/unspentoutput.js +110 -0
  137. package/test/util/js.js +76 -0
  138. package/test/util/preconditions.js +79 -0
package/test/hdkeys.js ADDED
@@ -0,0 +1,445 @@
1
+ 'use strict';
2
+
3
+ // Relax some linter options:
4
+ // * quote marks so "m/0'/1/2'/" doesn't need to be scaped
5
+ // * too many tests, maxstatements -> 100
6
+ // * store test vectors at the end, latedef: false
7
+ // * should call is never defined
8
+
9
+ var _ = require('../lib/util/_');
10
+ require('chai').should();
11
+ var expect = require('chai').expect;
12
+ var sinon = require('sinon');
13
+ var opcat = require('..');
14
+ var Networks = opcat.Networks;
15
+ var HDPrivateKey = opcat.HDPrivateKey;
16
+ var HDPublicKey = opcat.HDPublicKey;
17
+
18
+ describe('HDKeys building with static methods', function () {
19
+ var classes = [HDPublicKey, HDPrivateKey];
20
+
21
+ _.each(classes, function (Clazz) {
22
+ var expectStaticMethodFail = function (staticMethod, argument, message) {
23
+ expect(Clazz[staticMethod].bind(null, argument)).to.throw(message);
24
+ };
25
+ it(Clazz.name + ' fromJSON checks that a valid JSON is provided', function () {
26
+ var errorMessage = 'Invalid Argument: No valid argument was provided';
27
+ var method = 'fromObject';
28
+ expectStaticMethodFail(method, undefined, errorMessage);
29
+ expectStaticMethodFail(method, null, errorMessage);
30
+ expectStaticMethodFail(method, 'invalid JSON', errorMessage);
31
+ expectStaticMethodFail(method, "{'singlequotes': true}", errorMessage);
32
+ });
33
+ it(Clazz.name + ' fromString checks that a string is provided', function () {
34
+ var errorMessage = 'No valid string was provided';
35
+ var method = 'fromString';
36
+ expectStaticMethodFail(method, undefined, errorMessage);
37
+ expectStaticMethodFail(method, null, errorMessage);
38
+ expectStaticMethodFail(method, {}, errorMessage);
39
+ });
40
+ it(Clazz.name + ' fromObject checks that an object is provided', function () {
41
+ var errorMessage = 'No valid argument was provided';
42
+ var method = 'fromObject';
43
+ expectStaticMethodFail(method, undefined, errorMessage);
44
+ expectStaticMethodFail(method, null, errorMessage);
45
+ expectStaticMethodFail(method, '', errorMessage);
46
+ });
47
+ });
48
+ });
49
+
50
+ describe('BIP32 compliance', function () {
51
+ it('should initialize test vector 1 from the extended public key', function () {
52
+ new HDPublicKey(vector1MPublic).xpubkey.should.equal(vector1MPublic);
53
+ });
54
+
55
+ it('should initialize test vector 1 from the extended private key', function () {
56
+ new HDPrivateKey(vector1MPrivate).xprivkey.should.equal(vector1MPrivate);
57
+ });
58
+
59
+ it('can initialize a public key from an extended private key', function () {
60
+ new HDPublicKey(vector1MPrivate).xpubkey.should.equal(vector1MPublic);
61
+ });
62
+
63
+ it('toString should be equal to the `xpubkey` member', function () {
64
+ var privateKey = new HDPrivateKey(vector1MPrivate);
65
+ privateKey.toString().should.equal(privateKey.xprivkey);
66
+ });
67
+
68
+ it('toString should be equal to the `xpubkey` member', function () {
69
+ var publicKey = new HDPublicKey(vector1MPublic);
70
+ publicKey.toString().should.equal(publicKey.xpubkey);
71
+ });
72
+
73
+ it('should get the extended public key from the extended private key for test vector 1', function () {
74
+ HDPrivateKey(vector1MPrivate).xpubkey.should.equal(vector1MPublic);
75
+ });
76
+
77
+ it("should get m/0' ext. private key from test vector 1", function () {
78
+ var privateKey = new HDPrivateKey(vector1MPrivate).deriveChild("m/0'");
79
+ privateKey.xprivkey.should.equal(vector1m0hprivate);
80
+ });
81
+
82
+ it("should get m/0' ext. public key from test vector 1", function () {
83
+ HDPrivateKey(vector1MPrivate).deriveChild("m/0'").xpubkey.should.equal(vector1m0hPublic);
84
+ });
85
+
86
+ it("should get m/0'/1 ext. private key from test vector 1", function () {
87
+ HDPrivateKey(vector1MPrivate).deriveChild("m/0'/1").xprivkey.should.equal(vector1m0h1private);
88
+ });
89
+
90
+ it("should get m/0'/1 ext. public key from test vector 1", function () {
91
+ HDPrivateKey(vector1MPrivate).deriveChild("m/0'/1").xpubkey.should.equal(vector1m0h1public);
92
+ });
93
+
94
+ it("should get m/0'/1 ext. public key from m/0' public key from test vector 1", function () {
95
+ var derivedPublic = HDPrivateKey(vector1MPrivate)
96
+ .deriveChild("m/0'")
97
+ .hdPublicKey.deriveChild('m/1');
98
+ derivedPublic.xpubkey.should.equal(vector1m0h1public);
99
+ });
100
+
101
+ it("should get m/0'/1/2' ext. private key from test vector 1", function () {
102
+ var privateKey = new HDPrivateKey(vector1MPrivate);
103
+ var derived = privateKey.deriveChild("m/0'/1/2'");
104
+ derived.xprivkey.should.equal(vector1m0h12hprivate);
105
+ });
106
+
107
+ it("should get m/0'/1/2' ext. public key from test vector 1", function () {
108
+ HDPrivateKey(vector1MPrivate)
109
+ .deriveChild("m/0'/1/2'")
110
+ .xpubkey.should.equal(vector1m0h12hpublic);
111
+ });
112
+
113
+ it("should get m/0'/1/2'/2 ext. private key from test vector 1", function () {
114
+ HDPrivateKey(vector1MPrivate)
115
+ .deriveChild("m/0'/1/2'/2")
116
+ .xprivkey.should.equal(vector1m0h12h2private);
117
+ });
118
+
119
+ it("should get m/0'/1/2'/2 ext. public key from m/0'/1/2' public key from test vector 1", function () {
120
+ var derived = HDPrivateKey(vector1MPrivate).deriveChild("m/0'/1/2'").hdPublicKey;
121
+ derived.deriveChild('m/2').xpubkey.should.equal(vector1m0h12h2public);
122
+ });
123
+
124
+ it("should get m/0'/1/2h/2 ext. public key from test vector 1", function () {
125
+ HDPrivateKey(vector1MPrivate)
126
+ .deriveChild("m/0'/1/2'/2")
127
+ .xpubkey.should.equal(vector1m0h12h2public);
128
+ });
129
+
130
+ it("should get m/0'/1/2h/2/1000000000 ext. private key from test vector 1", function () {
131
+ HDPrivateKey(vector1MPrivate)
132
+ .deriveChild("m/0'/1/2'/2/1000000000")
133
+ .xprivkey.should.equal(vector1m0h12h21000000000private);
134
+ });
135
+
136
+ it("should get m/0'/1/2h/2/1000000000 ext. public key from test vector 1", function () {
137
+ HDPrivateKey(vector1MPrivate)
138
+ .deriveChild("m/0'/1/2'/2/1000000000")
139
+ .xpubkey.should.equal(vector1m0h12h21000000000public);
140
+ });
141
+
142
+ it("should get m/0'/1/2'/2/1000000000 ext. public key from m/0'/1/2'/2 public key from test vector 1", function () {
143
+ var derived = HDPrivateKey(vector1MPrivate).deriveChild("m/0'/1/2'/2").hdPublicKey;
144
+ derived.deriveChild('m/1000000000').xpubkey.should.equal(vector1m0h12h21000000000public);
145
+ });
146
+
147
+ it('should initialize test vector 2 from the extended public key', function () {
148
+ HDPublicKey(vector2mpublic).xpubkey.should.equal(vector2mpublic);
149
+ });
150
+
151
+ it('should initialize test vector 2 from the extended private key', function () {
152
+ HDPrivateKey(vector2mprivate).xprivkey.should.equal(vector2mprivate);
153
+ });
154
+
155
+ it('should get the extended public key from the extended private key for test vector 2', function () {
156
+ HDPrivateKey(vector2mprivate).xpubkey.should.equal(vector2mpublic);
157
+ });
158
+
159
+ it('should get m/0 ext. private key from test vector 2', function () {
160
+ HDPrivateKey(vector2mprivate).deriveChild(0).xprivkey.should.equal(vector2m0private);
161
+ });
162
+
163
+ it('should get m/0 ext. public key from test vector 2', function () {
164
+ HDPrivateKey(vector2mprivate).deriveChild(0).xpubkey.should.equal(vector2m0public);
165
+ });
166
+
167
+ it('should get m/0 ext. public key from m public key from test vector 2', function () {
168
+ HDPrivateKey(vector2mprivate).hdPublicKey.deriveChild(0).xpubkey.should.equal(vector2m0public);
169
+ });
170
+
171
+ it('should get m/0/2147483647h ext. private key from test vector 2', function () {
172
+ HDPrivateKey(vector2mprivate)
173
+ .deriveChild("m/0/2147483647'")
174
+ .xprivkey.should.equal(vector2m02147483647hprivate);
175
+ });
176
+
177
+ it('should get m/0/2147483647h ext. public key from test vector 2', function () {
178
+ HDPrivateKey(vector2mprivate)
179
+ .deriveChild("m/0/2147483647'")
180
+ .xpubkey.should.equal(vector2m02147483647hpublic);
181
+ });
182
+
183
+ it('should get m/0/2147483647h/1 ext. private key from test vector 2', function () {
184
+ HDPrivateKey(vector2mprivate)
185
+ .deriveChild("m/0/2147483647'/1")
186
+ .xprivkey.should.equal(vector2m02147483647h1private);
187
+ });
188
+
189
+ it('should get m/0/2147483647h/1 ext. public key from test vector 2', function () {
190
+ HDPrivateKey(vector2mprivate)
191
+ .deriveChild("m/0/2147483647'/1")
192
+ .xpubkey.should.equal(vector2m02147483647h1public);
193
+ });
194
+
195
+ it('should get m/0/2147483647h/1 ext. public key from m/0/2147483647h public key from test vector 2', function () {
196
+ var derived = HDPrivateKey(vector2mprivate).deriveChild("m/0/2147483647'").hdPublicKey;
197
+ derived.deriveChild(1).xpubkey.should.equal(vector2m02147483647h1public);
198
+ });
199
+
200
+ it('should get m/0/2147483647h/1/2147483646h ext. private key from test vector 2', function () {
201
+ HDPrivateKey(vector2mprivate)
202
+ .deriveChild("m/0/2147483647'/1/2147483646'")
203
+ .xprivkey.should.equal(vector2m02147483647h12147483646hprivate);
204
+ });
205
+
206
+ it('should get m/0/2147483647h/1/2147483646h ext. public key from test vector 2', function () {
207
+ HDPrivateKey(vector2mprivate)
208
+ .deriveChild("m/0/2147483647'/1/2147483646'")
209
+ .xpubkey.should.equal(vector2m02147483647h12147483646hpublic);
210
+ });
211
+
212
+ it('should get m/0/2147483647h/1/2147483646h/2 ext. private key from test vector 2', function () {
213
+ HDPrivateKey(vector2mprivate)
214
+ .deriveChild("m/0/2147483647'/1/2147483646'/2")
215
+ .xprivkey.should.equal(vector2m02147483647h12147483646h2private);
216
+ });
217
+
218
+ it('should get m/0/2147483647h/1/2147483646h/2 ext. public key from test vector 2', function () {
219
+ HDPrivateKey(vector2mprivate)
220
+ .deriveChild("m/0/2147483647'/1/2147483646'/2")
221
+ .xpubkey.should.equal(vector2m02147483647h12147483646h2public);
222
+ });
223
+
224
+ it('should get m/0/2147483647h/1/2147483646h/2 ext. public key from m/0/2147483647h/2147483646h public key from test vector 2', function () {
225
+ var derivedPublic = HDPrivateKey(vector2mprivate).deriveChild(
226
+ "m/0/2147483647'/1/2147483646'",
227
+ ).hdPublicKey;
228
+ derivedPublic.deriveChild('m/2').xpubkey.should.equal(vector2m02147483647h12147483646h2public);
229
+ });
230
+
231
+ it('should use full 32 bytes for private key data that is hashed (as per bip32)', function () {
232
+ // https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki
233
+ var privateKeyBuffer = Buffer.from(
234
+ '00000055378cf5fafb56c711c674143f9b0ee82ab0ba2924f19b64f5ae7cdbfd',
235
+ 'hex',
236
+ );
237
+ var chainCodeBuffer = Buffer.from(
238
+ '9c8a5c863e5941f3d99453e6ba66b328bb17cf0b8dec89ed4fc5ace397a1c089',
239
+ 'hex',
240
+ );
241
+ var key = HDPrivateKey.fromObject({
242
+ network: 'testnet',
243
+ depth: 0,
244
+ parentFingerPrint: 0,
245
+ childIndex: 0,
246
+ privateKey: privateKeyBuffer,
247
+ chainCode: chainCodeBuffer,
248
+ });
249
+ var derived = key.deriveChild("m/44'/0'/0'/0/0'");
250
+ derived.privateKey
251
+ .toHex()
252
+ .should.equal('3348069561d2a0fb925e74bf198762acc47dce7db27372257d2d959a9e6f8aeb');
253
+ });
254
+
255
+ it('should NOT use full 32 bytes for private key data that is hashed with nonCompliant flag', function () {
256
+ // This is to test that the previously implemented non-compliant to BIP32
257
+ var privateKeyBuffer = Buffer.from(
258
+ '00000055378cf5fafb56c711c674143f9b0ee82ab0ba2924f19b64f5ae7cdbfd',
259
+ 'hex',
260
+ );
261
+ var chainCodeBuffer = Buffer.from(
262
+ '9c8a5c863e5941f3d99453e6ba66b328bb17cf0b8dec89ed4fc5ace397a1c089',
263
+ 'hex',
264
+ );
265
+ var key = HDPrivateKey.fromObject({
266
+ network: 'testnet',
267
+ depth: 0,
268
+ parentFingerPrint: 0,
269
+ childIndex: 0,
270
+ privateKey: privateKeyBuffer,
271
+ chainCode: chainCodeBuffer,
272
+ });
273
+ var derived = key.deriveNonCompliantChild("m/44'/0'/0'/0/0'");
274
+ derived.privateKey
275
+ .toHex()
276
+ .should.equal('4811a079bab267bfdca855b3bddff20231ff7044e648514fa099158472df2836');
277
+ });
278
+
279
+ it('should NOT use full 32 bytes for private key data that is hashed with the nonCompliant derive method', function () {
280
+ // This is to test that the previously implemented non-compliant to BIP32
281
+ var privateKeyBuffer = Buffer.from(
282
+ '00000055378cf5fafb56c711c674143f9b0ee82ab0ba2924f19b64f5ae7cdbfd',
283
+ 'hex',
284
+ );
285
+ var chainCodeBuffer = Buffer.from(
286
+ '9c8a5c863e5941f3d99453e6ba66b328bb17cf0b8dec89ed4fc5ace397a1c089',
287
+ 'hex',
288
+ );
289
+ var key = HDPrivateKey.fromObject({
290
+ network: 'testnet',
291
+ depth: 0,
292
+ parentFingerPrint: 0,
293
+ childIndex: 0,
294
+ privateKey: privateKeyBuffer,
295
+ chainCode: chainCodeBuffer,
296
+ });
297
+ var derived = key.deriveNonCompliantChild("m/44'/0'/0'/0/0'");
298
+ derived.privateKey
299
+ .toHex()
300
+ .should.equal('4811a079bab267bfdca855b3bddff20231ff7044e648514fa099158472df2836');
301
+ });
302
+
303
+ describe('edge cases', function () {
304
+ var sandbox = sinon.createSandbox();
305
+ afterEach(function () {
306
+ sandbox.restore();
307
+ });
308
+ it('will handle edge case that derived private key is invalid', function () {
309
+ var invalid = Buffer.from(
310
+ '0000000000000000000000000000000000000000000000000000000000000000',
311
+ 'hex',
312
+ );
313
+ var privateKeyBuffer = Buffer.from(
314
+ '5f72914c48581fc7ddeb944a9616389200a9560177d24f458258e5b04527bcd1',
315
+ 'hex',
316
+ );
317
+ var chainCodeBuffer = Buffer.from(
318
+ '39816057bba9d952fe87fe998b7fd4d690a1bb58c2ff69141469e4d1dffb4b91',
319
+ 'hex',
320
+ );
321
+ var unstubbed = opcat.crypto.BN.prototype.toBuffer;
322
+ var count = 0;
323
+ sandbox.stub(opcat.crypto.BN.prototype, 'toBuffer').callsFake(function (args) {
324
+ // On the fourth call to the function give back an invalid private key
325
+ // otherwise use the normal behavior.
326
+ count++;
327
+ if (count === 2) {
328
+ return invalid;
329
+ }
330
+ var ret = unstubbed.apply(this, arguments);
331
+ return ret;
332
+ });
333
+ sandbox.spy(opcat.PrivateKey, 'isValid');
334
+ var key = HDPrivateKey.fromObject({
335
+ network: 'testnet',
336
+ depth: 0,
337
+ parentFingerPrint: 0,
338
+ childIndex: 0,
339
+ privateKey: privateKeyBuffer,
340
+ chainCode: chainCodeBuffer,
341
+ });
342
+ var derived = key.deriveChild("m/44'");
343
+ derived.privateKey
344
+ .toHex()
345
+ .should.equal('e177a510d6326595afdb1200e4ce56b59f8815cf3eee8d5c4745b2b70540b3f8');
346
+ opcat.PrivateKey.isValid.callCount.should.equal(1);
347
+ });
348
+ it('will handle edge case that a derive public key is invalid', function () {
349
+ var publicKeyBuffer = Buffer.from(
350
+ '029e58b241790284ef56502667b15157b3fc58c567f044ddc35653860f9455d099',
351
+ 'hex',
352
+ );
353
+ var chainCodeBuffer = Buffer.from(
354
+ '39816057bba9d952fe87fe998b7fd4d690a1bb58c2ff69141469e4d1dffb4b91',
355
+ 'hex',
356
+ );
357
+ var key = new HDPublicKey({
358
+ network: 'testnet',
359
+ depth: 0,
360
+ parentFingerPrint: 0,
361
+ childIndex: 0,
362
+ chainCode: chainCodeBuffer,
363
+ publicKey: publicKeyBuffer,
364
+ });
365
+ var unstubbed = opcat.PublicKey.fromPoint;
366
+ opcat.PublicKey.fromPoint = function () {
367
+ opcat.PublicKey.fromPoint = unstubbed;
368
+ throw new Error('Point cannot be equal to Infinity');
369
+ };
370
+ sandbox.spy(key, '_deriveWithNumber');
371
+ key.deriveChild('m/44');
372
+ key._deriveWithNumber.callCount.should.equal(2);
373
+ key.publicKey
374
+ .toString()
375
+ .should.equal('029e58b241790284ef56502667b15157b3fc58c567f044ddc35653860f9455d099');
376
+ });
377
+ });
378
+
379
+ describe('seed', function () {
380
+ it('should initialize a new BIP32 correctly from test vector 1 seed', function () {
381
+ var seededKey = HDPrivateKey.fromSeed(vector1Master, Networks.livenet);
382
+ seededKey.xprivkey.should.equal(vector1MPrivate);
383
+ seededKey.xpubkey.should.equal(vector1MPublic);
384
+ });
385
+
386
+ it('should initialize a new BIP32 correctly from test vector 2 seed', function () {
387
+ var seededKey = HDPrivateKey.fromSeed(vector2master, Networks.livenet);
388
+ seededKey.xprivkey.should.equal(vector2mprivate);
389
+ seededKey.xpubkey.should.equal(vector2mpublic);
390
+ });
391
+ });
392
+ });
393
+
394
+ // test vectors: https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki
395
+ var vector1Master = '000102030405060708090a0b0c0d0e0f';
396
+ var vector1MPublic =
397
+ 'xpub661MyMwAqRbcFtXgS5sYJABqqG9YLmC4Q1Rdap9gSE8NqtwybGhePY2gZ29ESFjqJoCu1Rupje8YtGqsefD265TMg7usUDFdp6W1EGMcet8';
398
+ var vector1MPrivate =
399
+ 'xprv9s21ZrQH143K3QTDL4LXw2F7HEK3wJUD2nW2nRk4stbPy6cq3jPPqjiChkVvvNKmPGJxWUtg6LnF5kejMRNNU3TGtRBeJgk33yuGBxrMPHi';
400
+ var vector1m0hPublic =
401
+ 'xpub68Gmy5EdvgibQVfPdqkBBCHxA5htiqg55crXYuXoQRKfDBFA1WEjWgP6LHhwBZeNK1VTsfTFUHCdrfp1bgwQ9xv5ski8PX9rL2dZXvgGDnw';
402
+ var vector1m0hprivate =
403
+ 'xprv9uHRZZhk6KAJC1avXpDAp4MDc3sQKNxDiPvvkX8Br5ngLNv1TxvUxt4cV1rGL5hj6KCesnDYUhd7oWgT11eZG7XnxHrnYeSvkzY7d2bhkJ7';
404
+ var vector1m0h1public =
405
+ 'xpub6ASuArnXKPbfEwhqN6e3mwBcDTgzisQN1wXN9BJcM47sSikHjJf3UFHKkNAWbWMiGj7Wf5uMash7SyYq527Hqck2AxYysAA7xmALppuCkwQ';
406
+ var vector1m0h1private =
407
+ 'xprv9wTYmMFdV23N2TdNG573QoEsfRrWKQgWeibmLntzniatZvR9BmLnvSxqu53Kw1UmYPxLgboyZQaXwTCg8MSY3H2EU4pWcQDnRnrVA1xe8fs';
408
+ var vector1m0h12hpublic =
409
+ 'xpub6D4BDPcP2GT577Vvch3R8wDkScZWzQzMMUm3PWbmWvVJrZwQY4VUNgqFJPMM3No2dFDFGTsxxpG5uJh7n7epu4trkrX7x7DogT5Uv6fcLW5';
410
+ var vector1m0h12hprivate =
411
+ 'xprv9z4pot5VBttmtdRTWfWQmoH1taj2axGVzFqSb8C9xaxKymcFzXBDptWmT7FwuEzG3ryjH4ktypQSAewRiNMjANTtpgP4mLTj34bhnZX7UiM';
412
+ var vector1m0h12h2public =
413
+ 'xpub6FHa3pjLCk84BayeJxFW2SP4XRrFd1JYnxeLeU8EqN3vDfZmbqBqaGJAyiLjTAwm6ZLRQUMv1ZACTj37sR62cfN7fe5JnJ7dh8zL4fiyLHV';
414
+ var vector1m0h12h2private =
415
+ 'xprvA2JDeKCSNNZky6uBCviVfJSKyQ1mDYahRjijr5idH2WwLsEd4Hsb2Tyh8RfQMuPh7f7RtyzTtdrbdqqsunu5Mm3wDvUAKRHSC34sJ7in334';
416
+ var vector1m0h12h21000000000public =
417
+ 'xpub6H1LXWLaKsWFhvm6RVpEL9P4KfRZSW7abD2ttkWP3SSQvnyA8FSVqNTEcYFgJS2UaFcxupHiYkro49S8yGasTvXEYBVPamhGW6cFJodrTHy';
418
+ var vector1m0h12h21000000000private =
419
+ 'xprvA41z7zogVVwxVSgdKUHDy1SKmdb533PjDz7J6N6mV6uS3ze1ai8FHa8kmHScGpWmj4WggLyQjgPie1rFSruoUihUZREPSL39UNdE3BBDu76';
420
+ var vector2master =
421
+ 'fffcf9f6f3f0edeae7e4e1dedbd8d5d2cfccc9c6c3c0bdbab7b4b1aeaba8a5a29f9c999693908d8a8784817e7b7875726f6c696663605d5a5754514e4b484542';
422
+ var vector2mpublic =
423
+ 'xpub661MyMwAqRbcFW31YEwpkMuc5THy2PSt5bDMsktWQcFF8syAmRUapSCGu8ED9W6oDMSgv6Zz8idoc4a6mr8BDzTJY47LJhkJ8UB7WEGuduB';
424
+ var vector2mprivate =
425
+ 'xprv9s21ZrQH143K31xYSDQpPDxsXRTUcvj2iNHm5NUtrGiGG5e2DtALGdso3pGz6ssrdK4PFmM8NSpSBHNqPqm55Qn3LqFtT2emdEXVYsCzC2U';
426
+ var vector2m0public =
427
+ 'xpub69H7F5d8KSRgmmdJg2KhpAK8SR3DjMwAdkxj3ZuxV27CprR9LgpeyGmXUbC6wb7ERfvrnKZjXoUmmDznezpbZb7ap6r1D3tgFxHmwMkQTPH';
428
+ var vector2m0private =
429
+ 'xprv9vHkqa6EV4sPZHYqZznhT2NPtPCjKuDKGY38FBWLvgaDx45zo9WQRUT3dKYnjwih2yJD9mkrocEZXo1ex8G81dwSM1fwqWpWkeS3v86pgKt';
430
+ var vector2m02147483647hpublic =
431
+ 'xpub6ASAVgeehLbnwdqV6UKMHVzgqAG8Gr6riv3Fxxpj8ksbH9ebxaEyBLZ85ySDhKiLDBrQSARLq1uNRts8RuJiHjaDMBU4Zn9h8LZNnBC5y4a';
432
+ var vector2m02147483647hprivate =
433
+ 'xprv9wSp6B7kry3Vj9m1zSnLvN3xH8RdsPP1Mh7fAaR7aRLcQMKTR2vidYEeEg2mUCTAwCd6vnxVrcjfy2kRgVsFawNzmjuHc2YmYRmagcEPdU9';
434
+ var vector2m02147483647h1public =
435
+ 'xpub6DF8uhdarytz3FWdA8TvFSvvAh8dP3283MY7p2V4SeE2wyWmG5mg5EwVvmdMVCQcoNJxGoWaU9DCWh89LojfZ537wTfunKau47EL2dhHKon';
436
+ var vector2m02147483647h1private =
437
+ 'xprv9zFnWC6h2cLgpmSA46vutJzBcfJ8yaJGg8cX1e5StJh45BBciYTRXSd25UEPVuesF9yog62tGAQtHjXajPPdbRCHuWS6T8XA2ECKADdw4Ef';
438
+ var vector2m02147483647h12147483646hpublic =
439
+ 'xpub6ERApfZwUNrhLCkDtcHTcxd75RbzS1ed54G1LkBUHQVHQKqhMkhgbmJbZRkrgZw4koxb5JaHWkY4ALHY2grBGRjaDMzQLcgJvLJuZZvRcEL';
440
+ var vector2m02147483647h12147483646hprivate =
441
+ 'xprvA1RpRA33e1JQ7ifknakTFpgNXPmW2YvmhqLQYMmrj4xJXXWYpDPS3xz7iAxn8L39njGVyuoseXzU6rcxFLJ8HFsTjSyQbLYnMpCqE2VbFWc';
442
+ var vector2m02147483647h12147483646h2public =
443
+ 'xpub6FnCn6nSzZAw5Tw7cgR9bi15UV96gLZhjDstkXXxvCLsUXBGXPdSnLFbdpq8p9HmGsApME5hQTZ3emM2rnY5agb9rXpVGyy3bdW6EEgAtqt';
444
+ var vector2m02147483647h12147483646h2private =
445
+ 'xprvA2nrNbFZABcdryreWet9Ea4LvTJcGsqrMzxHx98MMrotbir7yrKCEXw7nadnHM8Dq38EGfSh6dqA9QWTyefMLEcBYJUuekgW4BYPJcr9E7j';