@bitgo-beta/sdk-coin-flrp 1.0.1-beta.40 → 1.0.1-beta.401
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.
- package/dist/src/flrp.d.ts +10 -17
- package/dist/src/flrp.d.ts.map +1 -1
- package/dist/src/flrp.js +51 -77
- package/dist/src/index.d.ts +0 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +1 -2
- package/dist/src/lib/ExportInCTxBuilder.d.ts +43 -0
- package/dist/src/lib/ExportInCTxBuilder.d.ts.map +1 -0
- package/dist/src/lib/ExportInCTxBuilder.js +150 -0
- package/dist/src/lib/ExportInPTxBuilder.d.ts +28 -0
- package/dist/src/lib/ExportInPTxBuilder.d.ts.map +1 -0
- package/dist/src/lib/ExportInPTxBuilder.js +190 -0
- package/dist/src/lib/ImportInCTxBuilder.d.ts +34 -0
- package/dist/src/lib/ImportInCTxBuilder.d.ts.map +1 -0
- package/dist/src/lib/ImportInCTxBuilder.js +191 -0
- package/dist/src/lib/ImportInPTxBuilder.d.ts +38 -0
- package/dist/src/lib/ImportInPTxBuilder.d.ts.map +1 -0
- package/dist/src/lib/ImportInPTxBuilder.js +224 -0
- package/dist/src/lib/atomicInCTransactionBuilder.d.ts +12 -16
- package/dist/src/lib/atomicInCTransactionBuilder.d.ts.map +1 -1
- package/dist/src/lib/atomicInCTransactionBuilder.js +30 -41
- package/dist/src/lib/atomicTransactionBuilder.d.ts +126 -69
- package/dist/src/lib/atomicTransactionBuilder.d.ts.map +1 -1
- package/dist/src/lib/atomicTransactionBuilder.js +320 -211
- package/dist/src/lib/iface.d.ts +65 -57
- package/dist/src/lib/iface.d.ts.map +1 -1
- package/dist/src/lib/iface.js +20 -14
- package/dist/src/lib/index.d.ts +5 -0
- package/dist/src/lib/index.d.ts.map +1 -1
- package/dist/src/lib/index.js +12 -2
- package/dist/src/lib/keyPair.d.ts +5 -5
- package/dist/src/lib/keyPair.d.ts.map +1 -1
- package/dist/src/lib/keyPair.js +17 -9
- package/dist/src/lib/permissionlessValidatorTxBuilder.d.ts +41 -0
- package/dist/src/lib/permissionlessValidatorTxBuilder.d.ts.map +1 -0
- package/dist/src/lib/permissionlessValidatorTxBuilder.js +126 -0
- package/dist/src/lib/transaction.d.ts +30 -66
- package/dist/src/lib/transaction.d.ts.map +1 -1
- package/dist/src/lib/transaction.js +347 -199
- package/dist/src/lib/transactionBuilder.d.ts +115 -0
- package/dist/src/lib/transactionBuilder.d.ts.map +1 -0
- package/dist/src/lib/transactionBuilder.js +228 -0
- package/dist/src/lib/transactionBuilderFactory.d.ts +50 -30
- package/dist/src/lib/transactionBuilderFactory.d.ts.map +1 -1
- package/dist/src/lib/transactionBuilderFactory.js +129 -72
- package/dist/src/lib/utils.d.ts +131 -146
- package/dist/src/lib/utils.d.ts.map +1 -1
- package/dist/src/lib/utils.js +344 -321
- package/dist/test/resources/account.d.ts +81 -0
- package/dist/test/resources/account.d.ts.map +1 -0
- package/dist/test/resources/account.js +79 -0
- package/dist/test/resources/transactionData/exportInC.d.ts +50 -0
- package/dist/test/resources/transactionData/exportInC.d.ts.map +1 -0
- package/dist/test/resources/transactionData/exportInC.js +58 -0
- package/dist/test/resources/transactionData/exportInP.d.ts +60 -0
- package/dist/test/resources/transactionData/exportInP.d.ts.map +1 -0
- package/dist/test/resources/transactionData/exportInP.js +101 -0
- package/dist/test/resources/transactionData/importInC.d.ts +56 -0
- package/dist/test/resources/transactionData/importInC.d.ts.map +1 -0
- package/dist/test/resources/transactionData/importInC.js +120 -0
- package/dist/test/resources/transactionData/importInP.d.ts +66 -0
- package/dist/test/resources/transactionData/importInP.d.ts.map +1 -0
- package/dist/test/resources/transactionData/importInP.js +84 -0
- package/dist/test/unit/flrp.js +449 -68
- package/dist/test/unit/lib/exportInCTxBuilder.d.ts +2 -0
- package/dist/test/unit/lib/exportInCTxBuilder.d.ts.map +1 -0
- package/dist/test/unit/lib/exportInCTxBuilder.js +193 -0
- package/dist/test/unit/lib/exportInPTxBuilder.d.ts +2 -0
- package/dist/test/unit/lib/exportInPTxBuilder.d.ts.map +1 -0
- package/dist/test/unit/lib/exportInPTxBuilder.js +296 -0
- package/dist/test/unit/lib/importInCTxBuilder.d.ts +2 -0
- package/dist/test/unit/lib/importInCTxBuilder.d.ts.map +1 -0
- package/dist/test/unit/lib/importInCTxBuilder.js +309 -0
- package/dist/test/unit/lib/importInPTxBuilder.d.ts +2 -0
- package/dist/test/unit/lib/importInPTxBuilder.d.ts.map +1 -0
- package/dist/test/unit/lib/importInPTxBuilder.js +490 -0
- package/dist/test/unit/lib/keyPair.d.ts +2 -0
- package/dist/test/unit/lib/keyPair.d.ts.map +1 -0
- package/dist/test/unit/lib/keyPair.js +158 -0
- package/dist/test/unit/lib/signFlowTestSuit.d.ts +20 -0
- package/dist/test/unit/lib/signFlowTestSuit.d.ts.map +1 -0
- package/dist/test/unit/lib/signFlowTestSuit.js +83 -0
- package/dist/test/unit/lib/signatureIndex.d.ts +13 -0
- package/dist/test/unit/lib/signatureIndex.d.ts.map +1 -0
- package/dist/test/unit/lib/signatureIndex.js +1173 -0
- package/dist/test/unit/lib/transactionBuilderFactory.d.ts +2 -0
- package/dist/test/unit/lib/transactionBuilderFactory.d.ts.map +1 -0
- package/dist/test/unit/lib/transactionBuilderFactory.js +60 -0
- package/dist/test/unit/lib/utils.js +681 -206
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +20 -11
- package/.eslintignore +0 -5
- package/.eslintrc.json +0 -7
- package/.mocharc.yml +0 -8
- package/CHANGELOG.md +0 -0
- package/dist/src/iface.d.ts +0 -25
- package/dist/src/iface.d.ts.map +0 -1
- package/dist/src/iface.js +0 -3
- package/dist/src/lib/constants.d.ts +0 -11
- package/dist/src/lib/constants.d.ts.map +0 -1
- package/dist/src/lib/constants.js +0 -17
- package/dist/src/lib/errors.d.ts +0 -8
- package/dist/src/lib/errors.d.ts.map +0 -1
- package/dist/src/lib/errors.js +0 -19
- package/dist/src/lib/exportInCTxBuilder.d.ts +0 -77
- package/dist/src/lib/exportInCTxBuilder.d.ts.map +0 -1
- package/dist/src/lib/exportInCTxBuilder.js +0 -170
- package/dist/src/lib/exportInPTxBuilder.d.ts +0 -30
- package/dist/src/lib/exportInPTxBuilder.d.ts.map +0 -1
- package/dist/src/lib/exportInPTxBuilder.js +0 -56
- package/dist/test/unit/lib/atomicTransactionBuilder.d.ts +0 -2
- package/dist/test/unit/lib/atomicTransactionBuilder.d.ts.map +0 -1
- package/dist/test/unit/lib/atomicTransactionBuilder.js +0 -222
- package/dist/test/unit/lib/exportTxBuilder.d.ts +0 -2
- package/dist/test/unit/lib/exportTxBuilder.d.ts.map +0 -1
- package/dist/test/unit/lib/exportTxBuilder.js +0 -45
- package/dist/test/unit/lib/transaction.d.ts +0 -2
- package/dist/test/unit/lib/transaction.d.ts.map +0 -1
- package/dist/test/unit/lib/transaction.js +0 -460
- package/dist/test/unit/smoke.d.ts +0 -2
- package/dist/test/unit/smoke.d.ts.map +0 -1
- package/dist/test/unit/smoke.js +0 -23
package/dist/test/unit/flrp.js
CHANGED
|
@@ -32,87 +32,468 @@ var __importStar = (this && this.__importStar) || (function () {
|
|
|
32
32
|
return result;
|
|
33
33
|
};
|
|
34
34
|
})();
|
|
35
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
36
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
37
|
+
};
|
|
35
38
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
-
const
|
|
37
|
-
const assert = __importStar(require("assert"));
|
|
38
|
-
const flrp_1 = require("../../src/flrp");
|
|
39
|
+
const FlrpLib = __importStar(require("../../src/lib"));
|
|
39
40
|
const sdk_test_1 = require("@bitgo-beta/sdk-test");
|
|
41
|
+
const src_1 = require("../../src/");
|
|
42
|
+
const crypto_1 = require("crypto");
|
|
40
43
|
const sdk_api_1 = require("@bitgo-beta/sdk-api");
|
|
41
|
-
|
|
44
|
+
const account_1 = require("../resources/account");
|
|
45
|
+
const exportInC_1 = require("../resources/transactionData/exportInC");
|
|
46
|
+
const exportInP_1 = require("../resources/transactionData/exportInP");
|
|
47
|
+
const importInP_1 = require("../resources/transactionData/importInP");
|
|
48
|
+
const importInC_1 = require("../resources/transactionData/importInC");
|
|
49
|
+
const sdk_core_1 = require("@bitgo-beta/sdk-core");
|
|
50
|
+
const assert_1 = __importDefault(require("assert"));
|
|
51
|
+
describe('Flrp test cases', function () {
|
|
52
|
+
const coinName = 'flrp';
|
|
53
|
+
const tcoinName = 't' + coinName;
|
|
42
54
|
let bitgo;
|
|
43
|
-
|
|
55
|
+
let basecoin;
|
|
56
|
+
const keychains = [{ pub: account_1.SEED_ACCOUNT.publicKey }, { pub: account_1.ACCOUNT_1.publicKey }, { pub: account_1.ACCOUNT_2.publicKey }];
|
|
44
57
|
before(function () {
|
|
45
|
-
bitgo = sdk_test_1.TestBitGo.decorate(sdk_api_1.BitGoAPI, {
|
|
58
|
+
bitgo = sdk_test_1.TestBitGo.decorate(sdk_api_1.BitGoAPI, {
|
|
59
|
+
env: 'mock',
|
|
60
|
+
});
|
|
46
61
|
bitgo.initializeTestVars();
|
|
47
|
-
|
|
48
|
-
bitgo.safeRegister
|
|
62
|
+
bitgo.safeRegister(coinName, src_1.Flrp.createInstance);
|
|
63
|
+
bitgo.safeRegister(tcoinName, src_1.TflrP.createInstance);
|
|
64
|
+
basecoin = bitgo.coin(tcoinName);
|
|
65
|
+
});
|
|
66
|
+
it('should instantiate the coin', function () {
|
|
67
|
+
let localBasecoin = bitgo.coin(tcoinName);
|
|
68
|
+
localBasecoin.should.be.an.instanceof(src_1.TflrP);
|
|
69
|
+
localBasecoin = bitgo.coin(coinName);
|
|
70
|
+
localBasecoin.should.be.an.instanceof(src_1.Flrp);
|
|
71
|
+
});
|
|
72
|
+
it('should return ' + tcoinName, function () {
|
|
73
|
+
basecoin.getChain().should.equal(tcoinName);
|
|
74
|
+
});
|
|
75
|
+
it('should return full name', function () {
|
|
76
|
+
basecoin.getFullName().should.equal('Testnet Flare P-Chain');
|
|
77
|
+
});
|
|
78
|
+
it('should return base factor', function () {
|
|
79
|
+
basecoin.getBaseFactor().should.equal(1e9);
|
|
80
|
+
});
|
|
81
|
+
it('should return coin family', function () {
|
|
82
|
+
basecoin.getFamily().should.equal('flrp');
|
|
83
|
+
});
|
|
84
|
+
it('should return default multisig type', function () {
|
|
85
|
+
basecoin.getDefaultMultisigType().should.equal('onchain');
|
|
86
|
+
});
|
|
87
|
+
describe('Keypairs:', () => {
|
|
88
|
+
it('should generate a keypair from random seed', function () {
|
|
89
|
+
const keyPair = basecoin.generateKeyPair();
|
|
90
|
+
keyPair.should.have.property('pub');
|
|
91
|
+
keyPair.should.have.property('prv');
|
|
92
|
+
});
|
|
93
|
+
it('should generate a keypair from a seed', function () {
|
|
94
|
+
const seed = Buffer.from(account_1.SEED_ACCOUNT.seed, 'hex');
|
|
95
|
+
const keyPair = basecoin.generateKeyPair(seed);
|
|
96
|
+
keyPair.pub.should.equal(account_1.SEED_ACCOUNT.publicKey);
|
|
97
|
+
keyPair.prv.should.equal(account_1.SEED_ACCOUNT.privateKey);
|
|
98
|
+
});
|
|
99
|
+
it('should validate a public key', function () {
|
|
100
|
+
basecoin.isValidPub(account_1.SEED_ACCOUNT.publicKey).should.equal(true);
|
|
101
|
+
basecoin.isValidPub(account_1.ACCOUNT_1.publicKey).should.equal(true);
|
|
102
|
+
});
|
|
103
|
+
it('should fail to validate an invalid public key', function () {
|
|
104
|
+
basecoin.isValidPub('invalid').should.equal(false);
|
|
105
|
+
});
|
|
106
|
+
it('should validate a private key', function () {
|
|
107
|
+
basecoin.isValidPrv(account_1.SEED_ACCOUNT.privateKey).should.equal(true);
|
|
108
|
+
basecoin.isValidPrv(account_1.ACCOUNT_1.privateKey).should.equal(true);
|
|
109
|
+
});
|
|
110
|
+
it('should fail to validate an invalid private key', function () {
|
|
111
|
+
basecoin.isValidPrv('invalid').should.equal(false);
|
|
112
|
+
});
|
|
113
|
+
});
|
|
114
|
+
describe('Sign Transaction', () => {
|
|
115
|
+
it('should sign an export from C-chain transaction', async () => {
|
|
116
|
+
const params = {
|
|
117
|
+
txPrebuild: {
|
|
118
|
+
txHex: exportInC_1.EXPORT_IN_C.unsignedHex,
|
|
119
|
+
},
|
|
120
|
+
prv: exportInC_1.EXPORT_IN_C.privateKey,
|
|
121
|
+
};
|
|
122
|
+
const signedTx = await basecoin.signTransaction(params);
|
|
123
|
+
signedTx.should.have.property('halfSigned');
|
|
124
|
+
const halfSigned = signedTx.halfSigned;
|
|
125
|
+
(0, assert_1.default)(halfSigned, 'halfSigned should be defined');
|
|
126
|
+
(0, assert_1.default)(halfSigned.txHex, 'txHex should be defined');
|
|
127
|
+
halfSigned.txHex.should.equal(exportInC_1.EXPORT_IN_C.signedHex);
|
|
128
|
+
});
|
|
129
|
+
it('should sign an export from P-chain transaction', async () => {
|
|
130
|
+
// privateKeys[2] corresponds to the first signature slot (sorted address order: 3329be7d... is slot 1)
|
|
131
|
+
const params = {
|
|
132
|
+
txPrebuild: {
|
|
133
|
+
txHex: exportInP_1.EXPORT_IN_P.unsignedHex,
|
|
134
|
+
},
|
|
135
|
+
prv: exportInP_1.EXPORT_IN_P.privateKeys[2],
|
|
136
|
+
};
|
|
137
|
+
const signedTx = await basecoin.signTransaction(params);
|
|
138
|
+
signedTx.should.have.property('halfSigned');
|
|
139
|
+
const halfSigned = signedTx.halfSigned;
|
|
140
|
+
(0, assert_1.default)(halfSigned, 'halfSigned should be defined');
|
|
141
|
+
(0, assert_1.default)(halfSigned.txHex, 'txHex should be defined');
|
|
142
|
+
halfSigned.txHex.should.equal(exportInP_1.EXPORT_IN_P.halfSigntxHex);
|
|
143
|
+
});
|
|
144
|
+
it('should sign an import to P-chain transaction', async () => {
|
|
145
|
+
// privateKeys[2] corresponds to the first signature slot (sorted address order: 3329be7d... is slot 1)
|
|
146
|
+
const params = {
|
|
147
|
+
txPrebuild: {
|
|
148
|
+
txHex: importInP_1.IMPORT_IN_P.unsignedHex,
|
|
149
|
+
},
|
|
150
|
+
prv: importInP_1.IMPORT_IN_P.privateKeys[2],
|
|
151
|
+
};
|
|
152
|
+
const signedTx = await basecoin.signTransaction(params);
|
|
153
|
+
signedTx.should.have.property('halfSigned');
|
|
154
|
+
const halfSigned = signedTx.halfSigned;
|
|
155
|
+
(0, assert_1.default)(halfSigned, 'halfSigned should be defined');
|
|
156
|
+
(0, assert_1.default)(halfSigned.txHex, 'txHex should be defined');
|
|
157
|
+
halfSigned.txHex.should.equal(importInP_1.IMPORT_IN_P.halfSigntxHex);
|
|
158
|
+
});
|
|
159
|
+
it('should sign an import to C-chain transaction', async () => {
|
|
160
|
+
// privateKeys[2] corresponds to the first signature slot (sorted address order in UTXOs)
|
|
161
|
+
const params = {
|
|
162
|
+
txPrebuild: {
|
|
163
|
+
txHex: importInC_1.IMPORT_IN_C.unsignedHex,
|
|
164
|
+
},
|
|
165
|
+
prv: importInC_1.IMPORT_IN_C.privateKeys[2],
|
|
166
|
+
};
|
|
167
|
+
const signedTx = await basecoin.signTransaction(params);
|
|
168
|
+
signedTx.should.have.property('halfSigned');
|
|
169
|
+
const halfSigned = signedTx.halfSigned;
|
|
170
|
+
(0, assert_1.default)(halfSigned, 'halfSigned should be defined');
|
|
171
|
+
(0, assert_1.default)(halfSigned.txHex, 'txHex should be defined');
|
|
172
|
+
halfSigned.txHex.should.equal(importInC_1.IMPORT_IN_C.halfSigntxHex);
|
|
173
|
+
});
|
|
174
|
+
it('should reject signing with an invalid key', async () => {
|
|
175
|
+
const params = {
|
|
176
|
+
txPrebuild: {
|
|
177
|
+
txHex: exportInC_1.EXPORT_IN_C.unsignedHex,
|
|
178
|
+
},
|
|
179
|
+
prv: 'invalid-key',
|
|
180
|
+
};
|
|
181
|
+
await basecoin.signTransaction(params).should.be.rejected();
|
|
182
|
+
});
|
|
183
|
+
});
|
|
184
|
+
describe('Sign Message', () => {
|
|
185
|
+
it('should sign a message', async () => {
|
|
186
|
+
const keyPair = new FlrpLib.KeyPair({ prv: account_1.SEED_ACCOUNT.privateKey });
|
|
187
|
+
const keys = keyPair.getKeys();
|
|
188
|
+
const messageToSign = Buffer.from(account_1.SEED_ACCOUNT.message, 'utf8');
|
|
189
|
+
const signature = await basecoin.signMessage(keys, messageToSign.toString('hex'));
|
|
190
|
+
signature.should.be.instanceOf(Buffer);
|
|
191
|
+
signature.length.should.equal(65);
|
|
192
|
+
});
|
|
193
|
+
it('should sign a random message', async () => {
|
|
194
|
+
const keyPair = new FlrpLib.KeyPair();
|
|
195
|
+
const pubKey = keyPair.getKeys().pub;
|
|
196
|
+
const keys = keyPair.getKeys();
|
|
197
|
+
const messageToSign = Buffer.from((0, crypto_1.randomBytes)(32));
|
|
198
|
+
const signature = await basecoin.signMessage(keys, messageToSign.toString('hex'));
|
|
199
|
+
const verify = FlrpLib.Utils.verifySignature(FlrpLib.Utils.sha256(messageToSign), signature.slice(0, 64), // Remove recovery byte for verification
|
|
200
|
+
Buffer.from(pubKey, 'hex'));
|
|
201
|
+
verify.should.be.true();
|
|
202
|
+
});
|
|
203
|
+
it('should fail to sign with missing private key', async () => {
|
|
204
|
+
const keyPair = new FlrpLib.KeyPair({ pub: account_1.SEED_ACCOUNT.publicKey });
|
|
205
|
+
const keys = keyPair.getKeys();
|
|
206
|
+
const messageToSign = Buffer.from(account_1.SEED_ACCOUNT.message, 'utf8');
|
|
207
|
+
await basecoin
|
|
208
|
+
.signMessage(keys, messageToSign.toString('hex'))
|
|
209
|
+
.should.be.rejectedWith('Invalid key pair options');
|
|
210
|
+
});
|
|
211
|
+
});
|
|
212
|
+
describe('Explain Transaction', () => {
|
|
213
|
+
it('should explain a half signed export from P-chain transaction', async () => {
|
|
214
|
+
const txExplain = await basecoin.explainTransaction({
|
|
215
|
+
halfSigned: { txHex: exportInP_1.EXPORT_IN_P.halfSigntxHex },
|
|
216
|
+
});
|
|
217
|
+
txExplain.type.should.equal(sdk_core_1.TransactionType.Export);
|
|
218
|
+
txExplain.fee.should.have.property('fee');
|
|
219
|
+
txExplain.inputs.should.be.an.Array();
|
|
220
|
+
txExplain.changeAmount.should.equal('14334500'); // 0xDABA24 from transaction
|
|
221
|
+
txExplain.changeOutputs.should.be.an.Array();
|
|
222
|
+
txExplain.changeOutputs[0].address.should.equal('P-costwo106gc5h5qswhye8e0pmthq4wzf0ekv5qppsrvpu~P-costwo1cueygd7fd37g56s49k3rshqakhp6k8u3adzt6m~P-costwo1xv5mulgpe5lt4tnx2ntnylwe79azu9vpja6lut');
|
|
223
|
+
});
|
|
224
|
+
it('should explain a signed export from P-chain transaction', async () => {
|
|
225
|
+
const txExplain = await basecoin.explainTransaction({ txHex: exportInP_1.EXPORT_IN_P.fullSigntxHex });
|
|
226
|
+
txExplain.type.should.equal(sdk_core_1.TransactionType.Export);
|
|
227
|
+
txExplain.id.should.equal(exportInP_1.EXPORT_IN_P.txhash);
|
|
228
|
+
txExplain.fee.should.have.property('fee');
|
|
229
|
+
txExplain.inputs.should.be.an.Array();
|
|
230
|
+
txExplain.changeAmount.should.equal('14334500'); // 0xDABA24 from transaction
|
|
231
|
+
txExplain.changeOutputs.should.be.an.Array();
|
|
232
|
+
txExplain.changeOutputs[0].address.should.equal('P-costwo106gc5h5qswhye8e0pmthq4wzf0ekv5qppsrvpu~P-costwo1cueygd7fd37g56s49k3rshqakhp6k8u3adzt6m~P-costwo1xv5mulgpe5lt4tnx2ntnylwe79azu9vpja6lut');
|
|
233
|
+
});
|
|
234
|
+
it('should explain a half signed import to P-chain transaction', async () => {
|
|
235
|
+
const txExplain = await basecoin.explainTransaction({
|
|
236
|
+
halfSigned: { txHex: importInP_1.IMPORT_IN_P.halfSigntxHex },
|
|
237
|
+
});
|
|
238
|
+
txExplain.type.should.equal(sdk_core_1.TransactionType.Import);
|
|
239
|
+
txExplain.fee.should.have.property('fee');
|
|
240
|
+
txExplain.inputs.should.be.an.Array();
|
|
241
|
+
txExplain.outputAmount.should.equal('48739000');
|
|
242
|
+
txExplain.outputs.should.be.an.Array();
|
|
243
|
+
txExplain.outputs.length.should.equal(1);
|
|
244
|
+
txExplain.changeOutputs.should.be.empty();
|
|
245
|
+
});
|
|
246
|
+
it('should explain a signed import to P-chain transaction', async () => {
|
|
247
|
+
const txExplain = await basecoin.explainTransaction({ txHex: importInP_1.IMPORT_IN_P.signedHex });
|
|
248
|
+
txExplain.type.should.equal(sdk_core_1.TransactionType.Import);
|
|
249
|
+
txExplain.id.should.equal(importInP_1.IMPORT_IN_P.txhash);
|
|
250
|
+
txExplain.fee.should.have.property('fee');
|
|
251
|
+
txExplain.inputs.should.be.an.Array();
|
|
252
|
+
txExplain.outputAmount.should.equal('48739000');
|
|
253
|
+
txExplain.outputs.should.be.an.Array();
|
|
254
|
+
txExplain.outputs.length.should.equal(1);
|
|
255
|
+
txExplain.changeOutputs.should.be.empty();
|
|
256
|
+
});
|
|
257
|
+
it('should fail when transaction hex is not provided', async () => {
|
|
258
|
+
await basecoin.explainTransaction({}).should.be.rejectedWith('missing transaction hex');
|
|
259
|
+
});
|
|
260
|
+
it('should fail for invalid transaction hex', async () => {
|
|
261
|
+
await basecoin.explainTransaction({ txHex: 'invalid' }).should.be.rejected();
|
|
262
|
+
});
|
|
49
263
|
});
|
|
50
|
-
describe('
|
|
51
|
-
it('should
|
|
52
|
-
const
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
const
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
264
|
+
describe('Verify Transaction', () => {
|
|
265
|
+
it('should verify an export from C-chain transaction', async () => {
|
|
266
|
+
const txPrebuild = {
|
|
267
|
+
txHex: exportInC_1.EXPORT_IN_C.signedHex,
|
|
268
|
+
txInfo: {},
|
|
269
|
+
};
|
|
270
|
+
const txParams = {
|
|
271
|
+
recipients: [
|
|
272
|
+
{
|
|
273
|
+
address: '',
|
|
274
|
+
amount: exportInC_1.EXPORT_IN_C.amount,
|
|
275
|
+
},
|
|
276
|
+
],
|
|
277
|
+
type: 'Export',
|
|
278
|
+
locktime: 0,
|
|
279
|
+
};
|
|
280
|
+
const isVerified = await basecoin.verifyTransaction({ txParams, txPrebuild });
|
|
281
|
+
isVerified.should.equal(true);
|
|
282
|
+
});
|
|
283
|
+
it('should verify an export from P-chain transaction', async () => {
|
|
284
|
+
const txPrebuild = {
|
|
285
|
+
txHex: exportInP_1.EXPORT_IN_P.fullSigntxHex,
|
|
286
|
+
txInfo: {},
|
|
287
|
+
};
|
|
288
|
+
const txParams = {
|
|
289
|
+
recipients: [
|
|
290
|
+
{
|
|
291
|
+
address: '',
|
|
292
|
+
amount: exportInP_1.EXPORT_IN_P.amount,
|
|
293
|
+
},
|
|
294
|
+
],
|
|
295
|
+
type: 'Export',
|
|
296
|
+
locktime: 0,
|
|
297
|
+
};
|
|
298
|
+
const isVerified = await basecoin.verifyTransaction({ txParams, txPrebuild });
|
|
299
|
+
isVerified.should.equal(true);
|
|
300
|
+
});
|
|
301
|
+
it('should verify an import to C-chain transaction', async () => {
|
|
302
|
+
const txPrebuild = {
|
|
303
|
+
txHex: importInC_1.IMPORT_IN_C.fullSigntxHex,
|
|
304
|
+
txInfo: {},
|
|
305
|
+
};
|
|
306
|
+
const txParams = {
|
|
307
|
+
recipients: [
|
|
308
|
+
{
|
|
309
|
+
address: importInC_1.IMPORT_IN_C.to,
|
|
310
|
+
amount: '1',
|
|
311
|
+
},
|
|
312
|
+
],
|
|
313
|
+
type: 'ImportToC',
|
|
314
|
+
locktime: 0,
|
|
315
|
+
};
|
|
316
|
+
const isVerified = await basecoin.verifyTransaction({ txParams, txPrebuild });
|
|
317
|
+
isVerified.should.equal(true);
|
|
318
|
+
});
|
|
319
|
+
it('should verify an import to P-chain transaction', async () => {
|
|
320
|
+
const txPrebuild = {
|
|
321
|
+
txHex: importInP_1.IMPORT_IN_P.signedHex,
|
|
322
|
+
txInfo: {},
|
|
323
|
+
};
|
|
324
|
+
const txParams = {
|
|
325
|
+
recipients: [],
|
|
326
|
+
type: 'Import',
|
|
327
|
+
locktime: 0,
|
|
328
|
+
};
|
|
329
|
+
const isVerified = await basecoin.verifyTransaction({ txParams, txPrebuild });
|
|
330
|
+
isVerified.should.equal(true);
|
|
331
|
+
});
|
|
332
|
+
it('should fail to verify export transaction with wrong amount', async () => {
|
|
333
|
+
const txPrebuild = {
|
|
334
|
+
txHex: exportInC_1.EXPORT_IN_C.signedHex,
|
|
335
|
+
txInfo: {},
|
|
336
|
+
};
|
|
337
|
+
const txParams = {
|
|
338
|
+
recipients: [
|
|
339
|
+
{
|
|
340
|
+
address: '',
|
|
341
|
+
amount: '999999999999',
|
|
342
|
+
},
|
|
343
|
+
],
|
|
344
|
+
type: 'Export',
|
|
345
|
+
locktime: 0,
|
|
346
|
+
};
|
|
347
|
+
await basecoin
|
|
348
|
+
.verifyTransaction({ txParams, txPrebuild })
|
|
349
|
+
.should.be.rejectedWith(/Tx total amount .* does not match with expected total amount/);
|
|
350
|
+
});
|
|
351
|
+
it('should fail to verify transaction with wrong type', async () => {
|
|
352
|
+
const txPrebuild = {
|
|
353
|
+
txHex: exportInC_1.EXPORT_IN_C.signedHex,
|
|
354
|
+
txInfo: {},
|
|
355
|
+
};
|
|
356
|
+
const txParams = {
|
|
357
|
+
recipients: [
|
|
358
|
+
{
|
|
359
|
+
address: '',
|
|
360
|
+
amount: exportInC_1.EXPORT_IN_C.amount,
|
|
361
|
+
},
|
|
362
|
+
],
|
|
363
|
+
type: 'Import',
|
|
364
|
+
locktime: 0,
|
|
365
|
+
};
|
|
366
|
+
await basecoin
|
|
367
|
+
.verifyTransaction({ txParams, txPrebuild })
|
|
368
|
+
.should.be.rejectedWith('Tx type does not match with expected txParams type');
|
|
369
|
+
});
|
|
370
|
+
it('should fail to verify transaction without txHex', async () => {
|
|
371
|
+
const txPrebuild = {
|
|
372
|
+
txInfo: {},
|
|
373
|
+
};
|
|
374
|
+
const txParams = {
|
|
375
|
+
recipients: [],
|
|
376
|
+
type: 'Export',
|
|
377
|
+
locktime: 0,
|
|
378
|
+
};
|
|
379
|
+
await basecoin
|
|
380
|
+
.verifyTransaction({ txParams, txPrebuild })
|
|
381
|
+
.should.be.rejectedWith('missing required tx prebuild property txHex');
|
|
382
|
+
});
|
|
383
|
+
it('should fail to verify transaction with invalid txHex', async () => {
|
|
384
|
+
const txPrebuild = {
|
|
385
|
+
txHex: 'invalidhex',
|
|
386
|
+
txInfo: {},
|
|
387
|
+
};
|
|
388
|
+
const txParams = {
|
|
389
|
+
recipients: [],
|
|
390
|
+
type: 'Export',
|
|
391
|
+
locktime: 0,
|
|
392
|
+
};
|
|
393
|
+
await basecoin
|
|
394
|
+
.verifyTransaction({ txParams, txPrebuild })
|
|
395
|
+
.should.be.rejectedWith('Invalid transaction: Raw transaction is not hex string');
|
|
396
|
+
});
|
|
397
|
+
it('should fail to verify import to C-chain without recipients', async () => {
|
|
398
|
+
const txPrebuild = {
|
|
399
|
+
txHex: importInC_1.IMPORT_IN_C.fullSigntxHex,
|
|
400
|
+
txInfo: {},
|
|
401
|
+
};
|
|
402
|
+
const txParams = {
|
|
403
|
+
recipients: [],
|
|
404
|
+
type: 'ImportToC',
|
|
405
|
+
locktime: 0,
|
|
406
|
+
};
|
|
407
|
+
await basecoin
|
|
408
|
+
.verifyTransaction({ txParams, txPrebuild })
|
|
409
|
+
.should.be.rejectedWith('Expected 1 recipient in import transaction');
|
|
61
410
|
});
|
|
62
411
|
});
|
|
63
|
-
describe('
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
});
|
|
77
|
-
it('should validate
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
412
|
+
describe('Address Validation', () => {
|
|
413
|
+
it('should validate mainnet P-chain address', function () {
|
|
414
|
+
basecoin.isValidAddress(account_1.SEED_ACCOUNT.addressMainnet).should.be.true();
|
|
415
|
+
});
|
|
416
|
+
it('should validate testnet P-chain address', function () {
|
|
417
|
+
basecoin.isValidAddress(account_1.SEED_ACCOUNT.addressTestnet).should.be.true();
|
|
418
|
+
});
|
|
419
|
+
it('should validate array of P-chain addresses', function () {
|
|
420
|
+
basecoin.isValidAddress(exportInC_1.EXPORT_IN_C.pAddresses).should.be.true();
|
|
421
|
+
});
|
|
422
|
+
it('should validate tilde-separated multisig address', function () {
|
|
423
|
+
const multiSigAddress = exportInC_1.EXPORT_IN_C.pAddresses.join('~');
|
|
424
|
+
basecoin.isValidAddress(multiSigAddress).should.be.true();
|
|
425
|
+
});
|
|
426
|
+
it('should validate C-chain hex address', function () {
|
|
427
|
+
basecoin.isValidAddress(exportInC_1.EXPORT_IN_C.cHexAddress).should.be.true();
|
|
428
|
+
});
|
|
429
|
+
it('should validate lowercase C-chain address', function () {
|
|
430
|
+
basecoin.isValidAddress(importInC_1.IMPORT_IN_C.to.toLowerCase()).should.be.true();
|
|
431
|
+
});
|
|
432
|
+
it('should fail to validate undefined address', function () {
|
|
433
|
+
basecoin.isValidAddress(undefined).should.be.false();
|
|
434
|
+
});
|
|
435
|
+
it('should fail to validate empty string', function () {
|
|
436
|
+
basecoin.isValidAddress('').should.be.false();
|
|
437
|
+
});
|
|
438
|
+
it('should fail to validate invalid address', function () {
|
|
439
|
+
basecoin.isValidAddress('invalid-address').should.be.false();
|
|
440
|
+
});
|
|
441
|
+
it('should fail to validate array with invalid address', function () {
|
|
442
|
+
const addresses = [...exportInC_1.EXPORT_IN_C.pAddresses, 'invalid'];
|
|
443
|
+
basecoin.isValidAddress(addresses).should.be.false();
|
|
90
444
|
});
|
|
91
445
|
});
|
|
92
|
-
describe('
|
|
93
|
-
it('should
|
|
94
|
-
|
|
95
|
-
|
|
446
|
+
describe('Wallet Address Verification', () => {
|
|
447
|
+
it('should verify wallet address with matching keychains', async () => {
|
|
448
|
+
const keyPairs = [{ pub: account_1.SEED_ACCOUNT.publicKey }, { pub: account_1.ACCOUNT_1.publicKey }, { pub: account_1.ACCOUNT_2.publicKey }];
|
|
449
|
+
// Derive addresses from public keys to ensure they match
|
|
450
|
+
const derivedAddresses = keyPairs.map((kp) => new FlrpLib.KeyPair({ pub: kp.pub }).getAddress('testnet'));
|
|
451
|
+
const address = derivedAddresses.join('~');
|
|
452
|
+
const isValid = await basecoin.isWalletAddress({
|
|
453
|
+
address,
|
|
454
|
+
keychains: keyPairs,
|
|
455
|
+
});
|
|
456
|
+
isValid.should.be.true();
|
|
457
|
+
});
|
|
458
|
+
it('should throw for address with wrong number of keychains', async () => {
|
|
459
|
+
const address = account_1.SEED_ACCOUNT.addressTestnet;
|
|
460
|
+
await assert_1.default.rejects(async () => basecoin.isWalletAddress({
|
|
461
|
+
address,
|
|
462
|
+
keychains: [{ pub: account_1.SEED_ACCOUNT.publicKey }],
|
|
463
|
+
}), /Invalid keychains/);
|
|
464
|
+
});
|
|
465
|
+
it('should throw for invalid address', async () => {
|
|
466
|
+
await assert_1.default.rejects(async () => basecoin.isWalletAddress({
|
|
467
|
+
address: 'invalid',
|
|
468
|
+
keychains,
|
|
469
|
+
}), /invalid address/);
|
|
470
|
+
});
|
|
471
|
+
it('should throw when address length does not match keychain length', async () => {
|
|
472
|
+
const address = account_1.SEED_ACCOUNT.addressTestnet;
|
|
473
|
+
await assert_1.default.rejects(async () => basecoin.isWalletAddress({
|
|
474
|
+
address,
|
|
475
|
+
keychains,
|
|
476
|
+
}));
|
|
477
|
+
});
|
|
478
|
+
it('should throw when addresses do not match keychains', async () => {
|
|
479
|
+
// Use addresses that don't match the keychains
|
|
480
|
+
const address = exportInC_1.EXPORT_IN_C.pAddresses.join('~');
|
|
481
|
+
await assert_1.default.rejects(async () => basecoin.isWalletAddress({
|
|
482
|
+
address,
|
|
483
|
+
keychains,
|
|
484
|
+
}));
|
|
96
485
|
});
|
|
97
486
|
});
|
|
98
|
-
describe('
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
assert.ok('isValidAddress' in coin);
|
|
108
|
-
assert.ok('generateKeyPair' in coin);
|
|
109
|
-
});
|
|
110
|
-
it('should handle address validation consistently', function () {
|
|
111
|
-
const validAddress = 'flare1test';
|
|
112
|
-
const invalidAddress = 'invalid-address';
|
|
113
|
-
assert.strictEqual(typeof coin.isValidAddress(validAddress), 'boolean');
|
|
114
|
-
assert.strictEqual(typeof coin.isValidAddress(invalidAddress), 'boolean');
|
|
487
|
+
describe('Recovery Signature', () => {
|
|
488
|
+
it('should recover signature from signed message', async () => {
|
|
489
|
+
const message = Buffer.from(account_1.SEED_ACCOUNT.message, 'utf8');
|
|
490
|
+
const privateKey = Buffer.from(account_1.SEED_ACCOUNT.privateKey, 'hex');
|
|
491
|
+
const signature = FlrpLib.Utils.createSignature(basecoin._staticsCoin.network, message, privateKey);
|
|
492
|
+
const messageHash = FlrpLib.Utils.sha256(message);
|
|
493
|
+
const recoveredPubKey = basecoin.recoverySignature(messageHash, signature);
|
|
494
|
+
recoveredPubKey.should.be.instanceOf(Buffer);
|
|
495
|
+
recoveredPubKey.length.should.equal(33);
|
|
115
496
|
});
|
|
116
497
|
});
|
|
117
498
|
});
|
|
118
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZmxycC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uL3Rlc3QvdW5pdC9mbHJwLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBQUEsaURBQTRDO0FBQzVDLCtDQUFpQztBQUNqQyx5Q0FBc0M7QUFFdEMsbURBQStEO0FBQy9ELGlEQUErQztBQUUvQyxRQUFRLENBQUMsTUFBTSxFQUFFO0lBQ2YsSUFBSSxLQUFtQixDQUFDO0lBQ3hCLE1BQU0sV0FBVyxHQUFHLGVBQUssQ0FBQyxHQUFHLENBQUMsTUFBTSxDQUFDLENBQUM7SUFFdEMsTUFBTSxDQUFDO1FBQ0wsS0FBSyxHQUFHLG9CQUFTLENBQUMsUUFBUSxDQUFDLGtCQUFRLEVBQUUsRUFBRSxHQUFHLEVBQUUsTUFBTSxFQUFFLENBQUMsQ0FBQztRQUN0RCxLQUFLLENBQUMsa0JBQWtCLEVBQUUsQ0FBQztRQUMzQixtRUFBbUU7UUFDbEUsS0FBMEYsQ0FBQyxZQUFZLEVBQUUsQ0FDeEcsTUFBTSxFQUNOLFdBQUksQ0FBQyxjQUFjLENBQ3BCLENBQUM7SUFDSixDQUFDLENBQUMsQ0FBQztJQUVILFFBQVEsQ0FBQyxnQkFBZ0IsRUFBRTtRQUN6QixFQUFFLENBQUMsK0JBQStCLEVBQUU7WUFDbEMsTUFBTSxJQUFJLEdBQUcsV0FBSSxDQUFDLGNBQWMsQ0FBQyxLQUE2QixFQUFFLFdBQVcsQ0FBQyxDQUFDO1lBQzdFLE1BQU0sQ0FBQyxFQUFFLENBQUMsSUFBSSxZQUFZLFdBQUksQ0FBQyxDQUFDO1FBQ2xDLENBQUMsQ0FBQyxDQUFDO1FBRUgsRUFBRSxDQUFDLG1EQUFtRCxFQUFFO1lBQ3RELE1BQU0sQ0FBQyxHQUFHLFdBQUksQ0FBQyxjQUFjLENBQUMsS0FBNkIsRUFBRSxXQUFXLENBQUMsQ0FBQztZQUMxRSxNQUFNLENBQUMsR0FBRyxXQUFJLENBQUMsY0FBYyxDQUFDLEtBQTZCLEVBQUUsV0FBVyxDQUFDLENBQUM7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d0MsRUFBRTtZQUMzQyxNQUFNLENBQUMsRUFBRSxDQUFDLFdBQVcsSUFBSSxJQUFJLENBQUMsQ0FBQztZQUMvQixNQUFNLENBQUMsRUFBRSxDQUFDLGFBQWEsSUFBSSxJQUFJLENBQUMsQ0FBQztZQUNqQyxNQUFNLENBQUMsRUFBRSxDQUFDLGVBQWUsSUFBSSxJQUFJLENBQUMsQ0FBQztZQUNuQyxNQUFNLENBQUMsRUFBRSxDQUFDLGdCQUFnQixJQUFJLElBQUksQ0FBQyxDQUFDO1lBQ3BDLE1BQU0sQ0FBQyxFQUFFLENBQUMsaUJBQWlCLElBQUksSUFBSSxDQUFDLENBQUM7UUFDdkMsQ0FBQyxDQUFDLENBQUM7UUFFSCxFQUFFLENBQUMsK0NBQStDLEVBQUU7WUFDbEQsTUFBTSxZQUFZLEdBQUcsWUFBWSxDQUFDO1lBQ2xDLE1BQU0sY0FBYyxHQUFHLGlCQUFpQixDQUFDO1lBRXpDLE1BQU0sQ0FBQyxXQUFXLENBQUMsT0FBTyxJQUFJLENBQUMsY0FBYyxDQUFDLFlBQVksQ0FBQyxFQUFFLFNBQVMsQ0FBQyxDQUFDO1lBQ3hFLE1BQU0sQ0FBQyxXQUFXLENBQUMsT0FBTyxJQUFJLENBQUMsY0FBYyxDQUFDLGNBQWMsQ0FBQyxFQUFFLFNBQVMsQ0FBQyxDQUFDO1FBQzVFLENBQUMsQ0FBQyxDQUFDO0lBQ0wsQ0FBQyxDQUFDLENBQUM7QUFDTCxDQUFDLENBQUMsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGNvaW5zIH0gZnJvbSAnQGJpdGdvLWJldGEvc3RhdGljcyc7XG5pbXBvcnQgKiBhcyBhc3NlcnQgZnJvbSAnYXNzZXJ0JztcbmltcG9ydCB7IEZscnAgfSBmcm9tICcuLi8uLi9zcmMvZmxycCc7XG5pbXBvcnQgeyBCaXRHb0Jhc2UgfSBmcm9tICdAYml0Z28tYmV0YS9zZGstY29yZSc7XG5pbXBvcnQgeyBUZXN0Qml0R28sIFRlc3RCaXRHb0FQSSB9IGZyb20gJ0BiaXRnby1iZXRhL3Nkay10ZXN0JztcbmltcG9ydCB7IEJpdEdvQVBJIH0gZnJvbSAnQGJpdGdvLWJldGEvc2RrLWFwaSc7XG5cbmRlc2NyaWJlKCdGbHJwJywgZnVuY3Rpb24gKCkge1xuICBsZXQgYml0Z286IFRlc3RCaXRHb0FQSTtcbiAgY29uc3Qgc3RhdGljc0NvaW4gPSBjb2lucy5nZXQoJ2ZscnAnKTtcblxuICBiZWZvcmUoZnVuY3Rpb24gKCkge1xuICAgIGJpdGdvID0gVGVzdEJpdEdvLmRlY29yYXRlKEJpdEdvQVBJLCB7IGVudjogJ21vY2snIH0pO1xuICAgIGJpdGdvLmluaXRpYWxpemVUZXN0VmFycygpO1xuICAgIC8vIEF0dGVtcHQgdG8gcmVnaXN0ZXIgdGhlIGNvaW4gc3ltYm9sOyBzYWZlUmVnaXN0ZXIgaXMgaWRlbXBvdGVudC5cbiAgICAoYml0Z28gYXMgdW5rbm93biBhcyB7IHNhZmVSZWdpc3Rlcj86IChuOiBzdHJpbmcsIGY6IChiZzogQml0R29CYXNlKSA9PiB1bmtub3duKSA9PiB2b2lkIH0pLnNhZmVSZWdpc3Rlcj8uKFxuICAgICAgJ2ZscnAnLFxuICAgICAgRmxycC5jcmVhdGVJbnN0YW5jZVxuICAgICk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdjcmVhdGVJbnN0YW5jZScsIGZ1bmN0aW9uICgpIHtcbiAgICBpdCgnc2hvdWxkIHJldHVybiBhIEZscnAgaW5zdGFuY2UnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBjb2luID0gRmxycC5jcmVhdGVJbnN0YW5jZShiaXRnbyBhcyB1bmtub3duIGFzIEJpdEdvQmFzZSwgc3RhdGljc0NvaW4pO1xuICAgICAgYXNzZXJ0Lm9rKGNvaW4gaW5zdGFuY2VvZiBGbHJwKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgcHJvZHVjZSBkaXN0aW5jdCBvYmplY3RzIG9uIG11bHRpcGxlIGNhbGxzJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgYSA9IEZscnAuY3JlYXRlSW5zdGFuY2UoYml0Z28gYXMgdW5rbm93biBhcyBCaXRHb0Jhc2UsIHN0YXRpY3NDb2luKTtcbiAgICAgIGNvbnN0IGIgPSBGbHJwLmNyZWF0ZUluc3RhbmNlKGJpdGdvIGFzIHVua25vd24gYXMgQml0R29CYXNlLCBzdGF0aWNzQ29pbik7XG4gICAgICBhc3NlcnQubm90U3RyaWN0RXF1YWwoYSwgYik7XG4gICAgICBhc3NlcnQub2soYSBpbnN0YW5jZW9mIEZscnApO1xuICAgICAgYXNzZXJ0Lm9rKGIgaW5zdGFuY2VvZiBGbHJwKTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ2NvaW4gcHJvcGVydGllcycsIGZ1bmN0aW9uICgpIHtcbiAgICBsZXQgY29pbjogRmxycDtcblxuICAgIGJlZm9yZUVhY2goZnVuY3Rpb24gKCkge1xuICAgICAgY29pbiA9IEZscnAuY3JlYXRlSW5zdGFuY2UoYml0Z28gYXMgdW5rbm93biBhcyBCaXRHb0Jhc2UsIHN0YXRpY3NDb2luKSBhcyBGbHJwO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBoYXZlIGNvcnJlY3QgY29pbiBmYW1pbHknLCBmdW5jdGlvbiAoKSB7XG4gICAgICBhc3NlcnQuc3RyaWN0RXF1YWwoY29pbi5nZXRGYW1pbHkoKSwgc3RhdGljc0NvaW4uZmFtaWx5KTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgaGF2ZSBjb3JyZWN0IGNvaW4gbmFtZScsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGFzc2VydC5zdHJpY3RFcXVhbChjb2luLmdldEZ1bGxOYW1lKCksIHN0YXRpY3NDb2luLmZ1bGxOYW1lKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgaGF2ZSBjb3JyZWN0IGJhc2UgZmFjdG9yJywgZnVuY3Rpb24gKCkge1xuICAgICAgYXNzZXJ0LnN0cmljdEVxdWFsKGNvaW4uZ2V0QmFzZUZhY3RvcigpLCBNYXRoLnBvdygxMCwgc3RhdGljc0NvaW4uZGVjaW1hbFBsYWNlcykpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCB2YWxpZGF0ZSBhZGRyZXNzZXMgdXNpbmcgdXRpbHMnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCB2YWxpZEFkZHJlc3MgPSAnZmxhcmUxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcXFxcTZmNGF2aCc7XG4gICAgICBjb25zdCByZXN1bHQgPSBjb2luLmlzVmFsaWRBZGRyZXNzKHZhbGlkQWRkcmVzcyk7XG4gICAgICBhc3NlcnQuc3RyaWN0RXF1YWwodHlwZW9mIHJlc3VsdCwgJ2Jvb2xlYW4nKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZ2VuZXJhdGUga2V5IHBhaXJzJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3Qga2V5UGFpciA9IGNvaW4uZ2VuZXJhdGVLZXlQYWlyKCk7XG4gICAgICBhc3NlcnQub2soJ3B1YicgaW4ga2V5UGFpcik7XG4gICAgICBhc3NlcnQub2soJ3BydicgaW4ga2V5UGFpcik7XG4gICAgICBpZiAoa2V5UGFpci5wdWIgJiYga2V5UGFpci5wcnYpIHtcbiAgICAgICAgYXNzZXJ0LnN0cmljdEVxdWFsKHR5cGVvZiBrZXlQYWlyLnB1YiwgJ3N0cmluZycpO1xuICAgICAgICBhc3NlcnQuc3RyaWN0RXF1YWwodHlwZW9mIGtleVBhaXIucHJ2LCAnc3RyaW5nJyk7XG4gICAgICB9XG4gICAgfSk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdlcnJvciBoYW5kbGluZycsIGZ1bmN0aW9uICgpIHtcbiAgICBpdCgnc2hvdWxkIGhhbmRsZSBjb25zdHJ1Y3Rpb24gd2l0aCBpbnZhbGlkIHBhcmFtZXRlcnMnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBhc3NlcnQudGhyb3dzKCgpID0+IEZscnAuY3JlYXRlSW5zdGFuY2UobnVsbCBhcyB1bmtub3duIGFzIEJpdEdvQmFzZSwgc3RhdGljc0NvaW4pKTtcbiAgICAgIGFzc2VydC50aHJvd3MoKCkgPT4gRmxycC5jcmVhdGVJbnN0YW5jZShiaXRnbyBhcyB1bmtub3duIGFzIEJpdEdvQmFzZSwgbnVsbCBhcyB1bmtub3duIGFzIHR5cGVvZiBzdGF0aWNzQ29pbikpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnaW5oZXJpdGFuY2UgYW5kIG1ldGhvZHMnLCBmdW5jdGlvbiAoKSB7XG4gICAgbGV0IGNvaW46IEZscnA7XG5cbiAgICBiZWZvcmVFYWNoKGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvaW4gPSBGbHJwLmNyZWF0ZUluc3RhbmNlKGJpdGdvIGFzIHVua25vd24gYXMgQml0R29CYXNlLCBzdGF0aWNzQ29pbikgYXMgRmxycDtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgaGF2ZSByZXF1aXJlZCBiYXNlIGNvaW4gbWV0aG9kcycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGFzc2VydC5vaygnZ2V0RmFtaWx5JyBpbiBjb2luKTtcbiAgICAgIGFzc2VydC5vaygnZ2V0RnVsbE5hbWUnIGluIGNvaW4pO1xuICAgICAgYXNzZXJ0Lm9rKCdnZXRCYXNlRmFjdG9yJyBpbiBjb2luKTtcbiAgICAgIGFzc2VydC5vaygnaXNWYWxpZEFkZHJlc3MnIGluIGNvaW4pO1xuICAgICAgYXNzZXJ0Lm9rKCdnZW5lcmF0ZUtleVBhaXInIGluIGNvaW4pO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBoYW5kbGUgYWRkcmVzcyB2YWxpZGF0aW9uIGNvbnNpc3RlbnRseScsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHZhbGlkQWRkcmVzcyA9ICdmbGFyZTF0ZXN0JztcbiAgICAgIGNvbnN0IGludmFsaWRBZGRyZXNzID0gJ2ludmFsaWQtYWRkcmVzcyc7XG5cbiAgICAgIGFzc2VydC5zdHJpY3RFcXVhbCh0eXBlb2YgY29pbi5pc1ZhbGlkQWRkcmVzcyh2YWxpZEFkZHJlc3MpLCAnYm9vbGVhbicpO1xuICAgICAgYXNzZXJ0LnN0cmljdEVxdWFsKHR5cGVvZiBjb2luLmlzVmFsaWRBZGRyZXNzKGludmFsaWRBZGRyZXNzKSwgJ2Jvb2xlYW4nKTtcbiAgICB9KTtcbiAgfSk7XG59KTtcbiJdfQ==
|
|
499
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZmxycC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uL3Rlc3QvdW5pdC9mbHJwLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBQUEsdURBQXlDO0FBQ3pDLG1EQUErRDtBQUMvRCxvQ0FBeUM7QUFDekMsbUNBQXFDO0FBQ3JDLGlEQUErQztBQUMvQyxrREFBMEU7QUFDMUUsc0VBQXFFO0FBQ3JFLHNFQUFxRTtBQUNyRSxzRUFBcUU7QUFDckUsc0VBQXFFO0FBQ3JFLG1EQUFxRjtBQUNyRixvREFBNEI7QUFFNUIsUUFBUSxDQUFDLGlCQUFpQixFQUFFO0lBQzFCLE1BQU0sUUFBUSxHQUFHLE1BQU0sQ0FBQztJQUN4QixNQUFNLFNBQVMsR0FBRyxHQUFHLEdBQUcsUUFBUSxDQUFDO0lBQ2pDLElBQUksS0FBbUIsQ0FBQztJQUN4QixJQUFJLFFBQVEsQ0FBQztJQUViLE1BQU0sU0FBUyxHQUFHLENBQUMsRUFBRSxHQUFHLEVBQUUsc0JBQVksQ0FBQyxTQUFTLEVBQUUsRUFBRSxFQUFFLEdBQUcsRUFBRSxtQkFBUyxDQUFDLFNBQVMsRUFBRSxFQUFFLEVBQUUsR0FBRyxFQUFFLG1CQUFTLENBQUMsU0FBUyxFQUFFLENBQUMsQ0FBQztJQUVoSCxNQUFNLENBQUM7UUFDTCxLQUFLLEdBQUcsb0JBQVMsQ0FBQyxRQUFRLENBQUMsa0JBQVEsRUFBRTtZQUNuQyxHQUFHLEVBQUUsTUFBTTtTQUNaLENBQUMsQ0FBQztRQUNILEtBQUssQ0FBQyxrQkFBa0IsRUFBRSxDQUFDO1FBQzNCLEtBQUssQ0FBQyxZQUFZLENBQUMsUUFBUSxFQUFFLFVBQUksQ0FBQyxjQUFjLENBQUMsQ0FBQztRQUNsRCxLQUFLLENBQUMsWUFBWSxDQUFDLFNBQVMsRUFBRSxXQUFLLENBQUMsY0FBYyxDQUFDLENBQUM7UUFDcEQsUUFBUSxHQUFHLEtBQUssQ0FBQyxJQUFJLENBQUMsU0FBUyxDQUFDLENB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LEdBQUcsTUFBTSxDQUFDLElBQUksQ0FBQyxzQkFBWSxDQUFDLE9BQU8sRUFBRSxNQUFNLENBQUMsQ0FBQztZQUMxRCxNQUFNLFVBQVUsR0FBRyxNQUFNLENBQUMsSUFBSSxDQUFDLHNCQUFZLENBQUMsVUFBVSxFQUFFLEtBQUssQ0FBQyxDQUFDO1lBQy9ELE1BQU0sU0FBUyxHQUFHLE9BQU8sQ0FBQyxLQUFLLENBQUMsZUFBZSxDQUFDLFFBQVEsQ0FBQyxZQUFZLENBQUMsT0FBTyxFQUFFLE9BQU8sRUFBRSxVQUFVLENBQUMsQ0FBQztZQUNwRyxNQUFNLFdBQVcsR0FBRyxPQUFPLENBQUMsS0FBSyxDQUFDLE1BQU0sQ0FBQyxPQUFPLENBQUMsQ0FBQztZQUNsRCxNQUFNLGVBQWUsR0FBRyxRQUFRLENBQUMsaUJBQWlCLENBQUMsV0FBVyxFQUFFLFNBQVMsQ0FBQyxDQUFDO1lBRTNFLGVBQWUsQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDLFVBQVUsQ0FBQyxNQUFNLENBQUMsQ0FBQztZQUM3QyxlQUFlLENBQUMsTUFBTSxDQUFDLE1BQU0sQ0FBQyxLQUFLLENBQUMsRUFBRSxDQUFDLENBQUM7UUFDMUMsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDLENBQUMsQ0FBQztBQUNMLENBQUMsQ0FBQyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0ICogYXMgRmxycExpYiBmcm9tICcuLi8uLi9zcmMvbGliJztcbmltcG9ydCB7IFRlc3RCaXRHbywgVGVzdEJpdEdvQVBJIH0gZnJvbSAnQGJpdGdvLWJldGEvc2RrLXRlc3QnO1xuaW1wb3J0IHsgRmxycCwgVGZsclAgfSBmcm9tICcuLi8uLi9zcmMvJztcbmltcG9ydCB7IHJhbmRvbUJ5dGVzIH0gZnJvbSAnY3J5cHRvJztcbmltcG9ydCB7IEJpdEdvQVBJIH0gZnJvbSAnQGJpdGdvLWJldGEvc2RrLWFwaSc7XG5pbXBvcnQgeyBTRUVEX0FDQ09VTlQsIEFDQ09VTlRfMSwgQUNDT1VOVF8yIH0gZnJvbSAnLi4vcmVzb3VyY2VzL2FjY291bnQnO1xuaW1wb3J0IHsgRVhQT1JUX0lOX0MgfSBmcm9tICcuLi9yZXNvdXJjZXMvdHJhbnNhY3Rpb25EYXRhL2V4cG9ydEluQyc7XG5pbXBvcnQgeyBFWFBPUlRfSU5fUCB9IGZyb20gJy4uL3Jlc291cmNlcy90cmFuc2FjdGlvbkRhdGEvZXhwb3J0SW5QJztcbmltcG9ydCB7IElNUE9SVF9JTl9QIH0gZnJvbSAnLi4vcmVzb3VyY2VzL3RyYW5zYWN0aW9uRGF0YS9pbXBvcnRJblAnO1xuaW1wb3J0IHsgSU1QT1JUX0lOX0MgfSBmcm9tICcuLi9yZXNvdXJjZXMvdHJhbnNhY3Rpb25EYXRhL2ltcG9ydEluQyc7XG5pbXBvcnQgeyBIYWxmU2lnbmVkQWNjb3VudFRyYW5zYWN0aW9uLCBUcmFuc2FjdGlvblR5cGUgfSBmcm9tICdAYml0Z28tYmV0YS9zZGstY29yZSc7XG5pbXBvcnQgYXNzZXJ0IGZyb20gJ2Fzc2VydCc7XG5cbmRlc2NyaWJlKCdGbHJwIHRlc3QgY2FzZXMnLCBmdW5jdGlvbiAoKSB7XG4gIGNvbnN0IGNvaW5OYW1lID0gJ2ZscnAnO1xuICBjb25zdCB0Y29pbk5hbWUgPSAndCcgKyBjb2luTmFtZTtcbiAgbGV0IGJpdGdvOiBUZXN0Qml0R29BUEk7XG4gIGxldCBiYXNlY29pbjtcblxuICBjb25zdCBrZXljaGFpbnMgPSBbeyBwdWI6IFNFRURfQUNDT1VOVC5wdWJsaWNLZXkgfSwgeyBwdWI6IEFDQ09VTlRfMS5wdWJsaWNLZXkgfSwgeyBwdWI6IEFDQ09VTlRfMi5wdWJsaWNLZXkgfV07XG5cbiAgYmVmb3JlKGZ1bmN0aW9uICgpIHtcbiAgICBiaXRnbyA9IFRlc3RCaXRHby5kZWNvcmF0ZShCaXRHb0FQSSwge1xuICAgICAgZW52OiAnbW9jaycsXG4gICAgfSk7XG4gICAgYml0Z28uaW5pdGlhbGl6ZVRlc3RWYXJzKCk7XG4gICAgYml0Z28uc2FmZVJlZ2lzdGVyKGNvaW5OYW1lLCBGbHJwLmNyZWF0ZUluc3RhbmNlKTtcbiAgICBiaXRnby5zYWZlUmVnaXN0ZXIodGNvaW5OYW1lLCBUZmxyUC5jcmVhdGVJbnN0YW5jZSk7XG4gICAgYmFzZWNvaW4gPSBiaXRnby5jb2luKHRjb2luTmFtZSk7XG4gIH0pO1xuXG4gIGl0KCdzaG91bGQgaW5zdGFudGlhdGUgdGhlIGNvaW4nLCBmdW5jdGlvbiAoKSB7XG4gICAgbGV0IGxvY2FsQmFzZWNvaW4gPSBiaXRnby5jb2luKHRjb2luTmFtZSk7XG4gICAgbG9jYWxCYXNlY29pbi5zaG91bGQuYmUuYW4uaW5zdGFuY2VvZihUZmxyUCk7XG5cbiAgICBsb2NhbEJhc2Vjb2luID0gYml0Z28uY29pbihjb2luTmFtZSk7XG4gICAgbG9jYWxCYXNlY29pbi5zaG91bGQuYmUuYW4uaW5zdGFuY2VvZihGbHJwKTtcbiAgfSk7XG5cbiAgaXQoJ3Nob3VsZCByZXR1cm4gJyArIHRjb2luTmFtZSwgZnVuY3Rpb24gKCkge1xuICAgIGJhc2Vjb2luLmdldENoYWluKCkuc2hvdWxkLmVxdWFsKHRjb2luTmFtZSk7XG4gIH0pO1xuXG4gIGl0KCdzaG91bGQgcmV0dXJuIGZ1bGwgbmFtZScsIGZ1bmN0aW9uICgpIHtcbiAgICBiYXNlY29pbi5nZXRGdWxsTmFtZSgpLnNob3VsZC5lcXVhbCgnVGVzdG5ldCBGbGFyZSBQLUNoYWluJyk7XG4gIH0pO1xuXG4gIGl0KCdzaG91bGQgcmV0dXJuIGJhc2UgZmFjdG9yJywgZnVuY3Rpb24gKCkge1xuICAgIGJhc2Vjb2luLmdldEJhc2VGYWN0b3IoKS5zaG91bGQuZXF1YWwoMWU5KTtcbiAgfSk7XG5cbiAgaXQoJ3Nob3VsZCByZXR1cm4gY29pbiBmYW1pbHknLCBmdW5jdGlvbiAoKSB7XG4gICAgYmFzZWNvaW4uZ2V0RmFtaWx5KCkuc2hvdWxkLmVxdWFsKCdmbHJwJyk7XG4gIH0pO1xuXG4gIGl0KCdzaG91bGQgcmV0dXJuIGRlZmF1bHQgbXVsdGlzaWcgdHlwZScsIGZ1bmN0aW9uICgpIHtcbiAgICBiYXNlY29pbi5nZXREZWZhdWx0TXVsdGlzaWdUeXBlKCkuc2hvdWxkLmVxdWFsKCdvbmNoYWluJyk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdLZXlwYWlyczonLCAoKSA9PiB7XG4gICAgaXQoJ3Nob3VsZCBnZW5lcmF0ZSBhIGtleXBhaXIgZnJvbSByYW5kb20gc2VlZCcsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IGtleVBhaXIgPSBiYXNlY29pbi5nZW5lcmF0ZUtleVBhaXIoKTtcbiAgICAgIGtleVBhaXIuc2hvdWxkLmhhdmUucHJvcGVydHkoJ3B1YicpO1xuICAgICAga2V5UGFpci5zaG91bGQuaGF2ZS5wcm9wZXJ0eSgncHJ2Jyk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGdlbmVyYXRlIGEga2V5cGFpciBmcm9tIGEgc2VlZCcsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHNlZWQgPSBCdWZmZXIuZnJvbShTRUVEX0FDQ09VTlQuc2VlZCwgJ2hleCcpO1xuICAgICAgY29uc3Qga2V5UGFpciA9IGJhc2Vjb2luLmdlbmVyYXRlS2V5UGFpcihzZWVkKTtcbiAgICAgIGtleVBhaXIucHViLnNob3VsZC5lcXVhbChTRUVEX0FDQ09VTlQucHVibGljS2V5KTtcbiAgICAgIGtleVBhaXIucHJ2LnNob3VsZC5lcXVhbChTRUVEX0FDQ09VTlQucHJpdmF0ZUtleSk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHZhbGlkYXRlIGEgcHVibGljIGtleScsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGJhc2Vjb2luLmlzVmFsaWRQdWIoU0VFRF9BQ0NPVU5ULnB1YmxpY0tleSkuc2hvdWxkLmVxdWFsKHRydWUpO1xuICAgICAgYmFzZWNvaW4uaXNWYWxpZFB1YihBQ0NPVU5UXzEucHVibGljS2V5KS5zaG91bGQuZXF1YWwodHJ1ZSk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGZhaWwgdG8gdmFsaWRhdGUgYW4gaW52YWxpZCBwdWJsaWMga2V5JywgZnVuY3Rpb24gKCkge1xuICAgICAgYmFzZWNvaW4uaXNWYWxpZFB1YignaW52YWxpZCcpLnNob3VsZC5lcXVhbChmYWxzZSk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHZhbGlkYXRlIGEgcHJpdmF0ZSBrZXknLCBmdW5jdGlvbiAoKSB7XG4gICAgICBiYXNlY29pbi5pc1ZhbGlkUHJ2KFNFRURfQUNDT1VOVC5wcml2YXRlS2V5KS5zaG91bGQuZXF1YWwodHJ1ZSk7XG4gICAgICBiYXNlY29pbi5pc1ZhbGlkUHJ2KEFDQ09VTlRfMS5wcml2YXRlS2V5KS5zaG91bGQuZXF1YWwodHJ1ZSk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGZhaWwgdG8gdmFsaWRhdGUgYW4gaW52YWxpZCBwcml2YXRlIGtleScsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGJhc2Vjb2luLmlzVmFsaWRQcnYoJ2ludmFsaWQnKS5zaG91bGQuZXF1YWwoZmFsc2UpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnU2lnbiBUcmFuc2FjdGlvbicsICgpID0+IHtcbiAgICBpdCgnc2hvdWxkIHNpZ24gYW4gZXhwb3J0IGZyb20gQy1jaGFpbiB0cmFuc2FjdGlvbicsIGFzeW5jICgpID0+IHtcbiAgICAgIGNvbnN0IHBhcmFtcyA9IHtcbiAgICAgICAgdHhQcmVidWlsZDoge1xuICAgICAgICAgIHR4SGV4OiBFWFBPUlRfSU5fQy51bnNpZ25lZEhleCxcbiAgICAgICAgfSxcbiAgICAgICAgcHJ2OiBFWFBPUlRfSU5fQy5wcml2YXRlS2V5LFxuICAgICAgfTtcblxuICAgICAgY29uc3Qgc2lnbmVkVHggPSBhd2FpdCBiYXNlY29pbi5zaWduVHJhbnNhY3Rpb24ocGFyYW1zKTtcbiAgICAgIHNpZ25lZFR4LnNob3VsZC5oYXZlLnByb3BlcnR5KCdoYWxmU2lnbmVkJyk7XG4gICAgICBjb25zdCBoYWxmU2lnbmVkID0gKHNpZ25lZFR4IGFzIEhhbGZTaWduZWRBY2NvdW50VHJhbnNhY3Rpb24pLmhhbGZTaWduZWQ7XG4gICAgICBhc3NlcnQoaGFsZlNpZ25lZCwgJ2hhbGZTaWduZWQgc2hvdWxkIGJlIGRlZmluZWQnKTtcbiAgICAgIGFzc2VydChoYWxmU2lnbmVkLnR4SGV4LCAndHhIZXggc2hvdWxkIGJlIGRlZmluZWQnKTtcbiAgICAgIGhhbGZTaWduZWQudHhIZXguc2hvdWxkLmVxdWFsKEVYUE9SVF9JTl9DLnNpZ25lZEhleCk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHNpZ24gYW4gZXhwb3J0IGZyb20gUC1jaGFpbiB0cmFuc2FjdGlvbicsIGFzeW5jICgpID0+IHtcbiAgICAgIC8vIHByaXZhdGVLZXlzWzJdIGNvcnJlc3BvbmRzIHRvIHRoZSBmaXJzdCBzaWduYXR1cmUgc2xvdCAoc29ydGVkIGFkZHJlc3Mgb3JkZXI6IDMzMjliZTdkLi4uIGlzIHNsb3QgMSlcbiAgICAgIGNvbnN0IHBhcmFtcyA9IHtcbiAgICAgICAgdHhQcmVidWlsZDoge1xuICAgICAgICAgIHR4SGV4OiBFWFBPUlRfSU5fUC51bnNpZ25lZEhleCxcbiAgICAgICAgfSxcbiAgICAgICAgcHJ2OiBFWFBPUlRfSU5fUC5wcml2YXRlS2V5c1syXSxcbiAgICAgIH07XG5cbiAgICAgIGNvbnN0IHNpZ25lZFR4ID0gYXdhaXQgYmFzZWNvaW4uc2lnblRyYW5zYWN0aW9uKHBhcmFtcyk7XG4gICAgICBzaWduZWRUeC5zaG91bGQuaGF2ZS5wcm9wZXJ0eSgnaGFsZlNpZ25lZCcpO1xuICAgICAgY29uc3QgaGFsZlNpZ25lZCA9IChzaWduZWRUeCBhcyBIYWxmU2lnbmVkQWNjb3VudFRyYW5zYWN0aW9uKS5oYWxmU2lnbmVkO1xuICAgICAgYXNzZXJ0KGhhbGZTaWduZWQsICdoYWxmU2lnbmVkIHNob3VsZCBiZSBkZWZpbmVkJyk7XG4gICAgICBhc3NlcnQoaGFsZlNpZ25lZC50eEhleCwgJ3R4SGV4IHNob3VsZCBiZSBkZWZpbmVkJyk7XG4gICAgICBoYWxmU2lnbmVkLnR4SGV4LnNob3VsZC5lcXVhbChFWFBPUlRfSU5fUC5oYWxmU2lnbnR4SGV4KTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgc2lnbiBhbiBpbXBvcnQgdG8gUC1jaGFpbiB0cmFuc2FjdGlvbicsIGFzeW5jICgpID0+IHtcbiAgICAgIC8vIHByaXZhdGVLZXlzWzJdIGNvcnJlc3BvbmRzIHRvIHRoZSBmaXJzdCBzaWduYXR1cmUgc2xvdCAoc29ydGVkIGFkZHJlc3Mgb3JkZXI6IDMzMjliZTdkLi4uIGlzIHNsb3QgMSlcbiAgICAgIGNvbnN0IHBhcmFtcyA9IHtcbiAgICAgICAgdHhQcmVidWlsZDoge1xuICAgICAgICAgIHR4SGV4OiBJTVBPUlRfSU5fUC51bnNpZ25lZEhleCxcbiAgICAgICAgfSxcbiAgICAgICAgcHJ2OiBJTVBPUlRfSU5fUC5wcml2YXRlS2V5c1syXSxcbiAgICAgIH07XG5cbiAgICAgIGNvbnN0IHNpZ25lZFR4ID0gYXdhaXQgYmFzZWNvaW4uc2lnblRyYW5zYWN0aW9uKHBhcmFtcyk7XG4gICAgICBzaWduZWRUeC5zaG91bGQuaGF2ZS5wcm9wZXJ0eSgnaGFsZlNpZ25lZCcpO1xuICAgICAgY29uc3QgaGFsZlNpZ25lZCA9IChzaWduZWRUeCBhcyBIYWxmU2lnbmVkQWNjb3VudFRyYW5zYWN0aW9uKS5oYWxmU2lnbmVkO1xuICAgICAgYXNzZXJ0KGhhbGZTaWduZWQsICdoYWxmU2lnbmVkIHNob3VsZCBiZSBkZWZpbmVkJyk7XG4gICAgICBhc3NlcnQoaGFsZlNpZ25lZC50eEhleCwgJ3R4SGV4IHNob3VsZCBiZSBkZWZpbmVkJyk7XG4gICAgICBoYWxmU2lnbmVkLnR4SGV4LnNob3VsZC5lcXVhbChJTVBPUlRfSU5fUC5oYWxmU2lnbnR4SGV4KTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgc2lnbiBhbiBpbXBvcnQgdG8gQy1jaGFpbiB0cmFuc2FjdGlvbicsIGFzeW5jICgpID0+IHtcbiAgICAgIC8vIHByaXZhdGVLZXlzWzJdIGNvcnJlc3BvbmRzIHRvIHRoZSBmaXJzdCBzaWduYXR1cmUgc2xvdCAoc29ydGVkIGFkZHJlc3Mgb3JkZXIgaW4gVVRYT3MpXG4gICAgICBjb25zdCBwYXJhbXMgPSB7XG4gICAgICAgIHR4UHJlYnVpbGQ6IHtcbiAgICAgICAgICB0eEhleDogSU1QT1JUX0lOX0MudW5zaWduZWRIZXgsXG4gICAgICAgIH0sXG4gICAgICAgIHBydjogSU1QT1JUX0lOX0MucHJpdmF0ZUtleXNbMl0sXG4gICAgICB9O1xuXG4gICAgICBjb25zdCBzaWduZWRUeCA9IGF3YWl0IGJhc2Vjb2luLnNpZ25UcmFuc2FjdGlvbihwYXJhbXMpO1xuICAgICAgc2lnbmVkVHguc2hvdWxkLmhhdmUucHJvcGVydHkoJ2hhbGZTaWduZWQnKTtcbiAgICAgIGNvbnN0IGhhbGZTaWduZWQgPSAoc2lnbmVkVHggYXMgSGFsZlNpZ25lZEFjY291bnRUcmFuc2FjdGlvbikuaGFsZlNpZ25lZDtcbiAgICAgIGFzc2VydChoYWxmU2lnbmVkLCAnaGFsZlNpZ25lZCBzaG91bGQgYmUgZGVmaW5lZCcpO1xuICAgICAgYXNzZXJ0KGhhbGZTaWduZWQudHhIZXgsICd0eEhleCBzaG91bGQgYmUgZGVmaW5lZCcpO1xuICAgICAgaGFsZlNpZ25lZC50eEhleC5zaG91bGQuZXF1YWwoSU1QT1JUX0lOX0MuaGFsZlNpZ250eEhleCk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHJlamVjdCBzaWduaW5nIHdpdGggYW4gaW52YWxpZCBrZXknLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCBwYXJhbXMgPSB7XG4gICAgICAgIHR4UHJlYnVpbGQ6IHtcbiAgICAgICAgICB0eEhleDogRVhQT1JUX0lOX0MudW5zaWduZWRIZXgsXG4gICAgICAgIH0sXG4gICAgICAgIHBydjogJ2ludmFsaWQta2V5JyxcbiAgICAgIH07XG5cbiAgICAgIGF3YWl0IGJhc2Vjb2luLnNpZ25UcmFuc2FjdGlvbihwYXJhbXMpLnNob3VsZC5iZS5yZWplY3RlZCgpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnU2lnbiBNZXNzYWdlJywgKCkgPT4ge1xuICAgIGl0KCdzaG91bGQgc2lnbiBhIG1lc3NhZ2UnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCBrZXlQYWlyID0gbmV3IEZscnBMaWIuS2V5UGFpcih7IHBydjogU0VFRF9BQ0NPVU5ULnByaXZhdGVLZXkgfSk7XG4gICAgICBjb25zdCBrZXlzID0ga2V5UGFpci5nZXRLZXlzKCk7XG4gICAgICBjb25zdCBtZXNzYWdlVG9TaWduID0gQnVmZmVyLmZyb20oU0VFRF9BQ0NPVU5ULm1lc3NhZ2UsICd1dGY4Jyk7XG4gICAgICBjb25zdCBzaWduYXR1cmUgPSBhd2FpdCBiYXNlY29pbi5zaWduTWVzc2FnZShrZXlzLCBtZXNzYWdlVG9TaWduLnRvU3RyaW5nKCdoZXgnKSk7XG5cbiAgICAgIHNpZ25hdHVyZS5zaG91bGQuYmUuaW5zdGFuY2VPZihCdWZmZXIpO1xuICAgICAgc2lnbmF0dXJlLmxlbmd0aC5zaG91bGQuZXF1YWwoNjUpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBzaWduIGEgcmFuZG9tIG1lc3NhZ2UnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCBrZXlQYWlyID0gbmV3IEZscnBMaWIuS2V5UGFpcigpO1xuICAgICAgY29uc3QgcHViS2V5ID0ga2V5UGFpci5nZXRLZXlzKCkucHViO1xuICAgICAgY29uc3Qga2V5cyA9IGtleVBhaXIuZ2V0S2V5cygpO1xuICAgICAgY29uc3QgbWVzc2FnZVRvU2lnbiA9IEJ1ZmZlci5mcm9tKHJhbmRvbUJ5dGVzKDMyKSk7XG4gICAgICBjb25zdCBzaWduYXR1cmUgPSBhd2FpdCBiYXNlY29pbi5zaWduTWVzc2FnZShrZXlzLCBtZXNzYWdlVG9TaWduLnRvU3RyaW5nKCdoZXgnKSk7XG5cbiAgICAgIGNvbnN0IHZlcmlmeSA9IEZscnBMaWIuVXRpbHMudmVyaWZ5U2lnbmF0dXJlKFxuICAgICAgICBGbHJwTGliLlV0aWxzLnNoYTI1NihtZXNzYWdlVG9TaWduKSxcbiAgICAgICAgc2lnbmF0dXJlLnNsaWNlKDAsIDY0KSwgLy8gUmVtb3ZlIHJlY292ZXJ5IGJ5dGUgZm9yIHZlcmlmaWNhdGlvblxuICAgICAgICBCdWZmZXIuZnJvbShwdWJLZXksICdoZXgnKVxuICAgICAgKTtcbiAgICAgIHZlcmlmeS5zaG91bGQuYmUudHJ1ZSgpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBmYWlsIHRvIHNpZ24gd2l0aCBtaXNzaW5nIHByaXZhdGUga2V5JywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3Qga2V5UGFpciA9IG5ldyBGbHJwTGliLktleVBhaXIoeyBwdWI6IFNFRURfQUNDT1VOVC5wdWJsaWNLZXkgfSk7XG4gICAgICBjb25zdCBrZXlzID0ga2V5UGFpci5nZXRLZXlzKCk7XG4gICAgICBjb25zdCBtZXNzYWdlVG9TaWduID0gQnVmZmVyLmZyb20oU0VFRF9BQ0NPVU5ULm1lc3NhZ2UsICd1dGY4Jyk7XG5cbiAgICAgIGF3YWl0IGJhc2Vjb2luXG4gICAgICAgIC5zaWduTWVzc2FnZShrZXlzLCBtZXNzYWdlVG9TaWduLnRvU3RyaW5nKCdoZXgnKSlcbiAgICAgICAgLnNob3VsZC5iZS5yZWplY3RlZFdpdGgoJ0ludmFsaWQga2V5IHBhaXIgb3B0aW9ucycpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnRXhwbGFpbiBUcmFuc2FjdGlvbicsICgpID0+IHtcbiAgICBpdCgnc2hvdWxkIGV4cGxhaW4gYSBoYWxmIHNpZ25lZCBleHBvcnQgZnJvbSBQLWNoYWluIHRyYW5zYWN0aW9uJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhFeHBsYWluID0gYXdhaXQgYmFzZWNvaW4uZXhwbGFpblRyYW5zYWN0aW9uKHtcbiAgICAgICAgaGFsZlNpZ25lZDogeyB0eEhleDogRVhQT1JUX0lOX1AuaGFsZlNpZ250eEhleCB9LFxuICAgICAgfSk7XG5cbiAgICAgIHR4RXhwbGFpbi50eXBlLnNob3VsZC5lcXVhbChUcmFuc2FjdGlvblR5cGUuRXhwb3J0KTtcbiAgICAgIHR4RXhwbGFpbi5mZWUuc2hvdWxkLmhhdmUucHJvcGVydHkoJ2ZlZScpO1xuICAgICAgdHhFeHBsYWluLmlucHV0cy5zaG91bGQuYmUuYW4uQXJyYXkoKTtcbiAgICAgIHR4RXhwbGFpbi5jaGFuZ2VBbW91bnQuc2hvdWxkLmVxdWFsKCcxNDMzNDUwMCcpOyAvLyAweERBQkEyNCBmcm9tIHRyYW5zYWN0aW9uXG4gICAgICB0eEV4cGxhaW4uY2hhbmdlT3V0cHV0cy5zaG91bGQuYmUuYW4uQXJyYXkoKTtcbiAgICAgIHR4RXhwbGFpbi5jaGFuZ2VPdXRwdXRzWzBdLmFkZHJlc3Muc2hvdWxkLmVxdWFsKFxuICAgICAgICAnUC1jb3N0d28xMDZnYzVoNXFzd2h5ZThlMHBtdGhxNHd6ZjBla3Y1cXBwc3J2cHV+UC1jb3N0d28xY3VleWdkN2ZkMzdnNTZzNDlrM3JzaHFha2hwNms4dTNhZHp0Nm1+UC1jb3N0d28xeHY1bXVsZ3BlNWx0NHRueDJudG55bHdlNzlhenU5dnBqYTZsdXQnXG4gICAgICApO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBleHBsYWluIGEgc2lnbmVkIGV4cG9ydCBmcm9tIFAtY2hhaW4gdHJhbnNhY3Rpb24nLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eEV4cGxhaW4gPSBhd2FpdCBiYXNlY29pbi5leHBsYWluVHJhbnNhY3Rpb24oeyB0eEhleDogRVhQT1JUX0lOX1AuZnVsbFNpZ250eEhleCB9KTtcblxuICAgICAgdHhFeHBsYWluLnR5cGUuc2hvdWxkLmVxdWFsKFRyYW5zYWN0aW9uVHlwZS5FeHBvcnQpO1xuICAgICAgdHhFeHBsYWluLmlkLnNob3VsZC5lcXVhbChFWFBPUlRfSU5fUC50eGhhc2gpO1xuICAgICAgdHhFeHBsYWluLmZlZS5zaG91bGQuaGF2ZS5wcm9wZXJ0eSgnZmVlJyk7XG4gICAgICB0eEV4cGxhaW4uaW5wdXRzLnNob3VsZC5iZS5hbi5BcnJheSgpO1xuICAgICAgdHhFeHBsYWluLmNoYW5nZUFtb3VudC5zaG91bGQuZXF1YWwoJzE0MzM0NTAwJyk7IC8vIDB4REFCQTI0IGZyb20gdHJhbnNhY3Rpb25cbiAgICAgIHR4RXhwbGFpbi5jaGFuZ2VPdXRwdXRzLnNob3VsZC5iZS5hbi5BcnJheSgpO1xuICAgICAgdHhFeHBsYWluLmNoYW5nZU91dHB1dHNbMF0uYWRkcmVzcy5zaG91bGQuZXF1YWwoXG4gICAgICAgICdQLWNvc3R3bzEwNmdjNWg1cXN3aHllOGUwcG10aHE0d3pmMGVrdjVxcHBzcnZwdX5QLWNvc3R3bzFjdWV5Z2Q3ZmQzN2c1NnM0OWszcnNocWFraHA2azh1M2FkenQ2bX5QLWNvc3R3bzF4djVtdWxncGU1bHQ0dG54Mm50bnlsd2U3OWF6dTl2cGphNmx1dCdcbiAgICAgICk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGV4cGxhaW4gYSBoYWxmIHNpZ25lZCBpbXBvcnQgdG8gUC1jaGFpbiB0cmFuc2FjdGlvbicsIGFzeW5jICgpID0+IHtcbiAgICAgIGNvbnN0IHR4RXhwbGFpbiA9IGF3YWl0IGJhc2Vjb2luLmV4cGxhaW5UcmFuc2FjdGlvbih7XG4gICAgICAgIGhhbGZTaWduZWQ6IHsgdHhIZXg6IElNUE9SVF9JTl9QLmhhbGZTaWdudHhIZXggfSxcbiAgICAgIH0pO1xuXG4gICAgICB0eEV4cGxhaW4udHlwZS5zaG91bGQuZXF1YWwoVHJhbnNhY3Rpb25UeXBlLkltcG9ydCk7XG4gICAgICB0eEV4cGxhaW4uZmVlLnNob3VsZC5oYXZlLnByb3BlcnR5KCdmZWUnKTtcbiAgICAgIHR4RXhwbGFpbi5pbnB1dHMuc2hvdWxkLmJlLmFuLkFycmF5KCk7XG4gICAgICB0eEV4cGxhaW4ub3V0cHV0QW1vdW50LnNob3VsZC5lcXVhbCgnNDg3MzkwMDAnKTtcbiAgICAgIHR4RXhwbGFpbi5vdXRwdXRzLnNob3VsZC5iZS5hbi5BcnJheSgpO1xuICAgICAgdHhFeHBsYWluLm91dHB1dHMubGVuZ3RoLnNob3VsZC5lcXVhbCgxKTtcbiAgICAgIHR4RXhwbGFpbi5jaGFuZ2VPdXRwdXRzLnNob3VsZC5iZS5lbXB0eSgpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBleHBsYWluIGEgc2lnbmVkIGltcG9ydCB0byBQLWNoYWluIHRyYW5zYWN0aW9uJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhFeHBsYWluID0gYXdhaXQgYmFzZWNvaW4uZXhwbGFpblRyYW5zYWN0aW9uKHsgdHhIZXg6IElNUE9SVF9JTl9QLnNpZ25lZEhleCB9KTtcblxuICAgICAgdHhFeHBsYWluLnR5cGUuc2hvdWxkLmVxdWFsKFRyYW5zYWN0aW9uVHlwZS5JbXBvcnQpO1xuICAgICAgdHhFeHBsYWluLmlkLnNob3VsZC5lcXVhbChJTVBPUlRfSU5fUC50eGhhc2gpO1xuICAgICAgdHhFeHBsYWluLmZlZS5zaG91bGQuaGF2ZS5wcm9wZXJ0eSgnZmVlJyk7XG4gICAgICB0eEV4cGxhaW4uaW5wdXRzLnNob3VsZC5iZS5hbi5BcnJheSgpO1xuICAgICAgdHhFeHBsYWluLm91dHB1dEFtb3VudC5zaG91bGQuZXF1YWwoJzQ4NzM5MDAwJyk7XG4gICAgICB0eEV4cGxhaW4ub3V0cHV0cy5zaG91bGQuYmUuYW4uQXJyYXkoKTtcbiAgICAgIHR4RXhwbGFpbi5vdXRwdXRzLmxlbmd0aC5zaG91bGQuZXF1YWwoMSk7XG4gICAgICB0eEV4cGxhaW4uY2hhbmdlT3V0cHV0cy5zaG91bGQuYmUuZW1wdHkoKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZmFpbCB3aGVuIHRyYW5zYWN0aW9uIGhleCBpcyBub3QgcHJvdmlkZWQnLCBhc3luYyAoKSA9PiB7XG4gICAgICBhd2FpdCBiYXNlY29pbi5leHBsYWluVHJhbnNhY3Rpb24oe30pLnNob3VsZC5iZS5yZWplY3RlZFdpdGgoJ21pc3NpbmcgdHJhbnNhY3Rpb24gaGV4Jyk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGZhaWwgZm9yIGludmFsaWQgdHJhbnNhY3Rpb24gaGV4JywgYXN5bmMgKCkgPT4ge1xuICAgICAgYXdhaXQgYmFzZWNvaW4uZXhwbGFpblRyYW5zYWN0aW9uKHsgdHhIZXg6ICdpbnZhbGlkJyB9KS5zaG91bGQuYmUucmVqZWN0ZWQoKTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ1ZlcmlmeSBUcmFuc2FjdGlvbicsICgpID0+IHtcbiAgICBpdCgnc2hvdWxkIHZlcmlmeSBhbiBleHBvcnQgZnJvbSBDLWNoYWluIHRyYW5zYWN0aW9uJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhQcmVidWlsZCA9IHtcbiAgICAgICAgdHhIZXg6IEVYUE9SVF9JTl9DLnNpZ25lZEhleCxcbiAgICAgICAgdHhJbmZvOiB7fSxcbiAgICAgIH07XG4gICAgICBjb25zdCB0eFBhcmFtcyA9IHtcbiAgICAgICAgcmVjaXBpZW50czogW1xuICAgICAgICAgIHtcbiAgICAgICAgICAgIGFkZHJlc3M6ICcnLFxuICAgICAgICAgICAgYW1vdW50OiBFWFBPUlRfSU5fQy5hbW91bnQsXG4gICAgICAgICAgfSxcbiAgICAgICAgXSxcbiAgICAgICAgdHlwZTogJ0V4cG9ydCcsXG4gICAgICAgIGxvY2t0aW1lOiAwLFxuICAgICAgfTtcblxuICAgICAgY29uc3QgaXNWZXJpZmllZCA9IGF3YWl0IGJhc2Vjb2luLnZlcmlmeVRyYW5zYWN0aW9uKHsgdHhQYXJhbXMsIHR4UHJlYnVpbGQgfSk7XG4gICAgICBpc1ZlcmlmaWVkLnNob3VsZC5lcXVhbCh0cnVlKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgdmVyaWZ5IGFuIGV4cG9ydCBmcm9tIFAtY2hhaW4gdHJhbnNhY3Rpb24nLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eFByZWJ1aWxkID0ge1xuICAgICAgICB0eEhleDogRVhQT1JUX0lOX1AuZnVsbFNpZ250eEhleCxcbiAgICAgICAgdHhJbmZvOiB7fSxcbiAgICAgIH07XG4gICAgICBjb25zdCB0eFBhcmFtcyA9IHtcbiAgICAgICAgcmVjaXBpZW50czogW1xuICAgICAgICAgIHtcbiAgICAgICAgICAgIGFkZHJlc3M6ICcnLFxuICAgICAgICAgICAgYW1vdW50OiBFWFBPUlRfSU5fUC5hbW91bnQsXG4gICAgICAgICAgfSxcbiAgICAgICAgXSxcbiAgICAgICAgdHlwZTogJ0V4cG9ydCcsXG4gICAgICAgIGxvY2t0aW1lOiAwLFxuICAgICAgfTtcblxuICAgICAgY29uc3QgaXNWZXJpZmllZCA9IGF3YWl0IGJhc2Vjb2luLnZlcmlmeVRyYW5zYWN0aW9uKHsgdHhQYXJhbXMsIHR4UHJlYnVpbGQgfSk7XG4gICAgICBpc1ZlcmlmaWVkLnNob3VsZC5lcXVhbCh0cnVlKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgdmVyaWZ5IGFuIGltcG9ydCB0byBDLWNoYWluIHRyYW5zYWN0aW9uJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhQcmVidWlsZCA9IHtcbiAgICAgICAgdHhIZXg6IElNUE9SVF9JTl9DLmZ1bGxTaWdudHhIZXgsXG4gICAgICAgIHR4SW5mbzoge30sXG4gICAgICB9O1xuICAgICAgY29uc3QgdHhQYXJhbXMgPSB7XG4gICAgICAgIHJlY2lwaWVudHM6IFtcbiAgICAgICAgICB7XG4gICAgICAgICAgICBhZGRyZXNzOiBJTVBPUlRfSU5fQy50byxcbiAgICAgICAgICAgIGFtb3VudDogJzEnLFxuICAgICAgICAgIH0sXG4gICAgICAgIF0sXG4gICAgICAgIHR5cGU6ICdJbXBvcnRUb0MnLFxuICAgICAgICBsb2NrdGltZTogMCxcbiAgICAgIH07XG5cbiAgICAgIGNvbnN0IGlzVmVyaWZpZWQgPSBhd2FpdCBiYXNlY29pbi52ZXJpZnlUcmFuc2FjdGlvbih7IHR4UGFyYW1zLCB0eFByZWJ1aWxkIH0pO1xuICAgICAgaXNWZXJpZmllZC5zaG91bGQuZXF1YWwodHJ1ZSk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHZlcmlmeSBhbiBpbXBvcnQgdG8gUC1jaGFpbiB0cmFuc2FjdGlvbicsIGFzeW5jICgpID0+IHtcbiAgICAgIGNvbnN0IHR4UHJlYnVpbGQgPSB7XG4gICAgICAgIHR4SGV4OiBJTVBPUlRfSU5fUC5zaWduZWRIZXgsXG4gICAgICAgIHR4SW5mbzoge30sXG4gICAgICB9O1xuICAgICAgY29uc3QgdHhQYXJhbXMgPSB7XG4gICAgICAgIHJlY2lwaWVudHM6IFtdLFxuICAgICAgICB0eXBlOiAnSW1wb3J0JyxcbiAgICAgICAgbG9ja3RpbWU6IDAsXG4gICAgICB9O1xuXG4gICAgICBjb25zdCBpc1ZlcmlmaWVkID0gYXdhaXQgYmFzZWNvaW4udmVyaWZ5VHJhbnNhY3Rpb24oeyB0eFBhcmFtcywgdHhQcmVidWlsZCB9KTtcbiAgICAgIGlzVmVyaWZpZWQuc2hvdWxkLmVxdWFsKHRydWUpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBmYWlsIHRvIHZlcmlmeSBleHBvcnQgdHJhbnNhY3Rpb24gd2l0aCB3cm9uZyBhbW91bnQnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eFByZWJ1aWxkID0ge1xuICAgICAgICB0eEhleDogRVhQT1JUX0lOX0Muc2lnbmVkSGV4LFxuICAgICAgICB0eEluZm86IHt9LFxuICAgICAgfTtcbiAgICAgIGNvbnN0IHR4UGFyYW1zID0ge1xuICAgICAgICByZWNpcGllbnRzOiBbXG4gICAgICAgICAge1xuICAgICAgICAgICAgYWRkcmVzczogJycsXG4gICAgICAgICAgICBhbW91bnQ6ICc5OTk5OTk5OTk5OTknLFxuICAgICAgICAgIH0sXG4gICAgICAgIF0sXG4gICAgICAgIHR5cGU6ICdFeHBvcnQnLFxuICAgICAgICBsb2NrdGltZTogMCxcbiAgICAgIH07XG5cbiAgICAgIGF3YWl0IGJhc2Vjb2luXG4gICAgICAgIC52ZXJpZnlUcmFuc2FjdGlvbih7IHR4UGFyYW1zLCB0eFByZWJ1aWxkIH0pXG4gICAgICAgIC5zaG91bGQuYmUucmVqZWN0ZWRXaXRoKC9UeCB0b3RhbCBhbW91bnQgLiogZG9lcyBub3QgbWF0Y2ggd2l0aCBleHBlY3RlZCB0b3RhbCBhbW91bnQvKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZmFpbCB0byB2ZXJpZnkgdHJhbnNhY3Rpb24gd2l0aCB3cm9uZyB0eXBlJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhQcmVidWlsZCA9IHtcbiAgICAgICAgdHhIZXg6IEVYUE9SVF9JTl9DLnNpZ25lZEhleCxcbiAgICAgICAgdHhJbmZvOiB7fSxcbiAgICAgIH07XG4gICAgICBjb25zdCB0eFBhcmFtcyA9IHtcbiAgICAgICAgcmVjaXBpZW50czogW1xuICAgICAgICAgIHtcbiAgICAgICAgICAgIGFkZHJlc3M6ICcnLFxuICAgICAgICAgICAgYW1vdW50OiBFWFBPUlRfSU5fQy5hbW91bnQsXG4gICAgICAgICAgfSxcbiAgICAgICAgXSxcbiAgICAgICAgdHlwZTogJ0ltcG9ydCcsXG4gICAgICAgIGxvY2t0aW1lOiAwLFxuICAgICAgfTtcblxuICAgICAgYXdhaXQgYmFzZWNvaW5cbiAgICAgICAgLnZlcmlmeVRyYW5zYWN0aW9uKHsgdHhQYXJhbXMsIHR4UHJlYnVpbGQgfSlcbiAgICAgICAgLnNob3VsZC5iZS5yZWplY3RlZFdpdGgoJ1R4IHR5cGUgZG9lcyBub3QgbWF0Y2ggd2l0aCBleHBlY3RlZCB0eFBhcmFtcyB0eXBlJyk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGZhaWwgdG8gdmVyaWZ5IHRyYW5zYWN0aW9uIHdpdGhvdXQgdHhIZXgnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eFByZWJ1aWxkID0ge1xuICAgICAgICB0eEluZm86IHt9LFxuICAgICAgfTtcbiAgICAgIGNvbnN0IHR4UGFyYW1zID0ge1xuICAgICAgICByZWNpcGllbnRzOiBbXSxcbiAgICAgICAgdHlwZTogJ0V4cG9ydCcsXG4gICAgICAgIGxvY2t0aW1lOiAwLFxuICAgICAgfTtcblxuICAgICAgYXdhaXQgYmFzZWNvaW5cbiAgICAgICAgLnZlcmlmeVRyYW5zYWN0aW9uKHsgdHhQYXJhbXMsIHR4UHJlYnVpbGQgfSlcbiAgICAgICAgLnNob3VsZC5iZS5yZWplY3RlZFdpdGgoJ21pc3NpbmcgcmVxdWlyZWQgdHggcHJlYnVpbGQgcHJvcGVydHkgdHhIZXgnKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZmFpbCB0byB2ZXJpZnkgdHJhbnNhY3Rpb24gd2l0aCBpbnZhbGlkIHR4SGV4JywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhQcmVidWlsZCA9IHtcbiAgICAgICAgdHhIZXg6ICdpbnZhbGlkaGV4JyxcbiAgICAgICAgdHhJbmZvOiB7fSxcbiAgICAgIH07XG4gICAgICBjb25zdCB0eFBhcmFtcyA9IHtcbiAgICAgICAgcmVjaXBpZW50czogW10sXG4gICAgICAgIHR5cGU6ICdFeHBvcnQnLFxuICAgICAgICBsb2NrdGltZTogMCxcbiAgICAgIH07XG5cbiAgICAgIGF3YWl0IGJhc2Vjb2luXG4gICAgICAgIC52ZXJpZnlUcmFuc2FjdGlvbih7IHR4UGFyYW1zLCB0eFByZWJ1aWxkIH0pXG4gICAgICAgIC5zaG91bGQuYmUucmVqZWN0ZWRXaXRoKCdJbnZhbGlkIHRyYW5zYWN0aW9uOiBSYXcgdHJhbnNhY3Rpb24gaXMgbm90IGhleCBzdHJpbmcnKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZmFpbCB0byB2ZXJpZnkgaW1wb3J0IHRvIEMtY2hhaW4gd2l0aG91dCByZWNpcGllbnRzJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhQcmVidWlsZCA9IHtcbiAgICAgICAgdHhIZXg6IElNUE9SVF9JTl9DLmZ1bGxTaWdudHhIZXgsXG4gICAgICAgIHR4SW5mbzoge30sXG4gICAgICB9O1xuICAgICAgY29uc3QgdHhQYXJhbXMgPSB7XG4gICAgICAgIHJlY2lwaWVudHM6IFtdLFxuICAgICAgICB0eXBlOiAnSW1wb3J0VG9DJyxcbiAgICAgICAgbG9ja3RpbWU6IDAsXG4gICAgICB9O1xuXG4gICAgICBhd2FpdCBiYXNlY29pblxuICAgICAgICAudmVyaWZ5VHJhbnNhY3Rpb24oeyB0eFBhcmFtcywgdHhQcmVidWlsZCB9KVxuICAgICAgICAuc2hvdWxkLmJlLnJlamVjdGVkV2l0aCgnRXhwZWN0ZWQgMSByZWNpcGllbnQgaW4gaW1wb3J0IHRyYW5zYWN0aW9uJyk7XG4gICAgfSk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdBZGRyZXNzIFZhbGlkYXRpb24nLCAoKSA9PiB7XG4gICAgaXQoJ3Nob3VsZCB2YWxpZGF0ZSBtYWlubmV0IFAtY2hhaW4gYWRkcmVzcycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGJhc2Vjb2luLmlzVmFsaWRBZGRyZXNzKFNFRURfQUNDT1VOVC5hZGRyZXNzTWFpbm5ldCkuc2hvdWxkLmJlLnRydWUoKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgdmFsaWRhdGUgdGVzdG5ldCBQLWNoYWluIGFkZHJlc3MnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBiYXNlY29pbi5pc1ZhbGlkQWRkcmVzcyhTRUVEX0FDQ09VTlQuYWRkcmVzc1Rlc3RuZXQpLnNob3VsZC5iZS50cnVlKCk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHZhbGlkYXRlIGFycmF5IG9mIFAtY2hhaW4gYWRkcmVzc2VzJywgZnVuY3Rpb24gKCkge1xuICAgICAgYmFzZWNvaW4uaXNWYWxpZEFkZHJlc3MoRVhQT1JUX0lOX0MucEFkZHJlc3Nlcykuc2hvdWxkLmJlLnRydWUoKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgdmFsaWRhdGUgdGlsZGUtc2VwYXJhdGVkIG11bHRpc2lnIGFkZHJlc3MnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBtdWx0aVNpZ0FkZHJlc3MgPSBFWFBPUlRfSU5fQy5wQWRkcmVzc2VzLmpvaW4oJ34nKTtcbiAgICAgIGJhc2Vjb2luLmlzVmFsaWRBZGRyZXNzKG11bHRpU2lnQWRkcmVzcykuc2hvdWxkLmJlLnRydWUoKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgdmFsaWRhdGUgQy1jaGFpbiBoZXggYWRkcmVzcycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGJhc2Vjb2luLmlzVmFsaWRBZGRyZXNzKEVYUE9SVF9JTl9DLmNIZXhBZGRyZXNzKS5zaG91bGQuYmUudHJ1ZSgpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCB2YWxpZGF0ZSBsb3dlcmNhc2UgQy1jaGFpbiBhZGRyZXNzJywgZnVuY3Rpb24gKCkge1xuICAgICAgYmFzZWNvaW4uaXNWYWxpZEFkZHJlc3MoSU1QT1JUX0lOX0MudG8udG9Mb3dlckNhc2UoKSkuc2hvdWxkLmJlLnRydWUoKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZmFpbCB0byB2YWxpZGF0ZSB1bmRlZmluZWQgYWRkcmVzcycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGJhc2Vjb2luLmlzVmFsaWRBZGRyZXNzKHVuZGVmaW5lZCkuc2hvdWxkLmJlLmZhbHNlKCk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGZhaWwgdG8gdmFsaWRhdGUgZW1wdHkgc3RyaW5nJywgZnVuY3Rpb24gKCkge1xuICAgICAgYmFzZWNvaW4uaXNWYWxpZEFkZHJlc3MoJycpLnNob3VsZC5iZS5mYWxzZSgpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBmYWlsIHRvIHZhbGlkYXRlIGludmFsaWQgYWRkcmVzcycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGJhc2Vjb2luLmlzVmFsaWRBZGRyZXNzKCdpbnZhbGlkLWFkZHJlc3MnKS5zaG91bGQuYmUuZmFsc2UoKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZmFpbCB0byB2YWxpZGF0ZSBhcnJheSB3aXRoIGludmFsaWQgYWRkcmVzcycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IGFkZHJlc3NlcyA9IFsuLi5FWFBPUlRfSU5fQy5wQWRkcmVzc2VzLCAnaW52YWxpZCddO1xuICAgICAgYmFzZWNvaW4uaXNWYWxpZEFkZHJlc3MoYWRkcmVzc2VzKS5zaG91bGQuYmUuZmFsc2UoKTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ1dhbGxldCBBZGRyZXNzIFZlcmlmaWNhdGlvbicsICgpID0+IHtcbiAgICBpdCgnc2hvdWxkIHZlcmlmeSB3YWxsZXQgYWRkcmVzcyB3aXRoIG1hdGNoaW5nIGtleWNoYWlucycsIGFzeW5jICgpID0+IHtcbiAgICAgIGNvbnN0IGtleVBhaXJzID0gW3sgcHViOiBTRUVEX0FDQ09VTlQucHVibGljS2V5IH0sIHsgcHViOiBBQ0NPVU5UXzEucHVibGljS2V5IH0sIHsgcHViOiBBQ0NPVU5UXzIucHVibGljS2V5IH1dO1xuXG4gICAgICAvLyBEZXJpdmUgYWRkcmVzc2VzIGZyb20gcHVibGljIGtleXMgdG8gZW5zdXJlIHRoZXkgbWF0Y2hcbiAgICAgIGNvbnN0IGRlcml2ZWRBZGRyZXNzZXMgPSBrZXlQYWlycy5tYXAoKGtwKSA9PiBuZXcgRmxycExpYi5LZXlQYWlyKHsgcHViOiBrcC5wdWIgfSkuZ2V0QWRkcmVzcygndGVzdG5ldCcpKTtcbiAgICAgIGNvbnN0IGFkZHJlc3MgPSBkZXJpdmVkQWRkcmVzc2VzLmpvaW4oJ34nKTtcblxuICAgICAgY29uc3QgaXNWYWxpZCA9IGF3YWl0IGJhc2Vjb2luLmlzV2FsbGV0QWRkcmVzcyh7XG4gICAgICAgIGFkZHJlc3MsXG4gICAgICAgIGtleWNoYWluczoga2V5UGFpcnMsXG4gICAgICB9KTtcblxuICAgICAgaXNWYWxpZC5zaG91bGQuYmUudHJ1ZSgpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCB0aHJvdyBmb3IgYWRkcmVzcyB3aXRoIHdyb25nIG51bWJlciBvZiBrZXljaGFpbnMnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCBhZGRyZXNzID0gU0VFRF9BQ0NPVU5ULmFkZHJlc3NUZXN0bmV0O1xuXG4gICAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhcbiAgICAgICAgYXN5bmMgKCkgPT5cbiAgICAgICAgICBiYXNlY29pbi5pc1dhbGxldEFkZHJlc3Moe1xuICAgICAgICAgICAgYWRkcmVzcyxcbiAgICAgICAgICAgIGtleWNoYWluczogW3sgcHViOiBTRUVEX0FDQ09VTlQucHVibGljS2V5IH1dLFxuICAgICAgICAgIH0pLFxuICAgICAgICAvSW52YWxpZCBrZXljaGFpbnMvXG4gICAgICApO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCB0aHJvdyBmb3IgaW52YWxpZCBhZGRyZXNzJywgYXN5bmMgKCkgPT4ge1xuICAgICAgYXdhaXQgYXNzZXJ0LnJlamVjdHMoXG4gICAgICAgIGFzeW5jICgpID0+XG4gICAgICAgICAgYmFzZWNvaW4uaXNXYWxsZXRBZGRyZXNzKHtcbiAgICAgICAgICAgIGFkZHJlc3M6ICdpbnZhbGlkJyxcbiAgICAgICAgICAgIGtleWNoYWlucyxcbiAgICAgICAgICB9KSxcbiAgICAgICAgL2ludmFsaWQgYWRkcmVzcy9cbiAgICAgICk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHRocm93IHdoZW4gYWRkcmVzcyBsZW5ndGggZG9lcyBub3QgbWF0Y2gga2V5Y2hhaW4gbGVuZ3RoJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgYWRkcmVzcyA9IFNFRURfQUNDT1VOVC5hZGRyZXNzVGVzdG5ldDtcblxuICAgICAgYXdhaXQgYXNzZXJ0LnJlamVjdHMoYXN5bmMgKCkgPT5cbiAgICAgICAgYmFzZWNvaW4uaXNXYWxsZXRBZGRyZXNzKHtcbiAgICAgICAgICBhZGRyZXNzLFxuICAgICAgICAgIGtleWNoYWlucyxcbiAgICAgICAgfSlcbiAgICAgICk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHRocm93IHdoZW4gYWRkcmVzc2VzIGRvIG5vdCBtYXRjaCBrZXljaGFpbnMnLCBhc3luYyAoKSA9PiB7XG4gICAgICAvLyBVc2UgYWRkcmVzc2VzIHRoYXQgZG9uJ3QgbWF0Y2ggdGhlIGtleWNoYWluc1xuICAgICAgY29uc3QgYWRkcmVzcyA9IEVYUE9SVF9JTl9DLnBBZGRyZXNzZXMuam9pbignficpO1xuXG4gICAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhhc3luYyAoKSA9PlxuICAgICAgICBiYXNlY29pbi5pc1dhbGxldEFkZHJlc3Moe1xuICAgICAgICAgIGFkZHJlc3MsXG4gICAgICAgICAga2V5Y2hhaW5zLFxuICAgICAgICB9KVxuICAgICAgKTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ1JlY292ZXJ5IFNpZ25hdHVyZScsICgpID0+IHtcbiAgICBpdCgnc2hvdWxkIHJlY292ZXIgc2lnbmF0dXJlIGZyb20gc2lnbmVkIG1lc3NhZ2UnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCBtZXNzYWdlID0gQnVmZmVyLmZyb20oU0VFRF9BQ0NPVU5ULm1lc3NhZ2UsICd1dGY4Jyk7XG4gICAgICBjb25zdCBwcml2YXRlS2V5ID0gQnVmZmVyLmZyb20oU0VFRF9BQ0NPVU5ULnByaXZhdGVLZXksICdoZXgnKTtcbiAgICAgIGNvbnN0IHNpZ25hdHVyZSA9IEZscnBMaWIuVXRpbHMuY3JlYXRlU2lnbmF0dXJlKGJhc2Vjb2luLl9zdGF0aWNzQ29pbi5uZXR3b3JrLCBtZXNzYWdlLCBwcml2YXRlS2V5KTtcbiAgICAgIGNvbnN0IG1lc3NhZ2VIYXNoID0gRmxycExpYi5VdGlscy5zaGEyNTYobWVzc2FnZSk7XG4gICAgICBjb25zdCByZWNvdmVyZWRQdWJLZXkgPSBiYXNlY29pbi5yZWNvdmVyeVNpZ25hdHVyZShtZXNzYWdlSGFzaCwgc2lnbmF0dXJlKTtcblxuICAgICAgcmVjb3ZlcmVkUHViS2V5LnNob3VsZC5iZS5pbnN0YW5jZU9mKEJ1ZmZlcik7XG4gICAgICByZWNvdmVyZWRQdWJLZXkubGVuZ3RoLnNob3VsZC5lcXVhbCgzMyk7XG4gICAgfSk7XG4gIH0pO1xufSk7XG4iXX0=
|