@bitgo-beta/sdk-coin-hbar 2.0.73-alpha.13 → 2.0.73-alpha.130

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (50) hide show
  1. package/dist/src/hbar.d.ts +20 -3
  2. package/dist/src/hbar.d.ts.map +1 -1
  3. package/dist/src/hbar.js +183 -6
  4. package/dist/src/lib/index.d.ts +1 -0
  5. package/dist/src/lib/index.d.ts.map +1 -1
  6. package/dist/src/lib/index.js +1 -1
  7. package/dist/test/fixtures/hbar.d.ts +6 -0
  8. package/dist/test/fixtures/hbar.d.ts.map +1 -0
  9. package/dist/test/fixtures/hbar.js +9 -0
  10. package/dist/test/resources/hbar.d.ts +67 -0
  11. package/dist/test/resources/hbar.d.ts.map +1 -0
  12. package/dist/test/resources/hbar.js +73 -0
  13. package/dist/test/unit/fixtures/hbarBackupKey.d.ts +4 -0
  14. package/dist/test/unit/fixtures/hbarBackupKey.d.ts.map +1 -0
  15. package/dist/test/unit/fixtures/hbarBackupKey.js +10 -0
  16. package/dist/test/unit/getBuilderFactory.d.ts +3 -0
  17. package/dist/test/unit/getBuilderFactory.d.ts.map +1 -0
  18. package/dist/test/unit/getBuilderFactory.js +10 -0
  19. package/dist/test/unit/hbar.d.ts +2 -0
  20. package/dist/test/unit/hbar.d.ts.map +1 -0
  21. package/dist/test/unit/hbar.js +1437 -0
  22. package/dist/test/unit/hbarToken.d.ts +2 -0
  23. package/dist/test/unit/hbarToken.d.ts.map +1 -0
  24. package/dist/test/unit/hbarToken.js +34 -0
  25. package/dist/test/unit/keyPair.d.ts +2 -0
  26. package/dist/test/unit/keyPair.d.ts.map +1 -0
  27. package/dist/test/unit/keyPair.js +179 -0
  28. package/dist/test/unit/transaction.d.ts +2 -0
  29. package/dist/test/unit/transaction.d.ts.map +1 -0
  30. package/dist/test/unit/transaction.js +94 -0
  31. package/dist/test/unit/transactionBuilder/tokenAssociateBuilder.d.ts +2 -0
  32. package/dist/test/unit/transactionBuilder/tokenAssociateBuilder.d.ts.map +1 -0
  33. package/dist/test/unit/transactionBuilder/tokenAssociateBuilder.js +215 -0
  34. package/dist/test/unit/transactionBuilder/tokenTransferBuilder.d.ts +2 -0
  35. package/dist/test/unit/transactionBuilder/tokenTransferBuilder.d.ts.map +1 -0
  36. package/dist/test/unit/transactionBuilder/tokenTransferBuilder.js +329 -0
  37. package/dist/test/unit/transactionBuilder/transferBuilder.d.ts +2 -0
  38. package/dist/test/unit/transactionBuilder/transferBuilder.d.ts.map +1 -0
  39. package/dist/test/unit/transactionBuilder/transferBuilder.js +353 -0
  40. package/dist/test/unit/transactionBuilder/walletInitialization.d.ts +2 -0
  41. package/dist/test/unit/transactionBuilder/walletInitialization.d.ts.map +1 -0
  42. package/dist/test/unit/transactionBuilder/walletInitialization.js +214 -0
  43. package/dist/test/unit/utils.d.ts +2 -0
  44. package/dist/test/unit/utils.d.ts.map +1 -0
  45. package/dist/test/unit/utils.js +275 -0
  46. package/dist/tsconfig.tsbuildinfo +1 -0
  47. package/package.json +13 -10
  48. package/.eslintignore +0 -5
  49. package/.mocharc.yml +0 -8
  50. package/CHANGELOG.md +0 -743
