@bitgo-beta/unspents 0.13.2-beta.9 → 0.13.2-beta.91

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 (56) hide show
  1. package/CHANGELOG.md +60 -0
  2. package/bin/generate_tables.ts +94 -0
  3. package/dist/bin/generate_tables.d.ts +2 -0
  4. package/dist/bin/generate_tables.d.ts.map +1 -0
  5. package/dist/bin/generate_tables.js +94 -0
  6. package/dist/{codes.d.ts → src/codes.d.ts} +1 -0
  7. package/dist/src/codes.d.ts.map +1 -0
  8. package/dist/src/codes.js +168 -0
  9. package/dist/{dimensions.d.ts → src/dimensions.d.ts} +6 -7
  10. package/dist/src/dimensions.d.ts.map +1 -0
  11. package/dist/src/dimensions.js +485 -0
  12. package/dist/{index.d.ts → src/index.d.ts} +1 -0
  13. package/dist/src/index.d.ts.map +1 -0
  14. package/dist/{index.js → src/index.js} +1 -1
  15. package/dist/{inputWeights.d.ts → src/inputWeights.d.ts} +1 -0
  16. package/dist/src/inputWeights.d.ts.map +1 -0
  17. package/dist/src/inputWeights.js +97 -0
  18. package/dist/{scriptSizes.d.ts → src/scriptSizes.d.ts} +1 -0
  19. package/dist/src/scriptSizes.d.ts.map +1 -0
  20. package/dist/src/scriptSizes.js +51 -0
  21. package/dist/{types.d.ts → src/types.d.ts} +1 -0
  22. package/dist/src/types.d.ts.map +1 -0
  23. package/dist/{types.js → src/types.js} +1 -1
  24. package/dist/{virtualSizes.d.ts → src/virtualSizes.d.ts} +1 -0
  25. package/dist/src/virtualSizes.d.ts.map +1 -0
  26. package/dist/src/virtualSizes.js +114 -0
  27. package/dist/test/chain.d.ts +2 -0
  28. package/dist/test/chain.d.ts.map +1 -0
  29. package/dist/test/chain.js +92 -0
  30. package/dist/test/dimensions.d.ts +2 -0
  31. package/dist/test/dimensions.d.ts.map +1 -0
  32. package/dist/test/dimensions.js +211 -0
  33. package/dist/test/signedTx/inputWeights.d.ts +2 -0
  34. package/dist/test/signedTx/inputWeights.d.ts.map +1 -0
  35. package/dist/test/signedTx/inputWeights.js +113 -0
  36. package/dist/test/signedTx/txCombinations.d.ts +3 -0
  37. package/dist/test/signedTx/txCombinations.d.ts.map +1 -0
  38. package/dist/test/signedTx/txCombinations.js +116 -0
  39. package/dist/test/signedTx/txGen.d.ts +75 -0
  40. package/dist/test/signedTx/txGen.d.ts.map +1 -0
  41. package/dist/test/signedTx/txGen.js +219 -0
  42. package/dist/test/testutils.d.ts +36 -0
  43. package/dist/test/testutils.d.ts.map +1 -0
  44. package/dist/test/testutils.js +176 -0
  45. package/dist/test/virtualSizes.d.ts +2 -0
  46. package/dist/test/virtualSizes.d.ts.map +1 -0
  47. package/dist/test/virtualSizes.js +18 -0
  48. package/dist/tsconfig.build.tsbuildinfo +1 -0
  49. package/dist/tsconfig.tsbuildinfo +1 -0
  50. package/docs/input-costs.md +13 -0
  51. package/package.json +5 -5
  52. package/dist/codes.js +0 -168
  53. package/dist/dimensions.js +0 -490
  54. package/dist/inputWeights.js +0 -97
  55. package/dist/scriptSizes.js +0 -51
  56. package/dist/virtualSizes.js +0 -114
