@bitgo-beta/sdk-coin-trx 1.2.3-alpha.403 → 1.2.3-alpha.404

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.
@@ -0,0 +1,378 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ const node_assert_1 = __importDefault(require("node:assert"));
7
+ const crypto_1 = require("crypto");
8
+ const node_test_1 = require("node:test");
9
+ const sdk_api_1 = require("@bitgo-beta/sdk-api");
10
+ const sdk_test_1 = require("@bitgo-beta/sdk-test");
11
+ const src_1 = require("../../src");
12
+ const lib_1 = require("../../src/lib");
13
+ const resources_1 = require("../resources");
14
+ (0, node_test_1.describe)('TRON Verify Transaction:', function () {
15
+ const bitgo = sdk_test_1.TestBitGo.decorate(sdk_api_1.BitGoAPI, { env: 'test' });
16
+ bitgo.initializeTestVars();
17
+ bitgo.safeRegister('trx', src_1.Trx.createInstance);
18
+ bitgo.safeRegister('ttrx', src_1.Ttrx.createInstance);
19
+ let basecoin;
20
+ (0, node_test_1.before)(function () {
21
+ basecoin = bitgo.coin('ttrx');
22
+ });
23
+ (0, node_test_1.describe)('Parameter Validation', () => {
24
+ (0, node_test_1.it)('should throw error when txParams is missing', async function () {
25
+ const params = {
26
+ txPrebuild: {
27
+ txHex: JSON.stringify({
28
+ ...resources_1.UnsignedBuildTransaction,
29
+ raw_data: {
30
+ ...resources_1.UnsignedBuildTransaction.raw_data,
31
+ expiration: Date.now() + 3600000,
32
+ timestamp: Date.now(),
33
+ },
34
+ }),
35
+ },
36
+ wallet: {},
37
+ };
38
+ await node_assert_1.default.rejects(basecoin.verifyTransaction(params), {
39
+ message: 'missing txParams',
40
+ });
41
+ });
42
+ (0, node_test_1.it)('should throw error when wallet or txPrebuild is missing', async function () {
43
+ const params = {
44
+ txParams: {
45
+ recipients: [{ address: 'TQFxDSoXy2yXRE5HtKwAwrNRXGxYxkeSGk', amount: '1000000' }],
46
+ },
47
+ };
48
+ await node_assert_1.default.rejects(basecoin.verifyTransaction(params), {
49
+ message: 'missing txPrebuild',
50
+ });
51
+ });
52
+ (0, node_test_1.it)('should throw error when txPrebuild.txHex is missing', async function () {
53
+ const params = {
54
+ txParams: {
55
+ recipients: [{ address: 'TQFxDSoXy2yXRE5HtKwAwrNRXGxYxkeSGk', amount: '1000000' }],
56
+ },
57
+ txPrebuild: {},
58
+ wallet: {},
59
+ };
60
+ await node_assert_1.default.rejects(basecoin.verifyTransaction(params), {
61
+ message: 'missing txHex in txPrebuild',
62
+ });
63
+ });
64
+ });
65
+ (0, node_test_1.describe)('Contract Type Validation', () => {
66
+ (0, node_test_1.describe)('TransferContract', () => {
67
+ (0, node_test_1.it)('should validate valid TransferContract', async function () {
68
+ const timestamp = Date.now();
69
+ const transferContract = {
70
+ parameter: {
71
+ value: {
72
+ amount: 1000000,
73
+ owner_address: '4173a5993cd182ae152adad8203163f780c65a8aa5',
74
+ to_address: '41d6cd6a2c0ff35a319e6abb5b9503ba0278679882',
75
+ },
76
+ type_url: 'type.googleapis.com/protocol.TransferContract',
77
+ },
78
+ type: 'TransferContract',
79
+ };
80
+ const rawData = {
81
+ contract: [transferContract],
82
+ ref_block_bytes: 'c8cf',
83
+ ref_block_hash: '89177fd84c5d9196',
84
+ expiration: timestamp + 3600000,
85
+ timestamp: timestamp,
86
+ fee_limit: 150000000,
87
+ };
88
+ // Transform rawData to match the expected parameter structure
89
+ const transformedRawData = {
90
+ contract: rawData.contract,
91
+ refBlockBytes: rawData.ref_block_bytes,
92
+ refBlockHash: rawData.ref_block_hash,
93
+ expiration: rawData.expiration,
94
+ timestamp: rawData.timestamp,
95
+ feeLimit: rawData.fee_limit,
96
+ };
97
+ // Generate raw_data_hex using the utility function
98
+ const rawDataHex = lib_1.Utils.generateRawDataHex(transformedRawData);
99
+ // Calculate txID as SHA256 hash of raw_data_hex
100
+ const txID = (0, crypto_1.createHash)('sha256').update(Buffer.from(rawDataHex, 'hex')).digest('hex');
101
+ const params = {
102
+ txParams: {
103
+ recipients: [
104
+ {
105
+ address: lib_1.Utils.getBase58AddressFromHex('41d6cd6a2c0ff35a319e6abb5b9503ba0278679882'),
106
+ amount: '1000000',
107
+ },
108
+ ],
109
+ },
110
+ txPrebuild: {
111
+ txHex: JSON.stringify({
112
+ txID,
113
+ raw_data: rawData,
114
+ raw_data_hex: rawDataHex,
115
+ }),
116
+ },
117
+ wallet: {},
118
+ };
119
+ const result = await basecoin.verifyTransaction(params);
120
+ node_assert_1.default.strictEqual(result, true);
121
+ });
122
+ (0, node_test_1.it)('should fail with missing owner address', async function () {
123
+ const timestamp = Date.now();
124
+ const txID = '0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef';
125
+ const transferContract = {
126
+ parameter: {
127
+ value: {
128
+ amount: 1000000,
129
+ to_address: '41c25420255c2c5a2dd54ef69f92ef261e6bd4216a',
130
+ },
131
+ type_url: 'type.googleapis.com/protocol.TransferContract',
132
+ },
133
+ type: 'TransferContract',
134
+ };
135
+ const rawData = {
136
+ txID,
137
+ contract: [transferContract],
138
+ ref_block_bytes: 'c8cf',
139
+ ref_block_hash: '89177fd84c5d9196',
140
+ expiration: timestamp + 3600000,
141
+ timestamp: timestamp,
142
+ fee_limit: 150000000,
143
+ };
144
+ const transformedRawData = {
145
+ contract: rawData.contract,
146
+ refBlockBytes: rawData.ref_block_bytes,
147
+ refBlockHash: rawData.ref_block_hash,
148
+ expiration: rawData.expiration,
149
+ timestamp: rawData.timestamp,
150
+ feeLimit: rawData.fee_limit,
151
+ };
152
+ const expectedRawDataHex = lib_1.Utils.generateRawDataHex(transformedRawData);
153
+ const params = {
154
+ txParams: {
155
+ recipients: [{ address: 'TLWh67P93KgtnZNCtGnEHM1H33Nhq2uvvN', amount: '1000000' }],
156
+ },
157
+ txPrebuild: {
158
+ txHex: JSON.stringify({
159
+ txID,
160
+ raw_data: rawData,
161
+ raw_data_hex: expectedRawDataHex,
162
+ }),
163
+ },
164
+ wallet: {},
165
+ };
166
+ await node_assert_1.default.rejects(basecoin.verifyTransaction(params), {
167
+ message: 'Transaction has not have a valid id',
168
+ });
169
+ });
170
+ (0, node_test_1.it)('should fail with missing destination address', async function () {
171
+ const timestamp = Date.now();
172
+ const txID = '0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef';
173
+ const transferContract = {
174
+ parameter: {
175
+ value: {
176
+ amount: 1000000,
177
+ owner_address: '4173a5993cd182ae152adad8203163f780c65a8aa5',
178
+ },
179
+ type_url: 'type.googleapis.com/protocol.TransferContract',
180
+ },
181
+ type: 'TransferContract',
182
+ };
183
+ const rawData = {
184
+ txID,
185
+ contract: [transferContract],
186
+ ref_block_bytes: 'c8cf',
187
+ ref_block_hash: '89177fd84c5d9196',
188
+ expiration: timestamp + 3600000,
189
+ timestamp: timestamp,
190
+ fee_limit: 150000000,
191
+ };
192
+ const transformedRawData = {
193
+ contract: rawData.contract,
194
+ refBlockBytes: rawData.ref_block_bytes,
195
+ refBlockHash: rawData.ref_block_hash,
196
+ expiration: rawData.expiration,
197
+ timestamp: rawData.timestamp,
198
+ feeLimit: rawData.fee_limit,
199
+ };
200
+ const expectedRawDataHex = lib_1.Utils.generateRawDataHex(transformedRawData);
201
+ const params = {
202
+ txParams: {
203
+ recipients: [{ address: 'TLWh67P93KgtnZNCtGnEHM1H33Nhq2uvvN', amount: '1000000' }],
204
+ },
205
+ txPrebuild: {
206
+ txHex: JSON.stringify({
207
+ txID,
208
+ raw_data: rawData,
209
+ raw_data_hex: expectedRawDataHex,
210
+ }),
211
+ },
212
+ wallet: {},
213
+ };
214
+ await node_assert_1.default.rejects(basecoin.verifyTransaction(params), {
215
+ message: 'Transaction has not have a valid id',
216
+ });
217
+ });
218
+ (0, node_test_1.it)('should fail with missing amount', async function () {
219
+ const timestamp = Date.now();
220
+ const transferContract = {
221
+ parameter: {
222
+ value: {
223
+ owner_address: '4173a5993cd182ae152adad8203163f780c65a8aa5',
224
+ to_address: '41c25420255c2c5a2dd54ef69f92ef261e6bd4216a',
225
+ },
226
+ type_url: 'type.googleapis.com/protocol.TransferContract',
227
+ },
228
+ type: 'TransferContract',
229
+ };
230
+ const rawData = {
231
+ contract: [transferContract],
232
+ ref_block_bytes: 'c8cf',
233
+ ref_block_hash: '89177fd84c5d9196',
234
+ expiration: timestamp + 3600000,
235
+ timestamp: timestamp,
236
+ fee_limit: 150000000,
237
+ };
238
+ const transformedRawData = {
239
+ contract: rawData.contract,
240
+ refBlockBytes: rawData.ref_block_bytes,
241
+ refBlockHash: rawData.ref_block_hash,
242
+ expiration: rawData.expiration,
243
+ timestamp: rawData.timestamp,
244
+ feeLimit: rawData.fee_limit,
245
+ };
246
+ const expectedRawDataHex = lib_1.Utils.generateRawDataHex(transformedRawData);
247
+ const params = {
248
+ txParams: {
249
+ recipients: [{ address: 'TLWh67P93KgtnZNCtGnEHM1H33Nhq2uvvN', amount: '1000000' }],
250
+ },
251
+ txPrebuild: {
252
+ txHex: JSON.stringify({
253
+ raw_data: rawData,
254
+ raw_data_hex: expectedRawDataHex,
255
+ }),
256
+ },
257
+ wallet: {},
258
+ };
259
+ await node_assert_1.default.rejects(basecoin.verifyTransaction(params), {
260
+ message: 'Amount does not exist in this transfer contract.',
261
+ });
262
+ });
263
+ (0, node_test_1.it)('should fail due to amount missmatch', async function () {
264
+ const timestamp = Date.now();
265
+ const transferContract = {
266
+ parameter: {
267
+ value: {
268
+ amount: 2000000,
269
+ owner_address: '4173a5993cd182ae152adad8203163f780c65a8aa5',
270
+ to_address: '41d6cd6a2c0ff35a319e6abb5b9503ba0278679882',
271
+ },
272
+ type_url: 'type.googleapis.com/protocol.TransferContract',
273
+ },
274
+ type: 'TransferContract',
275
+ };
276
+ const rawData = {
277
+ contract: [transferContract],
278
+ ref_block_bytes: 'c8cf',
279
+ ref_block_hash: '89177fd84c5d9196',
280
+ expiration: timestamp + 3600000,
281
+ timestamp: timestamp,
282
+ fee_limit: 150000000,
283
+ };
284
+ // Transform rawData to match the expected parameter structure
285
+ const transformedRawData = {
286
+ contract: rawData.contract,
287
+ refBlockBytes: rawData.ref_block_bytes,
288
+ refBlockHash: rawData.ref_block_hash,
289
+ expiration: rawData.expiration,
290
+ timestamp: rawData.timestamp,
291
+ feeLimit: rawData.fee_limit,
292
+ };
293
+ // Generate raw_data_hex using the utility function
294
+ const rawDataHex = lib_1.Utils.generateRawDataHex(transformedRawData);
295
+ // Calculate txID as SHA256 hash of raw_data_hex
296
+ const txID = (0, crypto_1.createHash)('sha256').update(Buffer.from(rawDataHex, 'hex')).digest('hex');
297
+ const params = {
298
+ txParams: {
299
+ recipients: [
300
+ {
301
+ address: '41d6cd6a2c0ff35a319e6abb5b9503ba0278679882',
302
+ amount: '1000000',
303
+ },
304
+ ],
305
+ },
306
+ txPrebuild: {
307
+ txHex: JSON.stringify({
308
+ txID,
309
+ raw_data: rawData,
310
+ raw_data_hex: rawDataHex,
311
+ }),
312
+ },
313
+ wallet: {},
314
+ };
315
+ await node_assert_1.default.rejects(basecoin.verifyTransaction(params), {
316
+ message: 'transaction amount in txPrebuild does not match the value given by client',
317
+ });
318
+ });
319
+ (0, node_test_1.it)('should fail due to destination address missmatch', async function () {
320
+ const timestamp = Date.now();
321
+ const transferContract = {
322
+ parameter: {
323
+ value: {
324
+ amount: 1000000,
325
+ owner_address: '4173a5993cd182ae152adad8203163f780c65a8aa5',
326
+ to_address: '41d6cd6a2c0ff35a319e6abb5b9503ba0278679882',
327
+ },
328
+ type_url: 'type.googleapis.com/protocol.TransferContract',
329
+ },
330
+ type: 'TransferContract',
331
+ };
332
+ const rawData = {
333
+ contract: [transferContract],
334
+ ref_block_bytes: 'c8cf',
335
+ ref_block_hash: '89177fd84c5d9196',
336
+ expiration: timestamp + 3600000,
337
+ timestamp: timestamp,
338
+ fee_limit: 150000000,
339
+ };
340
+ // Transform rawData to match the expected parameter structure
341
+ const transformedRawData = {
342
+ contract: rawData.contract,
343
+ refBlockBytes: rawData.ref_block_bytes,
344
+ refBlockHash: rawData.ref_block_hash,
345
+ expiration: rawData.expiration,
346
+ timestamp: rawData.timestamp,
347
+ feeLimit: rawData.fee_limit,
348
+ };
349
+ // Generate raw_data_hex using the utility function
350
+ const rawDataHex = lib_1.Utils.generateRawDataHex(transformedRawData);
351
+ // Calculate txID as SHA256 hash of raw_data_hex
352
+ const txID = (0, crypto_1.createHash)('sha256').update(Buffer.from(rawDataHex, 'hex')).digest('hex');
353
+ const params = {
354
+ txParams: {
355
+ recipients: [
356
+ {
357
+ address: '41d6cd6a2c0ff35a319e6abb5b9503ba0278679883',
358
+ amount: '1000000',
359
+ },
360
+ ],
361
+ },
362
+ txPrebuild: {
363
+ txHex: JSON.stringify({
364
+ txID,
365
+ raw_data: rawData,
366
+ raw_data_hex: rawDataHex,
367
+ }),
368
+ },
369
+ wallet: {},
370
+ };
371
+ await node_assert_1.default.rejects(basecoin.verifyTransaction(params), {
372
+ message: 'destination address does not match with the recipient address',
373
+ });
374
+ });
375
+ });
376
+ });
377
+ });
378
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidmVyaWZ5VHJhbnNhY3Rpb24uanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi90ZXN0L3VuaXQvdmVyaWZ5VHJhbnNhY3Rpb24udHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7QUFBQSw4REFBaUM7QUFDakMsbUNBQW9DO0FBQ3BDLHlDQUFpRDtBQUNqRCxpREFBK0M7QUFDL0MsbURBQStEO0FBQy9ELG1DQUFzQztBQUN0Qyx1Q0FBc0M7QUFDdEMsNENBQXdEO0FBRXhELElBQUEsb0JBQVEsRUFBQywwQkFBMEIsRUFBRTtJQUNuQyxNQUFNLEtBQUssR0FBaUIsb0JBQVMsQ0FBQyxRQUFRLENBQUMsa0JBQVEsRUFBRSxFQUFFLEdBQUcsRUFBRSxNQUFNLEVBQUUsQ0FBQyxDQUFDO0lBQzFFLEtBQUssQ0FBQyxrQkFBa0IsRUFBRSxDQUFDO0lBQzNCLEtBQUssQ0FBQyxZQUFZLENBQUMsS0FBSyxFQUFFLFNBQUcsQ0FBQyxjQUFjLENBQUMsQ0FBQztJQUM5QyxLQUFLLENBQUMsWUFBWSxDQUFDLE1BQU0sRUFBRSxVQUFJLENBQUMsY0FBYyxDQUFDLENBQUM7SUFFaEQsSUFBSSxRQUFRLENBQUM7SUFFYixJQUFBLGtCQUFNLEVBQUM7UUFDTCxRQUFRLEdBQUcsS0FBSyxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQztJQUNoQyxDQUFDLENBQUMsQ0FBQztJQUVILElBQUEsb0JBQVEsRUFBQyxzQkFBc0IsRUFBRSxHQUFHLEVBQUU7UUFDcEMsSUFBQSxjQUFFLEVBQUMsNkNBQTZDLEVBQUUsS0FBSztZQUNyRCxNQUFNLE1BQU0sR0FBRztnQkFDYixVQUFVLEVBQUU7b0JBQ1YsS0FBSyxFQUFFLElBQUksQ0FBQyxTQUFTLENBQUM7d0JBQ3BCLEdBQUcsb0NBQXdCO3dCQUMzQixRQUFRLEVBQUU7NEJBQ1IsR0FBRyxvQ0FBd0IsQ0FBQyxRQUFROzRCQUNwQyxVQUFVLEVBQUUsSUFBSSxDQUFDLEdBQUcsRUFBRSxHQUFHLE9BQU87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QU0sQ0FBQyxLQUFLLENBQUMsQ0FBQztnQkFFdkYsTUFBTSxNQUFNLEdBQUc7b0JBQ2IsUUFBUSxFQUFFO3dCQUNSLFVBQVUsRUFBRTs0QkFDVjtnQ0FDRSxPQUFPLEVBQUUsNENBQTRDO2dDQUNyRCxNQUFNLEVBQUUsU0FBUzs2QkFDbEI7eUJBQ0Y7cUJBQ0Y7b0JBQ0QsVUFBVSxFQUFFO3dCQUNWLEtBQUssRUFBRSxJQUFJLENBQUMsU0FBUyxDQUFDOzRCQUNwQixJQUFJOzRCQUNKLFFBQVEsRUFBRSxPQUFPOzRCQUNqQixZQUFZLEVBQUUsVUFBVTt5QkFDekIsQ0FBQztxQkFDSDtvQkFDRCxNQUFNLEVBQUUsRUFBRTtpQkFDWCxDQUFDO2dCQUVGLE1BQU0scUJBQU0sQ0FBQyxPQUFPLENBQUMsUUFBUSxDQUFDLGlCQUFpQixDQUFDLE1BQU0sQ0FBQyxFQUFFO29CQUN2RCxPQUFPLEVBQUUsK0RBQStEO2lCQUN6RSxDQUFDLENBQUM7WUFDTCxDQUFDLENBQUMsQ0FBQztRQUNMLENBQUMsQ0FBQyxDQUFDO0lBQ0wsQ0FBQyxDQUFDLENBQUM7QUFDTCxDQUFDLENBQUMsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCBhc3NlcnQgZnJvbSAnbm9kZTphc3NlcnQnO1xuaW1wb3J0IHsgY3JlYXRlSGFzaCB9IGZyb20gJ2NyeXB0byc7XG5pbXBvcnQgeyBkZXNjcmliZSwgaXQsIGJlZm9yZSB9IGZyb20gJ25vZGU6dGVzdCc7XG5pbXBvcnQgeyBCaXRHb0FQSSB9IGZyb20gJ0BiaXRnby1iZXRhL3Nkay1hcGknO1xuaW1wb3J0IHsgVGVzdEJpdEdvQVBJLCBUZXN0Qml0R28gfSBmcm9tICdAYml0Z28tYmV0YS9zZGstdGVzdCc7XG5pbXBvcnQgeyBUcngsIFR0cnggfSBmcm9tICcuLi8uLi9zcmMnO1xuaW1wb3J0IHsgVXRpbHMgfSBmcm9tICcuLi8uLi9zcmMvbGliJztcbmltcG9ydCB7IFVuc2lnbmVkQnVpbGRUcmFuc2FjdGlvbiB9IGZyb20gJy4uL3Jlc291cmNlcyc7XG5cbmRlc2NyaWJlKCdUUk9OIFZlcmlmeSBUcmFuc2FjdGlvbjonLCBmdW5jdGlvbiAoKSB7XG4gIGNvbnN0IGJpdGdvOiBUZXN0Qml0R29BUEkgPSBUZXN0Qml0R28uZGVjb3JhdGUoQml0R29BUEksIHsgZW52OiAndGVzdCcgfSk7XG4gIGJpdGdvLmluaXRpYWxpemVUZXN0VmFycygpO1xuICBiaXRnby5zYWZlUmVnaXN0ZXIoJ3RyeCcsIFRyeC5jcmVhdGVJbnN0YW5jZSk7XG4gIGJpdGdvLnNhZmVSZWdpc3RlcigndHRyeCcsIFR0cnguY3JlYXRlSW5zdGFuY2UpO1xuXG4gIGxldCBiYXNlY29pbjtcblxuICBiZWZvcmUoZnVuY3Rpb24gKCkge1xuICAgIGJhc2Vjb2luID0gYml0Z28uY29pbigndHRyeCcpO1xuICB9KTtcblxuICBkZXNjcmliZSgnUGFyYW1ldGVyIFZhbGlkYXRpb24nLCAoKSA9PiB7XG4gICAgaXQoJ3Nob3VsZCB0aHJvdyBlcnJvciB3aGVuIHR4UGFyYW1zIGlzIG1pc3NpbmcnLCBhc3luYyBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBwYXJhbXMgPSB7XG4gICAgICAgIHR4UHJlYnVpbGQ6IHtcbiAgICAgICAgICB0eEhleDogSlNPTi5zdHJpbmdpZnkoe1xuICAgICAgICAgICAgLi4uVW5zaWduZWRCdWlsZFRyYW5zYWN0aW9uLFxuICAgICAgICAgICAgcmF3X2RhdGE6IHtcbiAgICAgICAgICAgICAgLi4uVW5zaWduZWRCdWlsZFRyYW5zYWN0aW9uLnJhd19kYXRhLFxuICAgICAgICAgICAgICBleHBpcmF0aW9uOiBEYXRlLm5vdygpICsgMzYwMDAwMCxcbiAgICAgICAgICAgICAgdGltZXN0YW1wOiBEYXRlLm5vdygpLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICB9KSxcbiAgICAgICAgfSxcbiAgICAgICAgd2FsbGV0OiB7fSxcbiAgICAgIH07XG5cbiAgICAgIGF3YWl0IGFzc2VydC5yZWplY3RzKGJhc2Vjb2luLnZlcmlmeVRyYW5zYWN0aW9uKHBhcmFtcyksIHtcbiAgICAgICAgbWVzc2FnZTogJ21pc3NpbmcgdHhQYXJhbXMnLFxuICAgICAgfSk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHRocm93IGVycm9yIHdoZW4gd2FsbGV0IG9yIHR4UHJlYnVpbGQgaXMgbWlzc2luZycsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHBhcmFtcyA9IHtcbiAgICAgICAgdHhQYXJhbXM6IHtcbiAgICAgICAgICByZWNpcGllbnRzOiBbeyBhZGRyZXNzOiAnVFFGeERTb1h5MnlYUkU1SHRLd0F3ck5SWEd4WXhrZVNHaycsIGFtb3VudDogJzEwMDAwMDAnIH1dLFxuICAgICAgICB9LFxuICAgICAgfTtcblxuICAgICAgYXdhaXQgYXNzZXJ0LnJlamVjdHMoYmFzZWNvaW4udmVyaWZ5VHJhbnNhY3Rpb24ocGFyYW1zKSwge1xuICAgICAgICBtZXNzYWdlOiAnbWlzc2luZyB0eFByZWJ1aWxkJyxcbiAgICAgIH0pO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCB0aHJvdyBlcnJvciB3aGVuIHR4UHJlYnVpbGQudHhIZXggaXMgbWlzc2luZycsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHBhcmFtcyA9IHtcbiAgICAgICAgdHhQYXJhbXM6IHtcbiAgICAgICAgICByZWNpcGllbnRzOiBbeyBhZGRyZXNzOiAnVFFGeERTb1h5MnlYUkU1SHRLd0F3ck5SWEd4WXhrZVNHaycsIGFtb3VudDogJzEwMDAwMDAnIH1dLFxuICAgICAgICB9LFxuICAgICAgICB0eFByZWJ1aWxkOiB7fSxcbiAgICAgICAgd2FsbGV0OiB7fSxcbiAgICAgIH07XG5cbiAgICAgIGF3YWl0IGFzc2VydC5yZWplY3RzKGJhc2Vjb2luLnZlcmlmeVRyYW5zYWN0aW9uKHBhcmFtcyksIHtcbiAgICAgICAgbWVzc2FnZTogJ21pc3NpbmcgdHhIZXggaW4gdHhQcmVidWlsZCcsXG4gICAgICB9KTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ0NvbnRyYWN0IFR5cGUgVmFsaWRhdGlvbicsICgpID0+IHtcbiAgICBkZXNjcmliZSgnVHJhbnNmZXJDb250cmFjdCcsICgpID0+IHtcbiAgICAgIGl0KCdzaG91bGQgdmFsaWRhdGUgdmFsaWQgVHJhbnNmZXJDb250cmFjdCcsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgICAgY29uc3QgdGltZXN0YW1wID0gRGF0ZS5ub3coKTtcbiAgICAgICAgY29uc3QgdHJhbnNmZXJDb250cmFjdCA9IHtcbiAgICAgICAgICBwYXJhbWV0ZXI6IHtcbiAgICAgICAgICAgIHZhbHVlOiB7XG4gICAgICAgICAgICAgIGFtb3VudDogMTAwMDAwMCxcbiAgICAgICAgICAgICAgb3duZXJfYWRkcmVzczogJzQxNzNhNTk5M2NkMTgyYWUxNTJhZGFkODIwMzE2M2Y3ODBjNjVhOGFhNScsXG4gICAgICAgICAgICAgIHRvX2FkZHJlc3M6ICc0MWQ2Y2Q2YTJjMGZmMzVhMzE5ZTZhYmI1Yjk1MDNiYTAyNzg2Nzk4ODInLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIHR5cGVfdXJsOiAndHlwZS5nb29nbGVhcGlzLmNvbS9wcm90b2NvbC5UcmFuc2ZlckNvbnRyYWN0JyxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHR5cGU6ICdUcmFuc2ZlckNvbnRyYWN0JyxcbiAgICAgICAgfTtcblxuICAgICAgICBjb25zdCByYXdEYXRhID0ge1xuICAgICAgICAgIGNvbnRyYWN0OiBbdHJhbnNmZXJDb250cmFjdF0sXG4gICAgICAgICAgcmVmX2Jsb2NrX2J5dGVzOiAnYzhjZicsXG4gICAgICAgICAgcmVmX2Jsb2NrX2hhc2g6ICc4OTE3N2ZkODRjNWQ5MTk2JyxcbiAgICAgICAgICBleHBpcmF0aW9uOiB0aW1lc3RhbXAgKyAzNjAwMDAwLFxuICAgICAgICAgIHRpbWVzdGFtcDogdGltZXN0YW1wLFxuICAgICAgICAgIGZlZV9saW1pdDogMTUwMDAwMDAwLFxuICAgICAgICB9O1xuXG4gICAgICAgIC8vIFRyYW5zZm9ybSByYXdEYXRhIHRvIG1hdGNoIHRoZSBleHBlY3RlZCBwYXJhbWV0ZXIgc3RydWN0dXJlXG4gICAgICAgIGNvbnN0IHRyYW5zZm9ybWVkUmF3RGF0YSA9IHtcbiAgICAgICAgICBjb250cmFjdDogcmF3RGF0YS5jb250cmFjdCBhcyBhbnksXG4gICAgICAgICAgcmVmQmxvY2tCeXRlczogcmF3RGF0YS5yZWZfYmxvY2tfYnl0ZXMsXG4gICAgICAgICAgcmVmQmxvY2tIYXNoOiByYXdEYXRhLnJlZl9ibG9ja19oYXNoLFxuICAgICAgICAgIGV4cGlyYXRpb246IHJhd0RhdGEuZXhwaXJhdGlvbixcbiAgICAgICAgICB0aW1lc3RhbXA6IHJhd0RhdGEudGltZXN0YW1wLFxuICAgICAgICAgIGZlZUxpbWl0OiByYXdEYXRhLmZlZV9saW1pdCxcbiAgICAgICAgfTtcblxuICAgICAgICAvLyBHZW5lcmF0ZSByYXdfZGF0YV9oZXggdXNpbmcgdGhlIHV0aWxpdHkgZnVuY3Rpb25cbiAgICAgICAgY29uc3QgcmF3RGF0YUhleCA9IFV0aWxzLmdlbmVyYXRlUmF3RGF0YUhleCh0cmFuc2Zvcm1lZFJhd0RhdGEpO1xuXG4gICAgICAgIC8vIENhbGN1bGF0ZSB0eElEIGFzIFNIQTI1NiBoYXNoIG9mIHJhd19kYXRhX2hleFxuICAgICAgICBjb25zdCB0eElEID0gY3JlYXRlSGFzaCgnc2hhMjU2JykudXBkYXRlKEJ1ZmZlci5mcm9tKHJhd0RhdGFIZXgsICdoZXgnKSkuZGlnZXN0KCdoZXgnKTtcblxuICAgICAgICBjb25zdCBwYXJhbXMgPSB7XG4gICAgICAgICAgdHhQYXJhbXM6IHtcbiAgICAgICAgICAgIHJlY2lwaWVudHM6IFtcbiAgICAgICAgICAgICAge1xuICAgICAgICAgICAgICAgIGFkZHJlc3M6IFV0aWxzLmdldEJhc2U1OEFkZHJlc3NGcm9tSGV4KCc0MWQ2Y2Q2YTJjMGZmMzVhMzE5ZTZhYmI1Yjk1MDNiYTAyNzg2Nzk4ODInKSxcbiAgICAgICAgICAgICAgICBhbW91bnQ6ICcxMDAwMDAwJyxcbiAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIF0sXG4gICAgICAgICAgfSxcbiAgICAgICAgICB0eFByZWJ1aWxkOiB7XG4gICAgICAgICAgICB0eEhleDogSlNPTi5zdHJpbmdpZnkoe1xuICAgICAgICAgICAgICB0eElELFxuICAgICAgICAgICAgICByYXdfZGF0YTogcmF3RGF0YSxcbiAgICAgICAgICAgICAgcmF3X2RhdGFfaGV4OiByYXdEYXRhSGV4LFxuICAgICAgICAgICAgfSksXG4gICAgICAgICAgfSxcbiAgICAgICAgICB3YWxsZXQ6IHt9LFxuICAgICAgICB9O1xuXG4gICAgICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGJhc2Vjb2luLnZlcmlmeVRyYW5zYWN0aW9uKHBhcmFtcyk7XG4gICAgICAgIGFzc2VydC5zdHJpY3RFcXVhbChyZXN1bHQsIHRydWUpO1xuICAgICAgfSk7XG5cbiAgICAgIGl0KCdzaG91bGQgZmFpbCB3aXRoIG1pc3Npbmcgb3duZXIgYWRkcmVzcycsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgICAgY29uc3QgdGltZXN0YW1wID0gRGF0ZS5ub3coKTtcbiAgICAgICAgY29uc3QgdHhJRCA9ICcwMTIzNDU2Nzg5YWJjZGVmMDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWYwMTIzNDU2Nzg5YWJjZGVmJztcbiAgICAgICAgY29uc3QgdHJhbnNmZXJDb250cmFjdCA9IHtcbiAgICAgICAgICBwYXJhbWV0ZXI6IHtcbiAgICAgICAgICAgIHZhbHVlOiB7XG4gICAgICAgICAgICAgIGFtb3VudDogMTAwMDAwMCxcbiAgICAgICAgICAgICAgdG9fYWRkcmVzczogJzQxYzI1NDIwMjU1YzJjNWEyZGQ1NGVmNjlmOTJlZjI2MWU2YmQ0MjE2YScsXG4gICAgICAgICAgICB9LFxuICAgICAgICAgICAgdHlwZV91cmw6ICd0eXBlLmdvb2dsZWFwaXMuY29tL3Byb3RvY29sLlRyYW5zZmVyQ29udHJhY3QnLFxuICAgICAgICAgIH0sXG4gICAgICAgICAgdHlwZTogJ1RyYW5zZmVyQ29udHJhY3QnLFxuICAgICAgICB9O1xuXG4gICAgICAgIGNvbnN0IHJhd0RhdGEgPSB7XG4gICAgICAgICAgdHhJRCxcbiAgICAgICAgICBjb250cmFjdDogW3RyYW5zZmVyQ29udHJhY3RdLFxuICAgICAgICAgIHJlZl9ibG9ja19ieXRlczogJ2M4Y2YnLFxuICAgICAgICAgIHJlZl9ibG9ja19oYXNoOiAnODkxNzdmZDg0YzVkOTE5NicsXG4gICAgICAgICAgZXhwaXJhdGlvbjogdGltZXN0YW1wICsgMzYwMDAwMCxcbiAgICAgICAgICB0aW1lc3RhbXA6IHRpbWVzdGFtcCxcbiAgICAgICAgICBmZWVfbGltaXQ6IDE1MDAwMDAwMCxcbiAgICAgICAgfTtcblxuICAgICAgICBjb25zdCB0cmFuc2Zvcm1lZFJhd0RhdGEgPSB7XG4gICAgICAgICAgY29udHJhY3Q6IHJhd0RhdGEuY29udHJhY3QgYXMgYW55LFxuICAgICAgICAgIHJlZkJsb2NrQnl0ZXM6IHJhd0RhdGEucmVmX2Jsb2NrX2J5dGVzLFxuICAgICAgICAgIHJlZkJsb2NrSGFzaDogcmF3RGF0YS5yZWZfYmxvY2tfaGFzaCxcbiAgICAgICAgICBleHBpcmF0aW9uOiByYXdEYXRhLmV4cGlyYXRpb24sXG4gICAgICAgICAgdGltZXN0YW1wOiByYXdEYXRhLnRpbWVzdGFtcCxcbiAgICAgICAgICBmZWVMaW1pdDogcmF3RGF0YS5mZWVfbGltaXQsXG4gICAgICAgIH07XG5cbiAgICAgICAgY29uc3QgZXhwZWN0ZWRSYXdEYXRhSGV4ID0gVXRpbHMuZ2VuZXJhdGVSYXdEYXRhSGV4KHRyYW5zZm9ybWVkUmF3RGF0YSk7XG5cbiAgICAgICAgY29uc3QgcGFyYW1zID0ge1xuICAgICAgICAgIHR4UGFyYW1zOiB7XG4gICAgICAgICAgICByZWNpcGllbnRzOiBbeyBhZGRyZXNzOiAnVExXaDY3UDkzS2d0blpOQ3RHbkVITTFIMzNOaHEydXZ2TicsIGFtb3VudDogJzEwMDAwMDAnIH1dLFxuICAgICAgICAgIH0sXG4gICAgICAgICAgdHhQcmVidWlsZDoge1xuICAgICAgICAgICAgdHhIZXg6IEpTT04uc3RyaW5naWZ5KHtcbiAgICAgICAgICAgICAgdHhJRCxcbiAgICAgICAgICAgICAgcmF3X2RhdGE6IHJhd0RhdGEsXG4gICAgICAgICAgICAgIHJhd19kYXRhX2hleDogZXhwZWN0ZWRSYXdEYXRhSGV4LFxuICAgICAgICAgICAgfSksXG4gICAgICAgICAgfSxcbiAgICAgICAgICB3YWxsZXQ6IHt9LFxuICAgICAgICB9O1xuXG4gICAgICAgIGF3YWl0IGFzc2VydC5yZWplY3RzKGJhc2Vjb2luLnZlcmlmeVRyYW5zYWN0aW9uKHBhcmFtcyksIHtcbiAgICAgICAgICBtZXNzYWdlOiAnVHJhbnNhY3Rpb24gaGFzIG5vdCBoYXZlIGEgdmFsaWQgaWQnLFxuICAgICAgICB9KTtcbiAgICAgIH0pO1xuXG4gICAgICBpdCgnc2hvdWxkIGZhaWwgd2l0aCBtaXNzaW5nIGRlc3RpbmF0aW9uIGFkZHJlc3MnLCBhc3luYyBmdW5jdGlvbiAoKSB7XG4gICAgICAgIGNvbnN0IHRpbWVzdGFtcCA9IERhdGUubm93KCk7XG4gICAgICAgIGNvbnN0IHR4SUQgPSAnMDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWYwMTIzNDU2Nzg5YWJjZGVmMDEyMzQ1Njc4OWFiY2RlZic7XG4gICAgICAgIGNvbnN0IHRyYW5zZmVyQ29udHJhY3QgPSB7XG4gICAgICAgICAgcGFyYW1ldGVyOiB7XG4gICAgICAgICAgICB2YWx1ZToge1xuICAgICAgICAgICAgICBhbW91bnQ6IDEwMDAwMDAsXG4gICAgICAgICAgICAgIG93bmVyX2FkZHJlc3M6ICc0MTczYTU5OTNjZDE4MmFlMTUyYWRhZDgyMDMxNjNmNzgwYzY1YThhYTUnLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIHR5cGVfdXJsOiAndHlwZS5nb29nbGVhcGlzLmNvbS9wcm90b2NvbC5UcmFuc2ZlckNvbnRyYWN0JyxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHR5cGU6ICdUcmFuc2ZlckNvbnRyYWN0JyxcbiAgICAgICAgfTtcblxuICAgICAgICBjb25zdCByYXdEYXRhID0ge1xuICAgICAgICAgIHR4SUQsXG4gICAgICAgICAgY29udHJhY3Q6IFt0cmFuc2ZlckNvbnRyYWN0XSxcbiAgICAgICAgICByZWZfYmxvY2tfYnl0ZXM6ICdjOGNmJyxcbiAgICAgICAgICByZWZfYmxvY2tfaGFzaDogJzg5MTc3ZmQ4NGM1ZDkxOTYnLFxuICAgICAgICAgIGV4cGlyYXRpb246IHRpbWVzdGFtcCArIDM2MDAwMDAsXG4gICAgICAgICAgdGltZXN0YW1wOiB0aW1lc3RhbXAsXG4gICAgICAgICAgZmVlX2xpbWl0OiAxNTAwMDAwMDAsXG4gICAgICAgIH07XG5cbiAgICAgICAgY29uc3QgdHJhbnNmb3JtZWRSYXdEYXRhID0ge1xuICAgICAgICAgIGNvbnRyYWN0OiByYXdEYXRhLmNvbnRyYWN0IGFzIGFueSxcbiAgICAgICAgICByZWZCbG9ja0J5dGVzOiByYXdEYXRhLnJlZl9ibG9ja19ieXRlcyxcbiAgICAgICAgICByZWZCbG9ja0hhc2g6IHJhd0RhdGEucmVmX2Jsb2NrX2hhc2gsXG4gICAgICAgICAgZXhwaXJhdGlvbjogcmF3RGF0YS5leHBpcmF0aW9uLFxuICAgICAgICAgIHRpbWVzdGFtcDogcmF3RGF0YS50aW1lc3RhbXAsXG4gICAgICAgICAgZmVlTGltaXQ6IHJhd0RhdGEuZmVlX2xpbWl0LFxuICAgICAgICB9O1xuXG4gICAgICAgIGNvbnN0IGV4cGVjdGVkUmF3RGF0YUhleCA9IFV0aWxzLmdlbmVyYXRlUmF3RGF0YUhleCh0cmFuc2Zvcm1lZFJhd0RhdGEpO1xuXG4gICAgICAgIGNvbnN0IHBhcmFtcyA9IHtcbiAgICAgICAgICB0eFBhcmFtczoge1xuICAgICAgICAgICAgcmVjaXBpZW50czogW3sgYWRkcmVzczogJ1RMV2g2N1A5M0tndG5aTkN0R25FSE0xSDMzTmhxMnV2dk4nLCBhbW91bnQ6ICcxMDAwMDAwJyB9XSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHR4UHJlYnVpbGQ6IHtcbiAgICAgICAgICAgIHR4SGV4OiBKU09OLnN0cmluZ2lmeSh7XG4gICAgICAgICAgICAgIHR4SUQsXG4gICAgICAgICAgICAgIHJhd19kYXRhOiByYXdEYXRhLFxuICAgICAgICAgICAgICByYXdfZGF0YV9oZXg6IGV4cGVjdGVkUmF3RGF0YUhleCxcbiAgICAgICAgICAgIH0pLFxuICAgICAgICAgIH0sXG4gICAgICAgICAgd2FsbGV0OiB7fSxcbiAgICAgICAgfTtcblxuICAgICAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhiYXNlY29pbi52ZXJpZnlUcmFuc2FjdGlvbihwYXJhbXMpLCB7XG4gICAgICAgICAgbWVzc2FnZTogJ1RyYW5zYWN0aW9uIGhhcyBub3QgaGF2ZSBhIHZhbGlkIGlkJyxcbiAgICAgICAgfSk7XG4gICAgICB9KTtcblxuICAgICAgaXQoJ3Nob3VsZCBmYWlsIHdpdGggbWlzc2luZyBhbW91bnQnLCBhc3luYyBmdW5jdGlvbiAoKSB7XG4gICAgICAgIGNvbnN0IHRpbWVzdGFtcCA9IERhdGUubm93KCk7XG4gICAgICAgIGNvbnN0IHRyYW5zZmVyQ29udHJhY3QgPSB7XG4gICAgICAgICAgcGFyYW1ldGVyOiB7XG4gICAgICAgICAgICB2YWx1ZToge1xuICAgICAgICAgICAgICBvd25lcl9hZGRyZXNzOiAnNDE3M2E1OTkzY2QxODJhZTE1MmFkYWQ4MjAzMTYzZjc4MGM2NWE4YWE1JyxcbiAgICAgICAgICAgICAgdG9fYWRkcmVzczogJzQxYzI1NDIwMjU1YzJjNWEyZGQ1NGVmNjlmOTJlZjI2MWU2YmQ0MjE2YScsXG4gICAgICAgICAgICB9LFxuICAgICAgICAgICAgdHlwZV91cmw6ICd0eXBlLmdvb2dsZWFwaXMuY29tL3Byb3RvY29sLlRyYW5zZmVyQ29udHJhY3QnLFxuICAgICAgICAgIH0sXG4gICAgICAgICAgdHlwZTogJ1RyYW5zZmVyQ29udHJhY3QnLFxuICAgICAgICB9O1xuXG4gICAgICAgIGNvbnN0IHJhd0RhdGEgPSB7XG4gICAgICAgICAgY29udHJhY3Q6IFt0cmFuc2ZlckNvbnRyYWN0XSxcbiAgICAgICAgICByZWZfYmxvY2tfYnl0ZXM6ICdjOGNmJyxcbiAgICAgICAgICByZWZfYmxvY2tfaGFzaDogJzg5MTc3ZmQ4NGM1ZDkxOTYnLFxuICAgICAgICAgIGV4cGlyYXRpb246IHRpbWVzdGFtcCArIDM2MDAwMDAsXG4gICAgICAgICAgdGltZXN0YW1wOiB0aW1lc3RhbXAsXG4gICAgICAgICAgZmVlX2xpbWl0OiAxNTAwMDAwMDAsXG4gICAgICAgIH07XG5cbiAgICAgICAgY29uc3QgdHJhbnNmb3JtZWRSYXdEYXRhID0ge1xuICAgICAgICAgIGNvbnRyYWN0OiByYXdEYXRhLmNvbnRyYWN0IGFzIGFueSxcbiAgICAgICAgICByZWZCbG9ja0J5dGVzOiByYXdEYXRhLnJlZl9ibG9ja19ieXRlcyxcbiAgICAgICAgICByZWZCbG9ja0hhc2g6IHJhd0RhdGEucmVmX2Jsb2NrX2hhc2gsXG4gICAgICAgICAgZXhwaXJhdGlvbjogcmF3RGF0YS5leHBpcmF0aW9uLFxuICAgICAgICAgIHRpbWVzdGFtcDogcmF3RGF0YS50aW1lc3RhbXAsXG4gICAgICAgICAgZmVlTGltaXQ6IHJhd0RhdGEuZmVlX2xpbWl0LFxuICAgICAgICB9O1xuXG4gICAgICAgIGNvbnN0IGV4cGVjdGVkUmF3RGF0YUhleCA9IFV0aWxzLmdlbmVyYXRlUmF3RGF0YUhleCh0cmFuc2Zvcm1lZFJhd0RhdGEpO1xuXG4gICAgICAgIGNvbnN0IHBhcmFtcyA9IHtcbiAgICAgICAgICB0eFBhcmFtczoge1xuICAgICAgICAgICAgcmVjaXBpZW50czogW3sgYWRkcmVzczogJ1RMV2g2N1A5M0tndG5aTkN0R25FSE0xSDMzTmhxMnV2dk4nLCBhbW91bnQ6ICcxMDAwMDAwJyB9XSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHR4UHJlYnVpbGQ6IHtcbiAgICAgICAgICAgIHR4SGV4OiBKU09OLnN0cmluZ2lmeSh7XG4gICAgICAgICAgICAgIHJhd19kYXRhOiByYXdEYXRhLFxuICAgICAgICAgICAgICByYXdfZGF0YV9oZXg6IGV4cGVjdGVkUmF3RGF0YUhleCxcbiAgICAgICAgICAgIH0pLFxuICAgICAgICAgIH0sXG4gICAgICAgICAgd2FsbGV0OiB7fSxcbiAgICAgICAgfTtcblxuICAgICAgICBhd2FpdCBhc3NlcnQucmVqZWN0cyhiYXNlY29pbi52ZXJpZnlUcmFuc2FjdGlvbihwYXJhbXMpLCB7XG4gICAgICAgICAgbWVzc2FnZTogJ0Ftb3VudCBkb2VzIG5vdCBleGlzdCBpbiB0aGlzIHRyYW5zZmVyIGNvbnRyYWN0LicsXG4gICAgICAgIH0pO1xuICAgICAgfSk7XG5cbiAgICAgIGl0KCdzaG91bGQgZmFpbCBkdWUgdG8gYW1vdW50IG1pc3NtYXRjaCcsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgICAgY29uc3QgdGltZXN0YW1wID0gRGF0ZS5ub3coKTtcbiAgICAgICAgY29uc3QgdHJhbnNmZXJDb250cmFjdCA9IHtcbiAgICAgICAgICBwYXJhbWV0ZXI6IHtcbiAgICAgICAgICAgIHZhbHVlOiB7XG4gICAgICAgICAgICAgIGFtb3VudDogMjAwMDAwMCxcbiAgICAgICAgICAgICAgb3duZXJfYWRkcmVzczogJzQxNzNhNTk5M2NkMTgyYWUxNTJhZGFkODIwMzE2M2Y3ODBjNjVhOGFhNScsXG4gICAgICAgICAgICAgIHRvX2FkZHJlc3M6ICc0MWQ2Y2Q2YTJjMGZmMzVhMzE5ZTZhYmI1Yjk1MDNiYTAyNzg2Nzk4ODInLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIHR5cGVfdXJsOiAndHlwZS5nb29nbGVhcGlzLmNvbS9wcm90b2NvbC5UcmFuc2ZlckNvbnRyYWN0JyxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHR5cGU6ICdUcmFuc2ZlckNvbnRyYWN0JyxcbiAgICAgICAgfTtcblxuICAgICAgICBjb25zdCByYXdEYXRhID0ge1xuICAgICAgICAgIGNvbnRyYWN0OiBbdHJhbnNmZXJDb250cmFjdF0sXG4gICAgICAgICAgcmVmX2Jsb2NrX2J5dGVzOiAnYzhjZicsXG4gICAgICAgICAgcmVmX2Jsb2NrX2hhc2g6ICc4OTE3N2ZkODRjNWQ5MTk2JyxcbiAgICAgICAgICBleHBpcmF0aW9uOiB0aW1lc3RhbXAgKyAzNjAwMDAwLFxuICAgICAgICAgIHRpbWVzdGFtcDogdGltZXN0YW1wLFxuICAgICAgICAgIGZlZV9saW1pdDogMTUwMDAwMDAwLFxuICAgICAgICB9O1xuXG4gICAgICAgIC8vIFRyYW5zZm9ybSByYXdEYXRhIHRvIG1hdGNoIHRoZSBleHBlY3RlZCBwYXJhbWV0ZXIgc3RydWN0dXJlXG4gICAgICAgIGNvbnN0IHRyYW5zZm9ybWVkUmF3RGF0YSA9IHtcbiAgICAgICAgICBjb250cmFjdDogcmF3RGF0YS5jb250cmFjdCBhcyBhbnksXG4gICAgICAgICAgcmVmQmxvY2tCeXRlczogcmF3RGF0YS5yZWZfYmxvY2tfYnl0ZXMsXG4gICAgICAgICAgcmVmQmxvY2tIYXNoOiByYXdEYXRhLnJlZl9ibG9ja19oYXNoLFxuICAgICAgICAgIGV4cGlyYXRpb246IHJhd0RhdGEuZXhwaXJhdGlvbixcbiAgICAgICAgICB0aW1lc3RhbXA6IHJhd0RhdGEudGltZXN0YW1wLFxuICAgICAgICAgIGZlZUxpbWl0OiByYXdEYXRhLmZlZV9saW1pdCxcbiAgICAgICAgfTtcblxuICAgICAgICAvLyBHZW5lcmF0ZSByYXdfZGF0YV9oZXggdXNpbmcgdGhlIHV0aWxpdHkgZnVuY3Rpb25cbiAgICAgICAgY29uc3QgcmF3RGF0YUhleCA9IFV0aWxzLmdlbmVyYXRlUmF3RGF0YUhleCh0cmFuc2Zvcm1lZFJhd0RhdGEpO1xuXG4gICAgICAgIC8vIENhbGN1bGF0ZSB0eElEIGFzIFNIQTI1NiBoYXNoIG9mIHJhd19kYXRhX2hleFxuICAgICAgICBjb25zdCB0eElEID0gY3JlYXRlSGFzaCgnc2hhMjU2JykudXBkYXRlKEJ1ZmZlci5mcm9tKHJhd0RhdGFIZXgsICdoZXgnKSkuZGlnZXN0KCdoZXgnKTtcblxuICAgICAgICBjb25zdCBwYXJhbXMgPSB7XG4gICAgICAgICAgdHhQYXJhbXM6IHtcbiAgICAgICAgICAgIHJlY2lwaWVudHM6IFtcbiAgICAgICAgICAgICAge1xuICAgICAgICAgICAgICAgIGFkZHJlc3M6ICc0MWQ2Y2Q2YTJjMGZmMzVhMzE5ZTZhYmI1Yjk1MDNiYTAyNzg2Nzk4ODInLFxuICAgICAgICAgICAgICAgIGFtb3VudDogJzEwMDAwMDAnLFxuICAgICAgICAgICAgICB9LFxuICAgICAgICAgICAgXSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHR4UHJlYnVpbGQ6IHtcbiAgICAgICAgICAgIHR4SGV4OiBKU09OLnN0cmluZ2lmeSh7XG4gICAgICAgICAgICAgIHR4SUQsXG4gICAgICAgICAgICAgIHJhd19kYXRhOiByYXdEYXRhLFxuICAgICAgICAgICAgICByYXdfZGF0YV9oZXg6IHJhd0RhdGFIZXgsXG4gICAgICAgICAgICB9KSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHdhbGxldDoge30sXG4gICAgICAgIH07XG5cbiAgICAgICAgYXdhaXQgYXNzZXJ0LnJlamVjdHMoYmFzZWNvaW4udmVyaWZ5VHJhbnNhY3Rpb24ocGFyYW1zKSwge1xuICAgICAgICAgIG1lc3NhZ2U6ICd0cmFuc2FjdGlvbiBhbW91bnQgaW4gdHhQcmVidWlsZCBkb2VzIG5vdCBtYXRjaCB0aGUgdmFsdWUgZ2l2ZW4gYnkgY2xpZW50JyxcbiAgICAgICAgfSk7XG4gICAgICB9KTtcblxuICAgICAgaXQoJ3Nob3VsZCBmYWlsIGR1ZSB0byBkZXN0aW5hdGlvbiBhZGRyZXNzIG1pc3NtYXRjaCcsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgICAgY29uc3QgdGltZXN0YW1wID0gRGF0ZS5ub3coKTtcbiAgICAgICAgY29uc3QgdHJhbnNmZXJDb250cmFjdCA9IHtcbiAgICAgICAgICBwYXJhbWV0ZXI6IHtcbiAgICAgICAgICAgIHZhbHVlOiB7XG4gICAgICAgICAgICAgIGFtb3VudDogMTAwMDAwMCxcbiAgICAgICAgICAgICAgb3duZXJfYWRkcmVzczogJzQxNzNhNTk5M2NkMTgyYWUxNTJhZGFkODIwMzE2M2Y3ODBjNjVhOGFhNScsXG4gICAgICAgICAgICAgIHRvX2FkZHJlc3M6ICc0MWQ2Y2Q2YTJjMGZmMzVhMzE5ZTZhYmI1Yjk1MDNiYTAyNzg2Nzk4ODInLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIHR5cGVfdXJsOiAndHlwZS5nb29nbGVhcGlzLmNvbS9wcm90b2NvbC5UcmFuc2ZlckNvbnRyYWN0JyxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHR5cGU6ICdUcmFuc2ZlckNvbnRyYWN0JyxcbiAgICAgICAgfTtcblxuICAgICAgICBjb25zdCByYXdEYXRhID0ge1xuICAgICAgICAgIGNvbnRyYWN0OiBbdHJhbnNmZXJDb250cmFjdF0sXG4gICAgICAgICAgcmVmX2Jsb2NrX2J5dGVzOiAnYzhjZicsXG4gICAgICAgICAgcmVmX2Jsb2NrX2hhc2g6ICc4OTE3N2ZkODRjNWQ5MTk2JyxcbiAgICAgICAgICBleHBpcmF0aW9uOiB0aW1lc3RhbXAgKyAzNjAwMDAwLFxuICAgICAgICAgIHRpbWVzdGFtcDogdGltZXN0YW1wLFxuICAgICAgICAgIGZlZV9saW1pdDogMTUwMDAwMDAwLFxuICAgICAgICB9O1xuXG4gICAgICAgIC8vIFRyYW5zZm9ybSByYXdEYXRhIHRvIG1hdGNoIHRoZSBleHBlY3RlZCBwYXJhbWV0ZXIgc3RydWN0dXJlXG4gICAgICAgIGNvbnN0IHRyYW5zZm9ybWVkUmF3RGF0YSA9IHtcbiAgICAgICAgICBjb250cmFjdDogcmF3RGF0YS5jb250cmFjdCBhcyBhbnksXG4gICAgICAgICAgcmVmQmxvY2tCeXRlczogcmF3RGF0YS5yZWZfYmxvY2tfYnl0ZXMsXG4gICAgICAgICAgcmVmQmxvY2tIYXNoOiByYXdEYXRhLnJlZl9ibG9ja19oYXNoLFxuICAgICAgICAgIGV4cGlyYXRpb246IHJhd0RhdGEuZXhwaXJhdGlvbixcbiAgICAgICAgICB0aW1lc3RhbXA6IHJhd0RhdGEudGltZXN0YW1wLFxuICAgICAgICAgIGZlZUxpbWl0OiByYXdEYXRhLmZlZV9saW1pdCxcbiAgICAgICAgfTtcblxuICAgICAgICAvLyBHZW5lcmF0ZSByYXdfZGF0YV9oZXggdXNpbmcgdGhlIHV0aWxpdHkgZnVuY3Rpb25cbiAgICAgICAgY29uc3QgcmF3RGF0YUhleCA9IFV0aWxzLmdlbmVyYXRlUmF3RGF0YUhleCh0cmFuc2Zvcm1lZFJhd0RhdGEpO1xuXG4gICAgICAgIC8vIENhbGN1bGF0ZSB0eElEIGFzIFNIQTI1NiBoYXNoIG9mIHJhd19kYXRhX2hleFxuICAgICAgICBjb25zdCB0eElEID0gY3JlYXRlSGFzaCgnc2hhMjU2JykudXBkYXRlKEJ1ZmZlci5mcm9tKHJhd0RhdGFIZXgsICdoZXgnKSkuZGlnZXN0KCdoZXgnKTtcblxuICAgICAgICBjb25zdCBwYXJhbXMgPSB7XG4gICAgICAgICAgdHhQYXJhbXM6IHtcbiAgICAgICAgICAgIHJlY2lwaWVudHM6IFtcbiAgICAgICAgICAgICAge1xuICAgICAgICAgICAgICAgIGFkZHJlc3M6ICc0MWQ2Y2Q2YTJjMGZmMzVhMzE5ZTZhYmI1Yjk1MDNiYTAyNzg2Nzk4ODMnLFxuICAgICAgICAgICAgICAgIGFtb3VudDogJzEwMDAwMDAnLFxuICAgICAgICAgICAgICB9LFxuICAgICAgICAgICAgXSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHR4UHJlYnVpbGQ6IHtcbiAgICAgICAgICAgIHR4SGV4OiBKU09OLnN0cmluZ2lmeSh7XG4gICAgICAgICAgICAgIHR4SUQsXG4gICAgICAgICAgICAgIHJhd19kYXRhOiByYXdEYXRhLFxuICAgICAgICAgICAgICByYXdfZGF0YV9oZXg6IHJhd0RhdGFIZXgsXG4gICAgICAgICAgICB9KSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHdhbGxldDoge30sXG4gICAgICAgIH07XG5cbiAgICAgICAgYXdhaXQgYXNzZXJ0LnJlamVjdHMoYmFzZWNvaW4udmVyaWZ5VHJhbnNhY3Rpb24ocGFyYW1zKSwge1xuICAgICAgICAgIG1lc3NhZ2U6ICdkZXN0aW5hdGlvbiBhZGRyZXNzIGRvZXMgbm90IG1hdGNoIHdpdGggdGhlIHJlY2lwaWVudCBhZGRyZXNzJyxcbiAgICAgICAgfSk7XG4gICAgICB9KTtcbiAgICB9KTtcbiAgfSk7XG59KTtcbiJdfQ==