@@ -0,0 +1,214 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ var __importDefault = (this && this.__importDefault) || function (mod) {
36
+ return (mod && mod.__esModule) ? mod : { "default": mod };
37
+ };
38
+ Object.defineProperty(exports, "__esModule", { value: true });
39
+ const assert_1 = __importDefault(require("assert"));
40
+ const should = __importStar(require("should"));
41
+ const getBuilderFactory_1 = require("../getBuilderFactory");
42
+ const src_1 = require("../../../src");
43
+ const testData = __importStar(require("../../resources/hbar"));
44
+ const sdk_core_1 = require("@bitgo-beta/sdk-core");
45
+ describe('HBAR Wallet initialization', () => {
46
+ const factory = (0, getBuilderFactory_1.getBuilderFactory)('thbar');
47
+ const initTxBuilder = () => {
48
+ const txBuilder = factory.getWalletInitializationBuilder();
49
+ txBuilder.fee({ fee: '1000000000' });
50
+ txBuilder.owner(testData.OWNER1);
51
+ txBuilder.owner(testData.OWNER2);
52
+ txBuilder.owner(testData.OWNER3);
53
+ txBuilder.source({ address: testData.OPERATOR.accountId });
54
+ txBuilder.sign({ key: testData.OPERATOR.privateKey });
55
+ return txBuilder;
56
+ };
57
+ describe('should build ', () => {
58
+ it('a valid raw tx for wallet init', async () => {
59
+ const builder = initTxBuilder();
60
+ const tx = await builder.build();
61
+ const raw = tx.toBroadcastFormat();
62
+ const builder2 = factory.from(raw);
63
+ const tx2 = await builder2.build();
64
+ should.deepEqual(tx.signature.length, 1);
65
+ should.deepEqual(tx.toJson(), tx2.toJson());
66
+ should.deepEqual(raw, tx2.toBroadcastFormat());
67
+ tx.type.should.equal(sdk_core_1.TransactionType.WalletInitialization);
68
+ tx2.type.should.equal(sdk_core_1.TransactionType.WalletInitialization);
69
+ });
70
+ it('an init transaction', async () => {
71
+ const txBuilder = initTxBuilder();
72
+ const tx = await txBuilder.build();
73
+ const txJson = tx.toJson();
74
+ txJson.fee.should.equal(1000000000);
75
+ should.deepEqual(tx.signature.length, 1);
76
+ should.equal(txJson.from, testData.OPERATOR.accountId);
77
+ tx.type.should.equal(sdk_core_1.TransactionType.WalletInitialization);
78
+ });
79
+ it('offline signing init transaction', async () => {
80
+ const txBuilder1 = factory.getWalletInitializationBuilder();
81
+ txBuilder1.startTime('1596110493.372646570');
82
+ txBuilder1.fee({ fee: '1000000000' });
83
+ txBuilder1.owner(testData.OWNER1);
84
+ txBuilder1.owner(testData.OWNER2);
85
+ txBuilder1.owner(testData.OWNER3);
86
+ txBuilder1.source({ address: testData.OPERATOR.accountId });
87
+ const tx1 = await txBuilder1.build();
88
+ const factory2 = (0, getBuilderFactory_1.getBuilderFactory)('thbar');
89
+ const txBuilder2 = factory2.from(tx1.toBroadcastFormat());
90
+ txBuilder2.sign({ key: testData.OPERATOR.privateKey });
91
+ const tx2 = await txBuilder2.build();
92
+ const factory3 = (0, getBuilderFactory_1.getBuilderFactory)('thbar');
93
+ const txBuilder3 = factory3.from(tx2.toBroadcastFormat());
94
+ txBuilder3.sign({ key: testData.ACCOUNT_1.prvKeyWithPrefix });
95
+ const tx3 = await txBuilder3.build();
96
+ should.deepEqual(tx2.signature.length, 1);
97
+ should.deepEqual(tx3.signature.length, 2);
98
+ should.deepEqual(tx2.toBroadcastFormat(), testData.WALLET_BUILDER_SIGNED_TRANSACTION);
99
+ should.deepEqual(tx3.toBroadcastFormat(), testData.WALLET_BUILDER_SIGNED_TWICE_TRANSACTION);
100
+ });
101
+ it('initialize from invalid tx adding new fields', async () => {
102
+ const txBuilder = factory.from(testData.WALLET_INIT_2_OWNERS);
103
+ txBuilder.owner(testData.OWNER3);
104
+ txBuilder.sign({ key: testData.OPERATOR.privateKey });
105
+ const tx = await txBuilder.build();
106
+ should.deepEqual(tx.signature.length, 1);
107
+ should.deepEqual(tx.toBroadcastFormat(), testData.WALLET_BUILDER_SIGNED_TRANSACTION);
108
+ });
109
+ it('an init transaction with external signature', async () => {
110
+ const txBuilder = factory.getWalletInitializationBuilder();
111
+ txBuilder.fee({ fee: '1000000000' });
112
+ txBuilder.owner(testData.OWNER1);
113
+ txBuilder.owner(testData.OWNER2);
114
+ txBuilder.owner(testData.OWNER3);
115
+ txBuilder.source({ address: testData.OPERATOR.accountId });
116
+ txBuilder.signature('20bc01a6da677b99974b17204de5ff6f34f8e5904f58d6df1ceb39b473e7295dccf60fcedaf4f' +
117
+ 'dc3f6bef93edcfbe2a7ec33cc94c893906a063383c27b014f09', new src_1.KeyPair({ pub: testData.ACCOUNT_1.pubKeyWithPrefix }));
118
+ const tx = await txBuilder.build();
119
+ const txJson = tx.toJson();
120
+ should.equal(txJson.from, testData.OPERATOR.accountId);
121
+ });
122
+ it('an init transaction with external signature included twice', async () => {
123
+ const txBuilder = factory.getWalletInitializationBuilder();
124
+ txBuilder.fee({ fee: '1000000000' });
125
+ txBuilder.owner(testData.OWNER1);
126
+ txBuilder.owner(testData.OWNER2);
127
+ txBuilder.owner(testData.OWNER3);
128
+ txBuilder.source({ address: testData.OPERATOR.accountId });
129
+ txBuilder.signature('20bc01a6da677b99974b17204de5ff6f34f8e5904f58d6df1ceb39b473e7295dccf60fcedaf4f' +
130
+ 'dc3f6bef93edcfbe2a7ec33cc94c893906a063383c27b014f09', new src_1.KeyPair({ pub: testData.ACCOUNT_1.pubKeyWithPrefix }));
131
+ txBuilder.signature('20bc01a6da677b99974b17204de5ff6f34f8e5904f58d6df1ceb39b473e7295dccf60fcedaf4f' +
132
+ 'dc3f6bef93edcfbe2a7ec33cc94c893906a063383c27b014f09', new src_1.KeyPair({ pub: testData.ACCOUNT_1.pubKeyWithPrefix }));
133
+ const tx = await txBuilder.build();
134
+ const txJson = tx.toJson();
135
+ should.equal(txJson.from, testData.OPERATOR.accountId);
136
+ });
137
+ });
138
+ describe('should fail to build', () => {
139
+ it('a transaction without fee', async () => {
140
+ const txBuilder = factory.getWalletInitializationBuilder();
141
+ txBuilder.owner(testData.OWNER1);
142
+ txBuilder.owner(testData.OWNER2);
143
+ txBuilder.owner(testData.OWNER3);
144
+ txBuilder.source({ address: testData.OPERATOR.accountId });
145
+ await txBuilder.build().should.be.rejectedWith('Invalid transaction: missing fee');
146
+ });
147
+ it('a wallet initialization the wrong number of owners', async () => {
148
+ const txBuilder = factory.getWalletInitializationBuilder();
149
+ txBuilder.fee({ fee: '1000000000' });
150
+ txBuilder.owner(testData.OWNER1);
151
+ txBuilder.owner(testData.OWNER2);
152
+ txBuilder.source({ address: testData.OPERATOR.accountId });
153
+ await txBuilder
154
+ .build()
155
+ .should.be.rejectedWith('Invalid transaction: wrong number of owners -- required: 3, found: 2');
156
+ assert_1.default.throws(() => txBuilder.owner(testData.OWNER1), new RegExp('Repeated owner address: ' + testData.OWNER1));
157
+ const newTxBuilder = factory.getWalletInitializationBuilder();
158
+ newTxBuilder.fee({ fee: '1000000000' });
159
+ newTxBuilder.source({ address: testData.OPERATOR.accountId });
160
+ await newTxBuilder
161
+ .build()
162
+ .should.be.rejectedWith('Invalid transaction: wrong number of owners -- required: 3, found: 0');
163
+ });
164
+ it('a transaction with invalid source', async () => {
165
+ const factory = (0, getBuilderFactory_1.getBuilderFactory)('thbar');
166
+ const txBuilder = factory.getWalletInitializationBuilder();
167
+ txBuilder.fee({ fee: '1000000000' });
168
+ txBuilder.owner(testData.OWNER1);
169
+ txBuilder.owner(testData.OWNER2);
170
+ txBuilder.owner(testData.OWNER3);
171
+ await txBuilder.build().should.be.rejectedWith('Invalid transaction: missing source');
172
+ });
173
+ });
174
+ describe('should validate', () => {
175
+ it('an address', async () => {
176
+ const txBuilder = factory.getWalletInitializationBuilder();
177
+ txBuilder.validateAddress(testData.VALID_ADDRESS);
178
+ assert_1.default.throws(() => txBuilder.validateAddress(testData.INVALID_ADDRESS), new RegExp('Invalid address ' + testData.INVALID_ADDRESS.address));
179
+ });
180
+ it('value should be greater than zero', () => {
181
+ const txBuilder = factory.getWalletInitializationBuilder();
182
+ assert_1.default.throws(() => txBuilder.fee({ fee: '-10' }));
183
+ should.doesNotThrow(() => txBuilder.fee({ fee: '10' }));
184
+ });
185
+ it('a private key', () => {
186
+ const txBuilder = factory.getWalletInitializationBuilder();
187
+ assert_1.default.throws(() => txBuilder.validateKey({ key: 'abc' }), /Invalid private key length/);
188
+ should.doesNotThrow(() => txBuilder.validateKey({ key: testData.ACCOUNT_1.prvKeyWithPrefix }));
189
+ });
190
+ it('a raw transaction', async () => {
191
+ const txBuilder = factory.getWalletInitializationBuilder();
192
+ should.doesNotThrow(() => txBuilder.validateRawTransaction(testData.WALLET_INITIALIZATION));
193
+ assert_1.default.throws(() => txBuilder.validateRawTransaction('0x00001000'));
194
+ assert_1.default.throws(() => txBuilder.validateRawTransaction(''));
195
+ assert_1.default.throws(() => txBuilder.validateRawTransaction('pqrs'));
196
+ assert_1.default.throws(() => txBuilder.validateRawTransaction(1234));
197
+ });
198
+ it('a transaction to build', async () => {
199
+ const txBuilder = factory.getWalletInitializationBuilder();
200
+ assert_1.default.throws(() => txBuilder.validateTransaction(), /Invalid transaction: wrong number of owners/);
201
+ txBuilder.fee({ fee: '10' });
202
+ assert_1.default.throws(() => txBuilder.validateTransaction(), /Invalid transaction: wrong number of owners/);
203
+ txBuilder.source(testData.VALID_ADDRESS);
204
+ assert_1.default.throws(() => txBuilder.validateTransaction(), /wrong number of owners -- required: 3, found: 0/);
205
+ txBuilder.owner(testData.OWNER1);
206
+ assert_1.default.throws(() => txBuilder.validateTransaction(), /wrong number of owners -- required: 3, found: 1/);
207
+ txBuilder.owner(testData.OWNER2);
208
+ assert_1.default.throws(() => txBuilder.validateTransaction(), /wrong number of owners -- required: 3, found: 2/);
209
+ txBuilder.owner(testData.OWNER3);
210
+ should.doesNotThrow(() => txBuilder.validateTransaction());
211
+ });
212
+ });
213
+ });
214
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoid2FsbGV0SW5pdGlhbGl6YXRpb24uanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi90ZXN0L3VuaXQvdHJhbnNhY3Rpb25CdWlsZGVyL3dhbGxldEluaXRpYWxpemF0aW9uLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBQUEsb0RBQTRCO0FBQzVCLCtDQUFpQztBQUNqQyw0REFBeUQ7QUFDekQsc0NBQXVDO0FBQ3ZDLCtEQUFpRDtBQUNqRCxtREFBdUQ7QUFHdkQsUUFBUSxDQUFDLDRCQUE0QixFQUFFLEdBQUcsRUFBRTtJQUMxQyxNQUFNLE9BQU8sR0FBRyxJQUFBLHFDQUFpQixFQUFDLE9BQU8sQ0FBQyxDQUFDO0lBRTNDLE1BQU0sYUFBYSxHQUFHLEdBQUcsRUFBRTtRQUN6QixNQUFNLFNBQVMsR0FBRyxPQUFPLENBQUMsOEJBQThCLEVBQUUsQ0FBQztRQUMzRCxTQUFTLENBQUMsR0FBRyxDQUFDLEVBQUUsR0FBRyxFQUFFLFlBQVksRUFBRSxDQUFDLENBQUM7UUFDckMsU0FBUyxDQUFDLEtBQUssQ0FBQyxRQUFRLENBQUMsTUFBTSxDQUFDLENBQUM7UUFDakMsU0FBUyxDQUFDLEtBQUssQ0FBQyxRQUFRLENBQUMsTUFBTSxDQUFDLENBQUM7UUFDakMsU0FBUyxDQUFDLEtBQUssQ0FBQyxRQUFRLENBQUMsTUFBTSxDQUFDLENBQUM7UUFDakMsU0FBUyxDQUFDLE1BQU0sQ0FBQyxFQUFFLE9BQU8sRUFBRSxRQUFRLENBQUMsUUFBUSxDQUFDLFNBQVMsRUFBRSxDQUFDLENBQUM7UUFDM0QsU0FBUyxDQUFDLElBQUksQ0FBQyxFQUFFLEdBQUcsRUFBRSxRQUFRLENBQUMsUUFBUSxDQUFDLFVBQVUsRUFBRSxDQUFDLENBQUM7UUFDdEQsT0FBTyxTQUFTLENBQUM7SUFDbkIsQ0FBQyxDQUFDO0lBRUYsUUFBUSxDQUFDLGVBQWUsRUFBRSxHQUFHLEVBQUU7UUFD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QUFDLENBQUM7WUFDN0IsZ0JBQU0sQ0FBQyxNQUFNLENBQUMsR0FBRyxFQUFFLENBQUMsU0FBUyxDQUFDLG1CQUFtQixFQUFFLEVBQUUsNkNBQTZDLENBQUMsQ0FBQztZQUNwRyxTQUFTLENBQUMsTUFBTSxDQUFDLFFBQVEsQ0FBQyxhQUFhLENBQUMsQ0FBQztZQUN6QyxnQkFBTSxDQUFDLE1BQU0sQ0FBQyxHQUFHLEVBQUUsQ0FBQyxTQUFTLENBQUMsbUJBQW1CLEVBQUUsRUFBRSxpREFBaUQsQ0FBQyxDQUFDO1lBQ3hHLFNBQVMsQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLE1BQU0sQ0FBQyxDQUFDO1lBQ2pDLGdCQUFNLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxDQUFDLFNBQVMsQ0FBQyxtQkFBbUIsRUFBRSxFQUFFLGlEQUFpRCxDQUFDLENBQUM7WUFDeEcsU0FBUyxDQUFDLEtBQUssQ0FBQyxRQUFRLENBQUMsTUFBTSxDQUFDLENBQUM7WUFDakMsZ0JBQU0sQ0FBQyxNQUFNLENBQUMsR0FBRyxFQUFFLENBQUMsU0FBUyxDQUFDLG1CQUFtQixFQUFFLEVBQUUsaURBQWlELENBQUMsQ0FBQztZQUN4RyxTQUFTLENBQUMsS0FBSyxDQUFDLFFBQVEsQ0FBQyxNQUFNLENBQUMsQ0FBQztZQUNqQyxNQUFNLENBQUMsWUFBWSxDQUFDLEdBQUcsRUFBRSxDQUFDLFNBQVMsQ0FBQyxtQkFBbUIsRUFBRSxDQUFDLENBQUM7UUFDN0QsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDLENBQUMsQ0FBQztBQUNMLENBQUMsQ0FBQyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IGFzc2VydCBmcm9tICdhc3NlcnQnO1xuaW1wb3J0ICogYXMgc2hvdWxkIGZyb20gJ3Nob3VsZCc7XG5pbXBvcnQgeyBnZXRCdWlsZGVyRmFjdG9yeSB9IGZyb20gJy4uL2dldEJ1aWxkZXJGYWN0b3J5JztcbmltcG9ydCB7IEtleVBhaXIgfSBmcm9tICcuLi8uLi8uLi9zcmMnO1xuaW1wb3J0ICogYXMgdGVzdERhdGEgZnJvbSAnLi4vLi4vcmVzb3VyY2VzL2hiYXInO1xuaW1wb3J0IHsgVHJhbnNhY3Rpb25UeXBlIH0gZnJvbSAnQGJpdGdvLWJldGEvc2RrLWNvcmUnO1xuaW1wb3J0IHsgV2FsbGV0SW5pdGlhbGl6YXRpb25CdWlsZGVyIH0gZnJvbSAnLi4vLi4vLi4vc3JjL2xpYi93YWxsZXRJbml0aWFsaXphdGlvbkJ1aWxkZXInO1xuXG5kZXNjcmliZSgnSEJBUiBXYWxsZXQgaW5pdGlhbGl6YXRpb24nLCAoKSA9PiB7XG4gIGNvbnN0IGZhY3RvcnkgPSBnZXRCdWlsZGVyRmFjdG9yeSgndGhiYXInKTtcblxuICBjb25zdCBpbml0VHhCdWlsZGVyID0gKCkgPT4ge1xuICAgIGNvbnN0IHR4QnVpbGRlciA9IGZhY3RvcnkuZ2V0V2FsbGV0SW5pdGlhbGl6YXRpb25CdWlsZGVyKCk7XG4gICAgdHhCdWlsZGVyLmZlZSh7IGZlZTogJzEwMDAwMDAwMDAnIH0pO1xuICAgIHR4QnVpbGRlci5vd25lcih0ZXN0RGF0YS5PV05FUjEpO1xuICAgIHR4QnVpbGRlci5vd25lcih0ZXN0RGF0YS5PV05FUjIpO1xuICAgIHR4QnVpbGRlci5vd25lcih0ZXN0RGF0YS5PV05FUjMpO1xuICAgIHR4QnVpbGRlci5zb3VyY2UoeyBhZGRyZXNzOiB0ZXN0RGF0YS5PUEVSQVRPUi5hY2NvdW50SWQgfSk7XG4gICAgdHhCdWlsZGVyLnNpZ24oeyBrZXk6IHRlc3REYXRhLk9QRVJBVE9SLnByaXZhdGVLZXkgfSk7XG4gICAgcmV0dXJuIHR4QnVpbGRlcjtcbiAgfTtcblxuICBkZXNjcmliZSgnc2hvdWxkIGJ1aWxkICcsICgpID0+IHtcbiAgICBpdCgnYSB2YWxpZCByYXcgdHggZm9yIHdhbGxldCBpbml0JywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgYnVpbGRlciA9IGluaXRUeEJ1aWxkZXIoKTtcbiAgICAgIGNvbnN0IHR4ID0gYXdhaXQgYnVpbGRlci5idWlsZCgpO1xuICAgICAgY29uc3QgcmF3ID0gdHgudG9Ccm9hZGNhc3RGb3JtYXQoKTtcbiAgICAgIGNvbnN0IGJ1aWxkZXIyID0gZmFjdG9yeS5mcm9tKHJhdyk7XG4gICAgICBjb25zdCB0eDIgPSBhd2FpdCBidWlsZGVyMi5idWlsZCgpO1xuICAgICAgc2hvdWxkLmRlZXBFcXVhbCh0eC5zaWduYXR1cmUubGVuZ3RoLCAxKTtcbiAgICAgIHNob3VsZC5kZWVwRXF1YWwodHgudG9Kc29uKCksIHR4Mi50b0pzb24oKSk7XG4gICAgICBzaG91bGQuZGVlcEVxdWFsKHJhdywgdHgyLnRvQnJvYWRjYXN0Rm9ybWF0KCkpO1xuICAgICAgdHgudHlwZS5zaG91bGQuZXF1YWwoVHJhbnNhY3Rpb25UeXBlLldhbGxldEluaXRpYWxpemF0aW9uKTtcbiAgICAgIHR4Mi50eXBlLnNob3VsZC5lcXVhbChUcmFuc2FjdGlvblR5cGUuV2FsbGV0SW5pdGlhbGl6YXRpb24pO1xuICAgIH0pO1xuXG4gICAgaXQoJ2FuIGluaXQgdHJhbnNhY3Rpb24nLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIgPSBpbml0VHhCdWlsZGVyKCk7XG4gICAgICBjb25zdCB0eCA9IGF3YWl0IHR4QnVpbGRlci5idWlsZCgpO1xuICAgICAgY29uc3QgdHhKc29uID0gdHgudG9Kc29uKCk7XG4gICAgICB0eEpzb24uZmVlLnNob3VsZC5lcXVhbCgxMDAwMDAwMDAwKTtcbiAgICAgIHNob3VsZC5kZWVwRXF1YWwodHguc2lnbmF0dXJlLmxlbmd0aCwgMSk7XG4gICAgICBzaG91bGQuZXF1YWwodHhKc29uLmZyb20sIHRlc3REYXRhLk9QRVJBVE9SLmFjY291bnRJZCk7XG4gICAgICB0eC50eXBlLnNob3VsZC5lcXVhbChUcmFuc2FjdGlvblR5cGUuV2FsbGV0SW5pdGlhbGl6YXRpb24pO1xuICAgIH0pO1xuXG4gICAgaXQoJ29mZmxpbmUgc2lnbmluZyBpbml0IHRyYW5zYWN0aW9uJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhCdWlsZGVyMSA9IGZhY3RvcnkuZ2V0V2FsbGV0SW5pdGlhbGl6YXRpb25CdWlsZGVyKCk7XG4gICAgICB0eEJ1aWxkZXIxLnN0YXJ0VGltZSgnMTU5NjExMDQ5My4zNzI2NDY1NzAnKTtcbiAgICAgIHR4QnVpbGRlcjEuZmVlKHsgZmVlOiAnMTAwMDAwMDAwMCcgfSk7XG4gICAgICB0eEJ1aWxkZXIxLm93bmVyKHRlc3REYXRhLk9XTkVSMSk7XG4gICAgICB0eEJ1aWxkZXIxLm93bmVyKHRlc3REYXRhLk9XTkVSMik7XG4gICAgICB0eEJ1aWxkZXIxLm93bmVyKHRlc3REYXRhLk9XTkVSMyk7XG4gICAgICB0eEJ1aWxkZXIxLnNvdXJjZSh7IGFkZHJlc3M6IHRlc3REYXRhLk9QRVJBVE9SLmFjY291bnRJZCB9KTtcbiAgICAgIGNvbnN0IHR4MSA9IGF3YWl0IHR4QnVpbGRlcjEuYnVpbGQoKTtcbiAgICAgIGNvbnN0IGZhY3RvcnkyID0gZ2V0QnVpbGRlckZhY3RvcnkoJ3RoYmFyJyk7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIyID0gZmFjdG9yeTIuZnJvbSh0eDEudG9Ccm9hZGNhc3RGb3JtYXQoKSk7XG4gICAgICB0eEJ1aWxkZXIyLnNpZ24oeyBrZXk6IHRlc3REYXRhLk9QRVJBVE9SLnByaXZhdGVLZXkgfSk7XG4gICAgICBjb25zdCB0eDIgPSBhd2FpdCB0eEJ1aWxkZXIyLmJ1aWxkKCk7XG5cbiAgICAgIGNvbnN0IGZhY3RvcnkzID0gZ2V0QnVpbGRlckZhY3RvcnkoJ3RoYmFyJyk7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIzID0gZmFjdG9yeTMuZnJvbSh0eDIudG9Ccm9hZGNhc3RGb3JtYXQoKSk7XG4gICAgICB0eEJ1aWxkZXIzLnNpZ24oeyBrZXk6IHRlc3REYXRhLkFDQ09VTlRfMS5wcnZLZXlXaXRoUHJlZml4IH0pO1xuICAgICAgY29uc3QgdHgzID0gYXdhaXQgdHhCdWlsZGVyMy5idWlsZCgpO1xuXG4gICAgICBzaG91bGQuZGVlcEVxdWFsKHR4Mi5zaWduYXR1cmUubGVuZ3RoLCAxKTtcbiAgICAgIHNob3VsZC5kZWVwRXF1YWwodHgzLnNpZ25hdHVyZS5sZW5ndGgsIDIpO1xuICAgICAgc2hvdWxkLmRlZXBFcXVhbCh0eDIudG9Ccm9hZGNhc3RGb3JtYXQoKSwgdGVzdERhdGEuV0FMTEVUX0JVSUxERVJfU0lHTkVEX1RSQU5TQUNUSU9OKTtcbiAgICAgIHNob3VsZC5kZWVwRXF1YWwodHgzLnRvQnJvYWRjYXN0Rm9ybWF0KCksIHRlc3REYXRhLldBTExFVF9CVUlMREVSX1NJR05FRF9UV0lDRV9UUkFOU0FDVElPTik7XG4gICAgfSk7XG5cbiAgICBpdCgnaW5pdGlhbGl6ZSBmcm9tIGludmFsaWQgdHggYWRkaW5nIG5ldyBmaWVsZHMnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIgPSBmYWN0b3J5LmZyb20odGVzdERhdGEuV0FMTEVUX0lOSVRfMl9PV05FUlMpIGFzIFdhbGxldEluaXRpYWxpemF0aW9uQnVpbGRlcjtcbiAgICAgIHR4QnVpbGRlci5vd25lcih0ZXN0RGF0YS5PV05FUjMpO1xuICAgICAgdHhCdWlsZGVyLnNpZ24oeyBrZXk6IHRlc3REYXRhLk9QRVJBVE9SLnByaXZhdGVLZXkgfSk7XG4gICAgICBjb25zdCB0eCA9IGF3YWl0IHR4QnVpbGRlci5idWlsZCgpO1xuXG4gICAgICBzaG91bGQuZGVlcEVxdWFsKHR4LnNpZ25hdHVyZS5sZW5ndGgsIDEpO1xuICAgICAgc2hvdWxkLmRlZXBFcXVhbCh0eC50b0Jyb2FkY2FzdEZvcm1hdCgpLCB0ZXN0RGF0YS5XQUxMRVRfQlVJTERFUl9TSUdORURfVFJBTlNBQ1RJT04pO1xuICAgIH0pO1xuXG4gICAgaXQoJ2FuIGluaXQgdHJhbnNhY3Rpb24gd2l0aCBleHRlcm5hbCBzaWduYXR1cmUnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIgPSBmYWN0b3J5LmdldFdhbGxldEluaXRpYWxpemF0aW9uQnVpbGRlcigpO1xuICAgICAgdHhCdWlsZGVyLmZlZSh7IGZlZTogJzEwMDAwMDAwMDAnIH0pO1xuICAgICAgdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMSk7XG4gICAgICB0eEJ1aWxkZXIub3duZXIodGVzdERhdGEuT1dORVIyKTtcbiAgICAgIHR4QnVpbGRlci5vd25lcih0ZXN0RGF0YS5PV05FUjMpO1xuICAgICAgdHhCdWlsZGVyLnNvdXJjZSh7IGFkZHJlc3M6IHRlc3REYXRhLk9QRVJBVE9SLmFjY291bnRJZCB9KTtcbiAgICAgIHR4QnVpbGRlci5zaWduYXR1cmUoXG4gICAgICAgICcyMGJjMDFhNmRhNjc3Yjk5OTc0YjE3MjA0ZGU1ZmY2ZjM0ZjhlNTkwNGY1OGQ2ZGYxY2ViMzliNDczZTcyOTVkY2NmNjBmY2VkYWY0ZicgK1xuICAgICAgICAgICdkYzNmNmJlZjkzZWRjZmJlMmE3ZWMzM2NjOTRjODkzOTA2YTA2MzM4M2MyN2IwMTRmMDknLFxuICAgICAgICBuZXcgS2V5UGFpcih7IHB1YjogdGVzdERhdGEuQUNDT1VOVF8xLnB1YktleVdpdGhQcmVmaXggfSlcbiAgICAgICk7XG5cbiAgICAgIGNvbnN0IHR4ID0gYXdhaXQgdHhCdWlsZGVyLmJ1aWxkKCk7XG4gICAgICBjb25zdCB0eEpzb24gPSB0eC50b0pzb24oKTtcbiAgICAgIHNob3VsZC5lcXVhbCh0eEpzb24uZnJvbSwgdGVzdERhdGEuT1BFUkFUT1IuYWNjb3VudElkKTtcbiAgICB9KTtcblxuICAgIGl0KCdhbiBpbml0IHRyYW5zYWN0aW9uIHdpdGggZXh0ZXJuYWwgc2lnbmF0dXJlIGluY2x1ZGVkIHR3aWNlJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhCdWlsZGVyID0gZmFjdG9yeS5nZXRXYWxsZXRJbml0aWFsaXphdGlvbkJ1aWxkZXIoKTtcbiAgICAgIHR4QnVpbGRlci5mZWUoeyBmZWU6ICcxMDAwMDAwMDAwJyB9KTtcbiAgICAgIHR4QnVpbGRlci5vd25lcih0ZXN0RGF0YS5PV05FUjEpO1xuICAgICAgdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMik7XG4gICAgICB0eEJ1aWxkZXIub3duZXIodGVzdERhdGEuT1dORVIzKTtcbiAgICAgIHR4QnVpbGRlci5zb3VyY2UoeyBhZGRyZXNzOiB0ZXN0RGF0YS5PUEVSQVRPUi5hY2NvdW50SWQgfSk7XG4gICAgICB0eEJ1aWxkZXIuc2lnbmF0dXJlKFxuICAgICAgICAnMjBiYzAxYTZkYTY3N2I5OTk3NGIxNzIwNGRlNWZmNmYzNGY4ZTU5MDRmNThkNmRmMWNlYjM5YjQ3M2U3Mjk1ZGNjZjYwZmNlZGFmNGYnICtcbiAgICAgICAgICAnZGMzZjZiZWY5M2VkY2ZiZTJhN2VjMzNjYzk0Yzg5MzkwNmEwNjMzODNjMjdiMDE0ZjA5JyxcbiAgICAgICAgbmV3IEtleVBhaXIoeyBwdWI6IHRlc3REYXRhLkFDQ09VTlRfMS5wdWJLZXlXaXRoUHJlZml4IH0pXG4gICAgICApO1xuICAgICAgdHhCdWlsZGVyLnNpZ25hdHVyZShcbiAgICAgICAgJzIwYmMwMWE2ZGE2NzdiOTk5NzRiMTcyMDRkZTVmZjZmMzRmOGU1OTA0ZjU4ZDZkZjFjZWIzOWI0NzNlNzI5NWRjY2Y2MGZjZWRhZjRmJyArXG4gICAgICAgICAgJ2RjM2Y2YmVmOTNlZGNmYmUyYTdlYzMzY2M5NGM4OTM5MDZhMDYzMzgzYzI3YjAxNGYwOScsXG4gICAgICAgIG5ldyBLZXlQYWlyKHsgcHViOiB0ZXN0RGF0YS5BQ0NPVU5UXzEucHViS2V5V2l0aFByZWZpeCB9KVxuICAgICAgKTtcblxuICAgICAgY29uc3QgdHggPSBhd2FpdCB0eEJ1aWxkZXIuYnVpbGQoKTtcbiAgICAgIGNvbnN0IHR4SnNvbiA9IHR4LnRvSnNvbigpO1xuICAgICAgc2hvdWxkLmVxdWFsKHR4SnNvbi5mcm9tLCB0ZXN0RGF0YS5PUEVSQVRPUi5hY2NvdW50SWQpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnc2hvdWxkIGZhaWwgdG8gYnVpbGQnLCAoKSA9PiB7XG4gICAgaXQoJ2EgdHJhbnNhY3Rpb24gd2l0aG91dCBmZWUnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIgPSBmYWN0b3J5LmdldFdhbGxldEluaXRpYWxpemF0aW9uQnVpbGRlcigpO1xuICAgICAgdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMSk7XG4gICAgICB0eEJ1aWxkZXIub3duZXIodGVzdERhdGEuT1dORVIyKTtcbiAgICAgIHR4QnVpbGRlci5vd25lcih0ZXN0RGF0YS5PV05FUjMpO1xuICAgICAgdHhCdWlsZGVyLnNvdXJjZSh7IGFkZHJlc3M6IHRlc3REYXRhLk9QRVJBVE9SLmFjY291bnRJZCB9KTtcbiAgICAgIGF3YWl0IHR4QnVpbGRlci5idWlsZCgpLnNob3VsZC5iZS5yZWplY3RlZFdpdGgoJ0ludmFsaWQgdHJhbnNhY3Rpb246IG1pc3NpbmcgZmVlJyk7XG4gICAgfSk7XG5cbiAgICBpdCgnYSB3YWxsZXQgaW5pdGlhbGl6YXRpb24gdGhlIHdyb25nIG51bWJlciBvZiBvd25lcnMnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIgPSBmYWN0b3J5LmdldFdhbGxldEluaXRpYWxpemF0aW9uQnVpbGRlcigpO1xuICAgICAgdHhCdWlsZGVyLmZlZSh7IGZlZTogJzEwMDAwMDAwMDAnIH0pO1xuICAgICAgdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMSk7XG4gICAgICB0eEJ1aWxkZXIub3duZXIodGVzdERhdGEuT1dORVIyKTtcbiAgICAgIHR4QnVpbGRlci5zb3VyY2UoeyBhZGRyZXNzOiB0ZXN0RGF0YS5PUEVSQVRPUi5hY2NvdW50SWQgfSk7XG4gICAgICBhd2FpdCB0eEJ1aWxkZXJcbiAgICAgICAgLmJ1aWxkKClcbiAgICAgICAgLnNob3VsZC5iZS5yZWplY3RlZFdpdGgoJ0ludmFsaWQgdHJhbnNhY3Rpb246IHdyb25nIG51bWJlciBvZiBvd25lcnMgLS0gcmVxdWlyZWQ6IDMsIGZvdW5kOiAyJyk7XG5cbiAgICAgIGFzc2VydC50aHJvd3MoKCkgPT4gdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMSksIG5ldyBSZWdFeHAoJ1JlcGVhdGVkIG93bmVyIGFkZHJlc3M6ICcgKyB0ZXN0RGF0YS5PV05FUjEpKTtcblxuICAgICAgY29uc3QgbmV3VHhCdWlsZGVyID0gZmFjdG9yeS5nZXRXYWxsZXRJbml0aWFsaXphdGlvbkJ1aWxkZXIoKTtcbiAgICAgIG5ld1R4QnVpbGRlci5mZWUoeyBmZWU6ICcxMDAwMDAwMDAwJyB9KTtcbiAgICAgIG5ld1R4QnVpbGRlci5zb3VyY2UoeyBhZGRyZXNzOiB0ZXN0RGF0YS5PUEVSQVRPUi5hY2NvdW50SWQgfSk7XG4gICAgICBhd2FpdCBuZXdUeEJ1aWxkZXJcbiAgICAgICAgLmJ1aWxkKClcbiAgICAgICAgLnNob3VsZC5iZS5yZWplY3RlZFdpdGgoJ0ludmFsaWQgdHJhbnNhY3Rpb246IHdyb25nIG51bWJlciBvZiBvd25lcnMgLS0gcmVxdWlyZWQ6IDMsIGZvdW5kOiAwJyk7XG4gICAgfSk7XG5cbiAgICBpdCgnYSB0cmFuc2FjdGlvbiB3aXRoIGludmFsaWQgc291cmNlJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgZmFjdG9yeSA9IGdldEJ1aWxkZXJGYWN0b3J5KCd0aGJhcicpO1xuICAgICAgY29uc3QgdHhCdWlsZGVyID0gZmFjdG9yeS5nZXRXYWxsZXRJbml0aWFsaXphdGlvbkJ1aWxkZXIoKTtcbiAgICAgIHR4QnVpbGRlci5mZWUoeyBmZWU6ICcxMDAwMDAwMDAwJyB9KTtcbiAgICAgIHR4QnVpbGRlci5vd25lcih0ZXN0RGF0YS5PV05FUjEpO1xuICAgICAgdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMik7XG4gICAgICB0eEJ1aWxkZXIub3duZXIodGVzdERhdGEuT1dORVIzKTtcbiAgICAgIGF3YWl0IHR4QnVpbGRlci5idWlsZCgpLnNob3VsZC5iZS5yZWplY3RlZFdpdGgoJ0ludmFsaWQgdHJhbnNhY3Rpb246IG1pc3Npbmcgc291cmNlJyk7XG4gICAgfSk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdzaG91bGQgdmFsaWRhdGUnLCAoKSA9PiB7XG4gICAgaXQoJ2FuIGFkZHJlc3MnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIgPSBmYWN0b3J5LmdldFdhbGxldEluaXRpYWxpemF0aW9uQnVpbGRlcigpO1xuICAgICAgdHhCdWlsZGVyLnZhbGlkYXRlQWRkcmVzcyh0ZXN0RGF0YS5WQUxJRF9BRERSRVNTKTtcbiAgICAgIGFzc2VydC50aHJvd3MoXG4gICAgICAgICgpID0+IHR4QnVpbGRlci52YWxpZGF0ZUFkZHJlc3ModGVzdERhdGEuSU5WQUxJRF9BRERSRVNTKSxcbiAgICAgICAgbmV3IFJlZ0V4cCgnSW52YWxpZCBhZGRyZXNzICcgKyB0ZXN0RGF0YS5JTlZBTElEX0FERFJFU1MuYWRkcmVzcylcbiAgICAgICk7XG4gICAgfSk7XG5cbiAgICBpdCgndmFsdWUgc2hvdWxkIGJlIGdyZWF0ZXIgdGhhbiB6ZXJvJywgKCkgPT4ge1xuICAgICAgY29uc3QgdHhCdWlsZGVyID0gZmFjdG9yeS5nZXRXYWxsZXRJbml0aWFsaXphdGlvbkJ1aWxkZXIoKTtcbiAgICAgIGFzc2VydC50aHJvd3MoKCkgPT4gdHhCdWlsZGVyLmZlZSh7IGZlZTogJy0xMCcgfSkpO1xuICAgICAgc2hvdWxkLmRvZXNOb3RUaHJvdygoKSA9PiB0eEJ1aWxkZXIuZmVlKHsgZmVlOiAnMTAnIH0pKTtcbiAgICB9KTtcblxuICAgIGl0KCdhIHByaXZhdGUga2V5JywgKCkgPT4ge1xuICAgICAgY29uc3QgdHhCdWlsZGVyID0gZmFjdG9yeS5nZXRXYWxsZXRJbml0aWFsaXphdGlvbkJ1aWxkZXIoKTtcbiAgICAgIGFzc2VydC50aHJvd3MoKCkgPT4gdHhCdWlsZGVyLnZhbGlkYXRlS2V5KHsga2V5OiAnYWJjJyB9KSwgL0ludmFsaWQgcHJpdmF0ZSBrZXkgbGVuZ3RoLyk7XG4gICAgICBzaG91bGQuZG9lc05vdFRocm93KCgpID0+IHR4QnVpbGRlci52YWxpZGF0ZUtleSh7IGtleTogdGVzdERhdGEuQUNDT1VOVF8xLnBydktleVdpdGhQcmVmaXggfSkpO1xuICAgIH0pO1xuXG4gICAgaXQoJ2EgcmF3IHRyYW5zYWN0aW9uJywgYXN5bmMgKCkgPT4ge1xuICAgICAgY29uc3QgdHhCdWlsZGVyID0gZmFjdG9yeS5nZXRXYWxsZXRJbml0aWFsaXphdGlvbkJ1aWxkZXIoKTtcbiAgICAgIHNob3VsZC5kb2VzTm90VGhyb3coKCkgPT4gdHhCdWlsZGVyLnZhbGlkYXRlUmF3VHJhbnNhY3Rpb24odGVzdERhdGEuV0FMTEVUX0lOSVRJQUxJWkFUSU9OKSk7XG4gICAgICBhc3NlcnQudGhyb3dzKCgpID0+IHR4QnVpbGRlci52YWxpZGF0ZVJhd1RyYW5zYWN0aW9uKCcweDAwMDAxMDAwJykpO1xuICAgICAgYXNzZXJ0LnRocm93cygoKSA9PiB0eEJ1aWxkZXIudmFsaWRhdGVSYXdUcmFuc2FjdGlvbignJykpO1xuICAgICAgYXNzZXJ0LnRocm93cygoKSA9PiB0eEJ1aWxkZXIudmFsaWRhdGVSYXdUcmFuc2FjdGlvbigncHFycycpKTtcbiAgICAgIGFzc2VydC50aHJvd3MoKCkgPT4gdHhCdWlsZGVyLnZhbGlkYXRlUmF3VHJhbnNhY3Rpb24oMTIzNCkpO1xuICAgIH0pO1xuXG4gICAgaXQoJ2EgdHJhbnNhY3Rpb24gdG8gYnVpbGQnLCBhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0eEJ1aWxkZXIgPSBmYWN0b3J5LmdldFdhbGxldEluaXRpYWxpemF0aW9uQnVpbGRlcigpO1xuICAgICAgYXNzZXJ0LnRocm93cygoKSA9PiB0eEJ1aWxkZXIudmFsaWRhdGVUcmFuc2FjdGlvbigpLCAvSW52YWxpZCB0cmFuc2FjdGlvbjogd3JvbmcgbnVtYmVyIG9mIG93bmVycy8pO1xuICAgICAgdHhCdWlsZGVyLmZlZSh7IGZlZTogJzEwJyB9KTtcbiAgICAgIGFzc2VydC50aHJvd3MoKCkgPT4gdHhCdWlsZGVyLnZhbGlkYXRlVHJhbnNhY3Rpb24oKSwgL0ludmFsaWQgdHJhbnNhY3Rpb246IHdyb25nIG51bWJlciBvZiBvd25lcnMvKTtcbiAgICAgIHR4QnVpbGRlci5zb3VyY2UodGVzdERhdGEuVkFMSURfQUREUkVTUyk7XG4gICAgICBhc3NlcnQudGhyb3dzKCgpID0+IHR4QnVpbGRlci52YWxpZGF0ZVRyYW5zYWN0aW9uKCksIC93cm9uZyBudW1iZXIgb2Ygb3duZXJzIC0tIHJlcXVpcmVkOiAzLCBmb3VuZDogMC8pO1xuICAgICAgdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMSk7XG4gICAgICBhc3NlcnQudGhyb3dzKCgpID0+IHR4QnVpbGRlci52YWxpZGF0ZVRyYW5zYWN0aW9uKCksIC93cm9uZyBudW1iZXIgb2Ygb3duZXJzIC0tIHJlcXVpcmVkOiAzLCBmb3VuZDogMS8pO1xuICAgICAgdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMik7XG4gICAgICBhc3NlcnQudGhyb3dzKCgpID0+IHR4QnVpbGRlci52YWxpZGF0ZVRyYW5zYWN0aW9uKCksIC93cm9uZyBudW1iZXIgb2Ygb3duZXJzIC0tIHJlcXVpcmVkOiAzLCBmb3VuZDogMi8pO1xuICAgICAgdHhCdWlsZGVyLm93bmVyKHRlc3REYXRhLk9XTkVSMyk7XG4gICAgICBzaG91bGQuZG9lc05vdFRocm93KCgpID0+IHR4QnVpbGRlci52YWxpZGF0ZVRyYW5zYWN0aW9uKCkpO1xuICAgIH0pO1xuICB9KTtcbn0pO1xuIl19
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=utils.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../../test/unit/utils.ts"],"names":[],"mappings":""}
@@ -0,0 +1,275 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ var __importDefault = (this && this.__importDefault) || function (mod) {
36
+ return (mod && mod.__esModule) ? mod : { "default": mod };
37
+ };
38
+ Object.defineProperty(exports, "__esModule", { value: true });
39
+ const assert_1 = __importDefault(require("assert"));
40
+ const should_1 = __importDefault(require("should"));
41
+ const stellar = __importStar(require("stellar-sdk"));
42
+ const Utils = __importStar(require("../../src/lib/utils"));
43
+ const testData = __importStar(require("../resources/hbar"));
44
+ const sdk_core_1 = require("@bitgo-beta/sdk-core");
45
+ describe('HBAR util library', function () {
46
+ describe('address', function () {
47
+ it('should validate addresses', function () {
48
+ const validAddresses = ['0', '0.0.0', '99.99.99', '0.0.41098'];
49
+ const validAddressesWithMemo = ['0.0.41098?memoId=4'];
50
+ for (const address of validAddresses) {
51
+ Utils.isValidAddress(address).should.be.true();
52
+ }
53
+ for (const address of validAddressesWithMemo) {
54
+ Utils.isValidAddress(address).should.be.true();
55
+ }
56
+ });
57
+ it('should fail to validate invalid addresses', function () {
58
+ const invalidAddresses = ['0.0', '0.0.0.0', 'abc', 'a.b.c', '', '0x23C3E227BE97281A70A549c7dDB8d5Caad3E7C84'];
59
+ const invalidAddressesWithMemo = ['0.0.41098?memoId=m?memoId=4'];
60
+ for (const address of invalidAddresses) {
61
+ should_1.default.doesNotThrow(() => Utils.isValidAddress(address));
62
+ Utils.isValidAddress(address).should.be.false();
63
+ }
64
+ for (const address of invalidAddressesWithMemo) {
65
+ should_1.default.doesNotThrow(() => Utils.isValidAddress(address));
66
+ Utils.isValidAddress(address).should.be.false();
67
+ }
68
+ });
69
+ });
70
+ describe('transaction id', function () {
71
+ it('should validate tx ids', function () {
72
+ const validHashes = ['0.0.14621@1595374723.356981689'];
73
+ for (const hash of validHashes) {
74
+ Utils.isValidTransactionId(hash).should.be.true();
75
+ }
76
+ });
77
+ it('should fail to validate invalid tx ids', function () {
78
+ const invalidHashes = ['0.0.14621', 'invalid', ''];
79
+ for (const hash of invalidHashes) {
80
+ Utils.isValidTransactionId(hash).should.be.false();
81
+ }
82
+ });
83
+ });
84
+ describe('transaction timestamp', function () {
85
+ it('should validate tx timestamps', function () {
86
+ const validTimestamps = ['1595374723.356981689', '1595374723'];
87
+ for (const timestamp of validTimestamps) {
88
+ Utils.isValidTimeString(timestamp).should.be.true();
89
+ }
90
+ });
91
+ it('should fail to validate invalid tx timestamp', function () {
92
+ const invalidTimestamp = ['0.0.14621', 'invalid', ''];
93
+ for (const timestamp of invalidTimestamp) {
94
+ Utils.isValidTimeString(timestamp).should.be.false();
95
+ }
96
+ });
97
+ });
98
+ describe('should remove prefix', function () {
99
+ it('from a private key', function () {
100
+ const rawPrivateKey = Utils.removePrefix(testData.ed25519PrivKeyPrefix, testData.ACCOUNT_1.prvKeyWithPrefix);
101
+ should_1.default.deepEqual(rawPrivateKey, '62b0b669de0ab5e91b4328e1431859a5ca47e7426e701019272f5c2d52825b01');
102
+ });
103
+ it('from a public key', function () {
104
+ const rawPublicKey = Utils.removePrefix(testData.ed25519PubKeyPrefix, testData.ACCOUNT_1.pubKeyWithPrefix);
105
+ should_1.default.deepEqual(rawPublicKey, '5a9111b5e6881ff20b9243a42ac1a9a67fa16cd4f01e58bab30c1fe611ea8cf9');
106
+ });
107
+ });
108
+ describe('should convert a stellar pub', function () {
109
+ it('and get back a valid ed pub', function () {
110
+ const stellarPub = 'GBVEZT27ZUCMJABF76XIPPO7M3KUABVR4GZNPBAD3YTPXUSDA57ANRLD';
111
+ const newPub = Utils.convertFromStellarPub(stellarPub);
112
+ should_1.default.equal((0, sdk_core_1.isValidEd25519PublicKey)(newPub), true);
113
+ });
114
+ it('and get back a specific ed pub', function () {
115
+ const stellarPub = 'GBVEZT27ZUCMJABF76XIPPO7M3KUABVR4GZNPBAD3YTPXUSDA57ANRLD';
116
+ const newPub = Utils.convertFromStellarPub(stellarPub);
117
+ newPub.should.equal('6a4ccf5fcd04c48025ffae87bddf66d54006b1e1b2d78403de26fbd243077e06');
118
+ });
119
+ it('and create a valid ed pub that can be transformed back into a stellar pub', function () {
120
+ const stellarPub = 'GBVEZT27ZUCMJABF76XIPPO7M3KUABVR4GZNPBAD3YTPXUSDA57ANRLD';
121
+ const newPub = Utils.convertFromStellarPub(stellarPub);
122
+ const stellarDecoded = stellar.StrKey.encodeEd25519PublicKey(Buffer.from(newPub, 'hex'));
123
+ const beginStellarKeyPair = stellar.Keypair.fromPublicKey(stellarPub);
124
+ const endStellarKeyPair = stellar.Keypair.fromPublicKey(stellarDecoded);
125
+ should_1.default.equal(beginStellarKeyPair.publicKey(), endStellarKeyPair.publicKey());
126
+ });
127
+ });
128
+ describe('should return the same key', function () {
129
+ it('from a private key without the prefix', function () {
130
+ const rawPrivateKey = Utils.removePrefix(testData.ed25519PrivKeyPrefix, testData.ACCOUNT_2.privateKey);
131
+ should_1.default.deepEqual(rawPrivateKey, testData.ACCOUNT_2.privateKey);
132
+ });
133
+ it('from a public key without the prefix', function () {
134
+ const rawPublicKey = Utils.removePrefix(testData.ed25519PubKeyPrefix, testData.ACCOUNT_2.publicKey);
135
+ should_1.default.deepEqual(rawPublicKey, testData.ACCOUNT_2.publicKey);
136
+ });
137
+ it('from a public key with chars of prefix in the middle', function () {
138
+ const publicKey = '592a4fbb7263c59d450e651d' + testData.ed25519PubKeyPrefix + 'f96620dc9208ee7c';
139
+ const rawPublicKey = Utils.removePrefix(testData.ed25519PubKeyPrefix, publicKey);
140
+ should_1.default.deepEqual(rawPublicKey, publicKey);
141
+ });
142
+ it('from a private key with chars of prefix in the middle', function () {
143
+ const privateKey = '5bb72603f237c099' + testData.ed25519PrivKeyPrefix + '3f7973d37fdade3c';
144
+ const rawPrivateKey = Utils.removePrefix(testData.ed25519PrivKeyPrefix, privateKey);
145
+ should_1.default.deepEqual(rawPrivateKey, privateKey);
146
+ });
147
+ });
148
+ describe('getAddressDetails', function () {
149
+ it('should get memoId and address', async function () {
150
+ const addr = '0.0.41098?memoId=23233';
151
+ const details = Utils.getAddressDetails(addr);
152
+ details.address.should.equal('0.0.41098');
153
+ details.memoId?.should.equal('23233');
154
+ });
155
+ it('should throw when memoId=null', async function () {
156
+ const addr = '0.0.41098?memoId=';
157
+ assert_1.default.throws(() => Utils.getAddressDetails(addr), /invalid address: '0.0.41098\?memoId=', memoId is not valid/);
158
+ });
159
+ it('should get memoId and address when no memoId', async function () {
160
+ const addr = '0.0.41098';
161
+ const details = Utils.getAddressDetails(addr);
162
+ details.address.should.equal('0.0.41098');
163
+ details.memoId?.should.equal(undefined);
164
+ });
165
+ });
166
+ describe('normalizeAddress', function () {
167
+ it('should build without a memoId if its missing for an address', async function () {
168
+ const address = '0.0.41098';
169
+ let memoId = undefined;
170
+ let norm = Utils.normalizeAddress({ address, memoId });
171
+ norm.should.equal('0.0.41098');
172
+ memoId = '';
173
+ norm = Utils.normalizeAddress({ address, memoId });
174
+ norm.should.equal('0.0.41098');
175
+ });
176
+ });
177
+ describe('getBaseAddress', function () {
178
+ it('should return the base address', async function () {
179
+ const addressWithMemo = '0.0.41098?memoId=1';
180
+ const baseAddress = '0.0.41098';
181
+ Utils.getBaseAddress(addressWithMemo).should.equal(baseAddress);
182
+ Utils.getBaseAddress(baseAddress).should.equal(baseAddress);
183
+ });
184
+ });
185
+ describe('isSameBaseAddress', function () {
186
+ it('should validate if base address match', async function () {
187
+ const address = '0.0.41098?memoId=1';
188
+ const baseAddress = '0.0.41098';
189
+ Utils.isSameBaseAddress(address, baseAddress).should.true();
190
+ const address2 = '0.0.41098';
191
+ const baseAddress2 = '0.0.41098';
192
+ Utils.isSameBaseAddress(address2, baseAddress2).should.true();
193
+ const address3 = '0.0.41099?memoId=1';
194
+ const baseAddress3 = '0.0.41098';
195
+ Utils.isSameBaseAddress(address3, baseAddress3).should.false();
196
+ const address4 = '0.0.41099';
197
+ const baseAddress4 = '0.0.41098';
198
+ Utils.isSameBaseAddress(address4, baseAddress4).should.false();
199
+ const address5 = '0.0.0.0';
200
+ const baseAddress5 = '0.0.41098';
201
+ assert_1.default.throws(() => Utils.isSameBaseAddress(address5, baseAddress5).should.false(), new RegExp(`invalid address: ${address5}`));
202
+ });
203
+ });
204
+ describe('isValidMemoId', function () {
205
+ it('should validate memoId', async function () {
206
+ const memo1 = 'testmemo';
207
+ Utils.isValidMemo(memo1).should.true();
208
+ const memo2 = '';
209
+ Utils.isValidMemo(memo2).should.false();
210
+ const memo3 = undefined;
211
+ // @ts-expect-error testing for error
212
+ Utils.isValidMemo(memo3).should.false();
213
+ const memo4 = 'memoooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo';
214
+ Utils.isValidMemo(memo4).should.false();
215
+ });
216
+ });
217
+ describe('isValidAddressWithPaymentId', function () {
218
+ it('should validate addresses with and without payment id', function () {
219
+ const validAddresses = ['0', '0.0.0', '99.99.99', '0.0.41098', '0.0.41098?memoId=4'];
220
+ for (const address of validAddresses) {
221
+ Utils.isValidAddressWithPaymentId(address).should.be.true();
222
+ }
223
+ });
224
+ it('should fail to validate invalid addresses', function () {
225
+ const invalidAddresses = [
226
+ '0.0.41098?memoId=memooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo',
227
+ '0.0.41098?memoId=',
228
+ '0.0',
229
+ '0.0.0.0',
230
+ 'abc',
231
+ 'a.b.c',
232
+ '',
233
+ '0x23C3E227BE97281A70A549c7dDB8d5Caad3E7C84',
234
+ ];
235
+ for (const address of invalidAddresses) {
236
+ Utils.isValidAddressWithPaymentId(address).should.be.false();
237
+ }
238
+ });
239
+ });
240
+ describe('shouldBroadcastNow', function () {
241
+ const getTimestampInSeconds = (secondsToChange = 0) => (Date.now() / 1000 + secondsToChange).toFixed();
242
+ it('should return true if the timestamp is in the valid time window', function () {
243
+ const timestamp = getTimestampInSeconds(-6);
244
+ Utils.shouldBroadcastNow(timestamp).should.be.true();
245
+ const timestamp2 = getTimestampInSeconds(-173);
246
+ Utils.shouldBroadcastNow(timestamp2).should.be.true();
247
+ });
248
+ it('should throw if the timestamp is in the past', function () {
249
+ const timestamp = getTimestampInSeconds(-1000);
250
+ assert_1.default.throws(() => Utils.shouldBroadcastNow(timestamp), (error) => {
251
+ assert_1.default.ok(error.message.includes('startTime window expired'));
252
+ return true;
253
+ });
254
+ });
255
+ it('should return false if the timestamp is in the future', function () {
256
+ const timestamp = getTimestampInSeconds(1000);
257
+ Utils.shouldBroadcastNow(timestamp).should.be.false();
258
+ });
259
+ });
260
+ describe('normalizeStarttime', function () {
261
+ it('should return the same timestamp', function () {
262
+ const timestamp = '1595374723.356981689';
263
+ Utils.normalizeStarttime(timestamp).should.equal(timestamp);
264
+ });
265
+ it('should return the timestamp with nanoseconds', function () {
266
+ const timestamp = '1595374723';
267
+ Utils.normalizeStarttime(timestamp).should.equal(timestamp + '.000000000');
268
+ });
269
+ it('should return the timestamp with nanoseconds', function () {
270
+ const timestamp = '1595374723.0145';
271
+ Utils.normalizeStarttime(timestamp).should.equal(timestamp + '00000');
272
+ });
273
+ });
274
+ });
275
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidXRpbHMuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi90ZXN0L3VuaXQvdXRpbHMudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBQSxvREFBNEI7QUFDNUIsb0RBQTRCO0FBQzVCLHFEQUF1QztBQUN2QywyREFBNkM7QUFDN0MsNERBQThDO0FBQzlDLG1EQUErRDtBQUUvRCxRQUFRLENBQUMsbUJBQW1CLEVBQUU7SUFDNUIsUUFBUSxDQUFDLFNBQVMsRUFBRTtRQUNsQixFQUFFLENBQUMsMkJBQTJCLEVBQUU7WUFDOUIsTUFBTSxjQUFjLEdBQUcsQ0FBQyxHQUFHLEVBQUUsT0FBTyxFQUFFLFVBQVUsRUFBRSxXQUFXLENBQUMsQ0FBQztZQUMvRCxNQUFNLHNCQUFzQixHQUFHLENBQUMsb0JBQW9CLENBQUMsQ0FBQztZQUV0RCxLQUFLLE1BQU0sT0FBTyxJQUFJLGNBQWMsRUFBRSxDQUFDO2dCQUNyQyxLQUFLLENBQUMsY0FBYyxDQUFDLE9BQU8sQ0FBQyxDQUFDLE1BQU0sQ0FBQyxFQUFFLENBQUMsSUFBSSxFQUFFLENBQUM7WUFDakQsQ0FBQztZQUVELEtBQUssTUFBTSxPQUFPLElBQUksc0JBQXNCLEVBQUUsQ0FBQztnQkFDN0MsS0FBSyxDQUFDLGNBQWMsQ0FBQyxPQUFPLENBQUMsQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDLElBQUksRUFBRSxDQUFDO1lBQ2pELENBQUM7UUFDSCxDQUFDLENBQUMsQ0FBQztRQUVILEVBQUUsQ0FBQywyQ0FBMkMsRUFBRTtZQUM5QyxNQUFNLGdCQUFnQixHQUFHLENBQUMsS0FBSyxFQUFFLFNBQVMsRUFBRSxLQUFLLEVBQUUsT0FBTyxFQUFFLEVBQUUsRUFBRSw0Q0FBNEMsQ0FBQyxDQUFDO1lBQzlHLE1BQU0sd0JBQXdCLEdBQUcsQ0FBQyw2QkFBNkIsQ0FBQyxDQUFDO1lBRWpFLEtBQUssTUFBTSxPQUFPLElBQUksZ0JB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RixDQUFDO1FBQ0osQ0FBQyxDQUFDLENBQUM7UUFFSCxFQUFFLENBQUMsdURBQXVELEVBQUU7WUFDMUQsTUFBTSxTQUFTLEdBQUcscUJBQXFCLENBQUMsSUFBSSxDQUFDLENBQUM7WUFDOUMsS0FBSyxDQUFDLGtCQUFrQixDQUFDLFNBQVMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxFQUFFLENBQUMsS0FBSyxFQUFFLENBQUM7UUFDeEQsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDLENBQUMsQ0FBQztJQUVILFFBQVEsQ0FBQyxvQkFBb0IsRUFBRTtRQUM3QixFQUFFLENBQUMsa0NBQWtDLEVBQUU7WUFDckMsTUFBTSxTQUFTLEdBQUcsc0JBQXNCLENBQUM7WUFDekMsS0FBSyxDQUFDLGtCQUFrQixDQUFDLFNBQVMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxLQUFLLENBQUMsU0FBUyxDQUFDLENBQUM7UUFDOUQsQ0FBQyxDQUFDLENBQUM7UUFFSCxFQUFFLENBQUMsOENBQThDLEVBQUU7WUFDakQsTUFBTSxTQUFTLEdBQUcsWUFBWSxDQUFDO1lBQy9CLEtBQUssQ0FBQyxrQkFBa0IsQ0FBQyxTQUFTLENBQUMsQ0FBQyxNQUFNLENBQUMsS0FBSyxDQUFDLFNBQVMsR0FBRyxZQUFZLENBQUMsQ0FBQztRQUM3RSxDQUFDLENBQUMsQ0FBQztRQUVILEVBQUUsQ0FBQyw4Q0FBOEMsRUFBRTtZQUNqRCxNQUFNLFNBQVMsR0FBRyxpQkFBaUIsQ0FBQztZQUNwQyxLQUFLLENBQUMsa0JBQWtCLENBQUMsU0FBUyxDQUFDLENBQUMsTUFBTSxDQUFDLEtBQUssQ0FBQyxTQUFTLEdBQUcsT0FBTyxDQUFDLENBQUM7UUFDeEUsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDLENBQUMsQ0FBQztBQUNMLENBQUMsQ0FBQyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IGFzc2VydCBmcm9tICdhc3NlcnQnO1xuaW1wb3J0IHNob3VsZCBmcm9tICdzaG91bGQnO1xuaW1wb3J0ICogYXMgc3RlbGxhciBmcm9tICdzdGVsbGFyLXNkayc7XG5pbXBvcnQgKiBhcyBVdGlscyBmcm9tICcuLi8uLi9zcmMvbGliL3V0aWxzJztcbmltcG9ydCAqIGFzIHRlc3REYXRhIGZyb20gJy4uL3Jlc291cmNlcy9oYmFyJztcbmltcG9ydCB7IGlzVmFsaWRFZDI1NTE5UHVibGljS2V5IH0gZnJvbSAnQGJpdGdvLWJldGEvc2RrLWNvcmUnO1xuXG5kZXNjcmliZSgnSEJBUiB1dGlsIGxpYnJhcnknLCBmdW5jdGlvbiAoKSB7XG4gIGRlc2NyaWJlKCdhZGRyZXNzJywgZnVuY3Rpb24gKCkge1xuICAgIGl0KCdzaG91bGQgdmFsaWRhdGUgYWRkcmVzc2VzJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgdmFsaWRBZGRyZXNzZXMgPSBbJzAnLCAnMC4wLjAnLCAnOTkuOTkuOTknLCAnMC4wLjQxMDk4J107XG4gICAgICBjb25zdCB2YWxpZEFkZHJlc3Nlc1dpdGhNZW1vID0gWycwLjAuNDEwOTg/bWVtb0lkPTQnXTtcblxuICAgICAgZm9yIChjb25zdCBhZGRyZXNzIG9mIHZhbGlkQWRkcmVzc2VzKSB7XG4gICAgICAgIFV0aWxzLmlzVmFsaWRBZGRyZXNzKGFkZHJlc3MpLnNob3VsZC5iZS50cnVlKCk7XG4gICAgICB9XG5cbiAgICAgIGZvciAoY29uc3QgYWRkcmVzcyBvZiB2YWxpZEFkZHJlc3Nlc1dpdGhNZW1vKSB7XG4gICAgICAgIFV0aWxzLmlzVmFsaWRBZGRyZXNzKGFkZHJlc3MpLnNob3VsZC5iZS50cnVlKCk7XG4gICAgICB9XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGZhaWwgdG8gdmFsaWRhdGUgaW52YWxpZCBhZGRyZXNzZXMnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBpbnZhbGlkQWRkcmVzc2VzID0gWycwLjAnLCAnMC4wLjAuMCcsICdhYmMnLCAnYS5iLmMnLCAnJywgJzB4MjNDM0UyMjdCRTk3MjgxQTcwQTU0OWM3ZERCOGQ1Q2FhZDNFN0M4NCddO1xuICAgICAgY29uc3QgaW52YWxpZEFkZHJlc3Nlc1dpdGhNZW1vID0gWycwLjAuNDEwOTg/bWVtb0lkPW0/bWVtb0lkPTQnXTtcblxuICAgICAgZm9yIChjb25zdCBhZGRyZXNzIG9mIGludmFsaWRBZGRyZXNzZXMpIHtcbiAgICAgICAgc2hvdWxkLmRvZXNOb3RUaHJvdygoKSA9PiBVdGlscy5pc1ZhbGlkQWRkcmVzcyhhZGRyZXNzKSk7XG4gICAgICAgIFV0aWxzLmlzVmFsaWRBZGRyZXNzKGFkZHJlc3MpLnNob3VsZC5iZS5mYWxzZSgpO1xuICAgICAgfVxuXG4gICAgICBmb3IgKGNvbnN0IGFkZHJlc3Mgb2YgaW52YWxpZEFkZHJlc3Nlc1dpdGhNZW1vKSB7XG4gICAgICAgIHNob3VsZC5kb2VzTm90VGhyb3coKCkgPT4gVXRpbHMuaXNWYWxpZEFkZHJlc3MoYWRkcmVzcykpO1xuICAgICAgICBVdGlscy5pc1ZhbGlkQWRkcmVzcyhhZGRyZXNzKS5zaG91bGQuYmUuZmFsc2UoKTtcbiAgICAgIH1cbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ3RyYW5zYWN0aW9uIGlkJywgZnVuY3Rpb24gKCkge1xuICAgIGl0KCdzaG91bGQgdmFsaWRhdGUgdHggaWRzJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgdmFsaWRIYXNoZXMgPSBbJzAuMC4xNDYyMUAxNTk1Mzc0NzIzLjM1Njk4MTY4OSddO1xuXG4gICAgICBmb3IgKGNvbnN0IGhhc2ggb2YgdmFsaWRIYXNoZXMpIHtcbiAgICAgICAgVXRpbHMuaXNWYWxpZFRyYW5zYWN0aW9uSWQoaGFzaCkuc2hvdWxkLmJlLnRydWUoKTtcbiAgICAgIH1cbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZmFpbCB0byB2YWxpZGF0ZSBpbnZhbGlkIHR4IGlkcycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IGludmFsaWRIYXNoZXMgPSBbJzAuMC4xNDYyMScsICdpbnZhbGlkJywgJyddO1xuXG4gICAgICBmb3IgKGNvbnN0IGhhc2ggb2YgaW52YWxpZEhhc2hlcykge1xuICAgICAgICBVdGlscy5pc1ZhbGlkVHJhbnNhY3Rpb25JZChoYXNoKS5zaG91bGQuYmUuZmFsc2UoKTtcbiAgICAgIH1cbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ3RyYW5zYWN0aW9uIHRpbWVzdGFtcCcsIGZ1bmN0aW9uICgpIHtcbiAgICBpdCgnc2hvdWxkIHZhbGlkYXRlIHR4IHRpbWVzdGFtcHMnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCB2YWxpZFRpbWVzdGFtcHMgPSBbJzE1OTUzNzQ3MjMuMzU2OTgxNjg5JywgJzE1OTUzNzQ3MjMnXTtcblxuICAgICAgZm9yIChjb25zdCB0aW1lc3RhbXAgb2YgdmFsaWRUaW1lc3RhbXBzKSB7XG4gICAgICAgIFV0aWxzLmlzVmFsaWRUaW1lU3RyaW5nKHRpbWVzdGFtcCkuc2hvdWxkLmJlLnRydWUoKTtcbiAgICAgIH1cbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgZmFpbCB0byB2YWxpZGF0ZSBpbnZhbGlkIHR4IHRpbWVzdGFtcCcsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IGludmFsaWRUaW1lc3RhbXAgPSBbJzAuMC4xNDYyMScsICdpbnZhbGlkJywgJyddO1xuXG4gICAgICBmb3IgKGNvbnN0IHRpbWVzdGFtcCBvZiBpbnZhbGlkVGltZXN0YW1wKSB7XG4gICAgICAgIFV0aWxzLmlzVmFsaWRUaW1lU3RyaW5nKHRpbWVzdGFtcCkuc2hvdWxkLmJlLmZhbHNlKCk7XG4gICAgICB9XG4gICAgfSk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdzaG91bGQgcmVtb3ZlIHByZWZpeCcsIGZ1bmN0aW9uICgpIHtcbiAgICBpdCgnZnJvbSBhIHByaXZhdGUga2V5JywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgcmF3UHJpdmF0ZUtleSA9IFV0aWxzLnJlbW92ZVByZWZpeCh0ZXN0RGF0YS5lZDI1NTE5UHJpdktleVByZWZpeCwgdGVzdERhdGEuQUNDT1VOVF8xLnBydktleVdpdGhQcmVmaXgpO1xuICAgICAgc2hvdWxkLmRlZXBFcXVhbChyYXdQcml2YXRlS2V5LCAnNjJiMGI2NjlkZTBhYjVlOTFiNDMyOGUxNDMxODU5YTVjYTQ3ZTc0MjZlNzAxMDE5MjcyZjVjMmQ1MjgyNWIwMScpO1xuICAgIH0pO1xuXG4gICAgaXQoJ2Zyb20gYSBwdWJsaWMga2V5JywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgcmF3UHVibGljS2V5ID0gVXRpbHMucmVtb3ZlUHJlZml4KHRlc3REYXRhLmVkMjU1MTlQdWJLZXlQcmVmaXgsIHRlc3REYXRhLkFDQ09VTlRfMS5wdWJLZXlXaXRoUHJlZml4KTtcbiAgICAgIHNob3VsZC5kZWVwRXF1YWwocmF3UHVibGljS2V5LCAnNWE5MTExYjVlNjg4MWZmMjBiOTI0M2E0MmFjMWE5YTY3ZmExNmNkNGYwMWU1OGJhYjMwYzFmZTYxMWVhOGNmOScpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnc2hvdWxkIGNvbnZlcnQgYSBzdGVsbGFyIHB1YicsIGZ1bmN0aW9uICgpIHtcbiAgICBpdCgnYW5kIGdldCBiYWNrIGEgdmFsaWQgZWQgcHViJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3Qgc3RlbGxhclB1YiA9ICdHQlZFWlQyN1pVQ01KQUJGNzZYSVBQTzdNM0tVQUJWUjRHWk5QQkFEM1lUUFhVU0RBNTdBTlJMRCc7XG4gICAgICBjb25zdCBuZXdQdWIgPSBVdGlscy5jb252ZXJ0RnJvbVN0ZWxsYXJQdWIoc3RlbGxhclB1Yik7XG4gICAgICBzaG91bGQuZXF1YWwoaXNWYWxpZEVkMjU1MTlQdWJsaWNLZXkobmV3UHViKSwgdHJ1ZSk7XG4gICAgfSk7XG5cbiAgICBpdCgnYW5kIGdldCBiYWNrIGEgc3BlY2lmaWMgZWQgcHViJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3Qgc3RlbGxhclB1YiA9ICdHQlZFWlQyN1pVQ01KQUJGNzZYSVBQTzdNM0tVQUJWUjRHWk5QQkFEM1lUUFhVU0RBNTdBTlJMRCc7XG4gICAgICBjb25zdCBuZXdQdWIgPSBVdGlscy5jb252ZXJ0RnJvbVN0ZWxsYXJQdWIoc3RlbGxhclB1Yik7XG4gICAgICBuZXdQdWIuc2hvdWxkLmVxdWFsKCc2YTRjY2Y1ZmNkMDRjNDgwMjVmZmFlODdiZGRmNjZkNTQwMDZiMWUxYjJkNzg0MDNkZTI2ZmJkMjQzMDc3ZTA2Jyk7XG4gICAgfSk7XG5cbiAgICBpdCgnYW5kIGNyZWF0ZSBhIHZhbGlkIGVkIHB1YiB0aGF0IGNhbiBiZSB0cmFuc2Zvcm1lZCBiYWNrIGludG8gYSBzdGVsbGFyIHB1YicsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHN0ZWxsYXJQdWIgPSAnR0JWRVpUMjdaVUNNSkFCRjc2WElQUE83TTNLVUFCVlI0R1pOUEJBRDNZVFBYVVNEQTU3QU5STEQnO1xuXG4gICAgICBjb25zdCBuZXdQdWIgPSBVdGlscy5jb252ZXJ0RnJvbVN0ZWxsYXJQdWIoc3RlbGxhclB1Yik7XG4gICAgICBjb25zdCBzdGVsbGFyRGVjb2RlZCA9IHN0ZWxsYXIuU3RyS2V5LmVuY29kZUVkMjU1MTlQdWJsaWNLZXkoQnVmZmVyLmZyb20obmV3UHViLCAnaGV4JykpO1xuICAgICAgY29uc3QgYmVnaW5TdGVsbGFyS2V5UGFpciA9IHN0ZWxsYXIuS2V5cGFpci5mcm9tUHVibGljS2V5KHN0ZWxsYXJQdWIpO1xuICAgICAgY29uc3QgZW5kU3RlbGxhcktleVBhaXIgPSBzdGVsbGFyLktleXBhaXIuZnJvbVB1YmxpY0tleShzdGVsbGFyRGVjb2RlZCk7XG5cbiAgICAgIHNob3VsZC5lcXVhbChiZWdpblN0ZWxsYXJLZXlQYWlyLnB1YmxpY0tleSgpLCBlbmRTdGVsbGFyS2V5UGFpci5wdWJsaWNLZXkoKSk7XG4gICAgfSk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdzaG91bGQgcmV0dXJuIHRoZSBzYW1lIGtleScsIGZ1bmN0aW9uICgpIHtcbiAgICBpdCgnZnJvbSBhIHByaXZhdGUga2V5IHdpdGhvdXQgdGhlIHByZWZpeCcsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHJhd1ByaXZhdGVLZXkgPSBVdGlscy5yZW1vdmVQcmVmaXgodGVzdERhdGEuZWQyNTUxOVByaXZLZXlQcmVmaXgsIHRlc3REYXRhLkFDQ09VTlRfMi5wcml2YXRlS2V5KTtcbiAgICAgIHNob3VsZC5kZWVwRXF1YWwocmF3UHJpdmF0ZUtleSwgdGVzdERhdGEuQUNDT1VOVF8yLnByaXZhdGVLZXkpO1xuICAgIH0pO1xuXG4gICAgaXQoJ2Zyb20gYSBwdWJsaWMga2V5IHdpdGhvdXQgdGhlIHByZWZpeCcsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHJhd1B1YmxpY0tleSA9IFV0aWxzLnJlbW92ZVByZWZpeCh0ZXN0RGF0YS5lZDI1NTE5UHViS2V5UHJlZml4LCB0ZXN0RGF0YS5BQ0NPVU5UXzIucHVibGljS2V5KTtcbiAgICAgIHNob3VsZC5kZWVwRXF1YWwocmF3UHVibGljS2V5LCB0ZXN0RGF0YS5BQ0NPVU5UXzIucHVibGljS2V5KTtcbiAgICB9KTtcblxuICAgIGl0KCdmcm9tIGEgcHVibGljIGtleSB3aXRoIGNoYXJzIG9mIHByZWZpeCBpbiB0aGUgbWlkZGxlJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgcHVibGljS2V5ID0gJzU5MmE0ZmJiNzI2M2M1OWQ0NTBlNjUxZCcgKyB0ZXN0RGF0YS5lZDI1NTE5UHViS2V5UHJlZml4ICsgJ2Y5NjYyMGRjOTIwOGVlN2MnO1xuICAgICAgY29uc3QgcmF3UHVibGljS2V5ID0gVXRpbHMucmVtb3ZlUHJlZml4KHRlc3REYXRhLmVkMjU1MTlQdWJLZXlQcmVmaXgsIHB1YmxpY0tleSk7XG4gICAgICBzaG91bGQuZGVlcEVxdWFsKHJhd1B1YmxpY0tleSwgcHVibGljS2V5KTtcbiAgICB9KTtcblxuICAgIGl0KCdmcm9tIGEgcHJpdmF0ZSBrZXkgd2l0aCBjaGFycyBvZiBwcmVmaXggaW4gdGhlIG1pZGRsZScsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHByaXZhdGVLZXkgPSAnNWJiNzI2MDNmMjM3YzA5OScgKyB0ZXN0RGF0YS5lZDI1NTE5UHJpdktleVByZWZpeCArICczZjc5NzNkMzdmZGFkZTNjJztcbiAgICAgIGNvbnN0IHJhd1ByaXZhdGVLZXkgPSBVdGlscy5yZW1vdmVQcmVmaXgodGVzdERhdGEuZWQyNTUxOVByaXZLZXlQcmVmaXgsIHByaXZhdGVLZXkpO1xuICAgICAgc2hvdWxkLmRlZXBFcXVhbChyYXdQcml2YXRlS2V5LCBwcml2YXRlS2V5KTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ2dldEFkZHJlc3NEZXRhaWxzJywgZnVuY3Rpb24gKCkge1xuICAgIGl0KCdzaG91bGQgZ2V0IG1lbW9JZCBhbmQgYWRkcmVzcycsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IGFkZHIgPSAnMC4wLjQxMDk4P21lbW9JZD0yMzIzMyc7XG4gICAgICBjb25zdCBkZXRhaWxzID0gVXRpbHMuZ2V0QWRkcmVzc0RldGFpbHMoYWRkcik7XG5cbiAgICAgIGRldGFpbHMuYWRkcmVzcy5zaG91bGQuZXF1YWwoJzAuMC40MTA5OCcpO1xuICAgICAgZGV0YWlscy5tZW1vSWQ/LnNob3VsZC5lcXVhbCgnMjMyMzMnKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgdGhyb3cgd2hlbiBtZW1vSWQ9bnVsbCcsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IGFkZHIgPSAnMC4wLjQxMDk4P21lbW9JZD0nO1xuICAgICAgYXNzZXJ0LnRocm93cygoKSA9PiBVdGlscy5nZXRBZGRyZXNzRGV0YWlscyhhZGRyKSwgL2ludmFsaWQgYWRkcmVzczogJzAuMC40MTA5OFxcP21lbW9JZD0nLCBtZW1vSWQgaXMgbm90IHZhbGlkLyk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIGdldCBtZW1vSWQgYW5kIGFkZHJlc3Mgd2hlbiBubyBtZW1vSWQnLCBhc3luYyBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBhZGRyID0gJzAuMC40MTA5OCc7XG4gICAgICBjb25zdCBkZXRhaWxzID0gVXRpbHMuZ2V0QWRkcmVzc0RldGFpbHMoYWRkcik7XG5cbiAgICAgIGRldGFpbHMuYWRkcmVzcy5zaG91bGQuZXF1YWwoJzAuMC40MTA5OCcpO1xuICAgICAgZGV0YWlscy5tZW1vSWQ/LnNob3VsZC5lcXVhbCh1bmRlZmluZWQpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnbm9ybWFsaXplQWRkcmVzcycsIGZ1bmN0aW9uICgpIHtcbiAgICBpdCgnc2hvdWxkIGJ1aWxkIHdpdGhvdXQgYSBtZW1vSWQgaWYgaXRzIG1pc3NpbmcgZm9yIGFuIGFkZHJlc3MnLCBhc3luYyBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBhZGRyZXNzID0gJzAuMC40MTA5OCc7XG4gICAgICBsZXQgbWVtb0lkOiBzdHJpbmcgfCB1bmRlZmluZWQgPSB1bmRlZmluZWQ7XG4gICAgICBsZXQgbm9ybSA9IFV0aWxzLm5vcm1hbGl6ZUFkZHJlc3MoeyBhZGRyZXNzLCBtZW1vSWQgfSk7XG4gICAgICBub3JtLnNob3VsZC5lcXVhbCgnMC4wLjQxMDk4Jyk7XG4gICAgICBtZW1vSWQgPSAnJztcbiAgICAgIG5vcm0gPSBVdGlscy5ub3JtYWxpemVBZGRyZXNzKHsgYWRkcmVzcywgbWVtb0lkIH0pO1xuICAgICAgbm9ybS5zaG91bGQuZXF1YWwoJzAuMC40MTA5OCcpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnZ2V0QmFzZUFkZHJlc3MnLCBmdW5jdGlvbiAoKSB7XG4gICAgaXQoJ3Nob3VsZCByZXR1cm4gdGhlIGJhc2UgYWRkcmVzcycsIGFzeW5jIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IGFkZHJlc3NXaXRoTWVtbyA9ICcwLjAuNDEwOTg/bWVtb0lkPTEnO1xuICAgICAgY29uc3QgYmFzZUFkZHJlc3MgPSAnMC4wLjQxMDk4JztcbiAgICAgIFV0aWxzLmdldEJhc2VBZGRyZXNzKGFkZHJlc3NXaXRoTWVtbykuc2hvdWxkLmVxdWFsKGJhc2VBZGRyZXNzKTtcbiAgICAgIFV0aWxzLmdldEJhc2VBZGRyZXNzKGJhc2VBZGRyZXNzKS5zaG91bGQuZXF1YWwoYmFzZUFkZHJlc3MpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnaXNTYW1lQmFzZUFkZHJlc3MnLCBmdW5jdGlvbiAoKSB7XG4gICAgaXQoJ3Nob3VsZCB2YWxpZGF0ZSBpZiBiYXNlIGFkZHJlc3MgbWF0Y2gnLCBhc3luYyBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCBhZGRyZXNzID0gJzAuMC40MTA5OD9tZW1vSWQ9MSc7XG4gICAgICBjb25zdCBiYXNlQWRkcmVzcyA9ICcwLjAuNDEwOTgnO1xuICAgICAgVXRpbHMuaXNTYW1lQmFzZUFkZHJlc3MoYWRkcmVzcywgYmFzZUFkZHJlc3MpLnNob3VsZC50cnVlKCk7XG5cbiAgICAgIGNvbnN0IGFkZHJlc3MyID0gJzAuMC40MTA5OCc7XG4gICAgICBjb25zdCBiYXNlQWRkcmVzczIgPSAnMC4wLjQxMDk4JztcbiAgICAgIFV0aWxzLmlzU2FtZUJhc2VBZGRyZXNzKGFkZHJlc3MyLCBiYXNlQWRkcmVzczIpLnNob3VsZC50cnVlKCk7XG5cbiAgICAgIGNvbnN0IGFkZHJlc3MzID0gJzAuMC40MTA5OT9tZW1vSWQ9MSc7XG4gICAgICBjb25zdCBiYXNlQWRkcmVzczMgPSAnMC4wLjQxMDk4JztcbiAgICAgIFV0aWxzLmlzU2FtZUJhc2VBZGRyZXNzKGFkZHJlc3MzLCBiYXNlQWRkcmVzczMpLnNob3VsZC5mYWxzZSgpO1xuXG4gICAgICBjb25zdCBhZGRyZXNzNCA9ICcwLjAuNDEwOTknO1xuICAgICAgY29uc3QgYmFzZUFkZHJlc3M0ID0gJzAuMC40MTA5OCc7XG4gICAgICBVdGlscy5pc1NhbWVCYXNlQWRkcmVzcyhhZGRyZXNzNCwgYmFzZUFkZHJlc3M0KS5zaG91bGQuZmFsc2UoKTtcblxuICAgICAgY29uc3QgYWRkcmVzczUgPSAnMC4wLjAuMCc7XG4gICAgICBjb25zdCBiYXNlQWRkcmVzczUgPSAnMC4wLjQxMDk4JztcbiAgICAgIGFzc2VydC50aHJvd3MoXG4gICAgICAgICgpID0+IFV0aWxzLmlzU2FtZUJhc2VBZGRyZXNzKGFkZHJlc3M1LCBiYXNlQWRkcmVzczUpLnNob3VsZC5mYWxzZSgpLFxuICAgICAgICBuZXcgUmVnRXhwKGBpbnZhbGlkIGFkZHJlc3M6ICR7YWRkcmVzczV9YClcbiAgICAgICk7XG4gICAgfSk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdpc1ZhbGlkTWVtb0lkJywgZnVuY3Rpb24gKCkge1xuICAgIGl0KCdzaG91bGQgdmFsaWRhdGUgbWVtb0lkJywgYXN5bmMgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgbWVtbzEgPSAndGVzdG1lbW8nO1xuICAgICAgVXRpbHMuaXNWYWxpZE1lbW8obWVtbzEpLnNob3VsZC50cnVlKCk7XG4gICAgICBjb25zdCBtZW1vMiA9ICcnO1xuICAgICAgVXRpbHMuaXNWYWxpZE1lbW8obWVtbzIpLnNob3VsZC5mYWxzZSgpO1xuICAgICAgY29uc3QgbWVtbzMgPSB1bmRlZmluZWQ7XG4gICAgICAvLyBAdHMtZXhwZWN0LWVycm9yIHRlc3RpbmcgZm9yIGVycm9yXG4gICAgICBVdGlscy5pc1ZhbGlkTWVtbyhtZW1vMykuc2hvdWxkLmZhbHNlKCk7XG4gICAgICBjb25zdCBtZW1vNCA9XG4gICAgICAgICdtZW1vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb28nO1xuICAgICAgVXRpbHMuaXNWYWxpZE1lbW8obWVtbzQpLnNob3VsZC5mYWxzZSgpO1xuICAgIH0pO1xuICB9KTtcblxuICBkZXNjcmliZSgnaXNWYWxpZEFkZHJlc3NXaXRoUGF5bWVudElkJywgZnVuY3Rpb24gKCkge1xuICAgIGl0KCdzaG91bGQgdmFsaWRhdGUgYWRkcmVzc2VzIHdpdGggYW5kIHdpdGhvdXQgcGF5bWVudCBpZCcsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHZhbGlkQWRkcmVzc2VzID0gWycwJywgJzAuMC4wJywgJzk5Ljk5Ljk5JywgJzAuMC40MTA5OCcsICcwLjAuNDEwOTg/bWVtb0lkPTQnXTtcblxuICAgICAgZm9yIChjb25zdCBhZGRyZXNzIG9mIHZhbGlkQWRkcmVzc2VzKSB7XG4gICAgICAgIFV0aWxzLmlzVmFsaWRBZGRyZXNzV2l0aFBheW1lbnRJZChhZGRyZXNzKS5zaG91bGQuYmUudHJ1ZSgpO1xuICAgICAgfVxuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCBmYWlsIHRvIHZhbGlkYXRlIGludmFsaWQgYWRkcmVzc2VzJywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgaW52YWxpZEFkZHJlc3NlcyA9IFtcbiAgICAgICAgJzAuMC40MTA5OD9tZW1vSWQ9bWVtb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vb29vbycsXG4gICAgICAgICcwLjAuNDEwOTg/bWVtb0lkPScsXG4gICAgICAgICcwLjAnLFxuICAgICAgICAnMC4wLjAuMCcsXG4gICAgICAgICdhYmMnLFxuICAgICAgICAnYS5iLmMnLFxuICAgICAgICAnJyxcbiAgICAgICAgJzB4MjNDM0UyMjdCRTk3MjgxQTcwQTU0OWM3ZERCOGQ1Q2FhZDNFN0M4NCcsXG4gICAgICBdO1xuXG4gICAgICBmb3IgKGNvbnN0IGFkZHJlc3Mgb2YgaW52YWxpZEFkZHJlc3Nlcykge1xuICAgICAgICBVdGlscy5pc1ZhbGlkQWRkcmVzc1dpdGhQYXltZW50SWQoYWRkcmVzcykuc2hvdWxkLmJlLmZhbHNlKCk7XG4gICAgICB9XG4gICAgfSk7XG4gIH0pO1xuXG4gIGRlc2NyaWJlKCdzaG91bGRCcm9hZGNhc3ROb3cnLCBmdW5jdGlvbiAoKSB7XG4gICAgY29uc3QgZ2V0VGltZXN0YW1wSW5TZWNvbmRzID0gKHNlY29uZHNUb0NoYW5nZSA9IDApID0+IChEYXRlLm5vdygpIC8gMTAwMCArIHNlY29uZHNUb0NoYW5nZSkudG9GaXhlZCgpO1xuICAgIGl0KCdzaG91bGQgcmV0dXJuIHRydWUgaWYgdGhlIHRpbWVzdGFtcCBpcyBpbiB0aGUgdmFsaWQgdGltZSB3aW5kb3cnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCB0aW1lc3RhbXAgPSBnZXRUaW1lc3RhbXBJblNlY29uZHMoLTYpO1xuICAgICAgVXRpbHMuc2hvdWxkQnJvYWRjYXN0Tm93KHRpbWVzdGFtcCkuc2hvdWxkLmJlLnRydWUoKTtcblxuICAgICAgY29uc3QgdGltZXN0YW1wMiA9IGdldFRpbWVzdGFtcEluU2Vjb25kcygtMTczKTtcbiAgICAgIFV0aWxzLnNob3VsZEJyb2FkY2FzdE5vdyh0aW1lc3RhbXAyKS5zaG91bGQuYmUudHJ1ZSgpO1xuICAgIH0pO1xuXG4gICAgaXQoJ3Nob3VsZCB0aHJvdyBpZiB0aGUgdGltZXN0YW1wIGlzIGluIHRoZSBwYXN0JywgZnVuY3Rpb24gKCkge1xuICAgICAgY29uc3QgdGltZXN0YW1wID0gZ2V0VGltZXN0YW1wSW5TZWNvbmRzKC0xMDAwKTtcbiAgICAgIGFzc2VydC50aHJvd3MoXG4gICAgICAgICgpID0+IFV0aWxzLnNob3VsZEJyb2FkY2FzdE5vdyh0aW1lc3RhbXApLFxuICAgICAgICAoZXJyb3I6IGFueSkgPT4ge1xuICAgICAgICAgIGFzc2VydC5vayhlcnJvci5tZXNzYWdlLmluY2x1ZGVzKCdzdGFydFRpbWUgd2luZG93IGV4cGlyZWQnKSk7XG4gICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIH1cbiAgICAgICk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHJldHVybiBmYWxzZSBpZiB0aGUgdGltZXN0YW1wIGlzIGluIHRoZSBmdXR1cmUnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCB0aW1lc3RhbXAgPSBnZXRUaW1lc3RhbXBJblNlY29uZHMoMTAwMCk7XG4gICAgICBVdGlscy5zaG91bGRCcm9hZGNhc3ROb3codGltZXN0YW1wKS5zaG91bGQuYmUuZmFsc2UoKTtcbiAgICB9KTtcbiAgfSk7XG5cbiAgZGVzY3JpYmUoJ25vcm1hbGl6ZVN0YXJ0dGltZScsIGZ1bmN0aW9uICgpIHtcbiAgICBpdCgnc2hvdWxkIHJldHVybiB0aGUgc2FtZSB0aW1lc3RhbXAnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCB0aW1lc3RhbXAgPSAnMTU5NTM3NDcyMy4zNTY5ODE2ODknO1xuICAgICAgVXRpbHMubm9ybWFsaXplU3RhcnR0aW1lKHRpbWVzdGFtcCkuc2hvdWxkLmVxdWFsKHRpbWVzdGFtcCk7XG4gICAgfSk7XG5cbiAgICBpdCgnc2hvdWxkIHJldHVybiB0aGUgdGltZXN0YW1wIHdpdGggbmFub3NlY29uZHMnLCBmdW5jdGlvbiAoKSB7XG4gICAgICBjb25zdCB0aW1lc3RhbXAgPSAnMTU5NTM3NDcyMyc7XG4gICAgICBVdGlscy5ub3JtYWxpemVTdGFydHRpbWUodGltZXN0YW1wKS5zaG91bGQuZXF1YWwodGltZXN0YW1wICsgJy4wMDAwMDAwMDAnKTtcbiAgICB9KTtcblxuICAgIGl0KCdzaG91bGQgcmV0dXJuIHRoZSB0aW1lc3RhbXAgd2l0aCBuYW5vc2Vjb25kcycsIGZ1bmN0aW9uICgpIHtcbiAgICAgIGNvbnN0IHRpbWVzdGFtcCA9ICcxNTk1Mzc0NzIzLjAxNDUnO1xuICAgICAgVXRpbHMubm9ybWFsaXplU3RhcnR0aW1lKHRpbWVzdGFtcCkuc2hvdWxkLmVxdWFsKHRpbWVzdGFtcCArICcwMDAwMCcpO1xuICAgIH0pO1xuICB9KTtcbn0pO1xuIl19