sliftutils 1.7.10 → 1.7.12

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 (84) hide show
  1. package/.claude/settings.local.json +2 -1
  2. package/examplestorage/exampleserver.ts +0 -2
  3. package/index.d.ts +301 -54
  4. package/misc/dist/environment.ts.cache +3 -3
  5. package/misc/dist/getSecret.ts.cache +139 -0
  6. package/misc/dist/strings.ts.cache +13 -0
  7. package/misc/dist/zip.ts.cache +9 -0
  8. package/misc/getSecret.ts +38 -16
  9. package/misc/https/cloudflareHelpers.d.ts +19 -0
  10. package/misc/https/cloudflareHelpers.ts +69 -0
  11. package/misc/https/dist/certs.ts.cache +115 -179
  12. package/misc/https/dist/cloudflareHelpers.ts.cache +68 -0
  13. package/misc/https/dist/dns.ts.cache +112 -100
  14. package/misc/https/dist/hostServer.ts.cache +130 -0
  15. package/misc/https/dist/httpsCerts.ts.cache +24 -5
  16. package/misc/https/dist/persistentLocalStorage.ts.cache +3 -2
  17. package/misc/https/dns.d.ts +41 -12
  18. package/misc/https/dns.ts +104 -101
  19. package/misc/https/hostServer.d.ts +0 -6
  20. package/misc/https/hostServer.ts +9 -5
  21. package/package.json +2 -2
  22. package/render-utils/dist/observer.tsx.cache +3 -2
  23. package/spec.txt +0 -90
  24. package/storage/ArchivesDisk.d.ts +2 -0
  25. package/storage/ArchivesDisk.ts +7 -3
  26. package/storage/BulkDatabase2/dist/BulkDatabaseBase.ts.cache +1242 -0
  27. package/storage/BulkDatabase2/dist/BulkDatabaseFormat.ts.cache +513 -0
  28. package/storage/BulkDatabase2/dist/BulkDatabaseMerge.ts.cache +352 -0
  29. package/storage/BulkDatabase2/dist/BulkDatabaseReader.ts.cache +306 -0
  30. package/storage/BulkDatabase2/dist/LoadedIndex.ts.cache +435 -0
  31. package/storage/BulkDatabase2/dist/WriteOverlay.ts.cache +58 -0
  32. package/storage/BulkDatabase2/dist/blockCache.ts.cache +179 -0
  33. package/storage/BulkDatabase2/dist/mergeLock.ts.cache +149 -0
  34. package/storage/BulkDatabase2/dist/mergeMarkers.ts.cache +101 -0
  35. package/storage/BulkDatabase2/dist/streamLog.ts.cache +227 -0
  36. package/storage/BulkDatabase2/dist/syncClient.ts.cache +104 -0
  37. package/storage/IArchives.d.ts +47 -15
  38. package/storage/IArchives.ts +86 -31
  39. package/storage/backblaze.d.ts +15 -0
  40. package/storage/backblaze.ts +199 -79
  41. package/storage/dist/ArchivesDisk.ts.cache +373 -0
  42. package/storage/dist/FileFolderAPI.tsx.cache +508 -65
  43. package/storage/dist/IArchives.ts.cache +44 -0
  44. package/storage/dist/IndexedDBFileFolderAPI.ts.cache +8 -2
  45. package/storage/dist/JSONStorage.ts.cache +6 -2
  46. package/storage/dist/PendingManager.tsx.cache +1 -1
  47. package/storage/dist/TransactionStorage.ts.cache +231 -92
  48. package/storage/dist/backblaze.ts.cache +797 -0
  49. package/storage/dist/fileSystemPointer.ts.cache +36 -3
  50. package/storage/dist/remoteFileStorage.ts.cache +495 -0
  51. package/storage/remoteStorage/ArchivesRemote.d.ts +5 -1
  52. package/storage/remoteStorage/ArchivesRemote.ts +28 -8
  53. package/storage/remoteStorage/ArchivesUrl.d.ts +2 -0
  54. package/storage/remoteStorage/ArchivesUrl.ts +16 -4
  55. package/storage/remoteStorage/blobStore.d.ts +63 -3
  56. package/storage/remoteStorage/blobStore.ts +419 -101
  57. package/storage/remoteStorage/createArchives.d.ts +31 -10
  58. package/storage/remoteStorage/createArchives.ts +470 -253
  59. package/storage/remoteStorage/dist/ArchivesRemote.ts.cache +197 -0
  60. package/storage/remoteStorage/dist/ArchivesUrl.ts.cache +85 -0
  61. package/storage/remoteStorage/dist/accessPage.tsx.cache +222 -0
  62. package/storage/remoteStorage/dist/blobStore.ts.cache +837 -0
  63. package/storage/remoteStorage/dist/cliArgs.ts.cache +16 -0
  64. package/storage/remoteStorage/dist/createArchives.ts.cache +610 -0
  65. package/storage/remoteStorage/dist/remoteConfig.ts.cache +206 -0
  66. package/storage/remoteStorage/dist/sourceWrapper.ts.cache +223 -0
  67. package/storage/remoteStorage/dist/storageController.ts.cache +500 -0
  68. package/storage/remoteStorage/dist/storageServer.ts.cache +106 -0
  69. package/storage/remoteStorage/dist/storageServerCli.ts.cache +39 -0
  70. package/storage/remoteStorage/dist/storageServerState.ts.cache +518 -0
  71. package/storage/remoteStorage/remoteConfig.d.ts +8 -0
  72. package/storage/remoteStorage/remoteConfig.ts +105 -5
  73. package/storage/remoteStorage/sourceWrapper.d.ts +41 -0
  74. package/storage/remoteStorage/sourceWrapper.ts +223 -0
  75. package/storage/remoteStorage/spec.md +31 -0
  76. package/storage/remoteStorage/storageController.d.ts +11 -0
  77. package/storage/remoteStorage/storageController.ts +109 -40
  78. package/storage/remoteStorage/storageServer.d.ts +0 -5
  79. package/storage/remoteStorage/storageServer.ts +17 -10
  80. package/storage/remoteStorage/storageServerCli.ts +0 -3
  81. package/storage/remoteStorage/storageServerState.d.ts +7 -1
  82. package/storage/remoteStorage/storageServerState.ts +230 -48
  83. package/testsite/server.ts +0 -2
  84. package/yarn.lock +11 -6