@@ -0,0 +1,211 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });
5
+ }) : (function(o, m, k, k2) {
6
+ if (k2 === undefined) k2 = k;
7
+ o[k2] = m[k];
8
+ }));
9
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
10
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
11
+ }) : function(o, v) {
12
+ o["default"] = v;
13
+ });
14
+ var __importStar = (this && this.__importStar) || function (mod) {
15
+ if (mod && mod.__esModule) return mod;
16
+ var result = {};
17
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
18
+ __setModuleDefault(result, mod);
19
+ return result;
20
+ };
21
+ Object.defineProperty(exports, "__esModule", { value: true });
22
+ /* eslint-disable @typescript-eslint/ban-ts-comment */
23
+ const should = __importStar(require("should"));
24
+ const utxo_lib_1 = require("@bitgo-beta/utxo-lib");
25
+ const { chainCodes, chainCodesP2sh, chainCodesP2shP2wsh, chainCodesP2tr, chainCodesP2trMusig2, chainCodesP2wsh } = utxo_lib_1.bitgo;
26
+ const src_1 = require("../src");
27
+ const testutils_1 = require("./testutils");
28
+ describe('Dimensions Attributes', function () {
29
+ it('has read-only nInputs and nOutputs', function () {
30
+ should.throws(() => (src_1.Dimensions.ZERO.nInputs = 1), /read-only/);
31
+ should.throws(() => (src_1.Dimensions.ZERO.nOutputs = 1), /read-only/);
32
+ });
33
+ });
34
+ describe('Output Dimensions', function () {
35
+ it('instantiates', function () {
36
+ const dims = new src_1.OutputDimensions({ size: 0, count: 0 });
37
+ should.throws(() => (dims.count += 1));
38
+ });
39
+ });
40
+ describe('Dimensions Arithmetic', function () {
41
+ it('sums correctly', function () {
42
+ src_1.Dimensions.zero()
43
+ .plus({ nP2shInputs: 1 })
44
+ .should.eql(new src_1.Dimensions({
45
+ nP2shInputs: 1,
46
+ nP2shP2wshInputs: 0,
47
+ nP2wshInputs: 0,
48
+ nP2trKeypathInputs: 0,
49
+ nP2trScriptPathLevel1Inputs: 0,
50
+ nP2trScriptPathLevel2Inputs: 0,
51
+ nP2shP2pkInputs: 0,
52
+ outputs: { size: 0, count: 0 },
53
+ }));
54
+ const components = [
55
+ { nP2shInputs: 1 },
56
+ { nP2shP2wshInputs: 2 },
57
+ { nP2wshInputs: 3 },
58
+ { nP2trKeypathInputs: 4 },
59
+ { nP2trScriptPathLevel1Inputs: 5 },
60
+ { nP2trScriptPathLevel2Inputs: 6 },
61
+ { outputs: { size: 23, count: 1 } },
62
+ { outputs: { size: 44, count: 2 } },
63
+ { outputs: { size: 0, count: 0 } },
64
+ ];
65
+ components.forEach((component) => should.doesNotThrow(() => src_1.Dimensions.sum(component)));
66
+ const sum = components.reduce((a, b) => a.plus(b), src_1.Dimensions.zero());
67
+ sum.should.eql(src_1.Dimensions.sum(...components));
68
+ sum.should.eql(new src_1.Dimensions({
69
+ nP2shInputs: 1,
70
+ nP2shP2wshInputs: 2,
71
+ nP2wshInputs: 3,
72
+ nP2trKeypathInputs: 4,
73
+ nP2trScriptPathLevel1Inputs: 5,
74
+ nP2trScriptPathLevel2Inputs: 6,
75
+ nP2shP2pkInputs: 0,
76
+ outputs: { size: 67, count: 3 },
77
+ }));
78
+ sum.nOutputs.should.eql(sum.outputs.count);
79
+ });
80
+ it('provides some typical output sizes', function () {
81
+ [
82
+ [src_1.Dimensions.SingleOutput.p2sh, src_1.VirtualSizes.txP2shOutputSize],
83
+ [src_1.Dimensions.SingleOutput.p2shP2wsh, src_1.VirtualSizes.txP2shP2wshOutputSize],
84
+ [src_1.Dimensions.SingleOutput.p2wsh, src_1.VirtualSizes.txP2wshOutputSize],
85
+ [src_1.Dimensions.SingleOutput.p2pkh, src_1.VirtualSizes.txP2pkhOutputSize],
86
+ [src_1.Dimensions.SingleOutput.p2wpkh, src_1.VirtualSizes.txP2wpkhOutputSize],
87
+ [src_1.Dimensions.SingleOutput.p2tr, src_1.VirtualSizes.txP2trOutputSize],
88
+ ].forEach(([dims, size]) => {
89
+ dims.getOutputsVSize().should.eql(size);
90
+ });
91
+ });
92
+ it('prevents sum of invalid data', function () {
93
+ should.doesNotThrow(() => src_1.Dimensions.sum({ outputs: { count: 0, size: 0 } }));
94
+ should.doesNotThrow(() => src_1.Dimensions.sum({ outputs: { count: 1, size: 1 } }));
95
+ should.throws(() => src_1.Dimensions.sum({ nOutputs: 1 }));
96
+ should.throws(() => src_1.Dimensions.sum({ nOutputs: 1, outputs: { count: 2, size: 1 } }));
97
+ // @ts-ignore
98
+ should.throws(() => src_1.Dimensions.sum({ nP2shInputs: 1 }, { nP2shInputs: 'foo' }));
99
+ should.throws(() => src_1.Dimensions.sum({ outputs: { count: 1, size: 0 } }));
100
+ should.throws(() => src_1.Dimensions.sum({ outputs: { count: 0, size: 1 } }));
101
+ should.throws(() => src_1.Dimensions.sum({ outputs: { count: 1, size: 1 } }, { outputs: { count: 1, size: 0 } }));
102
+ });
103
+ it('counts inputs correctly', function () {
104
+ Object.entries(src_1.Dimensions.SingleInput).forEach(([key, value]) => {
105
+ value.nInputs.should.eql(1, key);
106
+ });
107
+ });
108
+ it('multiplies correctly', function () {
109
+ const d = new src_1.Dimensions({
110
+ nP2shInputs: 1,
111
+ nP2shP2wshInputs: 2,
112
+ nP2wshInputs: 3,
113
+ nP2trKeypathInputs: 4,
114
+ nP2trScriptPathLevel1Inputs: 5,
115
+ nP2trScriptPathLevel2Inputs: 6,
116
+ nP2shP2pkInputs: 7,
117
+ outputs: { count: 1, size: 22 },
118
+ }).times(3);
119
+ d.should.eql(new src_1.Dimensions({
120
+ nP2shInputs: 3,
121
+ nP2shP2wshInputs: 6,
122
+ nP2wshInputs: 9,
123
+ nP2trKeypathInputs: 12,
124
+ nP2trScriptPathLevel1Inputs: 15,
125
+ nP2trScriptPathLevel2Inputs: 18,
126
+ nP2shP2pkInputs: 21,
127
+ outputs: { count: 3, size: 66 },
128
+ }));
129
+ d.getNInputs().should.eql(84);
130
+ d.nInputs.should.eql(84);
131
+ });
132
+ });
133
+ describe('Dimensions from unspent types', function () {
134
+ it('determines unspent size according to chain', function () {
135
+ chainCodesP2sh.forEach((chain) => src_1.Dimensions.fromUnspent({ chain }).should.eql(src_1.Dimensions.sum({ nP2shInputs: 1 })));
136
+ chainCodesP2shP2wsh.forEach((chain) => src_1.Dimensions.fromUnspent({ chain }).should.eql(src_1.Dimensions.sum({ nP2shP2wshInputs: 1 })));
137
+ chainCodesP2wsh.forEach((chain) => src_1.Dimensions.fromUnspent({ chain }).should.eql(src_1.Dimensions.sum({ nP2wshInputs: 1 })));
138
+ chainCodesP2tr.forEach((chain) => {
139
+ src_1.Dimensions.fromUnspent({ chain }).should.eql(src_1.Dimensions.sum({ nP2trScriptPathLevel1Inputs: 1 }));
140
+ src_1.Dimensions.fromUnspent({ chain }, { p2tr: { scriptPathLevel: 2 }, p2trMusig2: { scriptPathLevel: undefined } }).should.eql(src_1.Dimensions.sum({ nP2trScriptPathLevel2Inputs: 1 }));
141
+ });
142
+ chainCodesP2trMusig2.forEach((chain) => {
143
+ src_1.Dimensions.fromUnspent({ chain }).should.eql(src_1.Dimensions.sum({ nP2trScriptPathLevel1Inputs: 1 }));
144
+ src_1.Dimensions.fromUnspent({ chain }, { p2tr: { scriptPathLevel: undefined }, p2trMusig2: { scriptPathLevel: undefined } }).should.eql(src_1.Dimensions.sum({ nP2trKeypathInputs: 1 }));
145
+ });
146
+ src_1.Dimensions.fromUnspents(chainCodes.map((chain) => ({ chain }))).should.eql(new src_1.Dimensions({
147
+ nP2shP2wshInputs: 2,
148
+ nP2shInputs: 2,
149
+ nP2wshInputs: 2,
150
+ nP2trKeypathInputs: 0,
151
+ nP2trScriptPathLevel1Inputs: 4,
152
+ nP2trScriptPathLevel2Inputs: 0,
153
+ nP2shP2pkInputs: 0,
154
+ outputs: { count: 0, size: 0 },
155
+ }));
156
+ });
157
+ it('calculates output dimensions dynamically', function () {
158
+ const expectedSizes = new Map([
159
+ [testutils_1.UnspentTypeScript2of3.p2sh, src_1.VirtualSizes.txP2shOutputSize],
160
+ [testutils_1.UnspentTypeScript2of3.p2shP2wsh, src_1.VirtualSizes.txP2shP2wshOutputSize],
161
+ [testutils_1.UnspentTypeScript2of3.p2wsh, src_1.VirtualSizes.txP2wshOutputSize],
162
+ [testutils_1.UnspentTypeScript2of3.p2tr, src_1.VirtualSizes.txP2trOutputSize],
163
+ [testutils_1.UnspentTypeScript2of3.p2trMusig2, src_1.VirtualSizes.txP2trOutputSize],
164
+ [testutils_1.UnspentTypeScript2of3.taprootKeyPathSpend, src_1.VirtualSizes.txP2trOutputSize],
165
+ [testutils_1.UnspentTypePubKeyHash.p2pkh, src_1.VirtualSizes.txP2pkhOutputSize],
166
+ [testutils_1.UnspentTypePubKeyHash.p2wpkh, src_1.VirtualSizes.txP2wpkhOutputSize],
167
+ ]);
168
+ [...Object.keys(testutils_1.UnspentTypeScript2of3), ...Object.keys(testutils_1.UnspentTypePubKeyHash)].forEach((type) => testutils_1.getOutputDimensionsForUnspentType(type).outputs.size.should.eql(expectedSizes.get(type)));
169
+ });
170
+ });
171
+ describe('Dimensions estimates', function () {
172
+ it('calculates vsizes', function () {
173
+ function dim(nP2shInputs, nP2shP2wshInputs, nP2wshInputs, nOutputs) {
174
+ return src_1.Dimensions.sum({
175
+ nP2shInputs,
176
+ nP2shP2wshInputs,
177
+ nP2wshInputs,
178
+ }, testutils_1.getOutputDimensionsForUnspentType(testutils_1.UnspentTypePubKeyHash.p2pkh).times(nOutputs));
179
+ }
180
+ function dimP2tr(nP2trKeypathInputs, nP2trScriptPathLevel1Inputs, nP2trScriptPathLevel2Inputs, nOutputs) {
181
+ return src_1.Dimensions.sum({
182
+ nP2trKeypathInputs,
183
+ nP2trScriptPathLevel1Inputs,
184
+ nP2trScriptPathLevel2Inputs,
185
+ }, testutils_1.getOutputDimensionsForUnspentType(testutils_1.UnspentTypePubKeyHash.p2pkh).times(nOutputs));
186
+ }
187
+ const vectors = [
188
+ [dim(1, 0, 0, 1), [false, 10, 298, 34, 342]],
189
+ [dim(0, 1, 0, 1), [true, 11, 140, 34, 185]],
190
+ [dim(0, 0, 1, 1), [true, 11, 105, 34, 150]],
191
+ [dim(2, 0, 0, 1), [false, 10, 596, 34, 640]],
192
+ [dim(0, 2, 0, 1), [true, 11, 280, 34, 325]],
193
+ [dim(0, 0, 2, 1), [true, 11, 210, 34, 255]],
194
+ [dim(1, 1, 1, 1), [true, 11, 543, 34, 588]],
195
+ [dim(1, 1, 1, 2), [true, 11, 543, 68, 622]],
196
+ [dimP2tr(1, 0, 0, 1), [true, 11, 58, 34, 103]],
197
+ [dimP2tr(0, 1, 0, 1), [true, 11, 108, 34, 153]],
198
+ [dimP2tr(0, 0, 1, 1), [true, 11, 116, 34, 161]],
199
+ ];
200
+ vectors.forEach(([dimensions, props]) => {
201
+ [
202
+ dimensions.isSegwit(),
203
+ dimensions.getOverheadVSize(),
204
+ dimensions.getInputsVSize(),
205
+ dimensions.getOutputsVSize(),
206
+ dimensions.getVSize(),
207
+ ].should.eql(props);
208
+ });
209
+ });
210
+ });
211
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZGltZW5zaW9ucy5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uL3Rlc3QvZGltZW5zaW9ucy50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBQSxzREFBc0Q7QUFDdEQsK0NBQWlDO0FBQ2pDLG1EQUE2QztBQUM3QyxNQUFNLEVBQUUsVUFBVSxFQUFFLGNBQWMsRUFBRSxtQkFBbUIsRUFBRSxjQUFjLEVBQUUsb0JBQW9CLEVBQUUsZUFBZSxFQUFFLEdBQzlHLGdCQUFLLENBQUM7QUFDUixnQ0FBb0U7QUFFcEUsMkNBQThHO0FBRTlHLFFBQVEsQ0FBQyx1QkFBdUIsRUFBRTtJQUNoQyxFQUFFLENBQUMsb0NBQW9DLEVBQUU7UUFDdkMsTUFBTSxDQUFDLE1BQU0sQ0FBQyxHQUFHLEVBQUUsQ0FBQyxDQUFFLGdCQUFVLENBQUMsSUFBWSxDQUFDLE9BQU8sR0FBRyxDQUFDLENBQUMsRUFBRSxXQUFXLENBQUMsQ0FBQztRQUN6RSxNQUFNLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxDQUFDLENBQUUsZ0JBQVUsQ0FBQyxJQUFZLENBQUMsUUFBUSxHQUFHLENBQUMsQ0FBQyxFQUFFLFdBQVcsQ0FBQyxDQUFDO0lBQzVFLENBQUMsQ0FBQyxDQUFDO0FBQ0wsQ0FBQyxDQUFDLENBQUM7QUFFSCxRQUFRLENBQUMsbUJBQW1CLEVBQUU7SUFDNUIsRUFBRSxDQUFDLGNBQWMsRUFBRTtRQUNqQixNQUFNLElBQUksR0FBRyxJQUFJLHNCQUFnQixDQUFDLEVBQUUsSUFBSSxFQUFFLENBQUMsRUFBRSxLQUFLLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQztRQUN6RCxNQUFNLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxDQUFDLENBQUMsSUFBSSxDQUFDLEtBQUssSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDO0lBQ3pDLENBQUMsQ0FBQyxDQUFDO0FBQ0wsQ0FBQyxDQUFDLENBQUM7QUFFSCxRQUFRLENBQUMsdUJBQXVC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LEdBQUcsQ0FBQyxDQUFDO1lBQzVDLENBQUMsR0FBRyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxFQUFFLENBQUMsSUFBSSxFQUFFLEVBQUUsRUFBRSxHQUFHLEVBQUUsRUFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1lBQzNDLENBQUMsR0FBRyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxFQUFFLENBQUMsSUFBSSxFQUFFLEVBQUUsRUFBRSxHQUFHLEVBQUUsRUFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1lBQzNDLENBQUMsR0FBRyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxFQUFFLENBQUMsSUFBSSxFQUFFLEVBQUUsRUFBRSxHQUFHLEVBQUUsRUFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1lBQzNDLENBQUMsR0FBRyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxFQUFFLENBQUMsSUFBSSxFQUFFLEVBQUUsRUFBRSxHQUFHLEVBQUUsRUFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1lBRTNDLENBQUMsT0FBTyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxFQUFFLENBQUMsSUFBSSxFQUFFLEVBQUUsRUFBRSxFQUFFLEVBQUUsRUFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1lBQzlDLENBQUMsT0FBTyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxFQUFFLENBQUMsSUFBSSxFQUFFLEVBQUUsRUFBRSxHQUFHLEVBQUUsRUFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1lBQy9DLENBQUMsT0FBTyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxFQUFFLENBQUMsSUFBSSxFQUFFLEVBQUUsRUFBRSxHQUFHLEVBQUUsRUFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1NBQ2hELENBQUM7UUFFRixPQUFPLENBQUMsT0FBTyxDQUFDLENBQUMsQ0FBQyxVQUFVLEVBQUUsS0FBSyxDQUFDLEVBQUUsRUFBRTtZQUN0QztnQkFDRSxVQUFVLENBQUMsUUFBUSxFQUFFO2dCQUNyQixVQUFVLENBQUMsZ0JBQWdCLEVBQUU7Z0JBQzdCLFVBQVUsQ0FBQyxjQUFjLEVBQUU7Z0JBQzNCLFVBQVUsQ0FBQyxlQUFlLEVBQUU7Z0JBQzVCLFVBQVUsQ0FBQyxRQUFRLEVBQUU7YUFDdEIsQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUFDLEtBQUssQ0FBQyxDQUFDO1FBQ3RCLENBQUMsQ0FBQyxDQUFDO0lBQ0wsQ0FBQyxDQUFDLENBQUM7QUFDTCxDQUFDLENBQUMsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbIi8qIGVzbGludC1kaXNhYmxlIEB0eXBlc2NyaXB0LWVzbGludC9iYW4tdHMtY29tbWVudCAqL1xuaW1wb3J0ICogYXMgc2hvdWxkIGZyb20gJ3Nob3VsZCc7XG5pbXBvcnQgeyBiaXRnbyB9IGZyb20gJ0BiaXRnby1iZXRhL3V0eG8tbGliJztcbmNvbnN0IHsgY2hhaW5Db2RlcywgY2hhaW5Db2Rlc1Ayc2gsIGNoYWluQ29kZXNQMnNoUDJ3c2gsIGNoYWluQ29kZXNQMnRyLCBjaGFpbkNvZGVzUDJ0ck11c2lnMiwgY2hhaW5Db2Rlc1Ayd3NoIH0gPVxuICBiaXRnbztcbmltcG9ydCB7IERpbWVuc2lvbnMsIE91dHB1dERpbWVuc2lvbnMsIFZpcnR1YWxTaXplcyB9IGZyb20gJy4uL3NyYyc7XG5cbmltcG9ydCB7IGdldE91dHB1dERpbWVuc2lvbnNGb3JVbnNwZW50VHlwZSwgVW5zcGVudFR5cGVQdWJLZXlIYXNoLCBVbnNwZW50VHlwZVNjcmlwdDJvZjMgfSBmcm9tICcuL3Rlc3R1dGlscyc7XG5cbmRlc2NyaWJlKCdEaW1lbnNpb25zIEF0dHJpYnV0ZXMnLCBmdW5jdGlvbiAoKSB7XG4gIGl0KCdoYXMgcmVhZC1vbmx5IG5JbnB1dHMgYW5kIG5PdXRwdXRzJywgZnVuY3Rpb24gKCkge1xuICAgIHNob3VsZC50aHJvd3MoKCkgPT4gKChEaW1lbnNpb25zLlpFUk8gYXMgYW55KS5uSW5wdXRzID0gMSksIC9yZWFkLW9ubHkvKTtcbiAgICBzaG91bGQudGhyb3dzKCgpID0+ICgoRGltZW5zaW9ucy5aRVJPIGFzIGFueSkubk91dHB1dHMgPSAxKSwgL3JlYWQtb25seS8pO1xuICB9KTtcbn0pO1xuXG5kZXNjcmliZSgnT3V0cHV0IERpbWVuc2lvbnMnLCBmdW5jdGlvbiAoKSB7XG4gIGl0KCdpbnN0YW50aWF0ZXMnLCBmdW5jdGlvbiAoKSB7XG4gICAgY29uc3QgZGltcyA9IG5ldyBPdXRwdXREaW1lbnNpb25zKHsgc2l6ZTogMCwgY291bnQ6IDAgfSk7XG4gICAgc2hvdWxkLnRocm93cygoKSA9PiAoZGltcy5jb3VudCArPSAxKSk7XG4gIH0pO1xufSk7XG5cbmRlc2NyaWJlKCdEaW1lbnNpb25zIEFyaXRobWV0aWMnLCBmdW5jdGlvbiAoKSB7XG4gIGl0KCdzdW1zIGNvcnJlY3RseScsIGZ1bmN0aW9uICgpIHtcbiAgICBEaW1lbnNpb25zLnplcm8oKVxuICAgICAgLnBsdXMoeyBuUDJzaElucHV0czogMSB9KVxuICAgICAgLnNob3VsZC5lcWwoXG4gICAgICAgIG5ldyBEaW1lbnNpb25zKHtcbiAgICAgICAgICBuUDJzaElucHV0czogMSxcbiAgICAgICAgICBuUDJzaFAyd3NoSW5wdXRzOiAwLFxuICAgICAgICAgIG5QMndzaElucHV0czogMCxcbiAgICAgICAgICBuUDJ0cktleXBhdGhJbnB1dHM6IDAsXG4gICAgICAgICAgblAydHJTY3JpcHRQYXRoTGV2ZWwxSW5wdXRzOiAwLFxuICAgICAgICAgIG5QMnRyU2NyaXB0UGF0aExldmVsMklucHV0czogMCxcbiAgICAgICAgICBuUDJzaFAycGtJbnB1dHM6IDAsXG4gICAgICAgICAgb3V0cHV0czogeyBzaXplOiAwLCBjb3VudDogMCB9LFxuICAgICAgICB9KVxuICAgICAgKTtcblxuICAgIGNvbnN0IGNvbXBvbmVudHMgPSBbXG4gICAgICB7IG5QMnNoSW5wdXRzOiAxIH0sXG4gICAgICB7IG5QMnNoUDJ3c2hJbnB1dHM6IDIgfSxcbiAgICAgIHsgblAyd3NoSW5wdXRzOiAzIH0sXG4gICAgICB7IG5QMnRyS2V5cGF0aElucHV0czogNCB9LFxuICAgICAgeyBuUDJ0clNjcmlwdFBhdGhMZXZlbDFJbnB1dHM6IDUgfSxcbiAgICAgIHsgblAydHJTY3JpcHRQYXRoTGV2ZWwySW5wdXRzOiA2IH0sXG4gICAgICB7IG91dHB1dHM6IHsgc2l6ZTogMjMsIGNvdW50OiAxIH0gfSxcbiAgICAgIHsgb3V0cHV0czogeyBzaXplOiA0NCwgY291bnQ6IDIgfSB9LFxuICAgICAgeyBvdXRwdXRzOiB7IHNpemU6IDAsIGNvdW50OiAwIH0gfSxcbiAgICBdO1xuXG4gICAgY29tcG9uZW50cy5mb3JFYWNoKChjb21wb25lbnQpID0+IHNob3VsZC5kb2VzTm90VGhyb3coKCkgPT4gRGltZW5zaW9ucy5zdW0oY29tcG9uZW50KSkpO1xuXG4gICAgY29uc3Qgc3VtID0gY29tcG9uZW50cy5yZWR1Y2UoKGEsIGIpID0+IGEucGx1cyhiKSwgRGltZW5zaW9ucy56ZXJvKCkpO1xuXG4gICAgc3VtLnNob3VsZC5lcWwoRGltZW5zaW9ucy5zdW0oLi4uY29tcG9uZW50cykpO1xuXG4gICAgc3VtLnNob3VsZC5lcWwoXG4gICAgICBuZXcgRGltZW5zaW9ucyh7XG4gICAgICAgIG5QMnNoSW5wdXRzOiAxLFxuICAgICAgICBuUDJzaFAyd3NoSW5wdXRzOiAyLFxuICAgICAgICBuUDJ3c2hJbnB1dHM6IDMsXG4gICAgICAgIG5QMnRyS2V5cGF0aElucHV0czogNCxcbiAgICAgICAgblAydHJTY3JpcHRQYXRoTGV2ZWwxSW5wdXRzOiA1LFxuICAgICAgICBuUDJ0clNjcmlwdFBhdGhMZXZlbDJJbnB1dHM6IDYsXG4gICAgICAgIG5QMnNoUDJwa0lucHV0czogMCxcbiAgICAgICAgb3V0cHV0czogeyBzaXplOiA2NywgY291bnQ6IDMgfSxcbiAgICAgIH0pXG4gICAgKTtcblxuICAgIHN1bS5uT3V0cHV0cy5zaG91bGQuZXFsKHN1bS5vdXRwdXRzLmNvdW50KTtcbiAgfSk7XG5cbiAgaXQoJ3Byb3ZpZGVzIHNvbWUgdHlwaWNhbCBvdXRwdXQgc2l6ZXMnLCBmdW5jdGlvbiAoKSB7XG4gICAgKFxuICAgICAgW1xuICAgICAgICBbRGltZW5zaW9ucy5TaW5nbGVPdXRwdXQucDJzaCwgVmlydHVhbFNpemVzLnR4UDJzaE91dHB1dFNpemVdLFxuICAgICAgICBbRGltZW5zaW9ucy5TaW5nbGVPdXRwdXQucDJzaFAyd3NoLCBWaXJ0dWFsU2l6ZXMudHhQMnNoUDJ3c2hPdXRwdXRTaXplXSxcbiAgICAgICAgW0RpbWVuc2lvbnMuU2luZ2xlT3V0cHV0LnAyd3NoLCBWaXJ0dWFsU2l6ZXMudHhQMndzaE91dHB1dFNpemVdLFxuICAgICAgICBbRGltZW5zaW9ucy5TaW5nbGVPdXRwdXQucDJwa2gsIFZpcnR1YWxTaXplcy50eFAycGtoT3V0cHV0U2l6ZV0sXG4gICAgICAgIFtEaW1lbnNpb25zLlNpbmdsZU91dHB1dC5wMndwa2gsIFZpcnR1YWxTaXplcy50eFAyd3BraE91dHB1dFNpemVdLFxuICAgICAgICBbRGltZW5zaW9ucy5TaW5nbGVPdXRwdXQucDJ0ciwgVmlydHVhbFNpemVzLnR4UDJ0ck91dHB1dFNpemVdLFxuICAgICAgXSBhcyBbRGltZW5zaW9ucywgbnVtYmVyXVtdXG4gICAgKS5mb3JFYWNoKChbZGltcywgc2l6ZV0pID0+IHtcbiAgICAgIGRpbXMuZ2V0T3V0cHV0c1ZTaXplKCkuc2hvdWxkLmVxbChzaXplKTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgaXQoJ3ByZXZlbnRzIHN1bSBvZiBpbnZhbGlkIGRhdGEnLCBmdW5jdGlvbiAoKSB7XG4gICAgc2hvdWxkLmRvZXNOb3RUaHJvdygoKSA9PiBEaW1lbnNpb25zLnN1bSh7IG91dHB1dHM6IHsgY291bnQ6IDAsIHNpemU6IDAgfSB9KSk7XG4gICAgc2hvdWxkLmRvZXNOb3RUaHJvdygoKSA9PiBEaW1lbnNpb25zLnN1bSh7IG91dHB1dHM6IHsgY291bnQ6IDEsIHNpemU6IDEgfSB9KSk7XG4gICAgc2hvdWxkLnRocm93cygoKSA9PiBEaW1lbnNpb25zLnN1bSh7IG5PdXRwdXRzOiAxIH0pKTtcbiAgICBzaG91bGQudGhyb3dzKCgpID0+IERpbWVuc2lvbnMuc3VtKHsgbk91dHB1dHM6IDEsIG91dHB1dHM6IHsgY291bnQ6IDIsIHNpemU6IDEgfSB9KSk7XG4gICAgLy8gQHRzLWlnbm9yZVxuICAgIHNob3VsZC50aHJvd3MoKCkgPT4gRGltZW5zaW9ucy5zdW0oeyBuUDJzaElucHV0czogMSB9LCB7IG5QMnNoSW5wdXRzOiAnZm9vJyB9KSk7XG4gICAgc2hvdWxkLnRocm93cygoKSA9PiBEaW1lbnNpb25zLnN1bSh7IG91dHB1dHM6IHsgY291bnQ6IDEsIHNpemU6IDAgfSB9KSk7XG4gICAgc2hvdWxkLnRocm93cygoKSA9PiBEaW1lbnNpb25zLnN1bSh7IG91dHB1dHM6IHsgY291bnQ6IDAsIHNpemU6IDEgfSB9KSk7XG4gICAgc2hvdWxkLnRocm93cygoKSA9PiBEaW1lbnNpb25zLnN1bSh7IG91dHB1dHM6IHsgY291bnQ6IDEsIHNpemU6IDEgfSB9LCB7IG91dHB1dHM6IHsgY291bnQ6IDEsIHNpemU6IDAgfSB9KSk7XG4gIH0pO1xuXG4gIGl0KCdjb3VudHMgaW5wdXRzIGNvcnJlY3RseScsIGZ1bmN0aW9uICgpIHtcbiAgICBPYmplY3QuZW50cmllcyhEaW1lbnNpb25zLlNpbmdsZUlucHV0KS5mb3JFYWNoKChba2V5LCB2YWx1ZV0pID0+IHtcbiAgICAgIHZhbHVlLm5JbnB1dHMuc2hvdWxkLmVxbCgxLCBrZXkpO1xuICAgIH0pO1xuICB9KTtcblxuICBpdCgnbXVsdGlwbGllcyBjb3JyZWN0bHknLCBmdW5jdGlvbiAoKSB7XG4gICAgY29uc3QgZCA9IG5ldyBEaW1lbnNpb25zKHtcbiAgICAgIG5QMnNoSW5wdXRzOiAxLFxuICAgICAgblAyc2hQMndzaElucHV0czogMixcbiAgICAgIG5QMndzaElucHV0czogMyxcbiAgICAgIG5QMnRyS2V5cGF0aElucHV0czogNCxcbiAgICAgIG5QMnRyU2NyaXB0UGF0aExldmVsMUlucHV0czogNSxcbiAgICAgIG5QMnRyU2NyaXB0UGF0aExldmVsMklucHV0czogNixcbiAgICAgIG5QMnNoUDJwa0lucHV0czogNyxcbiAgICAgIG91dHB1dHM6IHsgY291bnQ6IDEsIHNpemU6IDIyIH0sXG4gICAgfSkudGltZXMoMyk7XG5cbiAgICBkLnNob3VsZC5lcWwoXG4gICAgICBuZXcgRGltZW5zaW9ucyh7XG4gICAgICAgIG5QMnNoSW5wdXRzOiAzLFxuICAgICAgICBuUDJzaFAyd3NoSW5wdXRzOiA2LFxuICAgICAgICBuUDJ3c2hJbnB1dHM6IDksXG4gICAgICAgIG5QMnRyS2V5cGF0aElucHV0czogMTIsXG4gICAgICAgIG5QMnRyU2NyaXB0UGF0aExldmVsMUlucHV0czogMTUsXG4gICAgICAgIG5QMnRyU2NyaXB0UGF0aExldmVsMklucHV0czogMTgsXG4gICAgICAgIG5QMnNoUDJwa0lucHV0czogMjEsXG4gICAgICAgIG91dHB1dHM6IHsgY291bnQ6IDMsIHNpemU6IDY2IH0sXG4gICAgICB9KVxuICAgICk7XG5cbiAgICBkLmdldE5JbnB1dHMoKS5zaG91bGQuZXFsKDg0KTtcbiAgICBkLm5JbnB1dHMuc2hvdWxkLmVxbCg4NCk7XG4gIH0pO1xufSk7XG5cbmRlc2NyaWJlKCdEaW1lbnNpb25zIGZyb20gdW5zcGVudCB0eXBlcycsIGZ1bmN0aW9uICgpIHtcbiAgaXQoJ2RldGVybWluZXMgdW5zcGVudCBzaXplIGFjY29yZGluZyB0byBjaGFpbicsIGZ1bmN0aW9uICgpIHtcbiAgICBjaGFpbkNvZGVzUDJzaC5mb3JFYWNoKChjaGFpbikgPT4gRGltZW5zaW9ucy5mcm9tVW5zcGVudCh7IGNoYWluIH0pLnNob3VsZC5lcWwoRGltZW5zaW9ucy5zdW0oeyBuUDJzaElucHV0czogMSB9KSkpO1xuXG4gICAgY2hhaW5Db2Rlc1Ayc2hQMndzaC5mb3JFYWNoKChjaGFpbikgPT5cbiAgICAgIERpbWVuc2lvbnMuZnJvbVVuc3BlbnQoeyBjaGFpbiB9KS5zaG91bGQuZXFsKERpbWVuc2lvbnMuc3VtKHsgblAyc2hQMndzaElucHV0czogMSB9KSlcbiAgICApO1xuXG4gICAgY2hhaW5Db2Rlc1Ayd3NoLmZvckVhY2goKGNoYWluKSA9PlxuICAgICAgRGltZW5zaW9ucy5mcm9tVW5zcGVudCh7IGNoYWluIH0pLnNob3VsZC5lcWwoRGltZW5zaW9ucy5zdW0oeyBuUDJ3c2hJbnB1dHM6IDEgfSkpXG4gICAgKTtcblxuICAgIGNoYWluQ29kZXNQMnRyLmZvckVhY2goKGNoYWluKSA9PiB7XG4gICAgICBEaW1lbnNpb25zLmZyb21VbnNwZW50KHsgY2hhaW4gfSkuc2hvdWxkLmVxbChEaW1lbnNpb25zLnN1bSh7IG5QMnRyU2NyaXB0UGF0aExldmVsMUlucHV0czogMSB9KSk7XG4gICAgICBEaW1lbnNpb25zLmZyb21VbnNwZW50KFxuICAgICAgICB7IGNoYWluIH0sXG4gICAgICAgIHsgcDJ0cjogeyBzY3JpcHRQYXRoTGV2ZWw6IDIgfSwgcDJ0ck11c2lnMjogeyBzY3JpcHRQYXRoTGV2ZWw6IHVuZGVmaW5lZCB9IH1cbiAgICAgICkuc2hvdWxkLmVxbChEaW1lbnNpb25zLnN1bSh7IG5QMnRyU2NyaXB0UGF0aExldmVsMklucHV0czogMSB9KSk7XG4gICAgfSk7XG5cbiAgICBjaGFpbkNvZGVzUDJ0ck11c2lnMi5mb3JFYWNoKChjaGFpbikgPT4ge1xuICAgICAgRGltZW5zaW9ucy5mcm9tVW5zcGVudCh7IGNoYWluIH0pLnNob3VsZC5lcWwoRGltZW5zaW9ucy5zdW0oeyBuUDJ0clNjcmlwdFBhdGhMZXZlbDFJbnB1dHM6IDEgfSkpO1xuICAgICAgRGltZW5zaW9ucy5mcm9tVW5zcGVudChcbiAgICAgICAgeyBjaGFpbiB9LFxuICAgICAgICB7IHAydHI6IHsgc2NyaXB0UGF0aExldmVsOiB1bmRlZmluZWQgfSwgcDJ0ck11c2lnMjogeyBzY3JpcHRQYXRoTGV2ZWw6IHVuZGVmaW5lZCB9IH1cbiAgICAgICkuc2hvdWxkLmVxbChEaW1lbnNpb25zLnN1bSh7IG5QMnRyS2V5cGF0aElucHV0czogMSB9KSk7XG4gICAgfSk7XG5cbiAgICBEaW1lbnNpb25zLmZyb21VbnNwZW50cyhjaGFpbkNvZGVzLm1hcCgoY2hhaW4pID0+ICh7IGNoYWluIH0pKSkuc2hvdWxkLmVxbChcbiAgICAgIG5ldyBEaW1lbnNpb25zKHtcbiAgICAgICAgblAyc2hQMndzaElucHV0czogMixcbiAgICAgICAgblAyc2hJbnB1dHM6IDIsXG4gICAgICAgIG5QMndzaElucHV0czogMixcbiAgICAgICAgblAydHJLZXlwYXRoSW5wdXRzOiAwLFxuICAgICAgICBuUDJ0clNjcmlwdFBhdGhMZXZlbDFJbnB1dHM6IDQsXG4gICAgICAgIG5QMnRyU2NyaXB0UGF0aExldmVsMklucHV0czogMCxcbiAgICAgICAgblAyc2hQMnBrSW5wdXRzOiAwLFxuICAgICAgICBvdXRwdXRzOiB7IGNvdW50OiAwLCBzaXplOiAwIH0sXG4gICAgICB9KVxuICAgICk7XG4gIH0pO1xuXG4gIGl0KCdjYWxjdWxhdGVzIG91dHB1dCBkaW1lbnNpb25zIGR5bmFtaWNhbGx5JywgZnVuY3Rpb24gKCkge1xuICAgIGNvbnN0IGV4cGVjdGVkU2l6ZXMgPSBuZXcgTWFwKFtcbiAgICAgIFtVbnNwZW50VHlwZVNjcmlwdDJvZjMucDJzaCwgVmlydHVhbFNpemVzLnR4UDJzaE91dHB1dFNpemVdLFxuICAgICAgW1Vuc3BlbnRUeXBlU2NyaXB0Mm9mMy5wMnNoUDJ3c2gsIFZpcnR1YWxTaXplcy50eFAyc2hQMndzaE91dHB1dFNpemVdLFxuICAgICAgW1Vuc3BlbnRUeXBlU2NyaXB0Mm9mMy5wMndzaCwgVmlydHVhbFNpemVzLnR4UDJ3c2hPdXRwdXRTaXplXSxcbiAgICAgIFtVbnNwZW50VHlwZVNjcmlwdDJvZjMucDJ0ciwgVmlydHVhbFNpemVzLnR4UDJ0ck91dHB1dFNpemVdLFxuICAgICAgW1Vuc3BlbnRUeXBlU2NyaXB0Mm9mMy5wMnRyTXVzaWcyLCBWaXJ0dWFsU2l6ZXMudHhQMnRyT3V0cHV0U2l6ZV0sXG4gICAgICBbVW5zcGVudFR5cGVTY3JpcHQyb2YzLnRhcHJvb3RLZXlQYXRoU3BlbmQsIFZpcnR1YWxTaXplcy50eFAydHJPdXRwdXRTaXplXSxcbiAgICAgIFtVbnNwZW50VHlwZVB1YktleUhhc2gucDJwa2gsIFZpcnR1YWxTaXplcy50eFAycGtoT3V0cHV0U2l6ZV0sXG4gICAgICBbVW5zcGVudFR5cGVQdWJLZXlIYXNoLnAyd3BraCwgVmlydHVhbFNpemVzLnR4UDJ3cGtoT3V0cHV0U2l6ZV0sXG4gICAgXSk7XG5cbiAgICBbLi4uT2JqZWN0LmtleXMoVW5zcGVudFR5cGVTY3JpcHQyb2YzKSwgLi4uT2JqZWN0LmtleXMoVW5zcGVudFR5cGVQdWJLZXlIYXNoKV0uZm9yRWFjaCgodHlwZSkgPT5cbiAgICAgIGdldE91dHB1dERpbWVuc2lvbnNGb3JVbnNwZW50VHlwZSh0eXBlKS5vdXRwdXRzLnNpemUuc2hvdWxkLmVxbChleHBlY3RlZFNpemVzLmdldCh0eXBlIGFzIGFueSkpXG4gICAgKTtcbiAgfSk7XG59KTtcblxuZGVzY3JpYmUoJ0RpbWVuc2lvbnMgZXN0aW1hdGVzJywgZnVuY3Rpb24gKCkge1xuICBpdCgnY2FsY3VsYXRlcyB2c2l6ZXMnLCBmdW5jdGlvbiAoKSB7XG4gICAgZnVuY3Rpb24gZGltKG5QMnNoSW5wdXRzOiBudW1iZXIsIG5QMnNoUDJ3c2hJbnB1dHM6IG51bWJlciwgblAyd3NoSW5wdXRzOiBudW1iZXIsIG5PdXRwdXRzOiBudW1iZXIpOiBEaW1lbnNpb25zIHtcbiAgICAgIHJldHVybiBEaW1lbnNpb25zLnN1bShcbiAgICAgICAge1xuICAgICAgICAgIG5QMnNoSW5wdXRzLFxuICAgICAgICAgIG5QMnNoUDJ3c2hJbnB1dHMsXG4gICAgICAgICAgblAyd3NoSW5wdXRzLFxuICAgICAgICB9LFxuICAgICAgICBnZXRPdXRwdXREaW1lbnNpb25zRm9yVW5zcGVudFR5cGUoVW5zcGVudFR5cGVQdWJLZXlIYXNoLnAycGtoKS50aW1lcyhuT3V0cHV0cylcbiAgICAgICk7XG4gICAgfVxuXG4gICAgZnVuY3Rpb24gZGltUDJ0cihcbiAgICAgIG5QMnRyS2V5cGF0aElucHV0czogbnVtYmVyLFxuICAgICAgblAydHJTY3JpcHRQYXRoTGV2ZWwxSW5wdXRzOiBudW1iZXIsXG4gICAgICBuUDJ0clNjcmlwdFBhdGhMZXZlbDJJbnB1dHM6IG51bWJlcixcbiAgICAgIG5PdXRwdXRzOiBudW1iZXJcbiAgICApOiBEaW1lbnNpb25zIHtcbiAgICAgIHJldHVybiBEaW1lbnNpb25zLnN1bShcbiAgICAgICAge1xuICAgICAgICAgIG5QMnRyS2V5cGF0aElucHV0cyxcbiAgICAgICAgICBuUDJ0clNjcmlwdFBhdGhMZXZlbDFJbnB1dHMsXG4gICAgICAgICAgblAydHJTY3JpcHRQYXRoTGV2ZWwySW5wdXRzLFxuICAgICAgICB9LFxuICAgICAgICBnZXRPdXRwdXREaW1lbnNpb25zRm9yVW5zcGVudFR5cGUoVW5zcGVudFR5cGVQdWJLZXlIYXNoLnAycGtoKS50aW1lcyhuT3V0cHV0cylcbiAgICAgICk7XG4gICAgfVxuXG4gICAgY29uc3QgdmVjdG9yczogW0RpbWVuc2lvbnMsIHVua25vd25bXV1bXSA9IFtcbiAgICAgIFtkaW0oMSwgMCwgMCwgMSksIFtmYWxzZSwgMTAsIDI5OCwgMzQsIDM0Ml1dLFxuICAgICAgW2RpbSgwLCAxLCAwLCAxKSwgW3RydWUsIDExLCAxNDAsIDM0LCAxODVdXSxcbiAgICAgIFtkaW0oMCwgMCwgMSwgMSksIFt0cnVlLCAxMSwgMTA1LCAzNCwgMTUwXV0sXG4gICAgICBbZGltKDIsIDAsIDAsIDEpLCBbZmFsc2UsIDEwLCA1OTYsIDM0LCA2NDBdXSxcbiAgICAgIFtkaW0oMCwgMiwgMCwgMSksIFt0cnVlLCAxMSwgMjgwLCAzNCwgMzI1XV0sXG4gICAgICBbZGltKDAsIDAsIDIsIDEpLCBbdHJ1ZSwgMTEsIDIxMCwgMzQsIDI1NV1dLFxuICAgICAgW2RpbSgxLCAxLCAxLCAxKSwgW3RydWUsIDExLCA1NDMsIDM0LCA1ODhdXSxcbiAgICAgIFtkaW0oMSwgMSwgMSwgMiksIFt0cnVlLCAxMSwgNTQzLCA2OCwgNjIyXV0sXG5cbiAgICAgIFtkaW1QMnRyKDEsIDAsIDAsIDEpLCBbdHJ1ZSwgMTEsIDU4LCAzNCwgMTAzXV0sXG4gICAgICBbZGltUDJ0cigwLCAxLCAwLCAxKSwgW3RydWUsIDExLCAxMDgsIDM0LCAxNTNdXSxcbiAgICAgIFtkaW1QMnRyKDAsIDAsIDEsIDEpLCBbdHJ1ZSwgMTEsIDExNiwgMzQsIDE2MV1dLFxuICAgIF07XG5cbiAgICB2ZWN0b3JzLmZvckVhY2goKFtkaW1lbnNpb25zLCBwcm9wc10pID0+IHtcbiAgICAgIFtcbiAgICAgICAgZGltZW5zaW9ucy5pc1NlZ3dpdCgpLFxuICAgICAgICBkaW1lbnNpb25zLmdldE92ZXJoZWFkVlNpemUoKSxcbiAgICAgICAgZGltZW5zaW9ucy5nZXRJbnB1dHNWU2l6ZSgpLFxuICAgICAgICBkaW1lbnNpb25zLmdldE91dHB1dHNWU2l6ZSgpLFxuICAgICAgICBkaW1lbnNpb25zLmdldFZTaXplKCksXG4gICAgICBdLnNob3VsZC5lcWwocHJvcHMpO1xuICAgIH0pO1xuICB9KTtcbn0pO1xuIl19
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=inputWeights.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"inputWeights.d.ts","sourceRoot":"","sources":["../../../test/signedTx/inputWeights.ts"],"names":[],"mappings":""}
@@ -0,0 +1,113 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });
5
+ }) : (function(o, m, k, k2) {
6
+ if (k2 === undefined) k2 = k;
7
+ o[k2] = m[k];
8
+ }));
9
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
10
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
11
+ }) : function(o, v) {
12
+ o["default"] = v;
13
+ });
14
+ var __importStar = (this && this.__importStar) || function (mod) {
15
+ if (mod && mod.__esModule) return mod;
16
+ var result = {};
17
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
18
+ __setModuleDefault(result, mod);
19
+ return result;
20
+ };
21
+ Object.defineProperty(exports, "__esModule", { value: true });
22
+ const assert = __importStar(require("assert"));
23
+ const utxolib = __importStar(require("@bitgo-beta/utxo-lib"));
24
+ const utxo_lib_1 = require("@bitgo-beta/utxo-lib");
25
+ const inputWeights_1 = require("../../src/inputWeights");
26
+ const scriptSizes_1 = require("../../src/scriptSizes");
27
+ const testutils_1 = require("../testutils");
28
+ describe('Input Script Sizes (Worst-Case)', function () {
29
+ const keys = [1, 2, 3].map((v) => utxo_lib_1.bip32.fromSeed(Buffer.alloc(16, `test/${v}`)));
30
+ const rootWalletKeys = new utxolib.bitgo.RootWalletKeys([keys[0], keys[1], keys[2]]);
31
+ function getLargestInputWithType(inputType, signKeys, inputCount = 100) {
32
+ const signerName = signKeys[0];
33
+ const cosignerName = signKeys.length > 1 ? signKeys[1] : signerName;
34
+ const inputScriptTypes = Array.from({ length: inputCount }).fill(inputType);
35
+ const outputScriptTypes = [testutils_1.UnspentTypeScript2of3.p2sh];
36
+ return testutils_1.getSignedTransaction(rootWalletKeys, signerName, cosignerName, inputScriptTypes, outputScriptTypes).ins.reduce((a, b) => (inputWeights_1.getInputWeight(a) > inputWeights_1.getInputWeight(b) ? a : b));
37
+ }
38
+ function getInputComponents(input) {
39
+ const decompiled = utxolib.script.decompile(input.script);
40
+ if (!decompiled) {
41
+ throw new Error();
42
+ }
43
+ const script = decompiled.map((v) => {
44
+ if (!Buffer.isBuffer(v)) {
45
+ return { length: 1 };
46
+ }
47
+ return { length: v.length + scriptSizes_1.pushdataEncodingLength(v.length) };
48
+ });
49
+ const witness = (input.witness || []).map((v) => ({ length: v.length }));
50
+ const scriptSize = script.reduce((a, b) => a + b.length, 0);
51
+ assert.strictEqual(scriptSize, input.script.length, utxolib.script.toASM(decompiled));
52
+ return {
53
+ script: script.map((v) => v.length),
54
+ witness: witness.map((v) => v.length),
55
+ };
56
+ }
57
+ function runTestComponentSizes(inputType, signKeys) {
58
+ const signKeysStr = signKeys.join(',');
59
+ describe(`inputType=${inputType} signKeys=${signKeysStr}`, function () {
60
+ it(`component sizes`, function () {
61
+ this.timeout(10000);
62
+ let expectedComponents;
63
+ switch (inputType) {
64
+ case 'p2sh':
65
+ expectedComponents = inputWeights_1.inputComponentsP2sh;
66
+ break;
67
+ case 'p2shP2wsh':
68
+ expectedComponents = inputWeights_1.inputComponentsP2shP2wsh;
69
+ break;
70
+ case 'p2wsh':
71
+ expectedComponents = inputWeights_1.inputComponentsP2wsh;
72
+ break;
73
+ case 'p2shP2pk':
74
+ expectedComponents = inputWeights_1.inputComponentsP2shP2pk;
75
+ break;
76
+ case 'p2tr':
77
+ if (signKeys[1] === 'bitgo') {
78
+ expectedComponents = inputWeights_1.inputComponentsP2trScriptSpendLevel1;
79
+ }
80
+ else if (signKeys[1] === 'backup') {
81
+ expectedComponents = inputWeights_1.inputComponentsP2trScriptSpendLevel2;
82
+ }
83
+ else {
84
+ throw new Error(`unexpected cosigner`);
85
+ }
86
+ break;
87
+ case 'p2trMusig2':
88
+ // assumes only script path
89
+ expectedComponents = inputWeights_1.inputComponentsP2trScriptSpendLevel1;
90
+ break;
91
+ case 'taprootKeyPathSpend':
92
+ expectedComponents = inputWeights_1.inputComponentsP2trKeySpend;
93
+ break;
94
+ default:
95
+ throw new Error(`invalid inputType ${inputType}`);
96
+ }
97
+ const input = getLargestInputWithType(inputType, signKeys, inputType === 'p2tr' || inputType === 'p2trMusig2' || inputType === 'taprootKeyPathSpend' ? 10 : 100);
98
+ const components = getInputComponents(input);
99
+ assert.deepStrictEqual(components, expectedComponents);
100
+ assert.strictEqual(inputWeights_1.getInputComponentsWeight(components), inputWeights_1.getInputWeight(input));
101
+ });
102
+ });
103
+ }
104
+ testutils_1.getInputScriptTypes().forEach((inputType) => {
105
+ if (inputType !== 'p2trMusig2') {
106
+ runTestComponentSizes(inputType, inputType === 'p2shP2pk' ? ['user'] : ['user', 'bitgo']);
107
+ }
108
+ if (inputType !== 'p2shP2pk' && inputType !== 'taprootKeyPathSpend') {
109
+ runTestComponentSizes(inputType, ['user', 'backup']);
110
+ }
111
+ });
112
+ });
113
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5wdXRXZWlnaHRzLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vdGVzdC9zaWduZWRUeC9pbnB1dFdlaWdodHMudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBQUEsK0NBQWlDO0FBR2pDLDhEQUFnRDtBQUNoRCxtREFBNkQ7QUFDN0QseURBV2dDO0FBQ2hDLHVEQUErRDtBQUMvRCw0Q0FNc0I7QUFFdEIsUUFBUSxDQUFDLGlDQUFpQyxFQUFFO0lBQzFDLE1BQU0sSUFBSSxHQUFHLENBQUMsQ0FBQyxFQUFFLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLEVBQUUsRUFBRSxDQUFDLGdCQUFLLENBQUMsUUFBUSxDQUFDLE1BQU0sQ0FBQyxLQUFLLENBQUMsRUFBRSxFQUFFLFFBQVEsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFxQixDQUFDO0lBQ3JHLE1BQU0sY0FBYyxHQUFHLElBQUksT0FBTyxDQUFDLEtBQUssQ0FBQyxjQUFjLENBQUMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFFckYsU0FBUyx1QkFBdUIsQ0FDOUIsU0FBaUIsRUFDakIsUUFBaUMsRUFDakMsVUFBVSxHQUFHLEdBQUc7UUFFaEIsTUFBTSxVQUFVLEdBQUcsUUFBUSxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBQy9CLE1BQU0sWUFBWSxHQUFHLFFBQVEsQ0FBQyxNQUFNLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxRQUFRLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLFVBQVUsQ0FBQztRQUNwRSxNQUFNLGdCQUFnQixHQUFHLEtBQUssQ0FBQyxJQUFJLENBQUMsRUFBRSxNQUFNLEVBQUUsVUFBVSxFQUFFLENBQUMsQ0FBQyxJQUFJLENBQUMsU0FBUyxDQUFzQixD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QUMsQ0FBQyxTQUFpQixFQUFFLEVBQUU7UUFDbEQsSUFBSSxTQUFTLEtBQUssWUFBWSxFQUFFO1lBQzlCLHFCQUFxQixDQUFDLFNBQVMsRUFBRSxTQUFTLEtBQUssVUFBVSxDQUFDLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLE1BQU0sRUFBRSxPQUFPLENBQUMsQ0FBQyxDQUFDO1NBQzNGO1FBQ0QsSUFBSSxTQUFTLEtBQUssVUFBVSxJQUFJLFNBQVMsS0FBSyxxQkFBcUIsRUFBRTtZQUNuRSxxQkFBcUIsQ0FBQyxTQUFTLEVBQUUsQ0FBQyxNQUFNLEVBQUUsUUFBUSxDQUFDLENBQUMsQ0FBQztTQUN0RDtJQUNILENBQUMsQ0FBQyxDQUFDO0FBQ0wsQ0FBQyxDQUFDLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgKiBhcyBhc3NlcnQgZnJvbSAnYXNzZXJ0JztcblxuaW1wb3J0ICogYXMgbW9jaGEgZnJvbSAnbW9jaGEnO1xuaW1wb3J0ICogYXMgdXR4b2xpYiBmcm9tICdAYml0Z28tYmV0YS91dHhvLWxpYic7XG5pbXBvcnQgeyBiaXAzMiwgQklQMzJJbnRlcmZhY2UgfSBmcm9tICdAYml0Z28tYmV0YS91dHhvLWxpYic7XG5pbXBvcnQge1xuICBnZXRJbnB1dENvbXBvbmVudHNXZWlnaHQsXG4gIGdldElucHV0V2VpZ2h0LFxuICBJbnB1dENvbXBvbmVudHMsXG4gIGlucHV0Q29tcG9uZW50c1Ayc2gsXG4gIGlucHV0Q29tcG9uZW50c1Ayc2hQMnBrLFxuICBpbnB1dENvbXBvbmVudHNQMnNoUDJ3c2gsXG4gIGlucHV0Q29tcG9uZW50c1AydHJLZXlTcGVuZCxcbiAgaW5wdXRDb21wb25lbnRzUDJ0clNjcmlwdFNwZW5kTGV2ZWwxLFxuICBpbnB1dENvbXBvbmVudHNQMnRyU2NyaXB0U3BlbmRMZXZlbDIsXG4gIGlucHV0Q29tcG9uZW50c1Ayd3NoLFxufSBmcm9tICcuLi8uLi9zcmMvaW5wdXRXZWlnaHRzJztcbmltcG9ydCB7IHB1c2hkYXRhRW5jb2RpbmdMZW5ndGggfSBmcm9tICcuLi8uLi9zcmMvc2NyaXB0U2l6ZXMnO1xuaW1wb3J0IHtcbiAgZ2V0SW5wdXRTY3JpcHRUeXBlcyxcbiAgZ2V0U2lnbmVkVHJhbnNhY3Rpb24sXG4gIElucHV0U2NyaXB0VHlwZSxcbiAgVGVzdFVuc3BlbnRUeXBlLFxuICBVbnNwZW50VHlwZVNjcmlwdDJvZjMsXG59IGZyb20gJy4uL3Rlc3R1dGlscyc7XG5cbmRlc2NyaWJlKCdJbnB1dCBTY3JpcHQgU2l6ZXMgKFdvcnN0LUNhc2UpJywgZnVuY3Rpb24gKCkge1xuICBjb25zdCBrZXlzID0gWzEsIDIsIDNdLm1hcCgodikgPT4gYmlwMzIuZnJvbVNlZWQoQnVmZmVyLmFsbG9jKDE2LCBgdGVzdC8ke3Z9YCkpKSBhcyBCSVAzMkludGVyZmFjZVtdO1xuICBjb25zdCByb290V2FsbGV0S2V5cyA9IG5ldyB1dHhvbGliLmJpdGdvLlJvb3RXYWxsZXRLZXlzKFtrZXlzWzBdLCBrZXlzWzFdLCBrZXlzWzJdXSk7XG5cbiAgZnVuY3Rpb24gZ2V0TGFyZ2VzdElucHV0V2l0aFR5cGUoXG4gICAgaW5wdXRUeXBlOiBzdHJpbmcsXG4gICAgc2lnbktleXM6IHV0eG9saWIuYml0Z28uS2V5TmFtZVtdLFxuICAgIGlucHV0Q291bnQgPSAxMDBcbiAgKTogdXR4b2xpYi5UeElucHV0IHtcbiAgICBjb25zdCBzaWduZXJOYW1lID0gc2lnbktleXNbMF07XG4gICAgY29uc3QgY29zaWduZXJOYW1lID0gc2lnbktleXMubGVuZ3RoID4gMSA/IHNpZ25LZXlzWzFdIDogc2lnbmVyTmFtZTtcbiAgICBjb25zdCBpbnB1dFNjcmlwdFR5cGVzID0gQXJyYXkuZnJvbSh7IGxlbmd0aDogaW5wdXRDb3VudCB9KS5maWxsKGlucHV0VHlwZSkgYXMgSW5wdXRTY3JpcHRUeXBlW107XG4gICAgY29uc3Qgb3V0cHV0U2NyaXB0VHlwZXMgPSBbVW5zcGVudFR5cGVTY3JpcHQyb2YzLnAyc2hdIGFzIFRlc3RVbnNwZW50VHlwZVtdO1xuICAgIHJldHVybiBnZXRTaWduZWRUcmFuc2FjdGlvbihcbiAgICAgIHJvb3RXYWxsZXRLZXlzLFxuICAgICAgc2lnbmVyTmFtZSxcbiAgICAgIGNvc2lnbmVyTmFtZSxcbiAgICAgIGlucHV0U2NyaXB0VHlwZXMsXG4gICAgICBvdXRwdXRTY3JpcHRUeXBlc1xuICAgICkuaW5zLnJlZHVjZSgoYSwgYikgPT4gKGdldElucHV0V2VpZ2h0KGEpID4gZ2V0SW5wdXRXZWlnaHQoYikgPyBhIDogYikpO1xuICB9XG5cbiAgZnVuY3Rpb24gZ2V0SW5wdXRDb21wb25lbnRzKGlucHV0OiB1dHhvbGliLlR4SW5wdXQpOiBJbnB1dENvbXBvbmVudHMge1xuICAgIGNvbnN0IGRlY29tcGlsZWQgPSB1dHhvbGliLnNjcmlwdC5kZWNvbXBpbGUoaW5wdXQuc2NyaXB0KTtcbiAgICBpZiAoIWRlY29tcGlsZWQpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcigpO1xuICAgIH1cblxuICAgIGNvbnN0IHNjcmlwdCA9IGRlY29tcGlsZWQubWFwKCh2KSA9PiB7XG4gICAgICBpZiAoIUJ1ZmZlci5pc0J1ZmZlcih2KSkge1xuICAgICAgICByZXR1cm4geyBsZW5ndGg6IDEgfTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB7IGxlbmd0aDogdi5sZW5ndGggKyBwdXNoZGF0YUVuY29kaW5nTGVuZ3RoKHYubGVuZ3RoKSB9O1xuICAgIH0pO1xuICAgIGNvbnN0IHdpdG5lc3MgPSAoaW5wdXQud2l0bmVzcyB8fCBbXSkubWFwKCh2KSA9PiAoeyBsZW5ndGg6IHYubGVuZ3RoIH0pKTtcblxuICAgIGNvbnN0IHNjcmlwdFNpemUgPSBzY3JpcHQucmVkdWNlKChhLCBiKSA9PiBhICsgYi5sZW5ndGgsIDApO1xuICAgIGFzc2VydC5zdHJpY3RFcXVhbChzY3JpcHRTaXplLCBpbnB1dC5zY3JpcHQubGVuZ3RoLCB1dHhvbGliLnNjcmlwdC50b0FTTShkZWNvbXBpbGVkKSk7XG5cbiAgICByZXR1cm4ge1xuICAgICAgc2NyaXB0OiBzY3JpcHQubWFwKCh2KSA9PiB2Lmxlbmd0aCksXG4gICAgICB3aXRuZXNzOiB3aXRuZXNzLm1hcCgodikgPT4gdi5sZW5ndGgpLFxuICAgIH07XG4gIH1cblxuICBmdW5jdGlvbiBydW5UZXN0Q29tcG9uZW50U2l6ZXMoaW5wdXRUeXBlOiBzdHJpbmcsIHNpZ25LZXlzOiB1dHhvbGliLmJpdGdvLktleU5hbWVbXSkge1xuICAgIGNvbnN0IHNpZ25LZXlzU3RyID0gc2lnbktleXMuam9pbignLCcpO1xuXG4gICAgZGVzY3JpYmUoYGlucHV0VHlwZT0ke2lucHV0VHlwZX0gc2lnbktleXM9JHtzaWduS2V5c1N0cn1gLCBmdW5jdGlvbiAoKSB7XG4gICAgICBpdChgY29tcG9uZW50IHNpemVzYCwgZnVuY3Rpb24gKHRoaXM6IG1vY2hhLkNvbnRleHQpIHtcbiAgICAgICAgdGhpcy50aW1lb3V0KDEwXzAwMCk7XG4gICAgICAgIGxldCBleHBlY3RlZENvbXBvbmVudHM7XG4gICAgICAgIHN3aXRjaCAoaW5wdXRUeXBlKSB7XG4gICAgICAgICAgY2FzZSAncDJzaCc6XG4gICAgICAgICAgICBleHBlY3RlZENvbXBvbmVudHMgPSBpbnB1dENvbXBvbmVudHNQMnNoO1xuICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgY2FzZSAncDJzaFAyd3NoJzpcbiAgICAgICAgICAgIGV4cGVjdGVkQ29tcG9uZW50cyA9IGlucHV0Q29tcG9uZW50c1Ayc2hQMndzaDtcbiAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgIGNhc2UgJ3Ayd3NoJzpcbiAgICAgICAgICAgIGV4cGVjdGVkQ29tcG9uZW50cyA9IGlucHV0Q29tcG9uZW50c1Ayd3NoO1xuICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgY2FzZSAncDJzaFAycGsnOlxuICAgICAgICAgICAgZXhwZWN0ZWRDb21wb25lbnRzID0gaW5wdXRDb21wb25lbnRzUDJzaFAycGs7XG4gICAgICAgICAgICBicmVhaztcbiAgICAgICAgICBjYXNlICdwMnRyJzpcbiAgICAgICAgICAgIGlmIChzaWduS2V5c1sxXSA9PT0gJ2JpdGdvJykge1xuICAgICAgICAgICAgICBleHBlY3RlZENvbXBvbmVudHMgPSBpbnB1dENvbXBvbmVudHNQMnRyU2NyaXB0U3BlbmRMZXZlbDE7XG4gICAgICAgICAgICB9IGVsc2UgaWYgKHNpZ25LZXlzWzFdID09PSAnYmFja3VwJykge1xuICAgICAgICAgICAgICBleHBlY3RlZENvbXBvbmVudHMgPSBpbnB1dENvbXBvbmVudHNQMnRyU2NyaXB0U3BlbmRMZXZlbDI7XG4gICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYHVuZXhwZWN0ZWQgY29zaWduZXJgKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgIGNhc2UgJ3AydHJNdXNpZzInOlxuICAgICAgICAgICAgLy8gYXNzdW1lcyBvbmx5IHNjcmlwdCBwYXRoXG4gICAgICAgICAgICBleHBlY3RlZENvbXBvbmVudHMgPSBpbnB1dENvbXBvbmVudHNQMnRyU2NyaXB0U3BlbmRMZXZlbDE7XG4gICAgICAgICAgICBicmVhaztcbiAgICAgICAgICBjYXNlICd0YXByb290S2V5UGF0aFNwZW5kJzpcbiAgICAgICAgICAgIGV4cGVjdGVkQ29tcG9uZW50cyA9IGlucHV0Q29tcG9uZW50c1AydHJLZXlTcGVuZDtcbiAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgIGRlZmF1bHQ6XG4gICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYGludmFsaWQgaW5wdXRUeXBlICR7aW5wdXRUeXBlfWApO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3QgaW5wdXQgPSBnZXRMYXJnZXN0SW5wdXRXaXRoVHlwZShcbiAgICAgICAgICBpbnB1dFR5cGUsXG4gICAgICAgICAgc2lnbktleXMsXG4gICAgICAgICAgaW5wdXRUeXBlID09PSAncDJ0cicgfHwgaW5wdXRUeXBlID09PSAncDJ0ck11c2lnMicgfHwgaW5wdXRUeXBlID09PSAndGFwcm9vdEtleVBhdGhTcGVuZCcgPyAxMCA6IDEwMFxuICAgICAgICApO1xuICAgICAgICBjb25zdCBjb21wb25lbnRzID0gZ2V0SW5wdXRDb21wb25lbnRzKGlucHV0KTtcbiAgICAgICAgYXNzZXJ0LmRlZXBTdHJpY3RFcXVhbChjb21wb25lbnRzLCBleHBlY3RlZENvbXBvbmVudHMpO1xuICAgICAgICBhc3NlcnQuc3RyaWN0RXF1YWwoZ2V0SW5wdXRDb21wb25lbnRzV2VpZ2h0KGNvbXBvbmVudHMpLCBnZXRJbnB1dFdlaWdodChpbnB1dCkpO1xuICAgICAgfSk7XG4gICAgfSk7XG4gIH1cblxuICBnZXRJbnB1dFNjcmlwdFR5cGVzKCkuZm9yRWFjaCgoaW5wdXRUeXBlOiBzdHJpbmcpID0+IHtcbiAgICBpZiAoaW5wdXRUeXBlICE9PSAncDJ0ck11c2lnMicpIHtcbiAgICAgIHJ1blRlc3RDb21wb25lbnRTaXplcyhpbnB1dFR5cGUsIGlucHV0VHlwZSA9PT0gJ3Ayc2hQMnBrJyA/IFsndXNlciddIDogWyd1c2VyJywgJ2JpdGdvJ10pO1xuICAgIH1cbiAgICBpZiAoaW5wdXRUeXBlICE9PSAncDJzaFAycGsnICYmIGlucHV0VHlwZSAhPT0gJ3RhcHJvb3RLZXlQYXRoU3BlbmQnKSB7XG4gICAgICBydW5UZXN0Q29tcG9uZW50U2l6ZXMoaW5wdXRUeXBlLCBbJ3VzZXInLCAnYmFja3VwJ10pO1xuICAgIH1cbiAgfSk7XG59KTtcbiJdfQ==
@@ -0,0 +1,3 @@
1
+ import * as utxolib from '@bitgo-beta/utxo-lib';
2
+ export declare type InputScriptType = utxolib.bitgo.outputScripts.ScriptType | 'taprootKeyPathSpend';
3
+ //# sourceMappingURL=txCombinations.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"txCombinations.d.ts","sourceRoot":"","sources":["../../../test/signedTx/txCombinations.ts"],"names":[],"mappings":"AAcA,OAAO,KAAK,OAAO,MAAM,sBAAsB,CAAC;AAEhD,oBAAY,eAAe,GAAG,OAAO,CAAC,KAAK,CAAC,aAAa,CAAC,UAAU,GAAG,qBAAqB,CAAC"}
@@ -0,0 +1,116 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });
5
+ }) : (function(o, m, k, k2) {
6
+ if (k2 === undefined) k2 = k;
7
+ o[k2] = m[k];
8
+ }));
9
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
10
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
11
+ }) : function(o, v) {
12
+ o["default"] = v;
13
+ });
14
+ var __importStar = (this && this.__importStar) || function (mod) {
15
+ if (mod && mod.__esModule) return mod;
16
+ var result = {};
17
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
18
+ __setModuleDefault(result, mod);
19
+ return result;
20
+ };
21
+ var __importDefault = (this && this.__importDefault) || function (mod) {
22
+ return (mod && mod.__esModule) ? mod : { "default": mod };
23
+ };
24
+ Object.defineProperty(exports, "__esModule", { value: true });
25
+ const should_1 = __importDefault(require("should"));
26
+ const src_1 = require("../../src");
27
+ const testutils_1 = require("../testutils");
28
+ const txGen_1 = require("./txGen");
29
+ const utxolib = __importStar(require("@bitgo-beta/utxo-lib"));
30
+ const keys = [1, 2, 3].map((v) => utxolib.bip32.fromSeed(Buffer.alloc(16, `test/2/${v}`), utxolib.networks.bitcoin));
31
+ const rootWalletKeys = new utxolib.bitgo.RootWalletKeys([keys[0], keys[1], keys[2]]);
32
+ const testDimensionsFromTx = (txCombo) => {
33
+ const { inputTypes, outputTypes, expectedDims } = txCombo;
34
+ describe(`Combination inputs=${inputTypes}; outputs=${outputTypes}`, function () {
35
+ const nInputs = inputTypes.length;
36
+ const outputDims = src_1.Dimensions.sum(...outputTypes.map(testutils_1.getOutputDimensionsForUnspentType));
37
+ it(`calculates dimensions from unsigned transaction`, function () {
38
+ const unsignedTx = txCombo.getUnsignedTx();
39
+ // does not work for unsigned transactions
40
+ should_1.default.throws(() => src_1.Dimensions.fromTransaction(unsignedTx));
41
+ // unless explicitly allowed
42
+ src_1.Dimensions.fromTransaction(unsignedTx, { assumeUnsigned: src_1.Dimensions.ASSUME_P2SH }).should.eql(src_1.Dimensions.sum({ nP2shInputs: nInputs }, outputDims));
43
+ src_1.Dimensions.fromTransaction(unsignedTx, { assumeUnsigned: src_1.Dimensions.ASSUME_P2SH_P2WSH }).should.eql(src_1.Dimensions.sum({ nP2shP2wshInputs: nInputs }, outputDims));
44
+ src_1.Dimensions.fromTransaction(unsignedTx, { assumeUnsigned: src_1.Dimensions.ASSUME_P2WSH }).should.eql(src_1.Dimensions.sum({ nP2wshInputs: nInputs }, outputDims));
45
+ });
46
+ it(`calculates dimensions for signed transaction`, function () {
47
+ const dimensions = src_1.Dimensions.fromTransaction(txCombo.getSignedTx());
48
+ dimensions.should.eql(expectedDims);
49
+ });
50
+ it(`calculates dimensions for signed input of transaction`, function () {
51
+ const signedTx = txCombo.getSignedTx();
52
+ // test Dimensions.fromInput()
53
+ inputTypes.forEach((input, i) => src_1.Dimensions.fromInput(signedTx.ins[i]).should.eql(src_1.Dimensions.sum(testutils_1.getInputDimensionsForUnspentType(input))));
54
+ });
55
+ });
56
+ };
57
+ const testDimensionsFromPsbt = (keys, inputTypes, outputTypes, expectedDims) => {
58
+ describe(`Psbt Combination inputs=${inputTypes}; outputs=${outputTypes}`, function () {
59
+ ['unsigned', 'halfsigned', 'fullysigned'].forEach((s) => {
60
+ it(`calculates dimensions from ${s} psbt`, function () {
61
+ const dimensions = src_1.Dimensions.fromPsbt(testutils_1.constructPsbt(keys, inputTypes, outputTypes, s));
62
+ dimensions.should.eql(expectedDims);
63
+ });
64
+ });
65
+ it(`calculates dimensions for signed input of psbt`, function () {
66
+ const signedPsbt = testutils_1.constructPsbt(keys, inputTypes, outputTypes, 'fullysigned');
67
+ inputTypes.forEach((input, i) => src_1.Dimensions.fromPsbtInput(signedPsbt.data.inputs[i]).should.eql(src_1.Dimensions.sum(testutils_1.getInputDimensionsForUnspentType(input))));
68
+ });
69
+ });
70
+ };
71
+ describe(`Dimensions for transaction combinations`, function () {
72
+ // p2trMusig2 is supported only with PSBT
73
+ const scriptTypes = utxolib.bitgo.outputScripts.scriptTypes2Of3.filter((t) => t !== 'p2trMusig2');
74
+ const params = {
75
+ inputTypes: [...scriptTypes, testutils_1.UnspentTypeP2shP2pk],
76
+ maxNInputs: 2,
77
+ outputTypes: [...scriptTypes, ...Object.keys(testutils_1.UnspentTypePubKeyHash)],
78
+ maxNOutputs: 2,
79
+ };
80
+ txGen_1.runCombinations(params, (inputTypeCombo, outputTypeCombo) => {
81
+ const expectedInputDims = src_1.Dimensions.sum(...inputTypeCombo.map(testutils_1.getInputDimensionsForUnspentType));
82
+ const expectedOutputDims = src_1.Dimensions.sum(...outputTypeCombo.map(testutils_1.getOutputDimensionsForUnspentType));
83
+ testDimensionsFromTx(new txGen_1.TxCombo(keys, inputTypeCombo, outputTypeCombo, expectedInputDims.plus(expectedOutputDims)));
84
+ // Doubling the inputs should yield twice the input dims
85
+ testDimensionsFromTx(new txGen_1.TxCombo(keys, [...inputTypeCombo, ...inputTypeCombo], outputTypeCombo, expectedInputDims.plus(expectedInputDims).plus(expectedOutputDims)));
86
+ // Same for outputs
87
+ testDimensionsFromTx(new txGen_1.TxCombo(keys, inputTypeCombo, [...outputTypeCombo, ...outputTypeCombo], expectedInputDims.plus(expectedOutputDims).plus(expectedOutputDims)));
88
+ });
89
+ });
90
+ describe(`Dimensions for PSBT combinations`, function () {
91
+ const params = {
92
+ inputTypes: [
93
+ ...utxolib.bitgo.outputScripts.scriptTypes2Of3,
94
+ utxolib.bitgo.outputScripts.scriptTypeP2shP2pk,
95
+ 'taprootKeyPathSpend',
96
+ ],
97
+ maxNInputs: 1,
98
+ outputTypes: [...Object.keys(testutils_1.UnspentTypeScript2of3), ...Object.keys(testutils_1.UnspentTypePubKeyHash)],
99
+ maxNOutputs: 1,
100
+ };
101
+ it(`does not work for unknown psbt input`, function () {
102
+ const psbt = utxolib.bitgo.createPsbtForNetwork({ network: utxolib.networks.bitcoin });
103
+ psbt.addInput({ hash: Buffer.alloc(32), index: 0 });
104
+ should_1.default.throws(() => src_1.Dimensions.fromPsbt(psbt));
105
+ });
106
+ txGen_1.runCombinations(params, (inputTypeCombo, outputTypeCombo) => {
107
+ const expectedInputDims = src_1.Dimensions.sum(...inputTypeCombo.map(testutils_1.getInputDimensionsForUnspentType));
108
+ const expectedOutputDims = src_1.Dimensions.sum(...outputTypeCombo.map(testutils_1.getOutputDimensionsForUnspentType));
109
+ testDimensionsFromPsbt(rootWalletKeys, inputTypeCombo, outputTypeCombo, expectedInputDims.plus(expectedOutputDims));
110
+ // Doubling the inputs should yield twice the input dims
111
+ testDimensionsFromPsbt(rootWalletKeys, [...inputTypeCombo, ...inputTypeCombo], outputTypeCombo, expectedInputDims.plus(expectedInputDims).plus(expectedOutputDims));
112
+ // Same for outputs
113
+ testDimensionsFromPsbt(rootWalletKeys, inputTypeCombo, [...outputTypeCombo, ...outputTypeCombo], expectedInputDims.plus(expectedOutputDims).plus(expectedOutputDims));
114
+ });
115
+ });
116
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidHhDb21iaW5hdGlvbnMuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi90ZXN0L3NpZ25lZFR4L3R4Q29tYmluYXRpb25zLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUFBLG9EQUE0QjtBQUM1QixtQ0FBdUM7QUFFdkMsNENBUXNCO0FBRXRCLG1DQUFtRDtBQUNuRCw4REFBZ0Q7QUFJaEQsTUFBTSxJQUFJLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsRUFBRSxFQUFFLENBQy9CLE9BQU8sQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLE1BQU0sQ0FBQyxLQUFLLENBQUMsRUFBRSxFQUFFLFVBQVUsQ0FBQyxFQUFFLENBQUMsRUFBRSxPQUFPLENBQUMsUUFBUSxDQUFDLE9BQU8sQ0FBQyxDQUN0RCxDQUFDO0FBRTlCLE1BQU0sY0FBYyxHQUFHLElBQUksT0FBTyxDQUFDLEtBQUssQ0FBQyxjQUFjLENBQUMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7QUFFckYsTUFBTSxvQkFBb0IsR0FBRyxDQUFDLE9BQVksRUFBRSxFQUFFO0lBQzVDLE1BQU0sRUFBRSxVQUFVLEVBQUUsV0FBVyxFQUFFLFlBQVksRUFBRSxHQUFHLE9BQU8sQ0FBQztJQUUxRCxRQUFRLENBQUMsc0JBQXNCLFVBQVUsYUFBYSxXQUFXLEVBQUUsRUFBRTtRQUNuRSxNQUFNLE9BQU8sR0FBRyxVQUFVLENBQUMsTUFBTSxDQUFDO1FBQ2xDLE1BQU0sVUFBVSxHQUFHLGdCQUFVLENBQUMsR0FBRyxDQUFDLEdBQUcsV0FBVyxDQUFDLEdBQUcsQ0FBQyw2Q0FBaUMsQ0FBQyxDQUFDLENBQUM7UUFFekYsRUFBRSxDQUFDLGlEQUFpRCxFQUFF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QUFDLENBQUMsQ0FBQztBQUNMLENBQUMsQ0FBQyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHNob3VsZCBmcm9tICdzaG91bGQnO1xuaW1wb3J0IHsgRGltZW5zaW9ucyB9IGZyb20gJy4uLy4uL3NyYyc7XG5cbmltcG9ydCB7XG4gIGNvbnN0cnVjdFBzYnQsXG4gIGdldElucHV0RGltZW5zaW9uc0ZvclVuc3BlbnRUeXBlLFxuICBnZXRPdXRwdXREaW1lbnNpb25zRm9yVW5zcGVudFR5cGUsXG4gIFRlc3RVbnNwZW50VHlwZSxcbiAgVW5zcGVudFR5cGVQMnNoUDJwayxcbiAgVW5zcGVudFR5cGVQdWJLZXlIYXNoLFxuICBVbnNwZW50VHlwZVNjcmlwdDJvZjMsXG59IGZyb20gJy4uL3Rlc3R1dGlscyc7XG5cbmltcG9ydCB7IHJ1bkNvbWJpbmF0aW9ucywgVHhDb21ibyB9IGZyb20gJy4vdHhHZW4nO1xuaW1wb3J0ICogYXMgdXR4b2xpYiBmcm9tICdAYml0Z28tYmV0YS91dHhvLWxpYic7XG5cbmV4cG9ydCB0eXBlIElucHV0U2NyaXB0VHlwZSA9IHV0eG9saWIuYml0Z28ub3V0cHV0U2NyaXB0cy5TY3JpcHRUeXBlIHwgJ3RhcHJvb3RLZXlQYXRoU3BlbmQnO1xuXG5jb25zdCBrZXlzID0gWzEsIDIsIDNdLm1hcCgodikgPT5cbiAgdXR4b2xpYi5iaXAzMi5mcm9tU2VlZChCdWZmZXIuYWxsb2MoMTYsIGB0ZXN0LzIvJHt2fWApLCB1dHhvbGliLm5ldHdvcmtzLmJpdGNvaW4pXG4pIGFzIHV0eG9saWIuQklQMzJJbnRlcmZhY2VbXTtcblxuY29uc3Qgcm9vdFdhbGxldEtleXMgPSBuZXcgdXR4b2xpYi5iaXRnby5Sb290V2FsbGV0S2V5cyhba2V5c1swXSwga2V5c1sxXSwga2V5c1syXV0pO1xuXG5jb25zdCB0ZXN0RGltZW5zaW9uc0Zyb21UeCA9ICh0eENvbWJvOiBhbnkpID0+IHtcbiAgY29uc3QgeyBpbnB1dFR5cGVzLCBvdXRwdXRUeXBlcywgZXhwZWN0ZWREaW1zIH0gPSB0eENvbWJvO1xuXG4gIGRlc2NyaWJlKGBDb21iaW5hdGlvbiBpbnB1dHM9JHtpbnB1dFR5cGVzfTsgb3V0cHV0cz0ke291dHB1dFR5cGVzfWAsIGZ1bmN0aW9uICgpIHtcbiAgICBjb25zdCBuSW5wdXRzID0gaW5wdXRUeXBlcy5sZW5ndGg7XG4gICAgY29uc3Qgb3V0cHV0RGltcyA9IERpbWVuc2lvbnMuc3VtKC4uLm91dHB1dFR5cGVzLm1hcChnZXRPdXRwdXREaW1lbnNpb25zRm9yVW5zcGVudFR5cGUpKTtcblxuICAgIGl0KGBjYWxjdWxhdGVzIGRpbWVuc2lvbnMgZnJvbSB1bnNpZ25lZCB0cmFuc2FjdGlvbmAsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHVuc2lnbmVkVHggPSB0eENvbWJvLmdldFVuc2lnbmVkVHgoKTtcblxuICAgICAgLy8gZG9lcyBub3Qgd29yayBmb3IgdW5zaWduZWQgdHJhbnNhY3Rpb25zXG4gICAgICBzaG91bGQudGhyb3dzKCgpID0+IERpbWVuc2lvbnMuZnJvbVRyYW5zYWN0aW9uKHVuc2lnbmVkVHgpKTtcblxuICAgICAgLy8gdW5sZXNzIGV4cGxpY2l0bHkgYWxsb3dlZFxuICAgICAgRGltZW5zaW9ucy5mcm9tVHJhbnNhY3Rpb24odW5zaWduZWRUeCwgeyBhc3N1bWVVbnNpZ25lZDogRGltZW5zaW9ucy5BU1NVTUVfUDJTSCB9KS5zaG91bGQuZXFsKFxuICAgICAgICBEaW1lbnNpb25zLnN1bSh7IG5QMnNoSW5wdXRzOiBuSW5wdXRzIH0sIG91dHB1dERpbXMpXG4gICAgICApO1xuXG4gICAgICBEaW1lbnNpb25zLmZyb21UcmFuc2FjdGlvbih1bnNpZ25lZFR4LCB7IGFzc3VtZVVuc2lnbmVkOiBEaW1lbnNpb25zLkFTU1VNRV9QMlNIX1AyV1NIIH0pLnNob3VsZC5lcWwoXG4gICAgICAgIERpbWVuc2lvbnMuc3VtKHsgblAyc2hQMndzaElucHV0czogbklucHV0cyB9LCBvdXRwdXREaW1zKVxuICAgICAgKTtcblxuICAgICAgRGltZW5zaW9ucy5mcm9tVHJhbnNhY3Rpb24odW5zaWduZWRUeCwgeyBhc3N1bWVVbnNpZ25lZDogRGltZW5zaW9ucy5BU1NVTUVfUDJXU0ggfSkuc2hvdWxkLmVxbChcbiAgICAgICAgRGltZW5zaW9ucy5zdW0oeyBuUDJ3c2hJbnB1dHM6IG5JbnB1dHMgfSwgb3V0cHV0RGltcylcbiAgICAgICk7XG4gICAgfSk7XG5cbiAgICBpdChgY2FsY3VsYXRlcyBkaW1lbnNpb25zIGZvciBzaWduZWQgdHJhbnNhY3Rpb25gLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBkaW1lbnNpb25zID0gRGltZW5zaW9ucy5mcm9tVHJhbnNhY3Rpb24odHhDb21iby5nZXRTaWduZWRUeCgpKTtcbiAgICAgIGRpbWVuc2lvbnMuc2hvdWxkLmVxbChleHBlY3RlZERpbXMpO1xuICAgIH0pO1xuXG4gICAgaXQoYGNhbGN1bGF0ZXMgZGltZW5zaW9ucyBmb3Igc2lnbmVkIGlucHV0IG9mIHRyYW5zYWN0aW9uYCwgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3Qgc2lnbmVkVHggPSB0eENvbWJvLmdldFNpZ25lZFR4KCk7XG5cbiAgICAgIC8vIHRlc3QgRGltZW5zaW9ucy5mcm9tSW5wdXQoKVxuICAgICAgaW5wdXRUeXBlcy5mb3JFYWNoKChpbnB1dDogYW55LCBpOiBudW1iZXIpID0+XG4gICAgICAgIERpbWVuc2lvbnMuZnJvbUlucHV0KHNpZ25lZFR4Lmluc1tpXSkuc2hvdWxkLmVxbChEaW1lbnNpb25zLnN1bShnZXRJbnB1dERpbWVuc2lvbnNGb3JVbnNwZW50VHlwZShpbnB1dCkpKVxuICAgICAgKTtcbiAgICB9KTtcbiAgfSk7XG59O1xuXG5jb25zdCB0ZXN0RGltZW5zaW9uc0Zyb21Qc2J0ID0gKFxuICBrZXlzOiB1dHhvbGliLmJpdGdvLlJvb3RXYWxsZXRLZXlzLFxuICBpbnB1dFR5cGVzOiBJbnB1dFNjcmlwdFR5cGVbXSxcbiAgb3V0cHV0VHlwZXM6IFRlc3RVbnNwZW50VHlwZVtdLFxuICBleHBlY3RlZERpbXM6IERpbWVuc2lvbnNcbikgPT4ge1xuICBkZXNjcmliZShgUHNidCBDb21iaW5hdGlvbiBpbnB1dHM9JHtpbnB1dFR5cGVzfTsgb3V0cHV0cz0ke291dHB1dFR5cGVzfWAsIGZ1bmN0aW9uICgpIHtcbiAgICAoWyd1bnNpZ25lZCcsICdoYWxmc2lnbmVkJywgJ2Z1bGx5c2lnbmVkJ10gYXMgY29uc3QpLmZvckVhY2goKHMpID0+IHtcbiAgICAgIGl0KGBjYWxjdWxhdGVzIGRpbWVuc2lvbnMgZnJvbSAke3N9IHBzYnRgLCBmdW5jdGlvbiAoKSB7XG4gICAgICAgIGNvbnN0IGRpbWVuc2lvbnMgPSBEaW1lbnNpb25zLmZyb21Qc2J0KGNvbnN0cnVjdFBzYnQoa2V5cywgaW5wdXRUeXBlcywgb3V0cHV0VHlwZXMsIHMpKTtcbiAgICAgICAgZGltZW5zaW9ucy5zaG91bGQuZXFsKGV4cGVjdGVkRGltcyk7XG4gICAgICB9KTtcbiAgICB9KTtcblxuICAgIGl0KGBjYWxjdWxhdGVzIGRpbWVuc2lvbnMgZm9yIHNpZ25lZCBpbnB1dCBvZiBwc2J0YCwgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3Qgc2lnbmVkUHNidCA9IGNvbnN0cnVjdFBzYnQoa2V5cywgaW5wdXRUeXBlcywgb3V0cHV0VHlwZXMsICdmdWxseXNpZ25lZCcpO1xuXG4gICAgICBpbnB1dFR5cGVzLmZvckVhY2goKGlucHV0OiBhbnksIGk6IG51bWJlcikgPT5cbiAgICAgICAgRGltZW5zaW9ucy5mcm9tUHNidElucHV0KHNpZ25lZFBzYnQuZGF0YS5pbnB1dHNbaV0pLnNob3VsZC5lcWwoXG4gICAgICAgICAgRGltZW5zaW9ucy5zdW0oZ2V0SW5wdXREaW1lbnNpb25zRm9yVW5zcGVudFR5cGUoaW5wdXQpKVxuICAgICAgICApXG4gICAgICApO1xuICAgIH0pO1xuICB9KTtcbn07XG5cbmRlc2NyaWJlKGBEaW1lbnNpb25zIGZvciB0cmFuc2FjdGlvbiBjb21iaW5hdGlvbnNgLCBmdW5jdGlvbiAoKSB7XG4gIC8vIHAydHJNdXNpZzIgaXMgc3VwcG9ydGVkIG9ubHkgd2l0aCBQU0JUXG4gIGNvbnN0IHNjcmlwdFR5cGVzID0gdXR4b2xpYi5iaXRnby5vdXRwdXRTY3JpcHRzLnNjcmlwdFR5cGVzMk9mMy5maWx0ZXIoKHQpID0+IHQgIT09ICdwMnRyTXVzaWcyJyk7XG4gIGNvbnN0IHBhcmFtcyA9IHtcbiAgICBpbnB1dFR5cGVzOiBbLi4uc2NyaXB0VHlwZXMsIFVuc3BlbnRUeXBlUDJzaFAycGtdIGFzIElucHV0U2NyaXB0VHlwZVtdLFxuICAgIG1heE5JbnB1dHM6IDIsXG4gICAgb3V0cHV0VHlwZXM6IFsuLi5zY3JpcHRUeXBlcywgLi4uT2JqZWN0LmtleXMoVW5zcGVudFR5cGVQdWJLZXlIYXNoKV0gYXMgVGVzdFVuc3BlbnRUeXBlW10sXG4gICAgbWF4Tk91dHB1dHM6IDIsXG4gIH07XG5cbiAgcnVuQ29tYmluYXRpb25zKHBhcmFtcywgKGlucHV0VHlwZUNvbWJvOiBJbnB1dFNjcmlwdFR5cGVbXSwgb3V0cHV0VHlwZUNvbWJvOiBUZXN0VW5zcGVudFR5cGVbXSkgPT4ge1xuICAgIGNvbnN0IGV4cGVjdGVkSW5wdXREaW1zID0gRGltZW5zaW9ucy5zdW0oLi4uaW5wdXRUeXBlQ29tYm8ubWFwKGdldElucHV0RGltZW5zaW9uc0ZvclVuc3BlbnRUeXBlKSk7XG4gICAgY29uc3QgZXhwZWN0ZWRPdXRwdXREaW1zID0gRGltZW5zaW9ucy5zdW0oLi4ub3V0cHV0VHlwZUNvbWJvLm1hcChnZXRPdXRwdXREaW1lbnNpb25zRm9yVW5zcGVudFR5cGUpKTtcblxuICAgIHRlc3REaW1lbnNpb25zRnJvbVR4KFxuICAgICAgbmV3IFR4Q29tYm8oa2V5cywgaW5wdXRUeXBlQ29tYm8sIG91dHB1dFR5cGVDb21ibywgZXhwZWN0ZWRJbnB1dERpbXMucGx1cyhleHBlY3RlZE91dHB1dERpbXMpKVxuICAgICk7XG5cbiAgICAvLyBEb3VibGluZyB0aGUgaW5wdXRzIHNob3VsZCB5aWVsZCB0d2ljZSB0aGUgaW5wdXQgZGltc1xuICAgIHRlc3REaW1lbnNpb25zRnJvbVR4KFxuICAgICAgbmV3IFR4Q29tYm8oXG4gICAgICAgIGtleXMsXG4gICAgICAgIFsuLi5pbnB1dFR5cGVDb21ibywgLi4uaW5wdXRUeXBlQ29tYm9dLFxuICAgICAgICBvdXRwdXRUeXBlQ29tYm8sXG4gICAgICAgIGV4cGVjdGVkSW5wdXREaW1zLnBsdXMoZXhwZWN0ZWRJbnB1dERpbXMpLnBsdXMoZXhwZWN0ZWRPdXRwdXREaW1zKVxuICAgICAgKVxuICAgICk7XG5cbiAgICAvLyBTYW1lIGZvciBvdXRwdXRzXG4gICAgdGVzdERpbWVuc2lvbnNGcm9tVHgoXG4gICAgICBuZXcgVHhDb21ibyhcbiAgICAgICAga2V5cyxcbiAgICAgICAgaW5wdXRUeXBlQ29tYm8sXG4gICAgICAgIFsuLi5vdXRwdXRUeXBlQ29tYm8sIC4uLm91dHB1dFR5cGVDb21ib10sXG4gICAgICAgIGV4cGVjdGVkSW5wdXREaW1zLnBsdXMoZXhwZWN0ZWRPdXRwdXREaW1zKS5wbHVzKGV4cGVjdGVkT3V0cHV0RGltcylcbiAgICAgIClcbiAgICApO1xuICB9KTtcbn0pO1xuXG5kZXNjcmliZShgRGltZW5zaW9ucyBmb3IgUFNCVCBjb21iaW5hdGlvbnNgLCBmdW5jdGlvbiAoKSB7XG4gIGNvbnN0IHBhcmFtcyA9IHtcbiAgICBpbnB1dFR5cGVzOiBbXG4gICAgICAuLi51dHhvbGliLmJpdGdvLm91dHB1dFNjcmlwdHMuc2NyaXB0VHlwZXMyT2YzLFxuICAgICAgdXR4b2xpYi5iaXRnby5vdXRwdXRTY3JpcHRzLnNjcmlwdFR5cGVQMnNoUDJwayxcbiAgICAgICd0YXByb290S2V5UGF0aFNwZW5kJyxcbiAgICBdIGFzIElucHV0U2NyaXB0VHlwZVtdLFxuICAgIG1heE5JbnB1dHM6IDEsXG4gICAgb3V0cHV0VHlwZXM6IFsuLi5PYmplY3Qua2V5cyhVbnNwZW50VHlwZVNjcmlwdDJvZjMpLCAuLi5PYmplY3Qua2V5cyhVbnNwZW50VHlwZVB1YktleUhhc2gpXSxcbiAgICBtYXhOT3V0cHV0czogMSxcbiAgfTtcblxuICBpdChgZG9lcyBub3Qgd29yayBmb3IgdW5rbm93biBwc2J0IGlucHV0YCwgZnVuY3Rpb24gKCkge1xuICAgIGNvbnN0IHBzYnQgPSB1dHhvbGliLmJpdGdvLmNyZWF0ZVBzYnRGb3JOZXR3b3JrKHsgbmV0d29yazogdXR4b2xpYi5uZXR3b3Jrcy5iaXRjb2luIH0pO1xuICAgIHBzYnQuYWRkSW5wdXQoeyBoYXNoOiBCdWZmZXIuYWxsb2MoMzIpLCBpbmRleDogMCB9KTtcbiAgICBzaG91bGQudGhyb3dzKCgpID0+IERpbWVuc2lvbnMuZnJvbVBzYnQocHNidCkpO1xuICB9KTtcblxuICBydW5Db21iaW5hdGlvbnMocGFyYW1zLCAoaW5wdXRUeXBlQ29tYm86IElucHV0U2NyaXB0VHlwZVtdLCBvdXRwdXRUeXBlQ29tYm86IFRlc3RVbnNwZW50VHlwZVtdKSA9PiB7XG4gICAgY29uc3QgZXhwZWN0ZWRJbnB1dERpbXMgPSBEaW1lbnNpb25zLnN1bSguLi5pbnB1dFR5cGVDb21iby5tYXAoZ2V0SW5wdXREaW1lbnNpb25zRm9yVW5zcGVudFR5cGUpKTtcbiAgICBjb25zdCBleHBlY3RlZE91dHB1dERpbXMgPSBEaW1lbnNpb25zLnN1bSguLi5vdXRwdXRUeXBlQ29tYm8ubWFwKGdldE91dHB1dERpbWVuc2lvbnNGb3JVbnNwZW50VHlwZSkpO1xuXG4gICAgdGVzdERpbWVuc2lvbnNGcm9tUHNidChyb290V2FsbGV0S2V5cywgaW5wdXRUeXBlQ29tYm8sIG91dHB1dFR5cGVDb21ibywgZXhwZWN0ZWRJbnB1dERpbXMucGx1cyhleHBlY3RlZE91dHB1dERpbXMpKTtcblxuICAgIC8vIERvdWJsaW5nIHRoZSBpbnB1dHMgc2hvdWxkIHlpZWxkIHR3aWNlIHRoZSBpbnB1dCBkaW1zXG4gICAgdGVzdERpbWVuc2lvbnNGcm9tUHNidChcbiAgICAgIHJvb3RXYWxsZXRLZXlzLFxuICAgICAgWy4uLmlucHV0VHlwZUNvbWJvLCAuLi5pbnB1dFR5cGVDb21ib10sXG4gICAgICBvdXRwdXRUeXBlQ29tYm8sXG4gICAgICBleHBlY3RlZElucHV0RGltcy5wbHVzKGV4cGVjdGVkSW5wdXREaW1zKS5wbHVzKGV4cGVjdGVkT3V0cHV0RGltcylcbiAgICApO1xuXG4gICAgLy8gU2FtZSBmb3Igb3V0cHV0c1xuICAgIHRlc3REaW1lbnNpb25zRnJvbVBzYnQoXG4gICAgICByb290V2FsbGV0S2V5cyxcbiAgICAgIGlucHV0VHlwZUNvbWJvLFxuICAgICAgWy4uLm91dHB1dFR5cGVDb21ibywgLi4ub3V0cHV0VHlwZUNvbWJvXSxcbiAgICAgIGV4cGVjdGVkSW5wdXREaW1zLnBsdXMoZXhwZWN0ZWRPdXRwdXREaW1zKS5wbHVzKGV4cGVjdGVkT3V0cHV0RGltcylcbiAgICApO1xuICB9KTtcbn0pO1xuIl19