@@ -0,0 +1,306 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true , configurable: true});
3
+ //exports.nullJoin = exports.READER_SIGNALS = exports.BulkDatabaseReader = void 0;
4
+ const WriteOverlay_1 = require("./WriteOverlay");
5
+ const format_1 = require("socket-function/src/formatting/format");
6
+ const logColors_1 = require("socket-function/src/formatting/logColors");
7
+ const NULL = String.fromCharCode(0);
8
+ const LOAD_SIGNAL = NULL + "load";
9
+ const OVERLAY_SIGNAL = NULL + "overlay";
10
+ const COMPACTING_SIGNAL = NULL + "compacting";
11
+ const TRIGGER_THROTTLE_FIRST_STEP_MS = 16;
12
+ function nullJoin(a, b) {
13
+ return a + NULL + b;
14
+ }
15
+ exports.nullJoin = nullJoin;
16
+ // Owns the current LoadedIndex and WriteOverlay and serves every read (async + sync reactive). Apply
17
+ // writes/deletes through applyWrite/applyDelete so the right signals fire. The host swaps in a fresh
18
+ // LoadedIndex atomically via setIndex once the new one has fully built — no lazy rebuild on the next
19
+ // read, no synchronous lag spike.
20
+ class BulkDatabaseReader {
21
+ constructor(cfg) {
22
+ this.cfg = cfg;
23
+ this.overlay = new WriteOverlay_1.WriteOverlay();
24
+ this.dataGen = 0;
25
+ this.columnCache = new Map();
26
+ this.pendingSignals = new Set();
27
+ this.currentTriggerDelay = 0;
28
+ this.lastTriggerTime = 0;
29
+ // Counter (so concurrent / nested merges in the same instance compose correctly). Signal fires
30
+ // immediately, not through the trigger throttle — UI spinners should show right away.
31
+ this.compactingCount = 0;
32
+ }
33
+ get name() { return this.cfg.name; }
34
+ get deps() { return this.cfg.deps; }
35
+ get dataGeneration() { return this.dataGen; }
36
+ setIndex(newIndex, options = {}) {
37
+ const prev = this.index;
38
+ if (prev && !options.dropStaleFallback)
39
+ newIndex.inheritStaleFrom(prev);
40
+ this.cfg.deps.batch(() => {
41
+ this.index = newIndex;
42
+ this.overlay.sweepCovered(key => {
43
+ var _a, _b;
44
+ return Math.max((_a = newIndex.reader.keyTimes.get(key)) !== null && _a !== void 0 ? _a : -Infinity, (_b = newIndex.reader.deleteTimes.get(key)) !== null && _b !== void 0 ? _b : -Infinity);
45
+ });
46
+ this.dataGen++;
47
+ this.columnCache.clear();
48
+ this.invalidateSignal(LOAD_SIGNAL);
49
+ this.invalidateSignal(OVERLAY_SIGNAL);
50
+ });
51
+ }
52
+ applyWrite(key, row, time) {
53
+ const wasLive = this.isLiveNow(key);
54
+ const { invalidatedColumns } = this.overlay.writeRow(key, row, time, wasLive);
55
+ this.notifyOverlayMutation(key, invalidatedColumns);
56
+ }
57
+ applyDelete(key, time) {
58
+ const wasLive = this.isLiveNow(key);
59
+ const { invalidatedColumns } = this.overlay.deleteKey(key, time, wasLive);
60
+ this.notifyOverlayMutation(key, invalidatedColumns);
61
+ }
62
+ isKeyWatched(key) {
63
+ var _a, _b, _c;
64
+ return (_c = (_b = (_a = this.cfg.deps).isObserved) === null || _b === void 0 ? void 0 : _b.call(_a, key)) !== null && _c !== void 0 ? _c : true;
65
+ }
66
+ isLiveNow(key) {
67
+ var _a, _b;
68
+ const e = this.overlay.get(key);
69
+ if (e)
70
+ return e.value !== WriteOverlay_1.DELETED;
71
+ return (_b = (_a = this.index) === null || _a === void 0 ? void 0 : _a.isLive(key)) !== null && _b !== void 0 ? _b : false;
72
+ }
73
+ localTime(key) {
74
+ var _a;
75
+ const e = this.overlay.get(key);
76
+ if (e)
77
+ return e.time;
78
+ const st = (_a = this.index) === null || _a === void 0 ? void 0 : _a.streamTimes.get(key);
79
+ if (st !== undefined)
80
+ return st;
81
+ return -Infinity;
82
+ }
83
+ beginCompaction() {
84
+ this.compactingCount++;
85
+ if (this.compactingCount === 1)
86
+ this.cfg.deps.invalidate(COMPACTING_SIGNAL);
87
+ }
88
+ endCompaction() {
89
+ this.compactingCount--;
90
+ if (this.compactingCount === 0)
91
+ this.cfg.deps.invalidate(COMPACTING_SIGNAL);
92
+ }
93
+ isCompactingSync() {
94
+ this.cfg.deps.observe(COMPACTING_SIGNAL);
95
+ return this.compactingCount > 0;
96
+ }
97
+ notifyOverlayMutation(key, columns) {
98
+ var _a, _b, _c;
99
+ this.dataGen++;
100
+ if (columns === "all")
101
+ this.columnCache.clear();
102
+ else
103
+ for (const c of columns)
104
+ this.columnCache.delete(c);
105
+ if ((_c = (_b = (_a = this.cfg.deps).isObserved) === null || _b === void 0 ? void 0 : _b.call(_a, key)) !== null && _c !== void 0 ? _c : true)
106
+ this.invalidateSignal(key);
107
+ this.invalidateSignal(OVERLAY_SIGNAL);
108
+ }
109
+ // ── async reads ──────────────────────────────────────────────────────────────────────────────────
110
+ async getKeys() {
111
+ const index = await this.requireIndex();
112
+ if (this.overlay.size === 0)
113
+ return [...index.keys];
114
+ const set = new Set(index.keys);
115
+ for (const [key, entry] of this.overlay) {
116
+ if (entry.value === WriteOverlay_1.DELETED)
117
+ set.delete(key);
118
+ else
119
+ set.add(key);
120
+ }
121
+ return [...set];
122
+ }
123
+ async getColumn(column) {
124
+ const col = String(column);
125
+ const cached = this.columnCache.get(col);
126
+ if (cached)
127
+ return cached;
128
+ const gen = this.dataGen;
129
+ const start = Date.now();
130
+ const index = await this.requireIndex();
131
+ let base = await index.getColumn(col);
132
+ let result = this.overlay.patchColumn(base, col);
133
+ const elapsed = Date.now() - start;
134
+ if (elapsed > 50) {
135
+ console.log(`${(0, logColors_1.blue)(`${this.cfg.name}.getColumn(${JSON.stringify(column)})`)} took ${(0, logColors_1.red)((0, format_1.formatTime)(elapsed))} ${this.formatInfo(index)}`);
136
+ }
137
+ Object.freeze(result);
138
+ if (this.dataGen === gen)
139
+ this.columnCache.set(col, result);
140
+ return result;
141
+ }
142
+ async getSingleField(key, column) {
143
+ var _a;
144
+ return (_a = (await this.getSingleFieldObj(key, column))) === null || _a === void 0 ? void 0 : _a.value;
145
+ }
146
+ async getSingleFieldObj(key, column) {
147
+ const col = String(column);
148
+ const entry = this.overlay.get(key);
149
+ if (entry !== undefined) {
150
+ if (entry.value === WriteOverlay_1.DELETED)
151
+ return undefined;
152
+ if (col in entry.value)
153
+ return { key, value: entry.value[col], time: entry.time };
154
+ }
155
+ const start = Date.now();
156
+ const index = await this.requireIndex();
157
+ const r = await index.getSingleField(key, col);
158
+ const elapsed = Date.now() - start;
159
+ if (elapsed > 50) {
160
+ console.log(`${(0, logColors_1.blue)(`${this.cfg.name}.getSingleFieldObj(${JSON.stringify(key)}, ${JSON.stringify(column)})`)} took ${(0, logColors_1.red)((0, format_1.formatTime)(elapsed))} ${this.formatInfo(index)}`);
161
+ }
162
+ if (r === undefined) {
163
+ if (entry !== undefined && entry.value !== WriteOverlay_1.DELETED)
164
+ return { key, value: undefined, time: entry.time };
165
+ return undefined;
166
+ }
167
+ return { key, value: r.value, time: r.time };
168
+ }
169
+ // ── sync (reactive) reads ────────────────────────────────────────────────────────────────────────
170
+ getSingleFieldSync(key, column) {
171
+ var _a;
172
+ return (_a = this.getSingleFieldObjSync(key, column)) === null || _a === void 0 ? void 0 : _a.value;
173
+ }
174
+ getSingleFieldObjSync(key, column) {
175
+ var _a;
176
+ this.cfg.deps.observe(LOAD_SIGNAL);
177
+ this.cfg.deps.observe(key);
178
+ const col = String(column);
179
+ const entry = this.overlay.get(key);
180
+ if (entry !== undefined) {
181
+ if (entry.value === WriteOverlay_1.DELETED)
182
+ return undefined;
183
+ if (col in entry.value) {
184
+ (_a = this.index) === null || _a === void 0 ? void 0 : _a.ensureBaseField(key, col, () => this.invalidateSignal(LOAD_SIGNAL));
185
+ return { key, value: entry.value[col], time: entry.time };
186
+ }
187
+ }
188
+ const index = this.index;
189
+ if (!index) {
190
+ if (entry !== undefined && entry.value !== WriteOverlay_1.DELETED)
191
+ return { key, value: undefined, time: entry.time };
192
+ return undefined;
193
+ }
194
+ const base = index.getBaseField(key, col);
195
+ // Trigger load if not loaded OR loaded only from stale fallback (refresh needed).
196
+ if (!base.loaded || !base.fresh)
197
+ index.ensureBaseField(key, col, () => this.invalidateSignal(LOAD_SIGNAL));
198
+ if (!base.loaded || base.value === undefined) {
199
+ if (entry !== undefined && entry.value !== WriteOverlay_1.DELETED)
200
+ return { key, value: undefined, time: entry.time };
201
+ return undefined;
202
+ }
203
+ return { key, value: base.value.value, time: base.value.time };
204
+ }
205
+ getColumnSync(column) {
206
+ this.cfg.deps.observe(LOAD_SIGNAL);
207
+ this.cfg.deps.observe(OVERLAY_SIGNAL);
208
+ const col = String(column);
209
+ const cached = this.columnCache.get(col);
210
+ if (cached)
211
+ return cached;
212
+ const index = this.index;
213
+ if (!index)
214
+ return undefined;
215
+ const base = index.getBaseColumn(col);
216
+ // Trigger load if not fresh (genuine first load OR a stale fallback awaiting refresh).
217
+ if (!base || !base.fresh)
218
+ index.ensureBaseColumn(col, () => this.invalidateSignal(LOAD_SIGNAL));
219
+ if (!base)
220
+ return undefined;
221
+ const result = this.overlay.patchColumn(base.entries, col);
222
+ if (base.fresh) {
223
+ Object.freeze(result);
224
+ this.columnCache.set(col, result);
225
+ }
226
+ return result;
227
+ }
228
+ isFieldLoadedSync(key, column) {
229
+ this.cfg.deps.observe(LOAD_SIGNAL);
230
+ this.cfg.deps.observe(key);
231
+ const entry = this.overlay.get(key);
232
+ if (entry !== undefined) {
233
+ if (entry.value === WriteOverlay_1.DELETED)
234
+ return true;
235
+ if (String(column) in entry.value)
236
+ return true;
237
+ }
238
+ const index = this.index;
239
+ if (!index)
240
+ return false;
241
+ if (index.isBaseFieldLoaded(key, String(column)))
242
+ return true;
243
+ index.ensureBaseField(key, String(column), () => this.invalidateSignal(LOAD_SIGNAL));
244
+ return false;
245
+ }
246
+ isColumnLoadedSync(column) {
247
+ this.cfg.deps.observe(LOAD_SIGNAL);
248
+ this.cfg.deps.observe(OVERLAY_SIGNAL);
249
+ const col = String(column);
250
+ if (this.columnCache.has(col))
251
+ return true;
252
+ const index = this.index;
253
+ if (!index)
254
+ return false;
255
+ if (index.isBaseColumnLoaded(col))
256
+ return true;
257
+ index.ensureBaseColumn(col, () => this.invalidateSignal(LOAD_SIGNAL));
258
+ return false;
259
+ }
260
+ // ── helpers ──────────────────────────────────────────────────────────────────────────────────────
261
+ // Both async reads await this. The host wires an `ensureIndex` that triggers the initial build if
262
+ // no index is loaded yet — reads that race the first load all wait on the same promise.
263
+ setEnsureIndex(fn) { this.ensureIndexFn = fn; }
264
+ async requireIndex() {
265
+ if (this.index)
266
+ return this.index;
267
+ if (!this.ensureIndexFn)
268
+ throw new Error(`${this.cfg.name}: index not set — call setIndex(...) before reading`);
269
+ return this.ensureIndexFn();
270
+ }
271
+ formatInfo(index) {
272
+ return `(collection has ${(0, logColors_1.blue)((0, format_1.formatNumber)(index.reader.rowCount))} rows, ${(0, logColors_1.blue)((0, format_1.formatNumber)(index.reader.totalBytes))}B)`;
273
+ }
274
+ // Notifications are rampingly delayed under sustained changes (so a high-rate writer can't re-run
275
+ // watchers per change). Underlying data is always current — only the observable notification is
276
+ // batched/delayed.
277
+ invalidateSignal(signal) {
278
+ var _a, _b, _c;
279
+ const maxMs = (_a = this.cfg.maxTriggerThrottleMs) !== null && _a !== void 0 ? _a : 0;
280
+ if (maxMs <= 0) {
281
+ this.cfg.deps.invalidate(signal);
282
+ return;
283
+ }
284
+ this.pendingSignals.add(signal);
285
+ const now = Date.now();
286
+ const lull = now - this.lastTriggerTime > maxMs;
287
+ this.lastTriggerTime = now;
288
+ if (this.triggerTimer !== undefined)
289
+ return;
290
+ this.currentTriggerDelay = lull ? 0 : Math.min(maxMs, Math.max(TRIGGER_THROTTLE_FIRST_STEP_MS, this.currentTriggerDelay * 2));
291
+ this.triggerTimer = setTimeout(() => { this.triggerTimer = undefined; this.flushSignals(); }, this.currentTriggerDelay);
292
+ (_c = (_b = this.triggerTimer).unref) === null || _c === void 0 ? void 0 : _c.call(_b);
293
+ }
294
+ flushSignals() {
295
+ if (this.pendingSignals.size === 0)
296
+ return;
297
+ const signals = [...this.pendingSignals];
298
+ this.pendingSignals.clear();
299
+ this.cfg.deps.batch(() => { for (const s of signals)
300
+ this.cfg.deps.invalidate(s); });
301
+ }
302
+ }
303
+ exports.BulkDatabaseReader = BulkDatabaseReader;
304
+ exports.READER_SIGNALS = { LOAD: LOAD_SIGNAL, OVERLAY: OVERLAY_SIGNAL };
305
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiQnVsa0RhdGFiYXNlUmVhZGVyLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiQnVsa0RhdGFiYXNlUmVhZGVyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7OztBQUNBLGlEQUF1RDtBQUV2RCxrRUFBaUY7QUFDakYsd0VBQXFFO0FBRXJFLE1BQU0sSUFBSSxHQUFHLE1BQU0sQ0FBQyxZQUFZLENBQUMsQ0FBQyxDQUFDLENBQUM7QUFDcEMsTUFBTSxXQUFXLEdBQUcsSUFBSSxHQUFHLE1BQU0sQ0FBQztBQUNsQyxNQUFNLGNBQWMsR0FBRyxJQUFJLEdBQUcsU0FBUyxDQUFDO0FBQ3hDLE1BQU0saUJBQWlCLEdBQUcsSUFBSSxHQUFHLFlBQVksQ0FBQztBQUM5QyxNQUFNLDhCQUE4QixHQUFHLEVBQUUsQ0FBQztBQUUxQyxTQUFTLFFBQVEsQ0FBQyxDQUFTLEVBQUUsQ0FBUztJQUNsQyxPQUFPLENBQUMsR0FBRyxJQUFJLEdBQUcsQ0FBQyxDQUFDO0FBQ3hCLENBQUM7QUFtUlEsNEJBQVE7QUExUWpCLHFHQUFxRztBQUNyRyxxR0FBcUc7QUFDckcscUdBQXFHO0FBQ3JHLGtDQUFrQztBQUNsQyxNQUFhLGtCQUFrQjtJQUMzQixZQUE2QixHQUFpQjtRQUFqQixRQUFHLEdBQUgsR0FBRyxDQUFjO1FBRzlCLFlBQU8sR0FBRyxJQUFJLDJCQUFZLEVBQUUsQ0FBQztRQUVyQyxZQUFPLEdBQUcsQ0FBQyxDQUFDO1FBQ1osZ0JBQVcsR0FBRyxJQUFJLEdBQUcsRUFBMkQsQ0FBQztRQUVqRixtQkFBYyxHQUFHLElBQUksR0FBRyxFQUFVLENBQUM7UUFFbkMsd0JBQW1CLEdBQUcsQ0FBQyxDQUFDO1FBQ3hCLG9CQUFlLEdBQUcsQ0FBQyxDQUFDO1FBb0Q1QiwrRkFBK0Y7UUFDL0Ysc0ZBQXNGO1FBQzlFLG9CQUFlLEdBQUcsQ0FBQyxDQUFDO0lBakVzQixDQUFDO0lBYW5ELElBQUksSUFBSSxLQUFhLE9BQU8sSUFBSSxDQUFDLEdBQUcsQ0FBQyxJQUFJLENB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LGtEQUFJLENBQUM7SUFDNUQsQ0FBQztJQUVPLFlBQVk7UUFDaEIsSUFBSSxJQUFJLENBQUMsY0FBYyxDQUFDLElBQUksS0FBSyxDQUFDO1lBQUUsT0FBTztRQUMzQyxNQUFNLE9BQU8sR0FBRyxDQUFDLEdBQUcsSUFBSSxDQUFDLGNBQWMsQ0FBQyxDQUFDO1FBQ3pDLElBQUksQ0FBQyxjQUFjLENBQUMsS0FBSyxFQUFFLENBQUM7UUFDNUIsSUFBSSxDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLEdBQUcsRUFBRSxHQUFHLEtBQUssTUFBTSxDQUFDLElBQUksT0FBTztZQUFFLElBQUksQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO0lBQ3pGLENBQUM7Q0FDSjtBQW5RRCxnREFtUUM7QUFFWSxRQUFBLGNBQWMsR0FBRyxFQUFFLElBQUksRUFBRSxXQUFXLEVBQUUsT0FBTyxFQUFFLGNBQWMsRUFBRSxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgTG9hZGVkSW5kZXggfSBmcm9tIFwiLi9Mb2FkZWRJbmRleFwiO1xuaW1wb3J0IHsgREVMRVRFRCwgV3JpdGVPdmVybGF5IH0gZnJvbSBcIi4vV3JpdGVPdmVybGF5XCI7XG5pbXBvcnQgdHlwZSB7IFJlYWN0aXZlRGVwcyB9IGZyb20gXCIuL0J1bGtEYXRhYmFzZUJhc2VcIjtcbmltcG9ydCB7IGZvcm1hdE51bWJlciwgZm9ybWF0VGltZSB9IGZyb20gXCJzb2NrZXQtZnVuY3Rpb24vc3JjL2Zvcm1hdHRpbmcvZm9ybWF0XCI7XG5pbXBvcnQgeyBibHVlLCByZWQgfSBmcm9tIFwic29ja2V0LWZ1bmN0aW9uL3NyYy9mb3JtYXR0aW5nL2xvZ0NvbG9yc1wiO1xuXG5jb25zdCBOVUxMID0gU3RyaW5nLmZyb21DaGFyQ29kZSgwKTtcbmNvbnN0IExPQURfU0lHTkFMID0gTlVMTCArIFwibG9hZFwiO1xuY29uc3QgT1ZFUkxBWV9TSUdOQUwgPSBOVUxMICsgXCJvdmVybGF5XCI7XG5jb25zdCBDT01QQUNUSU5HX1NJR05BTCA9IE5VTEwgKyBcImNvbXBhY3RpbmdcIjtcbmNvbnN0IFRSSUdHRVJfVEhST1RUTEVfRklSU1RfU1RFUF9NUyA9IDE2O1xuXG5mdW5jdGlvbiBudWxsSm9pbihhOiBzdHJpbmcsIGI6IHN0cmluZyk6IHN0cmluZyB7XG4gICAgcmV0dXJuIGEgKyBOVUxMICsgYjtcbn1cblxuZXhwb3J0IHR5cGUgUmVhZGVyQ29uZmlnID0ge1xuICAgIG5hbWU6IHN0cmluZztcbiAgICBkZXBzOiBSZWFjdGl2ZURlcHM7XG4gICAgLy8gU2VlIEJ1bGtEYXRhYmFzZTJDb25maWcubWF4VHJpZ2dlclRocm90dGxlTXMuXG4gICAgbWF4VHJpZ2dlclRocm90dGxlTXM/OiBudW1iZXI7XG59O1xuXG4vLyBPd25zIHRoZSBjdXJyZW50IExvYWRlZEluZGV4IGFuZCBXcml0ZU92ZXJsYXkgYW5kIHNlcnZlcyBldmVyeSByZWFkIChhc3luYyArIHN5bmMgcmVhY3RpdmUpLiBBcHBseVxuLy8gd3JpdGVzL2RlbGV0ZXMgdGhyb3VnaCBhcHBseVdyaXRlL2FwcGx5RGVsZXRlIHNvIHRoZSByaWdodCBzaWduYWxzIGZpcmUuIFRoZSBob3N0IHN3YXBzIGluIGEgZnJlc2hcbi8vIExvYWRlZEluZGV4IGF0b21pY2FsbHkgdmlhIHNldEluZGV4IG9uY2UgdGhlIG5ldyBvbmUgaGFzIGZ1bGx5IGJ1aWx0IOKAlCBubyBsYXp5IHJlYnVpbGQgb24gdGhlIG5leHRcbi8vIHJlYWQsIG5vIHN5bmNocm9ub3VzIGxhZyBzcGlrZS5cbmV4cG9ydCBjbGFzcyBCdWxrRGF0YWJhc2VSZWFkZXI8VCBleHRlbmRzIHsga2V5OiBzdHJpbmcgfT4ge1xuICAgIGNvbnN0cnVjdG9yKHByaXZhdGUgcmVhZG9ubHkgY2ZnOiBSZWFkZXJDb25maWcpIHsgfVxuXG4gICAgcHVibGljIGluZGV4OiBMb2FkZWRJbmRleDxUPiB8IHVuZGVmaW5lZDtcbiAgICBwdWJsaWMgcmVhZG9ubHkgb3ZlcmxheSA9IG5ldyBXcml0ZU92ZXJsYXkoKTtcblxuICAgIHByaXZhdGUgZGF0YUdlbiA9IDA7XG4gICAgcHJpdmF0ZSBjb2x1bW5DYWNoZSA9IG5ldyBNYXA8c3RyaW5nLCB7IGtleTogc3RyaW5nOyB2YWx1ZTogdW5rbm93bjsgdGltZTogbnVtYmVyIH1bXT4oKTtcblxuICAgIHByaXZhdGUgcGVuZGluZ1NpZ25hbHMgPSBuZXcgU2V0PHN0cmluZz4oKTtcbiAgICBwcml2YXRlIHRyaWdnZXJUaW1lcjogUmV0dXJuVHlwZTx0eXBlb2Ygc2V0VGltZW91dD4gfCB1bmRlZmluZWQ7XG4gICAgcHJpdmF0ZSBjdXJyZW50VHJpZ2dlckRlbGF5ID0gMDtcbiAgICBwcml2YXRlIGxhc3RUcmlnZ2VyVGltZSA9IDA7XG5cbiAgICBnZXQgbmFtZSgpOiBzdHJpbmcgeyByZXR1cm4gdGhpcy5jZmcubmFtZTsgfVxuICAgIGdldCBkZXBzKCk6IFJlYWN0aXZlRGVwcyB7IHJldHVybiB0aGlzLmNmZy5kZXBzOyB9XG4gICAgZ2V0IGRhdGFHZW5lcmF0aW9uKCk6IG51bWJlciB7IHJldHVybiB0aGlzLmRhdGFHZW47IH1cblxuICAgIHNldEluZGV4KG5ld0luZGV4OiBMb2FkZWRJbmRleDxUPiwgb3B0aW9uczogeyBkcm9wU3RhbGVGYWxsYmFjaz86IGJvb2xlYW4gfSA9IHt9KTogdm9pZCB7XG4gICAgICAgIGNvbnN0IHByZXYgPSB0aGlzLmluZGV4O1xuICAgICAgICBpZiAocHJldiAmJiAhb3B0aW9ucy5kcm9wU3RhbGVGYWxsYmFjaykgbmV3SW5kZXguaW5oZXJpdFN0YWxlRnJvbShwcmV2KTtcbiAgICAgICAgdGhpcy5jZmcuZGVwcy5iYXRjaCgoKSA9PiB7XG4gICAgICAgICAgICB0aGlzLmluZGV4ID0gbmV3SW5kZXg7XG4gICAgICAgICAgICB0aGlzLm92ZXJsYXkuc3dlZXBDb3ZlcmVkKGtleSA9PiBNYXRoLm1heChcbiAgICAgICAgICAgICAgICBuZXdJbmRleC5yZWFkZXIua2V5VGltZXMuZ2V0KGtleSkgPz8gLUluZmluaXR5LFxuICAgICAgICAgICAgICAgIG5ld0luZGV4LnJlYWRlci5kZWxldGVUaW1lcy5nZXQoa2V5KSA/PyAtSW5maW5pdHksXG4gICAgICAgICAgICApKTtcbiAgICAgICAgICAgIHRoaXMuZGF0YUdlbisrO1xuICAgICAgICAgICAgdGhpcy5jb2x1bW5DYWNoZS5jbGVhcigpO1xuICAgICAgICAgICAgdGhpcy5pbnZhbGlkYXRlU2lnbmFsKExPQURfU0lHTkFMKTtcbiAgICAgICAgICAgIHRoaXMuaW52YWxpZGF0ZVNpZ25hbChPVkVSTEFZX1NJR05BTCk7XG4gICAgICAgIH0pO1xuICAgIH1cblxuICAgIGFwcGx5V3JpdGUoa2V5OiBzdHJpbmcsIHJvdzogUmVjb3JkPHN0cmluZywgdW5rbm93bj4sIHRpbWU6IG51bWJlcik6IHZvaWQge1xuICAgICAgICBjb25zdCB3YXNMaXZlID0gdGhpcy5pc0xpdmVOb3coa2V5KTtcbiAgICAgICAgY29uc3QgeyBpbnZhbGlkYXRlZENvbHVtbnMgfSA9IHRoaXMub3ZlcmxheS53cml0ZVJvdyhrZXksIHJvdywgdGltZSwgd2FzTGl2ZSk7XG4gICAgICAgIHRoaXMubm90aWZ5T3ZlcmxheU11dGF0aW9uKGtleSwgaW52YWxpZGF0ZWRDb2x1bW5zKTtcbiAgICB9XG5cbiAgICBhcHBseURlbGV0ZShrZXk6IHN0cmluZywgdGltZTogbnVtYmVyKTogdm9pZCB7XG4gICAgICAgIGNvbnN0IHdhc0xpdmUgPSB0aGlzLmlzTGl2ZU5vdyhrZXkpO1xuICAgICAgICBjb25zdCB7IGludmFsaWRhdGVkQ29sdW1ucyB9ID0gdGhpcy5vdmVybGF5LmRlbGV0ZUtleShrZXksIHRpbWUsIHdhc0xpdmUpO1xuICAgICAgICB0aGlzLm5vdGlmeU92ZXJsYXlNdXRhdGlvbihrZXksIGludmFsaWRhdGVkQ29sdW1ucyk7XG4gICAgfVxuXG4gICAgaXNLZXlXYXRjaGVkKGtleTogc3RyaW5nKTogYm9vbGVhbiB7XG4gICAgICAgIHJldHVybiB0aGlzLmNmZy5kZXBzLmlzT2JzZXJ2ZWQ/LihrZXkpID8/IHRydWU7XG4gICAgfVxuXG4gICAgaXNMaXZlTm93KGtleTogc3RyaW5nKTogYm9vbGVhbiB7XG4gICAgICAgIGNvbnN0IGUgPSB0aGlzLm92ZXJsYXkuZ2V0KGtleSk7XG4gICAgICAgIGlmIChlKSByZXR1cm4gZS52YWx1ZSAhPT0gREVMRVRFRDtcbiAgICAgICAgcmV0dXJuIHRoaXMuaW5kZXg/LmlzTGl2ZShrZXkpID8/IGZhbHNlO1xuICAgIH1cblxuICAgIGxvY2FsVGltZShrZXk6IHN0cmluZyk6IG51bWJlciB7XG4gICAgICAgIGNvbnN0IGUgPSB0aGlzLm92ZXJsYXkuZ2V0KGtleSk7XG4gICAgICAgIGlmIChlKSByZXR1cm4gZS50aW1lO1xuICAgICAgICBjb25zdCBzdCA9IHRoaXMuaW5kZXg/LnN0cmVhbVRpbWVzLmdldChrZXkpO1xuICAgICAgICBpZiAoc3QgIT09IHVuZGVmaW5lZCkgcmV0dXJuIHN0O1xuICAgICAgICByZXR1cm4gLUluZmluaXR5O1xuICAgIH1cblxuICAgIC8vIENvdW50ZXIgKHNvIGNvbmN1cnJlbnQgLyBuZXN0ZWQgbWVyZ2VzIGluIHRoZSBzYW1lIGluc3RhbmNlIGNvbXBvc2UgY29ycmVjdGx5KS4gU2lnbmFsIGZpcmVzXG4gICAgLy8gaW1tZWRpYXRlbHksIG5vdCB0aHJvdWdoIHRoZSB0cmlnZ2VyIHRocm90dGxlIOKAlCBVSSBzcGlubmVycyBzaG91bGQgc2hvdyByaWdodCBhd2F5LlxuICAgIHByaXZhdGUgY29tcGFjdGluZ0NvdW50ID0gMDtcbiAgICBiZWdpbkNvbXBhY3Rpb24oKTogdm9pZCB7XG4gICAgICAgIHRoaXMuY29tcGFjdGluZ0NvdW50Kys7XG4gICAgICAgIGlmICh0aGlzLmNvbXBhY3RpbmdDb3VudCA9PT0gMSkgdGhpcy5jZmcuZGVwcy5pbnZhbGlkYXRlKENPTVBBQ1RJTkdfU0lHTkFMKTtcbiAgICB9XG4gICAgZW5kQ29tcGFjdGlvbigpOiB2b2lkIHtcbiAgICAgICAgdGhpcy5jb21wYWN0aW5nQ291bnQtLTtcbiAgICAgICAgaWYgKHRoaXMuY29tcGFjdGluZ0NvdW50ID09PSAwKSB0aGlzLmNmZy5kZXBzLmludmFsaWRhdGUoQ09NUEFDVElOR19TSUdOQUwpO1xuICAgIH1cbiAgICBpc0NvbXBhY3RpbmdTeW5jKCk6IGJvb2xlYW4ge1xuICAgICAgICB0aGlzLmNmZy5kZXBzLm9ic2VydmUoQ09NUEFDVElOR19TSUdOQUwpO1xuICAgICAgICByZXR1cm4gdGhpcy5jb21wYWN0aW5nQ291bnQgPiAwO1xuICAgIH1cblxuICAgIHByaXZhdGUgbm90aWZ5T3ZlcmxheU11dGF0aW9uKGtleTogc3RyaW5nLCBjb2x1bW5zOiBJdGVyYWJsZTxzdHJpbmc+IHwgXCJhbGxcIik6IHZvaWQge1xuICAgICAgICB0aGlzLmRhdGFHZW4rKztcbiAgICAgICAgaWYgKGNvbHVtbnMgPT09IFwiYWxsXCIpIHRoaXMuY29sdW1uQ2FjaGUuY2xlYXIoKTtcbiAgICAgICAgZWxzZSBmb3IgKGNvbnN0IGMgb2YgY29sdW1ucykgdGhpcy5jb2x1bW5DYWNoZS5kZWxldGUoYyk7XG4gICAgICAgIGlmICh0aGlzLmNmZy5kZXBzLmlzT2JzZXJ2ZWQ/LihrZXkpID8/IHRydWUpIHRoaXMuaW52YWxpZGF0ZVNpZ25hbChrZXkpO1xuICAgICAgICB0aGlzLmludmFsaWRhdGVTaWduYWwoT1ZFUkxBWV9TSUdOQUwpO1xuICAgIH1cblxuICAgIC8vIOKUgOKUgCBhc3luYyByZWFkcyDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIBcbiAgICBhc3luYyBnZXRLZXlzKCk6IFByb21pc2U8c3RyaW5nW10+IHtcbiAgICAgICAgY29uc3QgaW5kZXggPSBhd2FpdCB0aGlzLnJlcXVpcmVJbmRleCgpO1xuICAgICAgICBpZiAodGhpcy5vdmVybGF5LnNpemUgPT09IDApIHJldHVybiBbLi4uaW5kZXgua2V5c107XG4gICAgICAgIGNvbnN0IHNldCA9IG5ldyBTZXQoaW5kZXgua2V5cyk7XG4gICAgICAgIGZvciAoY29uc3QgW2tleSwgZW50cnldIG9mIHRoaXMub3ZlcmxheSkge1xuICAgICAgICAgICAgaWYgKGVudHJ5LnZhbHVlID09PSBERUxFVEVEKSBzZXQuZGVsZXRlKGtleSk7XG4gICAgICAgICAgICBlbHNlIHNldC5hZGQoa2V5KTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gWy4uLnNldF07XG4gICAgfVxuXG4gICAgYXN5bmMgZ2V0Q29sdW1uPEMgZXh0ZW5kcyBrZXlvZiBUPihjb2x1bW46IEMpOiBQcm9taXNlPHsga2V5OiBzdHJpbmc7IHZhbHVlOiBUW0NdOyB0aW1lOiBudW1iZXIgfVtdPiB7XG4gICAgICAgIGNvbnN0IGNvbCA9IFN0cmluZyhjb2x1bW4pO1xuICAgICAgICBjb25zdCBjYWNoZWQgPSB0aGlzLmNvbHVtbkNhY2hlLmdldChjb2wpO1xuICAgICAgICBpZiAoY2FjaGVkKSByZXR1cm4gY2FjaGVkIGFzIHsga2V5OiBzdHJpbmc7IHZhbHVlOiBUW0NdOyB0aW1lOiBudW1iZXIgfVtdO1xuICAgICAgICBjb25zdCBnZW4gPSB0aGlzLmRhdGFHZW47XG4gICAgICAgIGNvbnN0IHN0YXJ0ID0gRGF0ZS5ub3coKTtcbiAgICAgICAgY29uc3QgaW5kZXggPSBhd2FpdCB0aGlzLnJlcXVpcmVJbmRleCgpO1xuICAgICAgICBsZXQgYmFzZSA9IGF3YWl0IGluZGV4LmdldENvbHVtbihjb2wpO1xuICAgICAgICBsZXQgcmVzdWx0ID0gdGhpcy5vdmVybGF5LnBhdGNoQ29sdW1uKGJhc2UsIGNvbCkgYXMgeyBrZXk6IHN0cmluZzsgdmFsdWU6IFRbQ107IHRpbWU6IG51bWJlciB9W107XG4gICAgICAgIGNvbnN0IGVsYXBzZWQgPSBEYXRlLm5vdygpIC0gc3RhcnQ7XG4gICAgICAgIGlmIChlbGFwc2VkID4gNTApIHtcbiAgICAgICAgICAgIGNvbnNvbGUubG9nKGAke2JsdWUoYCR7dGhpcy5jZmcubmFtZX0uZ2V0Q29sdW1uKCR7SlNPTi5zdHJpbmdpZnkoY29sdW1uKX0pYCl9IHRvb2sgJHtyZWQoZm9ybWF0VGltZShlbGFwc2VkKSl9ICR7dGhpcy5mb3JtYXRJbmZvKGluZGV4KX1gKTtcbiAgICAgICAgfVxuICAgICAgICBPYmplY3QuZnJlZXplKHJlc3VsdCk7XG4gICAgICAgIGlmICh0aGlzLmRhdGFHZW4gPT09IGdlbikgdGhpcy5jb2x1bW5DYWNoZS5zZXQoY29sLCByZXN1bHQpO1xuICAgICAgICByZXR1cm4gcmVzdWx0O1xuICAgIH1cblxuICAgIGFzeW5jIGdldFNpbmdsZUZpZWxkPEMgZXh0ZW5kcyBrZXlvZiBUPihrZXk6IHN0cmluZywgY29sdW1uOiBDKTogUHJvbWlzZTxUW0NdIHwgdW5kZWZpbmVkPiB7XG4gICAgICAgIHJldHVybiAoYXdhaXQgdGhpcy5nZXRTaW5nbGVGaWVsZE9iaihrZXksIGNvbHVtbikpPy52YWx1ZTtcbiAgICB9XG5cbiAgICBhc3luYyBnZXRTaW5nbGVGaWVsZE9iajxDIGV4dGVuZHMga2V5b2YgVD4oa2V5OiBzdHJpbmcsIGNvbHVtbjogQyk6IFByb21pc2U8eyBrZXk6IHN0cmluZzsgdmFsdWU6IFRbQ107IHRpbWU6IG51bWJlciB9IHwgdW5kZWZpbmVkPiB7XG4gICAgICAgIGNvbnN0IGNvbCA9IFN0cmluZyhjb2x1bW4pO1xuICAgICAgICBjb25zdCBlbnRyeSA9IHRoaXMub3ZlcmxheS5nZXQoa2V5KTtcbiAgICAgICAgaWYgKGVudHJ5ICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICAgIGlmIChlbnRyeS52YWx1ZSA9PT0gREVMRVRFRCkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgICAgICAgIGlmIChjb2wgaW4gZW50cnkudmFsdWUpIHJldHVybiB7IGtleSwgdmFsdWU6IGVudHJ5LnZhbHVlW2NvbF0gYXMgVFtDXSwgdGltZTogZW50cnkudGltZSB9O1xuICAgICAgICB9XG4gICAgICAgIGNvbnN0IHN0YXJ0ID0gRGF0ZS5ub3coKTtcbiAgICAgICAgY29uc3QgaW5kZXggPSBhd2FpdCB0aGlzLnJlcXVpcmVJbmRleCgpO1xuICAgICAgICBjb25zdCByID0gYXdhaXQgaW5kZXguZ2V0U2luZ2xlRmllbGQoa2V5LCBjb2wpO1xuICAgICAgICBjb25zdCBlbGFwc2VkID0gRGF0ZS5ub3coKSAtIHN0YXJ0O1xuICAgICAgICBpZiAoZWxhcHNlZCA+IDUwKSB7XG4gICAgICAgICAgICBjb25zb2xlLmxvZyhgJHtibHVlKGAke3RoaXMuY2ZnLm5hbWV9LmdldFNpbmdsZUZpZWxkT2JqKCR7SlNPTi5zdHJpbmdpZnkoa2V5KX0sICR7SlNPTi5zdHJpbmdpZnkoY29sdW1uKX0pYCl9IHRvb2sgJHtyZWQoZm9ybWF0VGltZShlbGFwc2VkKSl9ICR7dGhpcy5mb3JtYXRJbmZvKGluZGV4KX1gKTtcbiAgICAgICAgfVxuICAgICAgICBpZiAociA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgICBpZiAoZW50cnkgIT09IHVuZGVmaW5lZCAmJiBlbnRyeS52YWx1ZSAhPT0gREVMRVRFRCkgcmV0dXJuIHsga2V5LCB2YWx1ZTogdW5kZWZpbmVkIGFzIFRbQ10sIHRpbWU6IGVudHJ5LnRpbWUgfTtcbiAgICAgICAgICAgIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHsga2V5LCB2YWx1ZTogci52YWx1ZSBhcyBUW0NdLCB0aW1lOiByLnRpbWUgfTtcbiAgICB9XG5cbiAgICAvLyDilIDilIAgc3luYyAocmVhY3RpdmUpIHJlYWRzIOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgFxuICAgIGdldFNpbmdsZUZpZWxkU3luYzxDIGV4dGVuZHMga2V5b2YgVD4oa2V5OiBzdHJpbmcsIGNvbHVtbjogQyk6IFRbQ10gfCB1bmRlZmluZWQge1xuICAgICAgICByZXR1cm4gdGhpcy5nZXRTaW5nbGVGaWVsZE9ialN5bmMoa2V5LCBjb2x1bW4pPy52YWx1ZTtcbiAgICB9XG5cbiAgICBnZXRTaW5nbGVGaWVsZE9ialN5bmM8QyBleHRlbmRzIGtleW9mIFQ+KGtleTogc3RyaW5nLCBjb2x1bW46IEMpOiB7IGtleTogc3RyaW5nOyB2YWx1ZTogVFtDXTsgdGltZTogbnVtYmVyIH0gfCB1bmRlZmluZWQge1xuICAgICAgICB0aGlzLmNmZy5kZXBzLm9ic2VydmUoTE9BRF9TSUdOQUwpO1xuICAgICAgICB0aGlzLmNmZy5kZXBzLm9ic2VydmUoa2V5KTtcbiAgICAgICAgY29uc3QgY29sID0gU3RyaW5nKGNvbHVtbik7XG4gICAgICAgIGNvbnN0IGVudHJ5ID0gdGhpcy5vdmVybGF5LmdldChrZXkpO1xuICAgICAgICBpZiAoZW50cnkgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgaWYgKGVudHJ5LnZhbHVlID09PSBERUxFVEVEKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgICAgICAgaWYgKGNvbCBpbiBlbnRyeS52YWx1ZSkge1xuICAgICAgICAgICAgICAgIHRoaXMuaW5kZXg/LmVuc3VyZUJhc2VGaWVsZChrZXksIGNvbCwgKCkgPT4gdGhpcy5pbnZhbGlkYXRlU2lnbmFsKExPQURfU0lHTkFMKSk7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHsga2V5LCB2YWx1ZTogZW50cnkudmFsdWVbY29sXSBhcyBUW0NdLCB0aW1lOiBlbnRyeS50aW1lIH07XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgY29uc3QgaW5kZXggPSB0aGlzLmluZGV4O1xuICAgICAgICBpZiAoIWluZGV4KSB7XG4gICAgICAgICAgICBpZiAoZW50cnkgIT09IHVuZGVmaW5lZCAmJiBlbnRyeS52YWx1ZSAhPT0gREVMRVRFRCkgcmV0dXJuIHsga2V5LCB2YWx1ZTogdW5kZWZpbmVkIGFzIFRbQ10sIHRpbWU6IGVudHJ5LnRpbWUgfTtcbiAgICAgICAgICAgIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICAgIH1cbiAgICAgICAgY29uc3QgYmFzZSA9IGluZGV4LmdldEJhc2VGaWVsZChrZXksIGNvbCk7XG4gICAgICAgIC8vIFRyaWdnZXIgbG9hZCBpZiBub3QgbG9hZGVkIE9SIGxvYWRlZCBvbmx5IGZyb20gc3RhbGUgZmFsbGJhY2sgKHJlZnJlc2ggbmVlZGVkKS5cbiAgICAgICAgaWYgKCFiYXNlLmxvYWRlZCB8fCAhYmFzZS5mcmVzaCkgaW5kZXguZW5zdXJlQmFzZUZpZWxkKGtleSwgY29sLCAoKSA9PiB0aGlzLmludmFsaWRhdGVTaWduYWwoTE9BRF9TSUdOQUwpKTtcbiAgICAgICAgaWYgKCFiYXNlLmxvYWRlZCB8fCBiYXNlLnZhbHVlID09PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICAgIGlmIChlbnRyeSAhPT0gdW5kZWZpbmVkICYmIGVudHJ5LnZhbHVlICE9PSBERUxFVEVEKSByZXR1cm4geyBrZXksIHZhbHVlOiB1bmRlZmluZWQgYXMgVFtDXSwgdGltZTogZW50cnkudGltZSB9O1xuICAgICAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4geyBrZXksIHZhbHVlOiBiYXNlLnZhbHVlLnZhbHVlIGFzIFRbQ10sIHRpbWU6IGJhc2UudmFsdWUudGltZSB9O1xuICAgIH1cblxuICAgIGdldENvbHVtblN5bmM8QyBleHRlbmRzIGtleW9mIFQ+KGNvbHVtbjogQyk6IHsga2V5OiBzdHJpbmc7IHZhbHVlOiBUW0NdOyB0aW1lOiBudW1iZXIgfVtdIHwgdW5kZWZpbmVkIHtcbiAgICAgICAgdGhpcy5jZmcuZGVwcy5vYnNlcnZlKExPQURfU0lHTkFMKTtcbiAgICAgICAgdGhpcy5jZmcuZGVwcy5vYnNlcnZlKE9WRVJMQVlfU0lHTkFMKTtcbiAgICAgICAgY29uc3QgY29sID0gU3RyaW5nKGNvbHVtbik7XG4gICAgICAgIGNvbnN0IGNhY2hlZCA9IHRoaXMuY29sdW1uQ2FjaGUuZ2V0KGNvbCk7XG4gICAgICAgIGlmIChjYWNoZWQpIHJldHVybiBjYWNoZWQgYXMgeyBrZXk6IHN0cmluZzsgdmFsdWU6IFRbQ107IHRpbWU6IG51bWJlciB9W107XG4gICAgICAgIGNvbnN0IGluZGV4ID0gdGhpcy5pbmRleDtcbiAgICAgICAgaWYgKCFpbmRleCkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgICAgY29uc3QgYmFzZSA9IGluZGV4LmdldEJhc2VDb2x1bW4oY29sKTtcbiAgICAgICAgLy8gVHJpZ2dlciBsb2FkIGlmIG5vdCBmcmVzaCAoZ2VudWluZSBmaXJzdCBsb2FkIE9SIGEgc3RhbGUgZmFsbGJhY2sgYXdhaXRpbmcgcmVmcmVzaCkuXG4gICAgICAgIGlmICghYmFzZSB8fCAhYmFzZS5mcmVzaCkgaW5kZXguZW5zdXJlQmFzZUNvbHVtbihjb2wsICgpID0+IHRoaXMuaW52YWxpZGF0ZVNpZ25hbChMT0FEX1NJR05BTCkpO1xuICAgICAgICBpZiAoIWJhc2UpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICAgIGNvbnN0IHJlc3VsdCA9IHRoaXMub3ZlcmxheS5wYXRjaENvbHVtbihiYXNlLmVudHJpZXMsIGNvbCkgYXMgeyBrZXk6IHN0cmluZzsgdmFsdWU6IFRbQ107IHRpbWU6IG51bWJlciB9W107XG4gICAgICAgIGlmIChiYXNlLmZyZXNoKSB7XG4gICAgICAgICAgICBPYmplY3QuZnJlZXplKHJlc3VsdCk7XG4gICAgICAgICAgICB0aGlzLmNvbHVtbkNhY2hlLnNldChjb2wsIHJlc3VsdCk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHJlc3VsdDtcbiAgICB9XG5cbiAgICBpc0ZpZWxkTG9hZGVkU3luYzxDIGV4dGVuZHMga2V5b2YgVD4oa2V5OiBzdHJpbmcsIGNvbHVtbjogQyk6IGJvb2xlYW4ge1xuICAgICAgICB0aGlzLmNmZy5kZXBzLm9ic2VydmUoTE9BRF9TSUdOQUwpO1xuICAgICAgICB0aGlzLmNmZy5kZXBzLm9ic2VydmUoa2V5KTtcbiAgICAgICAgY29uc3QgZW50cnkgPSB0aGlzLm92ZXJsYXkuZ2V0KGtleSk7XG4gICAgICAgIGlmIChlbnRyeSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgICBpZiAoZW50cnkudmFsdWUgPT09IERFTEVURUQpIHJldHVybiB0cnVlO1xuICAgICAgICAgICAgaWYgKFN0cmluZyhjb2x1bW4pIGluIGVudHJ5LnZhbHVlKSByZXR1cm4gdHJ1ZTtcbiAgICAgICAgfVxuICAgICAgICBjb25zdCBpbmRleCA9IHRoaXMuaW5kZXg7XG4gICAgICAgIGlmICghaW5kZXgpIHJldHVybiBmYWxzZTtcbiAgICAgICAgaWYgKGluZGV4LmlzQmFzZUZpZWxkTG9hZGVkKGtleSwgU3RyaW5nKGNvbHVtbikpKSByZXR1cm4gdHJ1ZTtcbiAgICAgICAgaW5kZXguZW5zdXJlQmFzZUZpZWxkKGtleSwgU3RyaW5nKGNvbHVtbiksICgpID0+IHRoaXMuaW52YWxpZGF0ZVNpZ25hbChMT0FEX1NJR05BTCkpO1xuICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuXG4gICAgaXNDb2x1bW5Mb2FkZWRTeW5jPEMgZXh0ZW5kcyBrZXlvZiBUPihjb2x1bW46IEMpOiBib29sZWFuIHtcbiAgICAgICAgdGhpcy5jZmcuZGVwcy5vYnNlcnZlKExPQURfU0lHTkFMKTtcbiAgICAgICAgdGhpcy5jZmcuZGVwcy5vYnNlcnZlKE9WRVJMQVlfU0lHTkFMKTtcbiAgICAgICAgY29uc3QgY29sID0gU3RyaW5nKGNvbHVtbik7XG4gICAgICAgIGlmICh0aGlzLmNvbHVtbkNhY2hlLmhhcyhjb2wpKSByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY29uc3QgaW5kZXggPSB0aGlzLmluZGV4O1xuICAgICAgICBpZiAoIWluZGV4KSByZXR1cm4gZmFsc2U7XG4gICAgICAgIGlmIChpbmRleC5pc0Jhc2VDb2x1bW5Mb2FkZWQoY29sKSkgcmV0dXJuIHRydWU7XG4gICAgICAgIGluZGV4LmVuc3VyZUJhc2VDb2x1bW4oY29sLCAoKSA9PiB0aGlzLmludmFsaWRhdGVTaWduYWwoTE9BRF9TSUdOQUwpKTtcbiAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cblxuICAgIC8vIOKUgOKUgCBoZWxwZXJzIOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgFxuICAgIC8vIEJvdGggYXN5bmMgcmVhZHMgYXdhaXQgdGhpcy4gVGhlIGhvc3Qgd2lyZXMgYW4gYGVuc3VyZUluZGV4YCB0aGF0IHRyaWdnZXJzIHRoZSBpbml0aWFsIGJ1aWxkIGlmXG4gICAgLy8gbm8gaW5kZXggaXMgbG9hZGVkIHlldCDigJQgcmVhZHMgdGhhdCByYWNlIHRoZSBmaXJzdCBsb2FkIGFsbCB3YWl0IG9uIHRoZSBzYW1lIHByb21pc2UuXG4gICAgc2V0RW5zdXJlSW5kZXgoZm46ICgpID0+IFByb21pc2U8TG9hZGVkSW5kZXg8VD4+KTogdm9pZCB7IHRoaXMuZW5zdXJlSW5kZXhGbiA9IGZuOyB9XG4gICAgcHJpdmF0ZSBlbnN1cmVJbmRleEZuOiAoKCkgPT4gUHJvbWlzZTxMb2FkZWRJbmRleDxUPj4pIHwgdW5kZWZpbmVkO1xuICAgIHByaXZhdGUgYXN5bmMgcmVxdWlyZUluZGV4KCk6IFByb21pc2U8TG9hZGVkSW5kZXg8VD4+IHtcbiAgICAgICAgaWYgKHRoaXMuaW5kZXgpIHJldHVybiB0aGlzLmluZGV4O1xuICAgICAgICBpZiAoIXRoaXMuZW5zdXJlSW5kZXhGbikgdGhyb3cgbmV3IEVycm9yKGAke3RoaXMuY2ZnLm5hbWV9OiBpbmRleCBub3Qgc2V0IOKAlCBjYWxsIHNldEluZGV4KC4uLikgYmVmb3JlIHJlYWRpbmdgKTtcbiAgICAgICAgcmV0dXJuIHRoaXMuZW5zdXJlSW5kZXhGbigpO1xuICAgIH1cblxuICAgIHByaXZhdGUgZm9ybWF0SW5mbyhpbmRleDogTG9hZGVkSW5kZXg8VD4pOiBzdHJpbmcge1xuICAgICAgICByZXR1cm4gYChjb2xsZWN0aW9uIGhhcyAke2JsdWUoZm9ybWF0TnVtYmVyKGluZGV4LnJlYWRlci5yb3dDb3VudCkpfSByb3dzLCAke2JsdWUoZm9ybWF0TnVtYmVyKGluZGV4LnJlYWRlci50b3RhbEJ5dGVzKSl9QilgO1xuICAgIH1cblxuICAgIC8vIE5vdGlmaWNhdGlvbnMgYXJlIHJhbXBpbmdseSBkZWxheWVkIHVuZGVyIHN1c3RhaW5lZCBjaGFuZ2VzIChzbyBhIGhpZ2gtcmF0ZSB3cml0ZXIgY2FuJ3QgcmUtcnVuXG4gICAgLy8gd2F0Y2hlcnMgcGVyIGNoYW5nZSkuIFVuZGVybHlpbmcgZGF0YSBpcyBhbHdheXMgY3VycmVudCDigJQgb25seSB0aGUgb2JzZXJ2YWJsZSBub3RpZmljYXRpb24gaXNcbiAgICAvLyBiYXRjaGVkL2RlbGF5ZWQuXG4gICAgcHJpdmF0ZSBpbnZhbGlkYXRlU2lnbmFsKHNpZ25hbDogc3RyaW5nKTogdm9pZCB7XG4gICAgICAgIGNvbnN0IG1heE1zID0gdGhpcy5jZmcubWF4VHJpZ2dlclRocm90dGxlTXMgPz8gMDtcbiAgICAgICAgaWYgKG1heE1zIDw9IDApIHsgdGhpcy5jZmcuZGVwcy5pbnZhbGlkYXRlKHNpZ25hbCk7IHJldHVybjsgfVxuICAgICAgICB0aGlzLnBlbmRpbmdTaWduYWxzLmFkZChzaWduYWwpO1xuICAgICAgICBjb25zdCBub3cgPSBEYXRlLm5vdygpO1xuICAgICAgICBjb25zdCBsdWxsID0gbm93IC0gdGhpcy5sYXN0VHJpZ2dlclRpbWUgPiBtYXhNcztcbiAgICAgICAgdGhpcy5sYXN0VHJpZ2dlclRpbWUgPSBub3c7XG4gICAgICAgIGlmICh0aGlzLnRyaWdnZXJUaW1lciAhPT0gdW5kZWZpbmVkKSByZXR1cm47XG4gICAgICAgIHRoaXMuY3VycmVudFRyaWdnZXJEZWxheSA9IGx1bGwgPyAwIDogTWF0aC5taW4obWF4TXMsIE1hdGgubWF4KFRSSUdHRVJfVEhST1RUTEVfRklSU1RfU1RFUF9NUywgdGhpcy5jdXJyZW50VHJpZ2dlckRlbGF5ICogMikpO1xuICAgICAgICB0aGlzLnRyaWdnZXJUaW1lciA9IHNldFRpbWVvdXQoKCkgPT4geyB0aGlzLnRyaWdnZXJUaW1lciA9IHVuZGVmaW5lZDsgdGhpcy5mbHVzaFNpZ25hbHMoKTsgfSwgdGhpcy5jdXJyZW50VHJpZ2dlckRlbGF5KTtcbiAgICAgICAgKHRoaXMudHJpZ2dlclRpbWVyIGFzIHsgdW5yZWY/OiAoKSA9PiB2b2lkIH0pLnVucmVmPy4oKTtcbiAgICB9XG5cbiAgICBwcml2YXRlIGZsdXNoU2lnbmFscygpOiB2b2lkIHtcbiAgICAgICAgaWYgKHRoaXMucGVuZGluZ1NpZ25hbHMuc2l6ZSA9PT0gMCkgcmV0dXJuO1xuICAgICAgICBjb25zdCBzaWduYWxzID0gWy4uLnRoaXMucGVuZGluZ1NpZ25hbHNdO1xuICAgICAgICB0aGlzLnBlbmRpbmdTaWduYWxzLmNsZWFyKCk7XG4gICAgICAgIHRoaXMuY2ZnLmRlcHMuYmF0Y2goKCkgPT4geyBmb3IgKGNvbnN0IHMgb2Ygc2lnbmFscykgdGhpcy5jZmcuZGVwcy5pbnZhbGlkYXRlKHMpOyB9KTtcbiAgICB9XG59XG5cbmV4cG9ydCBjb25zdCBSRUFERVJfU0lHTkFMUyA9IHsgTE9BRDogTE9BRF9TSUdOQUwsIE9WRVJMQVk6IE9WRVJMQVlfU0lHTkFMIH07XG5leHBvcnQgeyBudWxsSm9pbiB9O1xuIl19
306
+ /* _JS_SOURCE_HASH = "ca015ad4f2006823b4a0fde28d02fb87b03558ca59a6a2d8696ab7fd52da14e5"; */