sonamu 0.9.19 → 0.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/_virtual/_rolldown/runtime.js +36 -0
- package/dist/ai/agents/agent.js +5 -7
- package/dist/ai/agents/index.js +1 -2
- package/dist/ai/agents/types.js +1 -1
- package/dist/ai/index.js +1 -2
- package/dist/ai/providers/rtzr/api.js +2 -3
- package/dist/ai/providers/rtzr/error.js +14 -29
- package/dist/ai/providers/rtzr/index.js +1 -2
- package/dist/ai/providers/rtzr/model.js +13 -20
- package/dist/ai/providers/rtzr/options.js +2 -3
- package/dist/ai/providers/rtzr/provider.js +2 -3
- package/dist/ai/providers/rtzr/utils.js +12 -21
- package/dist/api/base-frame.js +4 -4
- package/dist/api/caster.js +21 -38
- package/dist/api/code-converters.js +41 -98
- package/dist/api/config.d.ts +1 -10
- package/dist/api/config.d.ts.map +1 -1
- package/dist/api/config.js +9 -8
- package/dist/api/context.js +2 -3
- package/dist/api/decorators.js +80 -116
- package/dist/api/index.js +2 -3
- package/dist/api/secret.js +6 -10
- package/dist/api/sonamu.d.ts.map +1 -1
- package/dist/api/sonamu.js +200 -387
- package/dist/api/validator.js +5 -8
- package/dist/api/websocket-helpers.js +21 -32
- package/dist/auth/audit-log/builders.js +2 -3
- package/dist/auth/audit-log/events.js +2 -2
- package/dist/auth/audit-log/plugin.js +30 -61
- package/dist/auth/audit-log-ingestor.js +19 -41
- package/dist/auth/auth-generator.js +16 -41
- package/dist/auth/better-auth-entities.js +3 -4
- package/dist/auth/index.js +2 -3
- package/dist/auth/knex-adapter.js +18 -45
- package/dist/auth/plugins/entity-definitions/admin.js +2 -2
- package/dist/auth/plugins/entity-definitions/anonymous.js +2 -2
- package/dist/auth/plugins/entity-definitions/api-key.js +2 -2
- package/dist/auth/plugins/entity-definitions/audit-log.js +2 -2
- package/dist/auth/plugins/entity-definitions/index.js +2 -3
- package/dist/auth/plugins/entity-definitions/jwt.js +2 -2
- package/dist/auth/plugins/entity-definitions/organization.js +2 -2
- package/dist/auth/plugins/entity-definitions/passkey.js +2 -2
- package/dist/auth/plugins/entity-definitions/phone-number.js +2 -2
- package/dist/auth/plugins/entity-definitions/sso.js +2 -2
- package/dist/auth/plugins/entity-definitions/two-factor.js +2 -2
- package/dist/auth/plugins/entity-definitions/types.js +1 -1
- package/dist/auth/plugins/entity-definitions/username.js +2 -2
- package/dist/auth/plugins/index.js +1 -2
- package/dist/auth/plugins/wrappers/admin.js +2 -3
- package/dist/auth/plugins/wrappers/anonymous.js +2 -3
- package/dist/auth/plugins/wrappers/api-key.js +2 -3
- package/dist/auth/plugins/wrappers/index.js +1 -2
- package/dist/auth/plugins/wrappers/jwt.js +2 -3
- package/dist/auth/plugins/wrappers/organization.js +2 -3
- package/dist/auth/plugins/wrappers/passkey.js +2 -3
- package/dist/auth/plugins/wrappers/phone-number.js +2 -3
- package/dist/auth/plugins/wrappers/sso.js +2 -3
- package/dist/auth/plugins/wrappers/two-factor.js +2 -3
- package/dist/auth/plugins/wrappers/username.js +2 -3
- package/dist/bin/build-config.js +2 -2
- package/dist/bin/cli.js +151 -258
- package/dist/bin/fixture.d.ts.map +1 -1
- package/dist/bin/fixture.js +55 -97
- package/dist/bin/hmr-hook-register.js +3 -3
- package/dist/bin/migrate-targets.d.ts +3 -0
- package/dist/bin/migrate-targets.d.ts.map +1 -0
- package/dist/bin/migrate-targets.js +11 -0
- package/dist/bin/test-command.js +25 -55
- package/dist/bin/ts-loader-register.js +5 -6
- package/dist/bin/ts-loader-registration.js +6 -13
- package/dist/cache/cache-manager.js +3 -4
- package/dist/cache/decorator.js +11 -21
- package/dist/cache/drivers.js +2 -3
- package/dist/cache/index.js +2 -3
- package/dist/cache/types.js +1 -1
- package/dist/cache-control/cache-control.js +21 -34
- package/dist/cache-control/types.js +1 -1
- package/dist/compress/compress.js +10 -10
- package/dist/compress/index.js +1 -2
- package/dist/compress/types.js +1 -1
- package/dist/cone/cone-generator.js +25 -63
- package/dist/database/_batch_update.js +26 -46
- package/dist/database/base-model.js +44 -97
- package/dist/database/base-model.types.js +1 -1
- package/dist/database/db.d.ts +8 -14
- package/dist/database/db.d.ts.map +1 -1
- package/dist/database/db.js +127 -72
- package/dist/database/knex.js +5 -8
- package/dist/database/puri-subset.types.js +1 -1
- package/dist/database/puri-wrapper.js +11 -15
- package/dist/database/puri.js +117 -234
- package/dist/database/puri.types.js +3 -4
- package/dist/database/transaction-context.js +4 -5
- package/dist/database/upsert-builder.js +109 -176
- package/dist/dict/en.d.ts +1 -0
- package/dist/dict/en.d.ts.map +1 -1
- package/dist/dict/en.js +4 -4
- package/dist/dict/index.js +2 -3
- package/dist/dict/ko.d.ts +1 -0
- package/dist/dict/ko.d.ts.map +1 -1
- package/dist/dict/ko.js +4 -4
- package/dist/dict/rc-keys.js +3 -4
- package/dist/dict/sd.js +8 -19
- package/dist/dict/sonamu-dictionary.js +141 -284
- package/dist/dict/types.js +1 -1
- package/dist/dict/utils.js +4 -5
- package/dist/entity/entity-manager.d.ts +2 -2
- package/dist/entity/entity-manager.js +34 -82
- package/dist/entity/entity-template-cone.js +33 -66
- package/dist/entity/entity.js +156 -310
- package/dist/env.d.ts +14 -0
- package/dist/env.d.ts.map +1 -0
- package/dist/env.js +75 -0
- package/dist/exceptions/error-handler.js +2 -3
- package/dist/exceptions/so-exceptions.js +7 -5
- package/dist/filter/index.js +1 -2
- package/dist/filter/types.js +3 -4
- package/dist/filter/utils.js +21 -54
- package/dist/index.js +8 -7
- package/dist/logger/category.js +6 -12
- package/dist/logger/configure.js +23 -34
- package/dist/migration/code-generation.js +146 -314
- package/dist/migration/index-where-predicate.js +52 -144
- package/dist/migration/migration-set.js +19 -33
- package/dist/migration/migrator.d.ts +2 -0
- package/dist/migration/migrator.d.ts.map +1 -1
- package/dist/migration/migrator.js +69 -53
- package/dist/migration/postgresql-schema-reader.js +126 -225
- package/dist/migration/slack-confirm.d.ts +1 -0
- package/dist/migration/slack-confirm.d.ts.map +1 -1
- package/dist/migration/slack-confirm.js +28 -38
- package/dist/migration/types.js +1 -1
- package/dist/naite/messaging-types.js +1 -1
- package/dist/naite/naite-reporter.js +15 -32
- package/dist/naite/naite.js +43 -76
- package/dist/ssr/index.js +6 -9
- package/dist/ssr/registry.js +10 -18
- package/dist/ssr/renderer.js +10 -21
- package/dist/ssr/types.js +1 -1
- package/dist/storage/base-file.js +5 -10
- package/dist/storage/buffered-file.js +3 -4
- package/dist/storage/drivers.js +2 -3
- package/dist/storage/index.js +2 -3
- package/dist/storage/s3-driver.js +5 -9
- package/dist/storage/storage-manager.js +5 -5
- package/dist/storage/types.js +1 -1
- package/dist/storage/uploaded-file.js +4 -6
- package/dist/stream/index.js +1 -2
- package/dist/stream/sse.js +8 -13
- package/dist/stream/ws-audience-resolver.js +5 -5
- package/dist/stream/ws-audience.js +3 -4
- package/dist/stream/ws-cluster-bus.js +3 -4
- package/dist/stream/ws-core.js +1 -1
- package/dist/stream/ws-delivery.js +11 -25
- package/dist/stream/ws-local-connection-store.js +9 -18
- package/dist/stream/ws-presence-store.js +43 -97
- package/dist/stream/ws-registry.js +17 -22
- package/dist/stream/ws-telemetry-memory.js +38 -45
- package/dist/stream/ws-telemetry-trace.js +4 -6
- package/dist/stream/ws-telemetry.js +82 -135
- package/dist/stream/ws.js +47 -91
- package/dist/syncer/api-parser.js +81 -147
- package/dist/syncer/checksum.js +9 -20
- package/dist/syncer/code-generator.js +29 -47
- package/dist/syncer/entity-operations.js +17 -27
- package/dist/syncer/event-batcher.js +8 -15
- package/dist/syncer/file-patterns.js +3 -4
- package/dist/syncer/file-tracking.js +6 -10
- package/dist/syncer/index.js +1 -2
- package/dist/syncer/module-loader.js +10 -26
- package/dist/syncer/syncer-actions.js +19 -37
- package/dist/syncer/syncer.js +46 -98
- package/dist/syncer/watcher.js +12 -26
- package/dist/tasks/decorator.js +7 -11
- package/dist/tasks/step-wrapper.js +7 -8
- package/dist/tasks/workflow-manager.js +18 -25
- package/dist/template/entity-converter.js +40 -64
- package/dist/template/helpers.js +32 -63
- package/dist/template/implementations/entity.template.js +7 -11
- package/dist/template/implementations/entry-server.template.js +2 -3
- package/dist/template/implementations/generated.template.js +25 -51
- package/dist/template/implementations/generated_http.template.js +31 -58
- package/dist/template/implementations/generated_sso.template.js +45 -85
- package/dist/template/implementations/init_types.template.js +4 -7
- package/dist/template/implementations/model.template.js +5 -10
- package/dist/template/implementations/model_test.template.js +2 -3
- package/dist/template/implementations/queries.template.js +4 -7
- package/dist/template/implementations/sd.template.js +17 -35
- package/dist/template/implementations/services.template.js +18 -30
- package/dist/template/implementations/view_form.template.js +72 -125
- package/dist/template/implementations/view_id_all_select.template.js +2 -3
- package/dist/template/implementations/view_list.template.js +86 -143
- package/dist/template/implementations/view_search_input.template.js +2 -3
- package/dist/template/index.js +5 -8
- package/dist/template/template-manager.js +13 -26
- package/dist/template/template-types.js +2 -3
- package/dist/template/template.js +7 -11
- package/dist/template/zod-converter.js +173 -348
- package/dist/testing/_relation-graph.js +18 -37
- package/dist/testing/bootstrap.js +5 -8
- package/dist/testing/data-explorer.js +34 -78
- package/dist/testing/dev-test-routes.js +54 -60
- package/dist/testing/dev-vitest-manager.js +33 -84
- package/dist/testing/faker-mappings.js +3 -4
- package/dist/testing/fixture-generator.d.ts +2 -1
- package/dist/testing/fixture-generator.d.ts.map +1 -1
- package/dist/testing/fixture-generator.js +159 -321
- package/dist/testing/fixture-loader.js +2 -2
- package/dist/testing/fixture-manager.d.ts.map +1 -1
- package/dist/testing/fixture-manager.js +124 -227
- package/dist/testing/global-setup.d.ts.map +1 -1
- package/dist/testing/global-setup.js +29 -17
- package/dist/testing/index.js +1 -2
- package/dist/testing/naite-vitest-reporter.js +2 -3
- package/dist/testing/parallel-db-manager.js +5 -3
- package/dist/testing/vitest-helpers.d.ts.map +1 -1
- package/dist/testing/vitest-helpers.js +15 -12
- package/dist/types/types.d.ts +14 -14
- package/dist/types/types.js +27 -50
- package/dist/ui/ai-api.js +6 -11
- package/dist/ui/ai-client.js +86 -134
- package/dist/ui/api.js +99 -195
- package/dist/ui/cdd-service.js +78 -130
- package/dist/ui/cdd-types.js +1 -1
- package/dist/ui-web/assets/{index-Df8q-fhb.js → index-DFStGyd0.js} +49 -49
- package/dist/ui-web/assets/index-Dx4ap5i4.css +1 -0
- package/dist/ui-web/index.html +2 -2
- package/dist/utils/async-utils.js +13 -25
- package/dist/utils/class-name.js +3 -4
- package/dist/utils/console-util.js +11 -26
- package/dist/utils/controller.d.ts.map +1 -1
- package/dist/utils/controller.js +14 -12
- package/dist/utils/esm-utils.js +5 -8
- package/dist/utils/formatter.js +10 -22
- package/dist/utils/fs-utils.js +14 -25
- package/dist/utils/lodash-able.js +3 -4
- package/dist/utils/model.js +7 -14
- package/dist/utils/object-utils.js +41 -73
- package/dist/utils/path-utils.js +5 -9
- package/dist/utils/process-utils.js +4 -7
- package/dist/utils/sql-parser.js +6 -13
- package/dist/utils/type-utils.js +16 -26
- package/dist/utils/utils.js +18 -40
- package/dist/utils/zod-error.js +9 -16
- package/dist/vector/chunking.js +24 -37
- package/dist/vector/config.js +2 -2
- package/dist/vector/embedding.js +8 -19
- package/dist/vector/index.js +1 -2
- package/dist/vector/types.js +1 -1
- package/package.json +7 -7
- package/src/__tests__/env.test.ts +127 -0
- package/src/api/__tests__/config.test.ts +10 -1
- package/src/api/config.ts +4 -12
- package/src/api/sonamu.ts +14 -4
- package/src/bin/__tests__/migrate-targets.test.ts +28 -0
- package/src/bin/__tests__/test-command.test.ts +82 -1
- package/src/bin/cli.ts +9 -18
- package/src/bin/fixture.ts +5 -4
- package/src/bin/migrate-targets.ts +7 -0
- package/src/bin/test-command.ts +2 -2
- package/src/database/__tests__/db.test.ts +175 -0
- package/src/database/db.ts +193 -71
- package/src/dict/en.ts +2 -0
- package/src/dict/ko.ts +2 -0
- package/src/env.ts +123 -0
- package/src/migration/__tests__/migrator.test.ts +149 -0
- package/src/migration/migrator.ts +74 -17
- package/src/migration/slack-confirm.ts +21 -0
- package/src/skills/sonamu/database.md +1 -1
- package/src/skills/sonamu/entity-basic.md +31 -0
- package/src/skills/sonamu/puri.md +22 -0
- package/src/skills/sonamu/testing-devrunner.md +1 -1
- package/src/skills/sonamu/upsert.md +53 -6
- package/src/stream/ws-telemetry-memory.ts +2 -2
- package/src/testing/fixture-generator.ts +2 -1
- package/src/testing/fixture-manager.ts +3 -4
- package/src/testing/global-setup.ts +42 -18
- package/src/testing/vitest-helpers.ts +14 -0
- package/src/utils/controller.ts +14 -7
- package/tsdown.api.config.ts +6 -0
- package/dist/_virtual/rolldown_runtime.js +0 -39
- package/dist/ui-web/assets/index-D4rYm-Xz.css +0 -1
package/dist/stream/ws.js
CHANGED
|
@@ -1,28 +1,19 @@
|
|
|
1
|
-
import { __esmMin } from "../_virtual/
|
|
1
|
+
import { __esmMin } from "../_virtual/_rolldown/runtime.js";
|
|
2
2
|
import { generateSpanId, init_ws_telemetry_trace, parseTraceParent } from "./ws-telemetry-trace.js";
|
|
3
3
|
import { createWebSocketTelemetryController, init_ws_telemetry, isPromiseLike } from "./ws-telemetry.js";
|
|
4
4
|
import { WebSocketRegistry, init_ws_registry } from "./ws-registry.js";
|
|
5
5
|
import { z as z$1 } from "zod";
|
|
6
6
|
import { randomUUID } from "node:crypto";
|
|
7
7
|
import { hostname } from "node:os";
|
|
8
|
-
|
|
9
8
|
//#region src/stream/ws.ts
|
|
10
9
|
function createWebSocketRuntime(options = {}) {
|
|
11
10
|
return new WebSocketRuntime(options);
|
|
12
11
|
}
|
|
13
12
|
function normalizeMessage(raw) {
|
|
14
|
-
if (typeof raw === "string")
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
if (raw instanceof Buffer)
|
|
18
|
-
return raw.toString("utf-8");
|
|
19
|
-
}
|
|
20
|
-
if (raw instanceof ArrayBuffer) {
|
|
21
|
-
return Buffer.from(raw).toString("utf-8");
|
|
22
|
-
}
|
|
23
|
-
if (Array.isArray(raw)) {
|
|
24
|
-
return Buffer.concat(raw.filter((chunk) => chunk instanceof Buffer)).toString("utf-8");
|
|
25
|
-
}
|
|
13
|
+
if (typeof raw === "string") return raw;
|
|
14
|
+
if (raw instanceof Buffer) return raw.toString("utf-8");
|
|
15
|
+
if (raw instanceof ArrayBuffer) return Buffer.from(raw).toString("utf-8");
|
|
16
|
+
if (Array.isArray(raw)) return Buffer.concat(raw.filter((chunk) => chunk instanceof Buffer)).toString("utf-8");
|
|
26
17
|
return JSON.stringify(raw);
|
|
27
18
|
}
|
|
28
19
|
function safeParseEnvelope(raw) {
|
|
@@ -35,13 +26,11 @@ function safeParseEnvelope(raw) {
|
|
|
35
26
|
}
|
|
36
27
|
}
|
|
37
28
|
function truncateCloseReason(reason) {
|
|
38
|
-
if (!reason)
|
|
39
|
-
return undefined;
|
|
40
|
-
}
|
|
29
|
+
if (!reason) return;
|
|
41
30
|
return Buffer.byteLength(reason, "utf-8") <= 123 ? reason : Buffer.from(reason).subarray(0, 123).toString("utf-8");
|
|
42
31
|
}
|
|
43
32
|
function deriveLifetimeStatus(code) {
|
|
44
|
-
if (code ===
|
|
33
|
+
if (code === void 0) return "unset";
|
|
45
34
|
if (code === 1e3 || code === 1001) return "ok";
|
|
46
35
|
return "error";
|
|
47
36
|
}
|
|
@@ -116,11 +105,13 @@ var init_ws = __esmMin((() => {
|
|
|
116
105
|
}
|
|
117
106
|
};
|
|
118
107
|
WebSocketConnectionImpl = class {
|
|
108
|
+
socket;
|
|
109
|
+
options;
|
|
119
110
|
id = randomUUID();
|
|
120
111
|
transport = "ws";
|
|
121
112
|
namespace;
|
|
122
113
|
closeCallbacks = [];
|
|
123
|
-
messageHandlers = new Map();
|
|
114
|
+
messageHandlers = /* @__PURE__ */ new Map();
|
|
124
115
|
pendingMessages = [];
|
|
125
116
|
pendingOutboundMessages = [];
|
|
126
117
|
closePromise;
|
|
@@ -199,7 +190,7 @@ var init_ws = __esmMin((() => {
|
|
|
199
190
|
this.options.registry.setUserId(this.id, userId);
|
|
200
191
|
}
|
|
201
192
|
clearUserId() {
|
|
202
|
-
this._userId =
|
|
193
|
+
this._userId = void 0;
|
|
203
194
|
this.options.registry.clearUserId(this.id);
|
|
204
195
|
}
|
|
205
196
|
getTelemetrySnapshot() {
|
|
@@ -234,7 +225,7 @@ var init_ws = __esmMin((() => {
|
|
|
234
225
|
name: "ws.message.rejected",
|
|
235
226
|
level: "warn",
|
|
236
227
|
...fields,
|
|
237
|
-
detail: event !==
|
|
228
|
+
detail: event !== void 0 ? {
|
|
238
229
|
reason,
|
|
239
230
|
event
|
|
240
231
|
} : { reason }
|
|
@@ -252,9 +243,7 @@ var init_ws = __esmMin((() => {
|
|
|
252
243
|
});
|
|
253
244
|
}
|
|
254
245
|
close(code, reason) {
|
|
255
|
-
if (this.closedInternal || this.closeStarted || this.socket.readyState === WS_CLOSED)
|
|
256
|
-
return;
|
|
257
|
-
}
|
|
246
|
+
if (this.closedInternal || this.closeStarted || this.socket.readyState === WS_CLOSED) return;
|
|
258
247
|
this.closeStarted = true;
|
|
259
248
|
try {
|
|
260
249
|
this.closeTransport(code, reason);
|
|
@@ -264,8 +253,7 @@ var init_ws = __esmMin((() => {
|
|
|
264
253
|
}
|
|
265
254
|
handleMessage = (raw) => {
|
|
266
255
|
this.enqueueMessageTask(async () => {
|
|
267
|
-
const
|
|
268
|
-
const parsedEnvelope = safeParseEnvelope(text);
|
|
256
|
+
const parsedEnvelope = safeParseEnvelope(normalizeMessage(raw));
|
|
269
257
|
if (!parsedEnvelope) {
|
|
270
258
|
this.emitInboundRejected("invalidPayload");
|
|
271
259
|
this.close(WS_CLOSE_CODE_INVALID_FRAME_PAYLOAD_DATA, "Invalid message payload");
|
|
@@ -297,14 +285,12 @@ var init_ws = __esmMin((() => {
|
|
|
297
285
|
const messageSpanId = generateSpanId();
|
|
298
286
|
if (this.options.telemetryController.getTraceOptions().propagateMessageTrace && envelope.meta?.traceparent) {
|
|
299
287
|
const parsed = parseTraceParent(envelope.meta.traceparent);
|
|
300
|
-
if (parsed) {
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
};
|
|
307
|
-
}
|
|
288
|
+
if (parsed) return {
|
|
289
|
+
traceId: parsed.traceId,
|
|
290
|
+
spanId: messageSpanId,
|
|
291
|
+
parentSpanId: parsed.parentId,
|
|
292
|
+
sampled: parsed.sampled
|
|
293
|
+
};
|
|
308
294
|
this.options.telemetryController.emit({
|
|
309
295
|
name: "ws.trace.invalid",
|
|
310
296
|
level: "debug",
|
|
@@ -366,9 +352,7 @@ var init_ws = __esmMin((() => {
|
|
|
366
352
|
sampled: traceCtx.sampled
|
|
367
353
|
};
|
|
368
354
|
try {
|
|
369
|
-
for (const handler of handlers)
|
|
370
|
-
await handler(parsed.data, traceCtx);
|
|
371
|
-
}
|
|
355
|
+
for (const handler of handlers) await handler(parsed.data, traceCtx);
|
|
372
356
|
this.options.telemetryController.emit({
|
|
373
357
|
name: "ws.message.dispatched",
|
|
374
358
|
level: "debug",
|
|
@@ -409,11 +393,9 @@ var init_ws = __esmMin((() => {
|
|
|
409
393
|
}
|
|
410
394
|
this.pendingMessages.length = 0;
|
|
411
395
|
this.pendingMessages.push(...remaining);
|
|
412
|
-
for (const message of toFlush) {
|
|
413
|
-
this.
|
|
414
|
-
|
|
415
|
-
});
|
|
416
|
-
}
|
|
396
|
+
for (const message of toFlush) this.enqueueMessageTask(async () => {
|
|
397
|
+
await this.dispatchEnvelope(message);
|
|
398
|
+
});
|
|
417
399
|
}
|
|
418
400
|
publishValidated(event, data) {
|
|
419
401
|
const schema = this.eventSchemasOut[event];
|
|
@@ -460,9 +442,7 @@ var init_ws = __esmMin((() => {
|
|
|
460
442
|
}), event, parsed.data);
|
|
461
443
|
}
|
|
462
444
|
markClosed(code, _reason) {
|
|
463
|
-
if (this.closedInternal)
|
|
464
|
-
return;
|
|
465
|
-
}
|
|
445
|
+
if (this.closedInternal) return;
|
|
466
446
|
this.closedInternal = true;
|
|
467
447
|
this.closeStarted = false;
|
|
468
448
|
this.stopHeartbeat();
|
|
@@ -472,15 +452,13 @@ var init_ws = __esmMin((() => {
|
|
|
472
452
|
level: "info",
|
|
473
453
|
...fields
|
|
474
454
|
});
|
|
475
|
-
if (this.options.telemetryController.getTraceOptions().recordConnectionLifetimeSpan) {
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
});
|
|
483
|
-
}
|
|
455
|
+
if (this.options.telemetryController.getTraceOptions().recordConnectionLifetimeSpan) this.options.telemetryController.recordSpan({
|
|
456
|
+
operationName: "ws.connection.lifetime",
|
|
457
|
+
kind: "server",
|
|
458
|
+
durationMs: performance.now() - this.connectionStartedAt,
|
|
459
|
+
status: deriveLifetimeStatus(code),
|
|
460
|
+
...fields
|
|
461
|
+
});
|
|
484
462
|
this.socket.off("message", this.handleMessage);
|
|
485
463
|
this.socket.off("close", this.handleClose);
|
|
486
464
|
this.socket.off("error", this.handleError);
|
|
@@ -489,24 +467,16 @@ var init_ws = __esmMin((() => {
|
|
|
489
467
|
this.pendingMessages.length = 0;
|
|
490
468
|
this.pendingOutboundMessages.length = 0;
|
|
491
469
|
this.options.registry.unregister(this.id);
|
|
492
|
-
for (const callback of this.closeCallbacks.splice(0)) {
|
|
493
|
-
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
void result.catch(() => {});
|
|
497
|
-
}
|
|
498
|
-
} catch {}
|
|
499
|
-
}
|
|
470
|
+
for (const callback of this.closeCallbacks.splice(0)) try {
|
|
471
|
+
const result = callback();
|
|
472
|
+
if (isPromiseLike(result)) result.catch(() => {});
|
|
473
|
+
} catch {}
|
|
500
474
|
this.resolveClosePromise();
|
|
501
475
|
}
|
|
502
476
|
startHeartbeat() {
|
|
503
|
-
if (this.heartbeatMs <= 0)
|
|
504
|
-
return;
|
|
505
|
-
}
|
|
477
|
+
if (this.heartbeatMs <= 0) return;
|
|
506
478
|
this.heartbeatTimer = setInterval(() => {
|
|
507
|
-
if (this.closedInternal || this.socket.readyState !== WS_OPEN)
|
|
508
|
-
return;
|
|
509
|
-
}
|
|
479
|
+
if (this.closedInternal || this.socket.readyState !== WS_OPEN) return;
|
|
510
480
|
if (this.awaitingPong) {
|
|
511
481
|
this.options.telemetryController.emit({
|
|
512
482
|
name: "ws.heartbeat.timeout",
|
|
@@ -521,9 +491,7 @@ var init_ws = __esmMin((() => {
|
|
|
521
491
|
}, this.heartbeatMs);
|
|
522
492
|
}
|
|
523
493
|
stopHeartbeat() {
|
|
524
|
-
if (!this.heartbeatTimer)
|
|
525
|
-
return;
|
|
526
|
-
}
|
|
494
|
+
if (!this.heartbeatTimer) return;
|
|
527
495
|
clearInterval(this.heartbeatTimer);
|
|
528
496
|
this.heartbeatTimer = null;
|
|
529
497
|
}
|
|
@@ -542,9 +510,7 @@ var init_ws = __esmMin((() => {
|
|
|
542
510
|
}
|
|
543
511
|
enqueueMessageTask(task) {
|
|
544
512
|
this.messageQueue = this.messageQueue.then(async () => {
|
|
545
|
-
if (this.closedInternal)
|
|
546
|
-
return;
|
|
547
|
-
}
|
|
513
|
+
if (this.closedInternal) return;
|
|
548
514
|
await task();
|
|
549
515
|
}).catch(() => {
|
|
550
516
|
this.close(WS_CLOSE_CODE_INTERNAL_ERROR, "Message handling failed");
|
|
@@ -574,9 +540,7 @@ var init_ws = __esmMin((() => {
|
|
|
574
540
|
this.scheduleOutboundFlush();
|
|
575
541
|
}
|
|
576
542
|
scheduleOutboundFlush(delayMs = 0) {
|
|
577
|
-
if (this.outboundFlushScheduled || this.closedInternal)
|
|
578
|
-
return;
|
|
579
|
-
}
|
|
543
|
+
if (this.outboundFlushScheduled || this.closedInternal) return;
|
|
580
544
|
this.outboundFlushScheduled = true;
|
|
581
545
|
const flush = () => {
|
|
582
546
|
this.outboundFlushScheduled = false;
|
|
@@ -589,9 +553,7 @@ var init_ws = __esmMin((() => {
|
|
|
589
553
|
setImmediate(flush);
|
|
590
554
|
}
|
|
591
555
|
flushOutboundMessages() {
|
|
592
|
-
if (this.closedInternal || this.socket.readyState !== WS_OPEN)
|
|
593
|
-
return;
|
|
594
|
-
}
|
|
556
|
+
if (this.closedInternal || this.socket.readyState !== WS_OPEN) return;
|
|
595
557
|
if (this.socket.bufferedAmount > MAX_SOCKET_BUFFERED_AMOUNT) {
|
|
596
558
|
this.options.telemetryController.emit({
|
|
597
559
|
name: "ws.backpressure.delayed",
|
|
@@ -604,9 +566,7 @@ var init_ws = __esmMin((() => {
|
|
|
604
566
|
let sent = 0;
|
|
605
567
|
while (sent < OUTBOUND_BATCH_SIZE && this.pendingOutboundMessages.length > 0 && this.socket.readyState === WS_OPEN) {
|
|
606
568
|
const next = this.pendingOutboundMessages.shift();
|
|
607
|
-
if (!next)
|
|
608
|
-
break;
|
|
609
|
-
}
|
|
569
|
+
if (!next) break;
|
|
610
570
|
const { payload, event } = next;
|
|
611
571
|
const startedAt = performance.now();
|
|
612
572
|
const fields = this.telemetryFields();
|
|
@@ -659,18 +619,14 @@ var init_ws = __esmMin((() => {
|
|
|
659
619
|
return;
|
|
660
620
|
}
|
|
661
621
|
sent += 1;
|
|
662
|
-
if (this.socket.bufferedAmount > MAX_SOCKET_BUFFERED_AMOUNT)
|
|
663
|
-
break;
|
|
664
|
-
}
|
|
665
|
-
}
|
|
666
|
-
if (this.pendingOutboundMessages.length > 0) {
|
|
667
|
-
this.scheduleOutboundFlush(this.socket.bufferedAmount > MAX_SOCKET_BUFFERED_AMOUNT ? OUTBOUND_RETRY_DELAY_MS : 0);
|
|
622
|
+
if (this.socket.bufferedAmount > MAX_SOCKET_BUFFERED_AMOUNT) break;
|
|
668
623
|
}
|
|
624
|
+
if (this.pendingOutboundMessages.length > 0) this.scheduleOutboundFlush(this.socket.bufferedAmount > MAX_SOCKET_BUFFERED_AMOUNT ? OUTBOUND_RETRY_DELAY_MS : 0);
|
|
669
625
|
}
|
|
670
626
|
};
|
|
671
627
|
}));
|
|
672
|
-
|
|
673
628
|
//#endregion
|
|
674
629
|
init_ws();
|
|
675
630
|
export { WebSocketRuntime, createWebSocketRuntime, init_ws };
|
|
676
|
-
//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoid3MuanMiLCJuYW1lcyI6WyJ6IiwicmVnaXN0cnlPcHRpb25zOiBXZWJTb2NrZXRSZWdpc3RyeU9wdGlvbnMiLCJzb2NrZXQ6IFdlYlNvY2tldCIsIm9wdGlvbnM6IFdlYlNvY2tldENvbm5lY3Rpb25PcHRpb25zPFRPdXRTY2hlbWEsIFRJblNjaGVtYT4iLCJyZXNvbHZlQ2xvc2VQcm9taXNlITogKCkgPT4gdm9pZCIsInJlbWFpbmluZzogUGFyc2VkRW52ZWxvcGVbXSIsInRvRmx1c2g6IFBhcnNlZEVudmVsb3BlW10iXSwic291cmNlcyI6WyIuLi8uLi9zcmMvc3RyZWFtL3dzLnRzIl0sInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IHJhbmRvbVVVSUQgfSBmcm9tIFwibm9kZTpjcnlwdG9cIjtcbmltcG9ydCB7IGhvc3RuYW1lIH0gZnJvbSBcIm5vZGU6b3NcIjtcblxuaW1wb3J0IHsgdHlwZSBXZWJTb2NrZXQgfSBmcm9tIFwid3NcIjtcbmltcG9ydCB7IHogfSBmcm9tIFwiem9kXCI7XG5cbmltcG9ydCB7IHR5cGUgV2ViU29ja2V0QXVkaWVuY2UgfSBmcm9tIFwiLi93cy1hdWRpZW5jZVwiO1xuaW1wb3J0IHsgdHlwZSBXZWJTb2NrZXRDbHVzdGVyQnVzIH0gZnJvbSBcIi4vd3MtY2x1c3Rlci1idXNcIjtcbmltcG9ydCB7IHR5cGUgV2ViU29ja2V0UHJlc2VuY2VTdG9yZSB9IGZyb20gXCIuL3dzLXByZXNlbmNlLXN0b3JlXCI7XG5pbXBvcnQge1xuICB0eXBlIE1hbmFnZWRXZWJTb2NrZXRDb25uZWN0aW9uLFxuICBXZWJTb2NrZXRSZWdpc3RyeSxcbiAgdHlwZSBXZWJTb2NrZXRSZWdpc3RyeU9wdGlvbnMsXG4gIHR5cGUgV2ViU29ja2V0Um9vbUlkLFxuICB0eXBlIFdlYlNvY2tldFVzZXJJZCxcbn0gZnJvbSBcIi4vd3MtcmVnaXN0cnlcIjtcbmltcG9ydCB7XG4gIHR5cGUgVGVsZW1ldHJ5Q29udGV4dFByb3ZpZGVyLFxuICB0eXBlIFdlYlNvY2tldFRlbGVtZXRyeUNvbm5lY3Rpb25TbmFwc2hvdCxcbiAgdHlwZSBXZWJTb2NrZXRUZWxlbWV0cnlDb25uZWN0aW9uQ29udGV4dCxcbiAgdHlwZSBXZWJTb2NrZXRUZWxlbWV0cnlDb250cm9sbGVyLFxuICB0eXBlIFdlYlNvY2tldFRlbGVtZXRyeU9wdGlvbnMsXG4gIHR5cGUgVGVsZW1ldHJ5SW5zcGVjdGFibGVDb25uZWN0aW9uLFxuICBjcmVhdGVXZWJTb2NrZXRUZWxlbWV0cnlDb250cm9sbGVyLFxuICBpc1Byb21pc2VMaWtlLFxufSBmcm9tIFwiLi93cy10ZWxlbWV0cnlcIjtcbmltcG9ydCB7IHBhcnNlVHJhY2VQYXJlbnQsIGdlbmVyYXRlU3BhbklkIH0gZnJvbSBcIi4vd3MtdGVsZW1ldHJ5LXRyYWNlXCI7XG5cbi8vIHRyYW5zcG9ydC1sZXZlbCDsg4HsiJjsmYAgcXVldWUgdGhyZXNob2xk66W8IO2VnCDtjIzsnbzsl5Ag66qo7JWEIGxpZmVjeWNsZS9iYWNrcHJlc3N1cmUg7KCV7LGF7J2EIOykkeyVme2ZlO2VqFxuY29uc3QgV1NfQ09OTkVDVElORyA9IDA7XG5jb25zdCBXU19PUEVOID0gMTtcbmNvbnN0IFdTX0NMT1NFRCA9IDM7XG4vLyBSRkMgNjQ1NSBjbG9zZSBjb2RlcyB1c2VkIGJ5IFNvbmFtdSdzIFdlYlNvY2tldCBydW50aW1lLlxuY29uc3QgV1NfQ0xPU0VfQ09ERV9HT0lOR19BV0FZID0gMTAwMTtcbmNvbnN0IFdTX0NMT1NFX0NPREVfSU5WQUxJRF9GUkFNRV9QQVlMT0FEX0RBVEEgPSAxMDA3O1xuY29uc3QgV1NfQ0xPU0VfQ09ERV9QT0xJQ1lfVklPTEFUSU9OID0gMTAwODtcbmNvbnN0IFdTX0NMT1NFX0NPREVfSU5URVJOQUxfRVJST1IgPSAxMDExO1xuY29uc3QgV1NfQ0xPU0VfQ09ERV9UUllfQUdBSU5fTEFURVIgPSAxMDEzO1xuY29uc3QgTUFYX1BFTkRJTkdfTUVTU0FHRVMgPSAxMDA7XG5jb25zdCBNQVhfUEVORElOR19PVVRCT1VORF9NRVNTQUdFUyA9IDFfMDAwO1xuY29uc3QgTUFYX1NPQ0tFVF9CVUZGRVJFRF9BTU9VTlQgPSAxXzA0OF81NzY7XG5jb25zdCBPVVRCT1VORF9CQVRDSF9TSVpFID0gNTA7XG5jb25zdCBPVVRCT1VORF9SRVRSWV9ERUxBWV9NUyA9IDU7XG5cbi8vIGVudmVsb3Bl7J2EIGB7ZXZlbnQsIGRhdGF9YCDtmJXtg5zroZwg6rOg7KCV7ZW0IHNlcnZlciBoYW5kbGVy7JmAIGdlbmVyYXRlZCBjbGllbnTqsIAg6rCZ7J2AIGZyYW1pbmcgY29udHJhY3Trpbwg7JOw6rKMIO2VqFxuLy8gbWV0YeuKlCBvcHRpb25hbOydtOuvgOuhnCDquLDsobQgYHtldmVudCwgZGF0YX1gIOuplOyLnOyngOuPhCDqt7jrjIDroZwg7YyM7Iux65CoIChiYWNrd2FyZC1jb21wYXRpYmxlKVxuY29uc3QgV2ViU29ja2V0RW52ZWxvcGVTY2hlbWEgPSB6Lm9iamVjdCh7XG4gIGV2ZW50OiB6LnN0cmluZygpLFxuICBkYXRhOiB6LnVua25vd24oKSxcbiAgbWV0YTogelxuICAgIC5vYmplY3Qoe1xuICAgICAgdHJhY2VwYXJlbnQ6IHouc3RyaW5nKCkub3B0aW9uYWwoKSxcbiAgICAgIHRyYWNlc3RhdGU6IHouc3RyaW5nKCkub3B0aW9uYWwoKSxcbiAgICB9KVxuICAgIC5vcHRpb25hbCgpLFxufSk7XG5cbnR5cGUgTWVzc2FnZUhhbmRsZXI8VD4gPSAoXG4gIGRhdGE6IFQsXG4gIHRlbGVtZXRyeUNvbnRleHQ/OiBXZWJTb2NrZXRUZWxlbWV0cnlDb25uZWN0aW9uQ29udGV4dCxcbikgPT4gdm9pZCB8IFByb21pc2U8dm9pZD47XG50eXBlIENsb3NlSGFuZGxlciA9ICgpID0+IHZvaWQgfCBQcm9taXNlPHZvaWQ+O1xuXG5leHBvcnQgdHlwZSBXZWJTb2NrZXRFdmVudE1hcCA9IFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuXG50eXBlIEluZmVyV2ViU29ja2V0RXZlbnRNYXA8VFNjaGVtYSBleHRlbmRzIHouWm9kUmF3U2hhcGU+ID0gei5pbmZlcjx6LlpvZE9iamVjdDxUU2NoZW1hPj47XG5cbmV4cG9ydCB0eXBlIFdlYlNvY2tldE91dEV2ZW50czxUT3V0IGV4dGVuZHMgV2ViU29ja2V0RXZlbnRNYXAgPSBXZWJTb2NrZXRFdmVudE1hcD4gPSBUT3V0O1xuXG5leHBvcnQgdHlwZSBXZWJTb2NrZXRJbkV2ZW50czxUSW4gZXh0ZW5kcyBXZWJTb2NrZXRFdmVudE1hcCA9IFdlYlNvY2tldEV2ZW50TWFwPiA9IFRJbjtcblxuZXhwb3J0IGludGVyZmFjZSBXZWJTb2NrZXRDb25uZWN0aW9uPFxuICBUT3V0IGV4dGVuZHMgV2ViU29ja2V0RXZlbnRNYXAgPSBXZWJTb2NrZXRFdmVudE1hcCxcbiAgVEluIGV4dGVuZHMgV2ViU29ja2V0RXZlbnRNYXAgPSBXZWJTb2NrZXRFdmVudE1hcCxcbj4gZXh0ZW5kcyBNYW5hZ2VkV2ViU29ja2V0Q29ubmVjdGlvbiB7XG4gIHRyYW5zcG9ydDogXCJ3c1wiO1xuICBvbkNsb3NlKGNhbGxiYWNrOiBDbG9zZUhhbmRsZXIpOiB2b2lkO1xuICBvbk1lc3NhZ2U8SyBleHRlbmRzIGtleW9mIFdlYlNvY2tldEluRXZlbnRzPFRJbj4+KFxuICAgIGV2ZW50OiBLLFxuICAgIGhhbmRsZXI6IE1lc3NhZ2VIYW5kbGVyPFdlYlNvY2tldEluRXZlbnRzPFRJbj5bS10+LFxuICApOiB2b2lkO1xuICBwdWJsaXNoPEsgZXh0ZW5kcyBrZXlvZiBXZWJTb2NrZXRPdXRFdmVudHM8VE91dD4+KFxuICAgIGV2ZW50OiBLLFxuICAgIGRhdGE6IFdlYlNvY2tldE91dEV2ZW50czxUT3V0PltLXSxcbiAgKTogdm9pZDtcbiAgd2FpdEZvckNsb3NlKCk6IFByb21pc2U8dm9pZD47XG4gIGpvaW4ocm9vbUlkOiBXZWJTb2NrZXRSb29tSWQpOiB2b2lkO1xuICBsZWF2ZShyb29tSWQ6IFdlYlNvY2tldFJvb21JZCk6IHZvaWQ7XG4gIHNldFVzZXJJZCh1c2VySWQ6IFdlYlNvY2tldFVzZXJJZCk6IHZvaWQ7XG4gIGNsZWFyVXNlcklkKCk6IHZvaWQ7XG59XG5cbmV4cG9ydCB0eXBlIEFueVdlYlNvY2tldENvbm5lY3Rpb24gPSBXZWJTb2NrZXRDb25uZWN0aW9uPFdlYlNvY2tldEV2ZW50TWFwLCBXZWJTb2NrZXRFdmVudE1hcD47XG5cbnR5cGUgUGFyc2VkRW52ZWxvcGUgPSB6LmluZmVyPHR5cGVvZiBXZWJTb2NrZXRFbnZlbG9wZVNjaGVtYT47XG5cbnR5cGUgV2ViU29ja2V0Q29ubmVjdGlvbk9wdGlvbnM8VE91dCBleHRlbmRzIHouWm9kUmF3U2hhcGUsIFRJbiBleHRlbmRzIHouWm9kUmF3U2hhcGU+ID0ge1xuICBuYW1lc3BhY2U/OiBzdHJpbmc7XG4gIGhlYXJ0YmVhdD86IG51bWJlcjtcbiAgYWN0aXZlPzogYm9vbGVhbjtcbiAgb3V0RXZlbnRzOiB6LlpvZE9iamVjdDxUT3V0PjtcbiAgaW5FdmVudHM6IHouWm9kT2JqZWN0PFRJbj47XG4gIHJlZ2lzdHJ5OiBXZWJTb2NrZXRSZWdpc3RyeTtcbiAgdGVsZW1ldHJ5Q29udHJvbGxlcjogV2ViU29ja2V0VGVsZW1ldHJ5Q29udHJvbGxlcjtcbiAgdHJhY2VJZD86IHN0cmluZztcbiAgc3BhbklkPzogc3RyaW5nO1xuICBwYXJlbnRTcGFuSWQ/OiBzdHJpbmc7XG4gIHNhbXBsZWQ/OiBib29sZWFuO1xufTtcblxuZXhwb3J0IHR5cGUgV2ViU29ja2V0UnVudGltZU9wdGlvbnMgPSB7XG4gIG5vZGVJZD86IHN0cmluZztcbiAgcHJlc2VuY2VTdG9yZT86IFdlYlNvY2tldFByZXNlbmNlU3RvcmU7XG4gIGNsdXN0ZXJCdXM/OiBXZWJTb2NrZXRDbHVzdGVyQnVzO1xuICB0ZWxlbWV0cnk/OiBib29sZWFuIHwgV2ViU29ja2V0VGVsZW1ldHJ5T3B0aW9ucztcbn07XG5cbi8vIHJlZ2lzdHJ566W8IOyGjOycoO2VmOqzoCBjb25uZWN0aW9uIOyDneyEsS9zaHV0ZG93buydhCDri7Tri7ntlaguIFNvbmFtdSDslaDtlIzrpqzsvIDsnbTshZgg7IiY66qF7KO86riw7JmAIOqwmeydtCDsm4Dsp4HsnbTrj4TroZ0g7ISk6rOE7ZWoXG5leHBvcnQgY2xhc3MgV2ViU29ja2V0UnVudGltZSB7XG4gIHJlYWRvbmx5IHJlZ2lzdHJ5OiBXZWJTb2NrZXRSZWdpc3RyeTtcbiAgcmVhZG9ubHkgdGVsZW1ldHJ5Q29udHJvbGxlcjogV2ViU29ja2V0VGVsZW1ldHJ5Q29udHJvbGxlcjtcblxuICBjb25zdHJ1Y3RvcihvcHRpb25zOiBXZWJTb2NrZXRSdW50aW1lT3B0aW9ucyA9IHt9KSB7XG4gICAgLy8g67aE7IKwIO2ZmOqyveyXkOyEnCDrhbjrk5wg6rCEIOy2qeuPjOydhCDrp4nquLAg7JyE7ZW0IGhvc3RuYW1lICsgcGlk66GcIOuUlO2PtO2KuCDsi53rs4TsnpDrpbwg66eM65Og64ukLlxuICAgIC8vIOqwmeydgCDtmLjsiqTtirjsl5Ag7Jes65+sIO2UhOuhnOyEuOyKpOqwgCDrlqAg7J6I7Ja064+EIHBpZOuhnCDqtazrtoTrkJjrqbAsIOuhnOq3uC/rqZTtirjrpq3sl5DshJzrj4Qg7Iud67OE7J20IOyJrOybgFxuICAgIGNvbnN0IHJlc29sdmVkTm9kZUlkID0gb3B0aW9ucy5ub2RlSWQgPz8gYCR7aG9zdG5hbWUoKX0tJHtwcm9jZXNzLnBpZH1gO1xuICAgIHRoaXMudGVsZW1ldHJ5Q29udHJvbGxlciA9IGNyZWF0ZVdlYlNvY2tldFRlbGVtZXRyeUNvbnRyb2xsZXIob3B0aW9ucy50ZWxlbWV0cnksIHtcbiAgICAgIHJ1bnRpbWVJZDogcmFuZG9tVVVJRCgpLFxuICAgICAgbm9kZUlkOiByZXNvbHZlZE5vZGVJZCxcbiAgICB9KTtcbiAgICBjb25zdCByZWdpc3RyeU9wdGlvbnM6IFdlYlNvY2tldFJlZ2lzdHJ5T3B0aW9ucyA9IHtcbiAgICAgIG5vZGVJZDogcmVzb2x2ZWROb2RlSWQsXG4gICAgICBwcmVzZW5jZVN0b3JlOiBvcHRpb25zLnByZXNlbmNlU3RvcmUsXG4gICAgICBjbHVzdGVyQnVzOiBvcHRpb25zLmNsdXN0ZXJCdXMsXG4gICAgICB0ZWxlbWV0cnlDb250cm9sbGVyOiB0aGlzLnRlbGVtZXRyeUNvbnRyb2xsZXIsXG4gICAgfTtcbiAgICB0aGlzLnJlZ2lzdHJ5ID0gbmV3IFdlYlNvY2tldFJlZ2lzdHJ5KHJlZ2lzdHJ5T3B0aW9ucyk7XG4gIH1cblxuICByZWdpc3RlckNvbm5lY3Rpb248VE91dFNjaGVtYSBleHRlbmRzIHouWm9kUmF3U2hhcGUsIFRJblNjaGVtYSBleHRlbmRzIHouWm9kUmF3U2hhcGU+KFxuICAgIHNvY2tldDogV2ViU29ja2V0LFxuICAgIG9wdGlvbnM6IE9taXQ8XG4gICAgICBXZWJTb2NrZXRDb25uZWN0aW9uT3B0aW9uczxUT3V0U2NoZW1hLCBUSW5TY2hlbWE+LFxuICAgICAgXCJyZWdpc3RyeVwiIHwgXCJ0ZWxlbWV0cnlDb250cm9sbGVyXCJcbiAgICA+LFxuICApOiBXZWJTb2NrZXRDb25uZWN0aW9uPEluZmVyV2ViU29ja2V0RXZlbnRNYXA8VE91dFNjaGVtYT4sIEluZmVyV2ViU29ja2V0RXZlbnRNYXA8VEluU2NoZW1hPj4ge1xuICAgIHJldHVybiBuZXcgV2ViU29ja2V0Q29ubmVjdGlvbkltcGwoc29ja2V0LCB7XG4gICAgICAuLi5vcHRpb25zLFxuICAgICAgcmVnaXN0cnk6IHRoaXMucmVnaXN0cnksXG4gICAgICB0ZWxlbWV0cnlDb250cm9sbGVyOiB0aGlzLnRlbGVtZXRyeUNvbnRyb2xsZXIsXG4gICAgfSk7XG4gIH1cblxuICBhY3RpdmF0ZUNvbm5lY3Rpb24oY29ubmVjdGlvbklkOiBzdHJpbmcpOiB2b2lkIHtcbiAgICB0aGlzLnJlZ2lzdHJ5LmFjdGl2YXRlKGNvbm5lY3Rpb25JZCk7XG4gIH1cblxuICBicm9hZGNhc3QoZXZlbnQ6IHN0cmluZywgZGF0YTogdW5rbm93biwgbmFtZXNwYWNlPzogc3RyaW5nKTogdm9pZCB7XG4gICAgdGhpcy5yZWdpc3RyeS5icm9hZGNhc3QoZXZlbnQsIGRhdGEsIG5hbWVzcGFjZSk7XG4gIH1cblxuICBwdWJsaXNoVG9Sb29tKHJvb21JZDogV2ViU29ja2V0Um9vbUlkLCBldmVudDogc3RyaW5nLCBkYXRhOiB1bmtub3duLCBuYW1lc3BhY2U/OiBzdHJpbmcpOiB2b2lkIHtcbiAgICB0aGlzLnJlZ2lzdHJ5LnB1Ymxpc2hUb1Jvb20ocm9vbUlkLCBldmVudCwgZGF0YSwgbmFtZXNwYWNlKTtcbiAgfVxuXG4gIHB1Ymxpc2hUb1VzZXIodXNlcklkOiBXZWJTb2NrZXRVc2VySWQsIGV2ZW50OiBzdHJpbmcsIGRhdGE6IHVua25vd24sIG5hbWVzcGFjZT86IHN0cmluZyk6IHZvaWQge1xuICAgIHRoaXMucmVnaXN0cnkucHVibGlzaFRvVXNlcih1c2VySWQsIGV2ZW50LCBkYXRhLCBuYW1lc3BhY2UpO1xuICB9XG5cbiAgcHVibGlzaFRvQXVkaWVuY2UoYXVkaWVuY2U6IFdlYlNvY2tldEF1ZGllbmNlLCBldmVudDogc3RyaW5nLCBkYXRhOiB1bmtub3duKTogdm9pZCB7XG4gICAgdGhpcy5yZWdpc3RyeS5wdWJsaXNoVG9BdWRpZW5jZShhdWRpZW5jZSwgZXZlbnQsIGRhdGEpO1xuICB9XG5cbiAgLy8g7ZSE66Gc7IS47IqkIOyiheujjCDsi5wg7IK07JWE7J6I64qUIOyXsOqysOydtCDrgqjsp4Ag7JWK64+E66GdIHJlZ2lzdHJ566W8IOyInO2ajO2VtCDsnbzqtIQg7KKF66OM7ZWoXG4gIGFzeW5jIHNodXRkb3duKFxuICAgIGNvZGU6IG51bWJlciA9IFdTX0NMT1NFX0NPREVfR09JTkdfQVdBWSxcbiAgICByZWFzb24gPSBcIlNlcnZlciBzaHV0dGluZyBkb3duXCIsXG4gICk6IFByb21pc2U8dm9pZD4ge1xuICAgIGF3YWl0IHRoaXMucmVnaXN0cnkuc2h1dGRvd24oY29kZSwgcmVhc29uKTtcbiAgICBhd2FpdCB0aGlzLnRlbGVtZXRyeUNvbnRyb2xsZXIuc2h1dGRvd24oKTtcbiAgfVxufVxuXG5leHBvcnQgZnVuY3Rpb24gY3JlYXRlV2ViU29ja2V0UnVudGltZShvcHRpb25zOiBXZWJTb2NrZXRSdW50aW1lT3B0aW9ucyA9IHt9KTogV2ViU29ja2V0UnVudGltZSB7XG4gIHJldHVybiBuZXcgV2ViU29ja2V0UnVudGltZShvcHRpb25zKTtcbn1cblxuY2xhc3MgV2ViU29ja2V0Q29ubmVjdGlvbkltcGw8VE91dFNjaGVtYSBleHRlbmRzIHouWm9kUmF3U2hhcGUsIFRJblNjaGVtYSBleHRlbmRzIHouWm9kUmF3U2hhcGU+XG4gIGltcGxlbWVudHNcbiAgICBXZWJTb2NrZXRDb25uZWN0aW9uPEluZmVyV2ViU29ja2V0RXZlbnRNYXA8VE91dFNjaGVtYT4sIEluZmVyV2ViU29ja2V0RXZlbnRNYXA8VEluU2NoZW1hPj4sXG4gICAgVGVsZW1ldHJ5SW5zcGVjdGFibGVDb25uZWN0aW9uLFxuICAgIFRlbGVtZXRyeUNvbnRleHRQcm92aWRlclxue1xuICByZWFkb25seSBpZCA9IHJhbmRvbVVVSUQoKTtcbiAgcmVhZG9ubHkgdHJhbnNwb3J0ID0gXCJ3c1wiO1xuICByZWFkb25seSBuYW1lc3BhY2U6IHN0cmluZztcblxuICBwcml2YXRlIHJlYWRvbmx5IGNsb3NlQ2FsbGJhY2tzOiBDbG9zZUhhbmRsZXJbXSA9IFtdO1xuICBwcml2YXRlIHJlYWRvbmx5IG1lc3NhZ2VIYW5kbGVycyA9IG5ldyBNYXA8c3RyaW5nLCBBcnJheTxNZXNzYWdlSGFuZGxlcjx1bmtub3duPj4+KCk7XG4gIHByaXZhdGUgcmVhZG9ubHkgcGVuZGluZ01lc3NhZ2VzOiBQYXJzZWRFbnZlbG9wZVtdID0gW107XG4gIHByaXZhdGUgcmVhZG9ubHkgcGVuZGluZ091dGJvdW5kTWVzc2FnZXM6IEFycmF5PHsgcGF5bG9hZDogc3RyaW5nOyBldmVudDogc3RyaW5nIH0+ID0gW107XG4gIHByaXZhdGUgcmVhZG9ubHkgY2xvc2VQcm9taXNlOiBQcm9taXNlPHZvaWQ+O1xuICBwcml2YXRlIHJlYWRvbmx5IHJlc29sdmVDbG9zZVByb21pc2U6ICgpID0+IHZvaWQ7XG4gIHByaXZhdGUgcmVhZG9ubHkgaGVhcnRiZWF0TXM6IG51bWJlcjtcbiAgcHJpdmF0ZSByZWFkb25seSBldmVudFNjaGVtYXNJbjogUmVjb3JkPHN0cmluZywgei5ab2RUeXBlQW55PjtcbiAgcHJpdmF0ZSByZWFkb25seSBldmVudFNjaGVtYXNPdXQ6IFJlY29yZDxzdHJpbmcsIHouWm9kVHlwZUFueT47XG5cbiAgcHJpdmF0ZSByZWFkb25seSBjb25uZWN0aW9uVHJhY2VJZD86IHN0cmluZztcbiAgcHJpdmF0ZSByZWFkb25seSBjb25uZWN0aW9uU3BhbklkPzogc3RyaW5nO1xuICBwcml2YXRlIHJlYWRvbmx5IGNvbm5lY3Rpb25QYXJlbnRTcGFuSWQ/OiBzdHJpbmc7XG4gIHByaXZhdGUgcmVhZG9ubHkgY29ubmVjdGlvblNhbXBsZWQ/OiBib29sZWFuO1xuICBwcml2YXRlIHJlYWRvbmx5IGNvbm5lY3Rpb25TdGFydGVkQXQgPSBwZXJmb3JtYW5jZS5ub3coKTtcblxuICAvLyBjb25uZWN0aW9uIOyImOuqhSDrj5nslYgg7Jyg7KeA65CY64qUIOyLneuzhOyekC4gc2V0VXNlcklkL2NsZWFyVXNlcklk66GcIOyXheuNsOydtO2KuOuQmOupsCBlbWl0IGhvdCBwYXRo7JeQ7IScIOunpOuyiCByZWdpc3RyeSBsb29rdXDtlZjsp4Ag7JWK64+E66GdIOy6kOyLnO2VqFxuICBwcml2YXRlIF91c2VySWQ/OiBzdHJpbmc7XG5cbiAgZ2V0IHVzZXJJZCgpOiBzdHJpbmcgfCB1bmRlZmluZWQge1xuICAgIHJldHVybiB0aGlzLl91c2VySWQ7XG4gIH1cblxuICBwcml2YXRlIGNsb3NlZEludGVybmFsID0gZmFsc2U7XG4gIHByaXZhdGUgY2xvc2VTdGFydGVkID0gZmFsc2U7XG4gIHByaXZhdGUgYXdhaXRpbmdQb25nID0gZmFsc2U7XG4gIHByaXZhdGUgaGVhcnRiZWF0VGltZXI6IFJldHVyblR5cGU8dHlwZW9mIHNldEludGVydmFsPiB8IG51bGwgPSBudWxsO1xuICBwcml2YXRlIG1lc3NhZ2VRdWV1ZTogUHJvbWlzZTx2b2lkPiA9IFByb21pc2UucmVzb2x2ZSgpO1xuICBwcml2YXRlIG91dGJvdW5kRmx1c2hTY2hlZHVsZWQgPSBmYWxzZTtcblxuICBjb25zdHJ1Y3RvcihcbiAgICBwcml2YXRlIHJlYWRvbmx5IHNvY2tldDogV2ViU29ja2V0LFxuICAgIHByaXZhdGUgcmVhZG9ubHkgb3B0aW9uczogV2ViU29ja2V0Q29ubmVjdGlvbk9wdGlvbnM8VE91dFNjaGVtYSwgVEluU2NoZW1hPixcbiAgKSB7XG4gICAgdGhpcy5uYW1lc3BhY2UgPSBvcHRpb25zLm5hbWVzcGFjZSA/PyBcImRlZmF1bHRcIjtcbiAgICB0aGlzLmhlYXJ0YmVhdE1zID0gb3B0aW9ucy5oZWFydGJlYXQgPz8gMzAwMDA7XG4gICAgdGhpcy5jb25uZWN0aW9uVHJhY2VJZCA9IG9wdGlvbnMudHJhY2VJZDtcbiAgICB0aGlzLmNvbm5lY3Rpb25TcGFuSWQgPSBvcHRpb25zLnNwYW5JZDtcbiAgICB0aGlzLmNvbm5lY3Rpb25QYXJlbnRTcGFuSWQgPSBvcHRpb25zLnBhcmVudFNwYW5JZDtcbiAgICB0aGlzLmNvbm5lY3Rpb25TYW1wbGVkID0gb3B0aW9ucy5zYW1wbGVkO1xuICAgIHRoaXMuZXZlbnRTY2hlbWFzSW4gPSBvcHRpb25zLmluRXZlbnRzLnNoYXBlIGFzIHVua25vd24gYXMgUmVjb3JkPHN0cmluZywgei5ab2RUeXBlQW55PjtcbiAgICB0aGlzLmV2ZW50U2NoZW1hc091dCA9IG9wdGlvbnMub3V0RXZlbnRzLnNoYXBlIGFzIHVua25vd24gYXMgUmVjb3JkPHN0cmluZywgei5ab2RUeXBlQW55PjtcblxuICAgIGxldCByZXNvbHZlQ2xvc2VQcm9taXNlITogKCkgPT4gdm9pZDtcbiAgICB0aGlzLmNsb3NlUHJvbWlzZSA9IG5ldyBQcm9taXNlPHZvaWQ+KChyZXNvbHZlKSA9PiB7XG4gICAgICByZXNvbHZlQ2xvc2VQcm9taXNlID0gcmVzb2x2ZTtcbiAgICB9KTtcbiAgICB0aGlzLnJlc29sdmVDbG9zZVByb21pc2UgPSByZXNvbHZlQ2xvc2VQcm9taXNlO1xuXG4gICAgdGhpcy5vcHRpb25zLnJlZ2lzdHJ5LnJlZ2lzdGVyKHRoaXMsIG9wdGlvbnMuYWN0aXZlID8/IHRydWUpO1xuICAgIHRoaXMuc29ja2V0Lm9uKFwibWVzc2FnZVwiLCB0aGlzLmhhbmRsZU1lc3NhZ2UpO1xuICAgIHRoaXMuc29ja2V0Lm9uKFwiY2xvc2VcIiwgdGhpcy5oYW5kbGVDbG9zZSk7XG4gICAgdGhpcy5zb2NrZXQub24oXCJlcnJvclwiLCB0aGlzLmhhbmRsZUVycm9yKTtcbiAgICB0aGlzLnNvY2tldC5vbihcInBvbmdcIiwgdGhpcy5oYW5kbGVQb25nKTtcbiAgICB0aGlzLnN0YXJ0SGVhcnRiZWF0KCk7XG4gIH1cblxuICBnZXQgY2xvc2VkKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLmNsb3NlZEludGVybmFsO1xuICB9XG5cbiAgb25DbG9zZShjYWxsYmFjazogQ2xvc2VIYW5kbGVyKTogdm9pZCB7XG4gICAgdGhpcy5jbG9zZUNhbGxiYWNrcy5wdXNoKGNhbGxiYWNrKTtcbiAgfVxuXG4gIG9uTWVzc2FnZTxLIGV4dGVuZHMga2V5b2YgSW5mZXJXZWJTb2NrZXRFdmVudE1hcDxUSW5TY2hlbWE+PihcbiAgICBldmVudDogSyxcbiAgICBoYW5kbGVyOiBNZXNzYWdlSGFuZGxlcjxJbmZlcldlYlNvY2tldEV2ZW50TWFwPFRJblNjaGVtYT5bS10+LFxuICApOiB2b2lkIHtcbiAgICBjb25zdCBldmVudEtleSA9IFN0cmluZyhldmVudCk7XG4gICAgY29uc3QgaGFuZGxlcnMgPSB0aGlzLm1lc3NhZ2VIYW5kbGVycy5nZXQoZXZlbnRLZXkpID8/IFtdO1xuICAgIGhhbmRsZXJzLnB1c2goaGFuZGxlciBhcyBNZXNzYWdlSGFuZGxlcjx1bmtub3duPik7XG4gICAgdGhpcy5tZXNzYWdlSGFuZGxlcnMuc2V0KGV2ZW50S2V5LCBoYW5kbGVycyk7XG4gICAgdGhpcy5mbHVzaFBlbmRpbmdNZXNzYWdlcyhldmVudEtleSk7XG4gIH1cblxuICBwdWJsaXNoPEsgZXh0ZW5kcyBrZXlvZiBJbmZlcldlYlNvY2tldEV2ZW50TWFwPFRPdXRTY2hlbWE+PihcbiAgICBldmVudDogSyxcbiAgICBkYXRhOiBJbmZlcldlYlNvY2tldEV2ZW50TWFwPFRPdXRTY2hlbWE+W0tdLFxuICApOiB2b2lkIHtcbiAgICB0aGlzLnB1Ymxpc2hWYWxpZGF0ZWQoU3RyaW5nKGV2ZW50KSwgZGF0YSk7XG4gIH1cblxuICBwdWJsaXNoVW50eXBlZChldmVudDogc3RyaW5nLCBkYXRhOiB1bmtub3duKTogdm9pZCB7XG4gICAgdGhpcy5wdWJsaXNoVmFsaWRhdGVkKGV2ZW50LCBkYXRhKTtcbiAgfVxuXG4gIHdhaXRGb3JDbG9zZSgpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICByZXR1cm4gdGhpcy5jbG9zZVByb21pc2U7XG4gIH1cblxuICBqb2luKHJvb21JZDogV2ViU29ja2V0Um9vbUlkKTogdm9pZCB7XG4gICAgdGhpcy5vcHRpb25zLnJlZ2lzdHJ5LmpvaW4odGhpcy5pZCwgcm9vbUlkKTtcbiAgfVxuXG4gIGxlYXZlKHJvb21JZDogV2ViU29ja2V0Um9vbUlkKTogdm9pZCB7XG4gICAgdGhpcy5vcHRpb25zLnJlZ2lzdHJ5LmxlYXZlKHRoaXMuaWQsIHJvb21JZCk7XG4gIH1cblxuICBzZXRVc2VySWQodXNlcklkOiBXZWJTb2NrZXRVc2VySWQpOiB2b2lkIHtcbiAgICB0aGlzLl91c2VySWQgPSBTdHJpbmcodXNlcklkKTtcbiAgICB0aGlzLm9wdGlvbnMucmVnaXN0cnkuc2V0VXNlcklkKHRoaXMuaWQsIHVzZXJJZCk7XG4gIH1cblxuICBjbGVhclVzZXJJZCgpOiB2b2lkIHtcbiAgICB0aGlzLl91c2VySWQgPSB1bmRlZmluZWQ7XG4gICAgdGhpcy5vcHRpb25zLnJlZ2lzdHJ5LmNsZWFyVXNlcklkKHRoaXMuaWQpO1xuICB9XG5cbiAgZ2V0VGVsZW1ldHJ5U25hcHNob3QoKTogV2ViU29ja2V0VGVsZW1ldHJ5Q29ubmVjdGlvblNuYXBzaG90IHtcbiAgICByZXR1cm4ge1xuICAgICAgcGVuZGluZ0luYm91bmRNZXNzYWdlczogdGhpcy5wZW5kaW5nTWVzc2FnZXMubGVuZ3RoLFxuICAgICAgcGVuZGluZ091dGJvdW5kTWVzc2FnZXM6IHRoaXMucGVuZGluZ091dGJvdW5kTWVzc2FnZXMubGVuZ3RoLFxuICAgICAgc29ja2V0QnVmZmVyZWRCeXRlczogdGhpcy5zb2NrZXQucmVhZHlTdGF0ZSA9PT0gV1NfT1BFTiA/IHRoaXMuc29ja2V0LmJ1ZmZlcmVkQW1vdW50IDogMCxcbiAgICB9O1xuICB9XG5cbiAgZ2V0VGVsZW1ldHJ5Q29udGV4dCgpOiBXZWJTb2NrZXRUZWxlbWV0cnlDb25uZWN0aW9uQ29udGV4dCB7XG4gICAgcmV0dXJuIHtcbiAgICAgIHRyYWNlSWQ6IHRoaXMuY29ubmVjdGlvblRyYWNlSWQsXG4gICAgICBzcGFuSWQ6IHRoaXMuY29ubmVjdGlvblNwYW5JZCxcbiAgICAgIHBhcmVudFNwYW5JZDogdGhpcy5jb25uZWN0aW9uUGFyZW50U3BhbklkLFxuICAgICAgc2FtcGxlZDogdGhpcy5jb25uZWN0aW9uU2FtcGxlZCxcbiAgICB9O1xuICB9XG5cbiAgLy8g66qo65OgIHRlbGVtZXRyeSBlbWl0IHNpdGXqsIAg6rO17Jyg7ZWY64qUIGNvbm5lY3Rpb24tbGV2ZWwgZmllbGQg66y27J2MLlxuICAvLyDtlqXtm4QgY29ubmVjdGlvbi1zY29wZWQg7Iud67OE7J6QKGUuZy4gdGVuYW50SWQp6rCAIOy2lOqwgOuQoCDrlYwg7ZWcIOqzs+unjCDshpDrjIDrqbQg65CoXG4gIHByaXZhdGUgdGVsZW1ldHJ5RmllbGRzKCkge1xuICAgIHJldHVybiB7XG4gICAgICBjb25uZWN0aW9uSWQ6IHRoaXMuaWQsXG4gICAgICBuYW1lc3BhY2U6IHRoaXMubmFtZXNwYWNlLFxuICAgICAgdXNlcklkOiB0aGlzLl91c2VySWQsXG4gICAgICB0cmFjZUlkOiB0aGlzLmNvbm5lY3Rpb25UcmFjZUlkLFxuICAgICAgc3BhbklkOiB0aGlzLmNvbm5lY3Rpb25TcGFuSWQsXG4gICAgICBwYXJlbnRTcGFuSWQ6IHRoaXMuY29ubmVjdGlvblBhcmVudFNwYW5JZCxcbiAgICAgIHNhbXBsZWQ6IHRoaXMuY29ubmVjdGlvblNhbXBsZWQsXG4gICAgfTtcbiAgfVxuXG4gIHByaXZhdGUgZW1pdEluYm91bmRSZWplY3RlZChyZWFzb246IHN0cmluZywgZXZlbnQ/OiBzdHJpbmcpOiB2b2lkIHtcbiAgICBjb25zdCBmaWVsZHMgPSB0aGlzLnRlbGVtZXRyeUZpZWxkcygpO1xuICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgbmFtZTogXCJ3cy5tZXNzYWdlLnJlamVjdGVkXCIsXG4gICAgICBsZXZlbDogXCJ3YXJuXCIsXG4gICAgICAuLi5maWVsZHMsXG4gICAgICBkZXRhaWw6IGV2ZW50ICE9PSB1bmRlZmluZWQgPyB7IHJlYXNvbiwgZXZlbnQgfSA6IHsgcmVhc29uIH0sXG4gICAgfSk7XG4gICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIucmVjb3JkTWV0cmljKHtcbiAgICAgIG5hbWU6IFwic29uYW11LndzLm1lc3NhZ2VzXCIsXG4gICAgICBraW5kOiBcImNvdW50ZXJcIixcbiAgICAgIHZhbHVlOiAxLFxuICAgICAgdW5pdDogXCIxXCIsXG4gICAgICB0YWdzOiB7IGRpcmVjdGlvbjogXCJpbmJvdW5kXCIsIG91dGNvbWU6IFwicmVqZWN0ZWRcIiB9LFxuICAgICAgLi4uZmllbGRzLFxuICAgIH0pO1xuICB9XG5cbiAgLy8gdHJhbnNwb3J0IOyiheujjCDrj4TspJEg7JiI7Jm46rCAIOuCmOuPhCBtYXJrQ2xvc2Vk6rCAIOuwmOuTnOyLnCDsi6TtlonrkJjrj4TroZ0gdHJ5L2ZpbmFsbHnroZwg6rCQ7IyIXG4gIGNsb3NlKGNvZGU/OiBudW1iZXIsIHJlYXNvbj86IHN0cmluZyk6IHZvaWQge1xuICAgIGlmICh0aGlzLmNsb3NlZEludGVybmFsIHx8IHRoaXMuY2xvc2VTdGFydGVkIHx8IHRoaXMuc29ja2V0LnJlYWR5U3RhdGUgPT09IFdTX0NMT1NFRCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuY2xvc2VTdGFydGVkID0gdHJ1ZTtcbiAgICB0cnkge1xuICAgICAgdGhpcy5jbG9zZVRyYW5zcG9ydChjb2RlLCByZWFzb24pO1xuICAgIH0gZmluYWxseSB7XG4gICAgICB0aGlzLm1hcmtDbG9zZWQoY29kZSwgcmVhc29uKTtcbiAgICB9XG4gIH1cblxuICAvLyDsnbjrsJTsmrTrk5wg66mU7Iuc7KeA66W8IOyInOywqCDsspjrpqwg7YGQ7JeQIOyYrOumvC4gU29uYW11IGVudmVsb3BlIOqygOymnSDsiJjtlolcbiAgcHJpdmF0ZSByZWFkb25seSBoYW5kbGVNZXNzYWdlID0gKHJhdzogdW5rbm93bikgPT4ge1xuICAgIHRoaXMuZW5xdWV1ZU1lc3NhZ2VUYXNrKGFzeW5jICgpID0+IHtcbiAgICAgIGNvbnN0IHRleHQgPSBub3JtYWxpemVNZXNzYWdlKHJhdyk7XG4gICAgICBjb25zdCBwYXJzZWRFbnZlbG9wZSA9IHNhZmVQYXJzZUVudmVsb3BlKHRleHQpO1xuICAgICAgaWYgKCFwYXJzZWRFbnZlbG9wZSkge1xuICAgICAgICB0aGlzLmVtaXRJbmJvdW5kUmVqZWN0ZWQoXCJpbnZhbGlkUGF5bG9hZFwiKTtcbiAgICAgICAgdGhpcy5jbG9zZShXU19DTE9TRV9DT0RFX0lOVkFMSURfRlJBTUVfUEFZTE9BRF9EQVRBLCBcIkludmFsaWQgbWVzc2FnZSBwYXlsb2FkXCIpO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICBuYW1lOiBcIndzLm1lc3NhZ2UucmVjZWl2ZWRcIixcbiAgICAgICAgbGV2ZWw6IFwiZGVidWdcIixcbiAgICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgICAgZGV0YWlsOiB7IGV2ZW50OiBwYXJzZWRFbnZlbG9wZS5ldmVudCB9LFxuICAgICAgICBwYXlsb2FkOiBwYXJzZWRFbnZlbG9wZS5kYXRhLFxuICAgICAgfSk7XG4gICAgICB0aGlzLm9wdGlvbnMucmVnaXN0cnkudG91Y2godGhpcy5pZCk7XG4gICAgICBhd2FpdCB0aGlzLmRpc3BhdGNoRW52ZWxvcGUocGFyc2VkRW52ZWxvcGUpO1xuICAgIH0pO1xuICB9O1xuXG4gIHByaXZhdGUgcmVhZG9ubHkgaGFuZGxlQ2xvc2UgPSAoY29kZT86IG51bWJlciwgcmVhc29uPzogQnVmZmVyIHwgc3RyaW5nKSA9PiB7XG4gICAgY29uc3QgcmVhc29uVGV4dCA9IHR5cGVvZiByZWFzb24gPT09IFwic3RyaW5nXCIgPyByZWFzb24gOiByZWFzb24/LnRvU3RyaW5nKCk7XG4gICAgdGhpcy5tYXJrQ2xvc2VkKGNvZGUsIHJlYXNvblRleHQpO1xuICB9O1xuXG4gIC8vIOyGjOy8k+ydtCB0cmFuc3BvcnQgZXJyb3LrpbwgZW1pdO2VmOuptCDsponsi5wgMTAxMSBjbG9zZeuhnCDsiJjroLTsi5zsvJwg7IOB7YOcIOuIhOudveydhCDrp4nsnYxcbiAgcHJpdmF0ZSByZWFkb25seSBoYW5kbGVFcnJvciA9ICgpID0+IHtcbiAgICB0aGlzLmNsb3NlKFdTX0NMT1NFX0NPREVfSU5URVJOQUxfRVJST1IsIFwiV2ViU29ja2V0IHRyYW5zcG9ydCBlcnJvclwiKTtcbiAgfTtcblxuICBwcml2YXRlIHJlYWRvbmx5IGhhbmRsZVBvbmcgPSAoKSA9PiB7XG4gICAgdGhpcy5hd2FpdGluZ1BvbmcgPSBmYWxzZTtcbiAgICB0aGlzLm9wdGlvbnMucmVnaXN0cnkudG91Y2godGhpcy5pZCk7XG4gIH07XG5cbiAgLy8gZW52ZWxvcGXsnZggbWV0YS50cmFjZXBhcmVudOuhnOu2gO2EsCB0cmFjZSBjb250ZXh066W8IOy2lOy2nO2VqFxuICAvLyBpbnZhbGlkIHRyYWNlcGFyZW5064qUIOyXsOqysOydhCDqsbDrtoDtlZjsp4Ag7JWK6rOgIGRlYnVnIOugiOuyqCDqsr3qs6Drp4wgZW1pdO2VqFxuICBwcml2YXRlIHJlc29sdmVNZXNzYWdlVHJhY2VDb250ZXh0KFxuICAgIGVudmVsb3BlOiBQYXJzZWRFbnZlbG9wZSxcbiAgKTogV2ViU29ja2V0VGVsZW1ldHJ5Q29ubmVjdGlvbkNvbnRleHQge1xuICAgIGNvbnN0IG1lc3NhZ2VTcGFuSWQgPSBnZW5lcmF0ZVNwYW5JZCgpO1xuXG4gICAgaWYgKFxuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZ2V0VHJhY2VPcHRpb25zKCkucHJvcGFnYXRlTWVzc2FnZVRyYWNlICYmXG4gICAgICBlbnZlbG9wZS5tZXRhPy50cmFjZXBhcmVudFxuICAgICkge1xuICAgICAgY29uc3QgcGFyc2VkID0gcGFyc2VUcmFjZVBhcmVudChlbnZlbG9wZS5tZXRhLnRyYWNlcGFyZW50KTtcbiAgICAgIGlmIChwYXJzZWQpIHtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICB0cmFjZUlkOiBwYXJzZWQudHJhY2VJZCxcbiAgICAgICAgICBzcGFuSWQ6IG1lc3NhZ2VTcGFuSWQsXG4gICAgICAgICAgcGFyZW50U3BhbklkOiBwYXJzZWQucGFyZW50SWQsXG4gICAgICAgICAgc2FtcGxlZDogcGFyc2VkLnNhbXBsZWQsXG4gICAgICAgIH07XG4gICAgICB9XG4gICAgICAvLyBpbnZhbGlkIHRyYWNlcGFyZW50OiB3YXJuIGJ1dCBkbyBub3QgcmVqZWN0XG4gICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgICAgbmFtZTogXCJ3cy50cmFjZS5pbnZhbGlkXCIsXG4gICAgICAgIGxldmVsOiBcImRlYnVnXCIsXG4gICAgICAgIC4uLnRoaXMudGVsZW1ldHJ5RmllbGRzKCksXG4gICAgICAgIGRldGFpbDogeyBzb3VyY2U6IFwibWVzc2FnZVwiLCB0cmFjZXBhcmVudDogZW52ZWxvcGUubWV0YS50cmFjZXBhcmVudCB9LFxuICAgICAgfSk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgIHRyYWNlSWQ6IHRoaXMuY29ubmVjdGlvblRyYWNlSWQsXG4gICAgICBzcGFuSWQ6IG1lc3NhZ2VTcGFuSWQsXG4gICAgICBwYXJlbnRTcGFuSWQ6IHRoaXMuY29ubmVjdGlvblNwYW5JZCA/PyB0aGlzLmNvbm5lY3Rpb25QYXJlbnRTcGFuSWQsXG4gICAgICBzYW1wbGVkOiB0aGlzLmNvbm5lY3Rpb25TYW1wbGVkLFxuICAgIH07XG4gIH1cblxuICAvLyBldmVudCDsobTsnqwg7Jes67aAIOKGkiBzY2hlbWEg6rKA7KadIOKGkiBoYW5kbGVyIOyLpO2WiSDsiJzsnLzroZwg67aE6riw7ZWoXG4gIC8vIGhhbmRsZXLqsIAg7JWE7KeBIOuTseuhneuQmOyngCDslYrsnYAg7LSI6riwIOuplOyLnOyngOuKlCDrsoTtjbzsl5Ag67O06rSA7ZaI64uk6rCAIG9uTWVzc2FnZSDrk7HroZ0g7IucIGZsdXNo7ZWoXG4gIC8vIGhhbmRsZXLripQgYGF3YWl0YOycvOuhnCDsiJzssKgg7Iuk7ZaJ7ZW0IO2VnCBjb25uZWN0aW9uIOyViOydmCDrqZTsi5zsp4Ag7Iic7ISc66W8IOuztOyepe2VqFxuICBwcml2YXRlIGFzeW5jIGRpc3BhdGNoRW52ZWxvcGUoZW52ZWxvcGU6IFBhcnNlZEVudmVsb3BlKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgY29uc3QgaGFuZGxlcnMgPSB0aGlzLm1lc3NhZ2VIYW5kbGVycy5nZXQoZW52ZWxvcGUuZXZlbnQpO1xuICAgIGNvbnN0IHNjaGVtYSA9IHRoaXMuZXZlbnRTY2hlbWFzSW5bZW52ZWxvcGUuZXZlbnRdO1xuXG4gICAgaWYgKCFzY2hlbWEpIHtcbiAgICAgIHRoaXMuZW1pdEluYm91bmRSZWplY3RlZChcInVua25vd25FdmVudFwiLCBlbnZlbG9wZS5ldmVudCk7XG4gICAgICB0aGlzLmNsb3NlKFdTX0NMT1NFX0NPREVfUE9MSUNZX1ZJT0xBVElPTiwgXCJVbmtub3duIGV2ZW50XCIpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IHBhcnNlZCA9IHNjaGVtYS5zYWZlUGFyc2UoZW52ZWxvcGUuZGF0YSk7XG4gICAgaWYgKCFwYXJzZWQuc3VjY2Vzcykge1xuICAgICAgdGhpcy5lbWl0SW5ib3VuZFJlamVjdGVkKFwiaW52YWxpZERhdGFcIiwgZW52ZWxvcGUuZXZlbnQpO1xuICAgICAgdGhpcy5jbG9zZShXU19DTE9TRV9DT0RFX0lOVkFMSURfRlJBTUVfUEFZTE9BRF9EQVRBLCBcIkludmFsaWQgZXZlbnQgZGF0YVwiKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBpZiAoIWhhbmRsZXJzIHx8IGhhbmRsZXJzLmxlbmd0aCA9PT0gMCkge1xuICAgICAgaWYgKHRoaXMucGVuZGluZ01lc3NhZ2VzLmxlbmd0aCA+PSBNQVhfUEVORElOR19NRVNTQUdFUykge1xuICAgICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgICAgICBuYW1lOiBcIndzLm1lc3NhZ2UuYnVmZmVyLmRyb3BwZWRcIixcbiAgICAgICAgICBsZXZlbDogXCJ3YXJuXCIsXG4gICAgICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgICAgICBkZXRhaWw6IHsgZXZlbnQ6IGVudmVsb3BlLmV2ZW50IH0sXG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLnBlbmRpbmdNZXNzYWdlcy5zaGlmdCgpO1xuICAgICAgfVxuICAgICAgdGhpcy5wZW5kaW5nTWVzc2FnZXMucHVzaChlbnZlbG9wZSk7XG4gICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgICAgbmFtZTogXCJ3cy5tZXNzYWdlLmJ1ZmZlcmVkXCIsXG4gICAgICAgIGxldmVsOiBcImRlYnVnXCIsXG4gICAgICAgIC4uLnRoaXMudGVsZW1ldHJ5RmllbGRzKCksXG4gICAgICAgIGRldGFpbDogeyBldmVudDogZW52ZWxvcGUuZXZlbnQgfSxcbiAgICAgIH0pO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IHRyYWNlQ3R4ID0gdGhpcy5yZXNvbHZlTWVzc2FnZVRyYWNlQ29udGV4dChlbnZlbG9wZSk7XG4gICAgLy8gbWVzc2FnZS1sZXZlbCB0cmFjZeuKlCBjb25uZWN0aW9uLWxldmVsIHRyYWNl66W8IG92ZXJyaWRl7ZWoLiB1c2VySWQgLyBjb25uZWN0aW9uSWQgLyBuYW1lc3BhY2XripQg6re464yA66GcIOycoOyngFxuICAgIGNvbnN0IG1lc3NhZ2VUcmFjZUZpZWxkcyA9IHtcbiAgICAgIGNvbm5lY3Rpb25JZDogdGhpcy5pZCxcbiAgICAgIG5hbWVzcGFjZTogdGhpcy5uYW1lc3BhY2UsXG4gICAgICB1c2VySWQ6IHRoaXMuX3VzZXJJZCxcbiAgICAgIHRyYWNlSWQ6IHRyYWNlQ3R4LnRyYWNlSWQsXG4gICAgICBzcGFuSWQ6IHRyYWNlQ3R4LnNwYW5JZCxcbiAgICAgIHBhcmVudFNwYW5JZDogdHJhY2VDdHgucGFyZW50U3BhbklkLFxuICAgICAgc2FtcGxlZDogdHJhY2VDdHguc2FtcGxlZCxcbiAgICB9O1xuICAgIHRyeSB7XG4gICAgICBmb3IgKGNvbnN0IGhhbmRsZXIgb2YgaGFuZGxlcnMpIHtcbiAgICAgICAgYXdhaXQgaGFuZGxlcihwYXJzZWQuZGF0YSwgdHJhY2VDdHgpO1xuICAgICAgfVxuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgIG5hbWU6IFwid3MubWVzc2FnZS5kaXNwYXRjaGVkXCIsXG4gICAgICAgIGxldmVsOiBcImRlYnVnXCIsXG4gICAgICAgIC4uLm1lc3NhZ2VUcmFjZUZpZWxkcyxcbiAgICAgICAgZGV0YWlsOiB7IGV2ZW50OiBlbnZlbG9wZS5ldmVudCB9LFxuICAgICAgfSk7XG4gICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5yZWNvcmRNZXRyaWMoe1xuICAgICAgICBuYW1lOiBcInNvbmFtdS53cy5tZXNzYWdlc1wiLFxuICAgICAgICBraW5kOiBcImNvdW50ZXJcIixcbiAgICAgICAgdmFsdWU6IDEsXG4gICAgICAgIHVuaXQ6IFwiMVwiLFxuICAgICAgICB0YWdzOiB7IGRpcmVjdGlvbjogXCJpbmJvdW5kXCIsIGV2ZW50OiBlbnZlbG9wZS5ldmVudCwgb3V0Y29tZTogXCJhY2NlcHRlZFwiIH0sXG4gICAgICAgIC4uLm1lc3NhZ2VUcmFjZUZpZWxkcyxcbiAgICAgIH0pO1xuICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgICAgbmFtZTogXCJ3cy5tZXNzYWdlLmZhaWxlZFwiLFxuICAgICAgICBsZXZlbDogXCJlcnJvclwiLFxuICAgICAgICAuLi5tZXNzYWdlVHJhY2VGaWVsZHMsXG4gICAgICAgIGRldGFpbDogeyBldmVudDogZW52ZWxvcGUuZXZlbnQgfSxcbiAgICAgIH0pO1xuICAgICAgdGhyb3cgZXJyb3I7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBmbHVzaFBlbmRpbmdNZXNzYWdlcyhldmVudDogc3RyaW5nKTogdm9pZCB7XG4gICAgY29uc3QgcmVtYWluaW5nOiBQYXJzZWRFbnZlbG9wZVtdID0gW107XG4gICAgY29uc3QgdG9GbHVzaDogUGFyc2VkRW52ZWxvcGVbXSA9IFtdO1xuXG4gICAgZm9yIChjb25zdCBtZXNzYWdlIG9mIHRoaXMucGVuZGluZ01lc3NhZ2VzKSB7XG4gICAgICBpZiAobWVzc2FnZS5ldmVudCAhPT0gZXZlbnQpIHtcbiAgICAgICAgcmVtYWluaW5nLnB1c2gobWVzc2FnZSk7XG4gICAgICAgIGNvbnRpbnVlO1xuICAgICAgfVxuXG4gICAgICB0b0ZsdXNoLnB1c2gobWVzc2FnZSk7XG4gICAgfVxuXG4gICAgdGhpcy5wZW5kaW5nTWVzc2FnZXMubGVuZ3RoID0gMDtcbiAgICB0aGlzLnBlbmRpbmdNZXNzYWdlcy5wdXNoKC4uLnJlbWFpbmluZyk7XG5cbiAgICBmb3IgKGNvbnN0IG1lc3NhZ2Ugb2YgdG9GbHVzaCkge1xuICAgICAgdGhpcy5lbnF1ZXVlTWVzc2FnZVRhc2soYXN5bmMgKCkgPT4ge1xuICAgICAgICBhd2FpdCB0aGlzLmRpc3BhdGNoRW52ZWxvcGUobWVzc2FnZSk7XG4gICAgICB9KTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIHB1Ymxpc2hWYWxpZGF0ZWQoZXZlbnQ6IHN0cmluZywgZGF0YTogdW5rbm93bik6IHZvaWQge1xuICAgIGNvbnN0IHNjaGVtYSA9IHRoaXMuZXZlbnRTY2hlbWFzT3V0W2V2ZW50XTtcbiAgICBpZiAoIXNjaGVtYSkge1xuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgIG5hbWU6IFwid3MucHVibGlzaC5yZWplY3RlZFwiLFxuICAgICAgICBsZXZlbDogXCJlcnJvclwiLFxuICAgICAgICAuLi50aGlzLnRlbGVtZXRyeUZpZWxkcygpLFxuICAgICAgICBkZXRhaWw6IHsgZXZlbnQsIHJlYXNvbjogXCJ1bmtub3duRXZlbnRcIiB9LFxuICAgICAgfSk7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoYFVua25vd24gd2Vic29ja2V0IGV2ZW50OiAke2V2ZW50fWApO1xuICAgIH1cblxuICAgIGNvbnN0IHBhcnNlZCA9IHNjaGVtYS5zYWZlUGFyc2UoZGF0YSk7XG4gICAgaWYgKCFwYXJzZWQuc3VjY2Vzcykge1xuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgIG5hbWU6IFwid3MucHVibGlzaC5yZWplY3RlZFwiLFxuICAgICAgICBsZXZlbDogXCJlcnJvclwiLFxuICAgICAgICAuLi50aGlzLnRlbGVtZXRyeUZpZWxkcygpLFxuICAgICAgICBkZXRhaWw6IHsgZXZlbnQsIHJlYXNvbjogXCJpbnZhbGlkUGF5bG9hZFwiIH0sXG4gICAgICB9KTtcbiAgICAgIHRocm93IG5ldyBFcnJvcihgSW52YWxpZCB3ZWJzb2NrZXQgZXZlbnQgcGF5bG9hZDogJHtldmVudH1gKTtcbiAgICB9XG5cbiAgICBpZiAodGhpcy5jbG9zZWRJbnRlcm5hbCB8fCB0aGlzLnNvY2tldC5yZWFkeVN0YXRlICE9PSBXU19PUEVOKSB7XG4gICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgICAgbmFtZTogXCJ3cy5wdWJsaXNoLmRyb3BwZWRcIixcbiAgICAgICAgbGV2ZWw6IFwiZGVidWdcIixcbiAgICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgICAgZGV0YWlsOiB7IGV2ZW50LCByZWFzb246IFwiY29ubmVjdGlvbkNsb3NlZFwiIH0sXG4gICAgICB9KTtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLmVucXVldWVPdXRib3VuZE1lc3NhZ2UoXG4gICAgICBKU09OLnN0cmluZ2lmeSh7XG4gICAgICAgIGV2ZW50LFxuICAgICAgICBkYXRhOiBwYXJzZWQuZGF0YSxcbiAgICAgIH0pLFxuICAgICAgZXZlbnQsXG4gICAgICBwYXJzZWQuZGF0YSxcbiAgICApO1xuICB9XG5cbiAgLy8gbGlzdGVuZXIg7ZW07KCcIC8gaGVhcnRiZWF0IOykkeuLqCAvIHBlbmRpbmcgcXVldWUg67mE7JuAIC8gcmVnaXN0cnkgdW5yZWdpc3RlciAvIG9uQ2xvc2Ug7Iuk7ZaJIC8gd2FpdEZvckNsb3NlIHJlc29sdmUg7J2EIO2VnCDqs7Psl5Ag66qo7JWEIOybkOyekOyggeycvOuhnCDsspjrpqztlahcbiAgLy8gYXN5bmMgb25DbG9zZeqwgCByZWplY3TtlbTrj4QgdW5oYW5kbGVkIHJlamVjdGlvbuycvOuhnCDsg4jsp4Ag7JWK64+E66GdIGNhdGNo66GcIOqyqeumrO2VqFxuICBwcml2YXRlIG1hcmtDbG9zZWQoY29kZT86IG51bWJlciwgX3JlYXNvbj86IHN0cmluZyk6IHZvaWQge1xuICAgIGlmICh0aGlzLmNsb3NlZEludGVybmFsKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5jbG9zZWRJbnRlcm5hbCA9IHRydWU7XG4gICAgdGhpcy5jbG9zZVN0YXJ0ZWQgPSBmYWxzZTtcbiAgICB0aGlzLnN0b3BIZWFydGJlYXQoKTtcbiAgICBjb25zdCBmaWVsZHMgPSB0aGlzLnRlbGVtZXRyeUZpZWxkcygpO1xuICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgbmFtZTogXCJ3cy5jb25uZWN0aW9uLmNsb3NlZFwiLFxuICAgICAgbGV2ZWw6IFwiaW5mb1wiLFxuICAgICAgLi4uZmllbGRzLFxuICAgIH0pO1xuICAgIGlmICh0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5nZXRUcmFjZU9wdGlvbnMoKS5yZWNvcmRDb25uZWN0aW9uTGlmZXRpbWVTcGFuKSB7XG4gICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5yZWNvcmRTcGFuKHtcbiAgICAgICAgb3BlcmF0aW9uTmFtZTogXCJ3cy5jb25uZWN0aW9uLmxpZmV0aW1lXCIsXG4gICAgICAgIGtpbmQ6IFwic2VydmVyXCIsXG4gICAgICAgIGR1cmF0aW9uTXM6IHBlcmZvcm1hbmNlLm5vdygpIC0gdGhpcy5jb25uZWN0aW9uU3RhcnRlZEF0LFxuICAgICAgICBzdGF0dXM6IGRlcml2ZUxpZmV0aW1lU3RhdHVzKGNvZGUpLFxuICAgICAgICAuLi5maWVsZHMsXG4gICAgICB9KTtcbiAgICB9XG4gICAgdGhpcy5zb2NrZXQub2ZmKFwibWVzc2FnZVwiLCB0aGlzLmhhbmRsZU1lc3NhZ2UpO1xuICAgIHRoaXMuc29ja2V0Lm9mZihcImNsb3NlXCIsIHRoaXMuaGFuZGxlQ2xvc2UpO1xuICAgIHRoaXMuc29ja2V0Lm9mZihcImVycm9yXCIsIHRoaXMuaGFuZGxlRXJyb3IpO1xuICAgIHRoaXMuc29ja2V0Lm9mZihcInBvbmdcIiwgdGhpcy5oYW5kbGVQb25nKTtcbiAgICB0aGlzLmF3YWl0aW5nUG9uZyA9IGZhbHNlO1xuICAgIHRoaXMucGVuZGluZ01lc3NhZ2VzLmxlbmd0aCA9IDA7XG4gICAgdGhpcy5wZW5kaW5nT3V0Ym91bmRNZXNzYWdlcy5sZW5ndGggPSAwO1xuICAgIHRoaXMub3B0aW9ucy5yZWdpc3RyeS51bnJlZ2lzdGVyKHRoaXMuaWQpO1xuICAgIGZvciAoY29uc3QgY2FsbGJhY2sgb2YgdGhpcy5jbG9zZUNhbGxiYWNrcy5zcGxpY2UoMCkpIHtcbiAgICAgIHRyeSB7XG4gICAgICAgIGNvbnN0IHJlc3VsdCA9IGNhbGxiYWNrKCk7XG4gICAgICAgIGlmIChpc1Byb21pc2VMaWtlKHJlc3VsdCkpIHtcbiAgICAgICAgICB2b2lkIHJlc3VsdC5jYXRjaCgoKSA9PiB7XG4gICAgICAgICAgICAvLyBhc3luYyBjbG9zZSBjYWxsYmFja3MgbXVzdCBub3QgZXNjYXBlIGFzIHVuaGFuZGxlZCByZWplY3Rpb25zXG4gICAgICAgICAgfSk7XG4gICAgICAgIH1cbiAgICAgIH0gY2F0Y2gge1xuICAgICAgICAvLyBjbG9zZSBjYWxsYmFja3MgbXVzdCBub3QgYmxvY2sgdHJhbnNwb3J0IGNsZWFudXBcbiAgICAgIH1cbiAgICB9XG4gICAgdGhpcy5yZXNvbHZlQ2xvc2VQcm9taXNlKCk7XG4gIH1cblxuICAvLyBwb25n7J20IOyYpOyngCDslYrsnYAg7IOB7YOc7JeQ7IScIOuLpOydjCB0aWNr7J20IOyYpOuptCB0aW1lb3V0IGNsb3Nl66GcIOyymOumrO2VtCB6b21iaWUgY29ubmVjdGlvbuydhCDsoJXrpqztlahcbiAgcHJpdmF0ZSBzdGFydEhlYXJ0YmVhdCgpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5oZWFydGJlYXRNcyA8PSAwKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5oZWFydGJlYXRUaW1lciA9IHNldEludGVydmFsKCgpID0+IHtcbiAgICAgIGlmICh0aGlzLmNsb3NlZEludGVybmFsIHx8IHRoaXMuc29ja2V0LnJlYWR5U3RhdGUgIT09IFdTX09QRU4pIHtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICBpZiAodGhpcy5hd2FpdGluZ1BvbmcpIHtcbiAgICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgICAgbmFtZTogXCJ3cy5oZWFydGJlYXQudGltZW91dFwiLFxuICAgICAgICAgIGxldmVsOiBcIndhcm5cIixcbiAgICAgICAgICAuLi50aGlzLnRlbGVtZXRyeUZpZWxkcygpLFxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5jbG9zZShXU19DTE9TRV9DT0RFX0dPSU5HX0FXQVksIFwiSGVhcnRiZWF0IHRpbWVvdXRcIik7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cblxuICAgICAgdGhpcy5hd2FpdGluZ1BvbmcgPSB0cnVlO1xuICAgICAgdGhpcy5zb2NrZXQucGluZygpO1xuICAgIH0sIHRoaXMuaGVhcnRiZWF0TXMpO1xuICB9XG5cbiAgcHJpdmF0ZSBzdG9wSGVhcnRiZWF0KCk6IHZvaWQge1xuICAgIGlmICghdGhpcy5oZWFydGJlYXRUaW1lcikge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNsZWFySW50ZXJ2YWwodGhpcy5oZWFydGJlYXRUaW1lcik7XG4gICAgdGhpcy5oZWFydGJlYXRUaW1lciA9IG51bGw7XG4gIH1cblxuICAvLyBjbG9zZeqwgCDsi6TtjKjtlbTrj4QgdGVybWluYXRlIO2PtOuwseq5jOyngCDsi5zrj4TtlZjqs6AsIOuBneuCtCDsi6TtjKjtlZjrqbQgbWFya0Nsb3NlZOyXkCDsg4Htg5wg7KCV66as66W8IOychOyehO2VqFxuICBwcml2YXRlIGNsb3NlVHJhbnNwb3J0KGNvZGU/OiBudW1iZXIsIHJlYXNvbj86IHN0cmluZyk6IHZvaWQge1xuICAgIHRyeSB7XG4gICAgICBpZiAodGhpcy5zb2NrZXQucmVhZHlTdGF0ZSA9PT0gV1NfT1BFTiB8fCB0aGlzLnNvY2tldC5yZWFkeVN0YXRlID09PSBXU19DT05ORUNUSU5HKSB7XG4gICAgICAgIHRoaXMuc29ja2V0LmNsb3NlKGNvZGUsIHRydW5jYXRlQ2xvc2VSZWFzb24ocmVhc29uKSk7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cblxuICAgICAgdGhpcy5zb2NrZXQudGVybWluYXRlKCk7XG4gICAgfSBjYXRjaCB7XG4gICAgICB0cnkge1xuICAgICAgICB0aGlzLnNvY2tldC50ZXJtaW5hdGUoKTtcbiAgICAgIH0gY2F0Y2gge1xuICAgICAgICAvLyB0cmFuc3BvcnQgaXMgYWxyZWFkeSBicm9rZW47IHN0YXRlIGNsZWFudXAgaXMgaGFuZGxlZCBieSBtYXJrQ2xvc2VkKClcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICAvLyDsnbjrsJTsmrTrk5wgaGFuZGxlcuulvCBwcm9taXNlIGNoYWlu7Jy866GcIHNlcmlhbGl6ZSDtlZjqs6AsIGhhbmRsZXIg7JiI7Jm464qUIGNvbm5lY3Rpb24tbG9jYWwgMTAxMSBjbG9zZeuhnCDstpXshoztlahcbiAgcHJpdmF0ZSBlbnF1ZXVlTWVzc2FnZVRhc2sodGFzazogKCkgPT4gUHJvbWlzZTx2b2lkPik6IHZvaWQge1xuICAgIHRoaXMubWVzc2FnZVF1ZXVlID0gdGhpcy5tZXNzYWdlUXVldWVcbiAgICAgIC50aGVuKGFzeW5jICgpID0+IHtcbiAgICAgICAgaWYgKHRoaXMuY2xvc2VkSW50ZXJuYWwpIHtcbiAgICAgICAgICByZXR1cm47XG4gICAgICAgIH1cblxuICAgICAgICBhd2FpdCB0YXNrKCk7XG4gICAgICB9KVxuICAgICAgLmNhdGNoKCgpID0+IHtcbiAgICAgICAgdGhpcy5jbG9zZShXU19DTE9TRV9DT0RFX0lOVEVSTkFMX0VSUk9SLCBcIk1lc3NhZ2UgaGFuZGxpbmcgZmFpbGVkXCIpO1xuICAgICAgfSk7XG4gIH1cblxuICAvLyBxdWV1ZeqwgCDtlZzqs4Tsl5Ag64+E64us7ZWY66m0IDEwMTPsnLzroZwg64ur7JWEIOuKkOumsCDshozruYTsnpDqsIAg66mU66qo66as66W8IOuBneyXhuydtCDsnqHslYTrqLnsp4Ag66q77ZWY6rKMIO2VqFxuICAvLyBkYXRhIOyduOyekOuKlCB0ZWxlbWV0cnkgcGF5bG9hZCBwcmV2aWV3IOyaqeuPhOuhnOunjCDsgqzsmqntlZjrqbAgcGVuZGluZ091dGJvdW5kTWVzc2FnZXPsl5DripQg7KCA7J6l7ZWY7KeAIOyViuydjCAo7YGQIOuplOuqqOumrCDrs7TtmLgpXG4gIHByaXZhdGUgZW5xdWV1ZU91dGJvdW5kTWVzc2FnZShwYXlsb2FkOiBzdHJpbmcsIGV2ZW50OiBzdHJpbmcsIGRhdGE6IHVua25vd24pOiB2b2lkIHtcbiAgICBpZiAodGhpcy5wZW5kaW5nT3V0Ym91bmRNZXNzYWdlcy5sZW5ndGggPj0gTUFYX1BFTkRJTkdfT1VUQk9VTkRfTUVTU0FHRVMpIHtcbiAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICBuYW1lOiBcIndzLmJhY2twcmVzc3VyZS5vdmVyZmxvd1wiLFxuICAgICAgICBsZXZlbDogXCJlcnJvclwiLFxuICAgICAgICAuLi50aGlzLnRlbGVtZXRyeUZpZWxkcygpLFxuICAgICAgfSk7XG4gICAgICB0aGlzLmNsb3NlKFdTX0NMT1NFX0NPREVfVFJZX0FHQUlOX0xBVEVSLCBcIldlYlNvY2tldCBiYWNrcHJlc3N1cmUgb3ZlcmZsb3dcIik7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5wZW5kaW5nT3V0Ym91bmRNZXNzYWdlcy5wdXNoKHsgcGF5bG9hZCwgZXZlbnQgfSk7XG4gICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICBuYW1lOiBcIndzLnB1Ymxpc2gucXVldWVkXCIsXG4gICAgICBsZXZlbDogXCJkZWJ1Z1wiLFxuICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgIGRldGFpbDogeyBldmVudCB9LFxuICAgICAgcGF5bG9hZDogZGF0YSxcbiAgICB9KTtcbiAgICB0aGlzLnNjaGVkdWxlT3V0Ym91bmRGbHVzaCgpO1xuICB9XG5cbiAgcHJpdmF0ZSBzY2hlZHVsZU91dGJvdW5kRmx1c2goZGVsYXlNczogbnVtYmVyID0gMCk6IHZvaWQge1xuICAgIGlmICh0aGlzLm91dGJvdW5kRmx1c2hTY2hlZHVsZWQgfHwgdGhpcy5jbG9zZWRJbnRlcm5hbCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMub3V0Ym91bmRGbHVzaFNjaGVkdWxlZCA9IHRydWU7XG4gICAgY29uc3QgZmx1c2ggPSAoKSA9PiB7XG4gICAgICB0aGlzLm91dGJvdW5kRmx1c2hTY2hlZHVsZWQgPSBmYWxzZTtcbiAgICAgIHRoaXMuZmx1c2hPdXRib3VuZE1lc3NhZ2VzKCk7XG4gICAgfTtcblxuICAgIGlmIChkZWxheU1zID4gMCkge1xuICAgICAgc2V0VGltZW91dChmbHVzaCwgZGVsYXlNcyk7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgc2V0SW1tZWRpYXRlKGZsdXNoKTtcbiAgfVxuXG4gIC8vIGJ1ZmZlcmVkQW1vdW506rCAIOyehOqzhOy5mOulvCDrhJjsnLzrqbQgZmx1c2jrpbwg66+466SEIHNvY2tldCDrgrTrtoAg7YGQ6rCAIO2EsOyngOyngCDslYrrj4TroZ0gYmFja3ByZXNzdXJl66W8IOyhtOykke2VqFxuICAvLyDtlZwg67KI7JeQIOuwsOy5mCDri6jsnITroZzrp4wgc2VuZO2VtCDrj5nquLAg66Oo7ZSE6rCAIOydtOuypO2KuCDro6jtlITrpbwg7J6l7Iuc6rCEIOygkOycoO2VmOyngCDslYrqsowg7ZWoXG4gIHByaXZhdGUgZmx1c2hPdXRib3VuZE1lc3NhZ2VzKCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmNsb3NlZEludGVybmFsIHx8IHRoaXMuc29ja2V0LnJlYWR5U3RhdGUgIT09IFdTX09QRU4pIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBpZiAodGhpcy5zb2NrZXQuYnVmZmVyZWRBbW91bnQgPiBNQVhfU09DS0VUX0JVRkZFUkVEX0FNT1VOVCkge1xuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgIG5hbWU6IFwid3MuYmFja3ByZXNzdXJlLmRlbGF5ZWRcIixcbiAgICAgICAgbGV2ZWw6IFwid2FyblwiLFxuICAgICAgICAuLi50aGlzLnRlbGVtZXRyeUZpZWxkcygpLFxuICAgICAgfSk7XG4gICAgICB0aGlzLnNjaGVkdWxlT3V0Ym91bmRGbHVzaChPVVRCT1VORF9SRVRSWV9ERUxBWV9NUyk7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgbGV0IHNlbnQgPSAwO1xuICAgIHdoaWxlIChcbiAgICAgIHNlbnQgPCBPVVRCT1VORF9CQVRDSF9TSVpFICYmXG4gICAgICB0aGlzLnBlbmRpbmdPdXRib3VuZE1lc3NhZ2VzLmxlbmd0aCA+IDAgJiZcbiAgICAgIHRoaXMuc29ja2V0LnJlYWR5U3RhdGUgPT09IFdTX09QRU5cbiAgICApIHtcbiAgICAgIGNvbnN0IG5leHQgPSB0aGlzLnBlbmRpbmdPdXRib3VuZE1lc3NhZ2VzLnNoaWZ0KCk7XG4gICAgICBpZiAoIW5leHQpIHtcbiAgICAgICAgYnJlYWs7XG4gICAgICB9XG4gICAgICBjb25zdCB7IHBheWxvYWQsIGV2ZW50IH0gPSBuZXh0O1xuXG4gICAgICBjb25zdCBzdGFydGVkQXQgPSBwZXJmb3JtYW5jZS5ub3coKTtcbiAgICAgIGNvbnN0IGZpZWxkcyA9IHRoaXMudGVsZW1ldHJ5RmllbGRzKCk7XG4gICAgICB0cnkge1xuICAgICAgICB0aGlzLnNvY2tldC5zZW5kKHBheWxvYWQpO1xuICAgICAgICBjb25zdCBkdXJhdGlvbk1zID0gcGVyZm9ybWFuY2Uubm93KCkgLSBzdGFydGVkQXQ7XG4gICAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICAgIG5hbWU6IFwid3MucHVibGlzaC5zZW50XCIsXG4gICAgICAgICAgbGV2ZWw6IFwiZGVidWdcIixcbiAgICAgICAgICAuLi5maWVsZHMsXG4gICAgICAgICAgZGV0YWlsOiB7IGV2ZW50IH0sXG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5yZWNvcmRTcGFuKHtcbiAgICAgICAgICBvcGVyYXRpb25OYW1lOiBcIndzLnB1Ymxpc2guc2VuZFwiLFxuICAgICAgICAgIGtpbmQ6IFwicHJvZHVjZXJcIixcbiAgICAgICAgICBkdXJhdGlvbk1zLFxuICAgICAgICAgIHN0YXR1czogXCJ1bnNldFwiLFxuICAgICAgICAgIC4uLmZpZWxkcyxcbiAgICAgICAgICBhdHRyaWJ1dGVzOiB7IGV2ZW50IH0sXG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5yZWNvcmRNZXRyaWMoe1xuICAgICAgICAgIG5hbWU6IFwic29uYW11LndzLnB1Ymxpc2hlc1wiLFxuICAgICAgICAgIGtpbmQ6IFwiY291bnRlclwiLFxuICAgICAgICAgIHZhbHVlOiAxLFxuICAgICAgICAgIHVuaXQ6IFwiMVwiLFxuICAgICAgICAgIHRhZ3M6IHsgb3V0Y29tZTogXCJzZW50XCIsIGV2ZW50IH0sXG4gICAgICAgICAgLi4uZmllbGRzLFxuICAgICAgICB9KTtcbiAgICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICAgIGNvbnN0IGR1cmF0aW9uTXMgPSBwZXJmb3JtYW5jZS5ub3coKSAtIHN0YXJ0ZWRBdDtcbiAgICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgICAgbmFtZTogXCJ3cy5wdWJsaXNoLmZhaWxlZFwiLFxuICAgICAgICAgIGxldmVsOiBcImVycm9yXCIsXG4gICAgICAgICAgLi4uZmllbGRzLFxuICAgICAgICAgIGRldGFpbDogeyBldmVudCB9LFxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIucmVjb3JkU3Bhbih7XG4gICAgICAgICAgb3BlcmF0aW9uTmFtZTogXCJ3cy5wdWJsaXNoLnNlbmRcIixcbiAgICAgICAgICBraW5kOiBcInByb2R1Y2VyXCIsXG4gICAgICAgICAgZHVyYXRpb25NcyxcbiAgICAgICAgICBzdGF0dXM6IFwiZXJyb3JcIixcbiAgICAgICAgICAuLi5maWVsZHMsXG4gICAgICAgICAgYXR0cmlidXRlczogeyBldmVudCB9LFxuICAgICAgICAgIGVycm9yVHlwZTogZXJyb3IgaW5zdGFuY2VvZiBFcnJvciA/IGVycm9yLm5hbWUgOiB0eXBlb2YgZXJyb3IsXG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLmNsb3NlKFdTX0NMT1NFX0NPREVfSU5URVJOQUxfRVJST1IsIFwiT3V0Ym91bmQgcHVibGlzaCBmYWlsZWRcIik7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cblxuICAgICAgc2VudCArPSAxO1xuICAgICAgaWYgKHRoaXMuc29ja2V0LmJ1ZmZlcmVkQW1vdW50ID4gTUFYX1NPQ0tFVF9CVUZGRVJFRF9BTU9VTlQpIHtcbiAgICAgICAgYnJlYWs7XG4gICAgICB9XG4gICAgfVxuXG4gICAgaWYgKHRoaXMucGVuZGluZ091dGJvdW5kTWVzc2FnZXMubGVuZ3RoID4gMCkge1xuICAgICAgdGhpcy5zY2hlZHVsZU91dGJvdW5kRmx1c2goXG4gICAgICAgIHRoaXMuc29ja2V0LmJ1ZmZlcmVkQW1vdW50ID4gTUFYX1NPQ0tFVF9CVUZGRVJFRF9BTU9VTlQgPyBPVVRCT1VORF9SRVRSWV9ERUxBWV9NUyA6IDAsXG4gICAgICApO1xuICAgIH1cbiAgfVxufVxuXG5mdW5jdGlvbiBub3JtYWxpemVNZXNzYWdlKHJhdzogdW5rbm93bik6IHN0cmluZyB7XG4gIGlmICh0eXBlb2YgcmF3ID09PSBcInN0cmluZ1wiKSB7XG4gICAgcmV0dXJuIHJhdztcbiAgfVxuXG4gIGlmIChyYXcgaW5zdGFuY2VvZiBCdWZmZXIpIHtcbiAgICByZXR1cm4gcmF3LnRvU3RyaW5nKFwidXRmLThcIik7XG4gIH1cblxuICBpZiAocmF3IGluc3RhbmNlb2YgQXJyYXlCdWZmZXIpIHtcbiAgICByZXR1cm4gQnVmZmVyLmZyb20ocmF3KS50b1N0cmluZyhcInV0Zi04XCIpO1xuICB9XG5cbiAgaWYgKEFycmF5LmlzQXJyYXkocmF3KSkge1xuICAgIHJldHVybiBCdWZmZXIuY29uY2F0KHJhdy5maWx0ZXIoKGNodW5rKTogY2h1bmsgaXMgQnVmZmVyID0+IGNodW5rIGluc3RhbmNlb2YgQnVmZmVyKSkudG9TdHJpbmcoXG4gICAgICBcInV0Zi04XCIsXG4gICAgKTtcbiAgfVxuXG4gIHJldHVybiBKU09OLnN0cmluZ2lmeShyYXcpO1xufVxuXG5mdW5jdGlvbiBzYWZlUGFyc2VFbnZlbG9wZShyYXc6IHN0cmluZyk6IFBhcnNlZEVudmVsb3BlIHwgbnVsbCB7XG4gIHRyeSB7XG4gICAgY29uc3QgcGFyc2VkID0gSlNPTi5wYXJzZShyYXcpIGFzIHVua25vd247XG4gICAgY29uc3QgdmFsaWRhdGVkID0gV2ViU29ja2V0RW52ZWxvcGVTY2hlbWEuc2FmZVBhcnNlKHBhcnNlZCk7XG4gICAgcmV0dXJuIHZhbGlkYXRlZC5zdWNjZXNzID8gdmFsaWRhdGVkLmRhdGEgOiBudWxsO1xuICB9IGNhdGNoIHtcbiAgICByZXR1cm4gbnVsbDtcbiAgfVxufVxuXG4vLyBSRkMgNjQ1NeqwgCBjbG9zZSBmcmFtZSByZWFzb27snYQgMTIzIGJ5dGXroZwg7KCc7ZWc7ZWY66+A66GcIOy0iOqzvOu2hOydgCDsnpjrnbwg7KCE7IahIOyLpO2MqOulvCDrsKnsp4DtlahcbmZ1bmN0aW9uIHRydW5jYXRlQ2xvc2VSZWFzb24ocmVhc29uPzogc3RyaW5nKTogc3RyaW5nIHwgdW5kZWZpbmVkIHtcbiAgaWYgKCFyZWFzb24pIHtcbiAgICByZXR1cm4gdW5kZWZpbmVkO1xuICB9XG5cbiAgcmV0dXJuIEJ1ZmZlci5ieXRlTGVuZ3RoKHJlYXNvbiwgXCJ1dGYtOFwiKSA8PSAxMjNcbiAgICA/IHJlYXNvblxuICAgIDogQnVmZmVyLmZyb20ocmVhc29uKS5zdWJhcnJheSgwLCAxMjMpLnRvU3RyaW5nKFwidXRmLThcIik7XG59XG5cbi8vIGNvbm5lY3Rpb24gbGlmZXRpbWUgc3BhbuydmCBzdGF0dXPrpbwgY2xvc2UgY29kZSDquLDspIDsnLzroZwg67aE6riw7ZWoICgxMDAwLzEwMDEg7KCV7IOBIOyiheujjCwg6re4IOyZuCBrbm93biBjb2RlIGVycm9yLCBjb2RlIOuvuOyDgeydgCB1bnNldClcbmZ1bmN0aW9uIGRlcml2ZUxpZmV0aW1lU3RhdHVzKGNvZGU6IG51bWJlciB8IHVuZGVmaW5lZCk6IFwib2tcIiB8IFwiZXJyb3JcIiB8IFwidW5zZXRcIiB7XG4gIGlmIChjb2RlID09PSB1bmRlZmluZWQpIHJldHVybiBcInVuc2V0XCI7XG4gIGlmIChjb2RlID09PSAxMDAwIHx8IGNvZGUgPT09IDEwMDEpIHJldHVybiBcIm9rXCI7XG4gIHJldHVybiBcImVycm9yXCI7XG59XG4iXSwibWFwcGluZ3MiOiI7Ozs7Ozs7OztBQXVMQSxTQUFnQix1QkFBdUIsVUFBbUMsRUFBRSxFQUFvQjtBQUM5RixRQUFPLElBQUksaUJBQWlCLFFBQVE7O0FBZ3BCdEMsU0FBUyxpQkFBaUIsS0FBc0I7QUFDOUMsS0FBSSxPQUFPLFFBQVEsVUFBVTtBQUMzQixTQUFPOztBQUdULEtBQUksZUFBZSxRQUFRO0FBQ3pCLFNBQU8sSUFBSSxTQUFTLFFBQVE7O0FBRzlCLEtBQUksZUFBZSxhQUFhO0FBQzlCLFNBQU8sT0FBTyxLQUFLLElBQUksQ0FBQyxTQUFTLFFBQVE7O0FBRzNDLEtBQUksTUFBTSxRQUFRLElBQUksRUFBRTtBQUN0QixTQUFPLE9BQU8sT0FBTyxJQUFJLFFBQVEsVUFBMkIsaUJBQWlCLE9BQU8sQ0FBQyxDQUFDLFNBQ3BGLFFBQ0Q7O0FBR0gsUUFBTyxLQUFLLFVBQVUsSUFBSTs7QUFHNUIsU0FBUyxrQkFBa0IsS0FBb0M7QUFDN0QsS0FBSTtFQUNGLE1BQU0sU0FBUyxLQUFLLE1BQU0sSUFBSTtFQUM5QixNQUFNLFlBQVksd0JBQXdCLFVBQVUsT0FBTztBQUMzRCxTQUFPLFVBQVUsVUFBVSxVQUFVLE9BQU87U0FDdEM7QUFDTixTQUFPOzs7QUFLWCxTQUFTLG9CQUFvQixRQUFxQztBQUNoRSxLQUFJLENBQUMsUUFBUTtBQUNYLFNBQU87O0FBR1QsUUFBTyxPQUFPLFdBQVcsUUFBUSxRQUFRLElBQUksTUFDekMsU0FDQSxPQUFPLEtBQUssT0FBTyxDQUFDLFNBQVMsR0FBRyxJQUFJLENBQUMsU0FBUyxRQUFROztBQUk1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
|
|
631
|
+
|
|
632
|
+
//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoid3MuanMiLCJuYW1lcyI6WyJ6Il0sInNvdXJjZXMiOlsiLi4vLi4vc3JjL3N0cmVhbS93cy50cyJdLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyByYW5kb21VVUlEIH0gZnJvbSBcIm5vZGU6Y3J5cHRvXCI7XG5pbXBvcnQgeyBob3N0bmFtZSB9IGZyb20gXCJub2RlOm9zXCI7XG5cbmltcG9ydCB7IHR5cGUgV2ViU29ja2V0IH0gZnJvbSBcIndzXCI7XG5pbXBvcnQgeyB6IH0gZnJvbSBcInpvZFwiO1xuXG5pbXBvcnQgeyB0eXBlIFdlYlNvY2tldEF1ZGllbmNlIH0gZnJvbSBcIi4vd3MtYXVkaWVuY2VcIjtcbmltcG9ydCB7IHR5cGUgV2ViU29ja2V0Q2x1c3RlckJ1cyB9IGZyb20gXCIuL3dzLWNsdXN0ZXItYnVzXCI7XG5pbXBvcnQgeyB0eXBlIFdlYlNvY2tldFByZXNlbmNlU3RvcmUgfSBmcm9tIFwiLi93cy1wcmVzZW5jZS1zdG9yZVwiO1xuaW1wb3J0IHtcbiAgdHlwZSBNYW5hZ2VkV2ViU29ja2V0Q29ubmVjdGlvbixcbiAgV2ViU29ja2V0UmVnaXN0cnksXG4gIHR5cGUgV2ViU29ja2V0UmVnaXN0cnlPcHRpb25zLFxuICB0eXBlIFdlYlNvY2tldFJvb21JZCxcbiAgdHlwZSBXZWJTb2NrZXRVc2VySWQsXG59IGZyb20gXCIuL3dzLXJlZ2lzdHJ5XCI7XG5pbXBvcnQge1xuICB0eXBlIFRlbGVtZXRyeUNvbnRleHRQcm92aWRlcixcbiAgdHlwZSBXZWJTb2NrZXRUZWxlbWV0cnlDb25uZWN0aW9uU25hcHNob3QsXG4gIHR5cGUgV2ViU29ja2V0VGVsZW1ldHJ5Q29ubmVjdGlvbkNvbnRleHQsXG4gIHR5cGUgV2ViU29ja2V0VGVsZW1ldHJ5Q29udHJvbGxlcixcbiAgdHlwZSBXZWJTb2NrZXRUZWxlbWV0cnlPcHRpb25zLFxuICB0eXBlIFRlbGVtZXRyeUluc3BlY3RhYmxlQ29ubmVjdGlvbixcbiAgY3JlYXRlV2ViU29ja2V0VGVsZW1ldHJ5Q29udHJvbGxlcixcbiAgaXNQcm9taXNlTGlrZSxcbn0gZnJvbSBcIi4vd3MtdGVsZW1ldHJ5XCI7XG5pbXBvcnQgeyBwYXJzZVRyYWNlUGFyZW50LCBnZW5lcmF0ZVNwYW5JZCB9IGZyb20gXCIuL3dzLXRlbGVtZXRyeS10cmFjZVwiO1xuXG4vLyB0cmFuc3BvcnQtbGV2ZWwg7IOB7IiY7JmAIHF1ZXVlIHRocmVzaG9sZOulvCDtlZwg7YyM7J287JeQIOuqqOyVhCBsaWZlY3ljbGUvYmFja3ByZXNzdXJlIOygleyxheydhCDspJHslZntmZTtlahcbmNvbnN0IFdTX0NPTk5FQ1RJTkcgPSAwO1xuY29uc3QgV1NfT1BFTiA9IDE7XG5jb25zdCBXU19DTE9TRUQgPSAzO1xuLy8gUkZDIDY0NTUgY2xvc2UgY29kZXMgdXNlZCBieSBTb25hbXUncyBXZWJTb2NrZXQgcnVudGltZS5cbmNvbnN0IFdTX0NMT1NFX0NPREVfR09JTkdfQVdBWSA9IDEwMDE7XG5jb25zdCBXU19DTE9TRV9DT0RFX0lOVkFMSURfRlJBTUVfUEFZTE9BRF9EQVRBID0gMTAwNztcbmNvbnN0IFdTX0NMT1NFX0NPREVfUE9MSUNZX1ZJT0xBVElPTiA9IDEwMDg7XG5jb25zdCBXU19DTE9TRV9DT0RFX0lOVEVSTkFMX0VSUk9SID0gMTAxMTtcbmNvbnN0IFdTX0NMT1NFX0NPREVfVFJZX0FHQUlOX0xBVEVSID0gMTAxMztcbmNvbnN0IE1BWF9QRU5ESU5HX01FU1NBR0VTID0gMTAwO1xuY29uc3QgTUFYX1BFTkRJTkdfT1VUQk9VTkRfTUVTU0FHRVMgPSAxXzAwMDtcbmNvbnN0IE1BWF9TT0NLRVRfQlVGRkVSRURfQU1PVU5UID0gMV8wNDhfNTc2O1xuY29uc3QgT1VUQk9VTkRfQkFUQ0hfU0laRSA9IDUwO1xuY29uc3QgT1VUQk9VTkRfUkVUUllfREVMQVlfTVMgPSA1O1xuXG4vLyBlbnZlbG9wZeydhCBge2V2ZW50LCBkYXRhfWAg7ZiV7YOc66GcIOqzoOygle2VtCBzZXJ2ZXIgaGFuZGxlcuyZgCBnZW5lcmF0ZWQgY2xpZW506rCAIOqwmeydgCBmcmFtaW5nIGNvbnRyYWN066W8IOyTsOqyjCDtlahcbi8vIG1ldGHripQgb3B0aW9uYWzsnbTrr4DroZwg6riw7KG0IGB7ZXZlbnQsIGRhdGF9YCDrqZTsi5zsp4Drj4Qg6re464yA66GcIO2MjOyLseuQqCAoYmFja3dhcmQtY29tcGF0aWJsZSlcbmNvbnN0IFdlYlNvY2tldEVudmVsb3BlU2NoZW1hID0gei5vYmplY3Qoe1xuICBldmVudDogei5zdHJpbmcoKSxcbiAgZGF0YTogei51bmtub3duKCksXG4gIG1ldGE6IHpcbiAgICAub2JqZWN0KHtcbiAgICAgIHRyYWNlcGFyZW50OiB6LnN0cmluZygpLm9wdGlvbmFsKCksXG4gICAgICB0cmFjZXN0YXRlOiB6LnN0cmluZygpLm9wdGlvbmFsKCksXG4gICAgfSlcbiAgICAub3B0aW9uYWwoKSxcbn0pO1xuXG50eXBlIE1lc3NhZ2VIYW5kbGVyPFQ+ID0gKFxuICBkYXRhOiBULFxuICB0ZWxlbWV0cnlDb250ZXh0PzogV2ViU29ja2V0VGVsZW1ldHJ5Q29ubmVjdGlvbkNvbnRleHQsXG4pID0+IHZvaWQgfCBQcm9taXNlPHZvaWQ+O1xudHlwZSBDbG9zZUhhbmRsZXIgPSAoKSA9PiB2b2lkIHwgUHJvbWlzZTx2b2lkPjtcblxuZXhwb3J0IHR5cGUgV2ViU29ja2V0RXZlbnRNYXAgPSBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcblxudHlwZSBJbmZlcldlYlNvY2tldEV2ZW50TWFwPFRTY2hlbWEgZXh0ZW5kcyB6LlpvZFJhd1NoYXBlPiA9IHouaW5mZXI8ei5ab2RPYmplY3Q8VFNjaGVtYT4+O1xuXG5leHBvcnQgdHlwZSBXZWJTb2NrZXRPdXRFdmVudHM8VE91dCBleHRlbmRzIFdlYlNvY2tldEV2ZW50TWFwID0gV2ViU29ja2V0RXZlbnRNYXA+ID0gVE91dDtcblxuZXhwb3J0IHR5cGUgV2ViU29ja2V0SW5FdmVudHM8VEluIGV4dGVuZHMgV2ViU29ja2V0RXZlbnRNYXAgPSBXZWJTb2NrZXRFdmVudE1hcD4gPSBUSW47XG5cbmV4cG9ydCBpbnRlcmZhY2UgV2ViU29ja2V0Q29ubmVjdGlvbjxcbiAgVE91dCBleHRlbmRzIFdlYlNvY2tldEV2ZW50TWFwID0gV2ViU29ja2V0RXZlbnRNYXAsXG4gIFRJbiBleHRlbmRzIFdlYlNvY2tldEV2ZW50TWFwID0gV2ViU29ja2V0RXZlbnRNYXAsXG4+IGV4dGVuZHMgTWFuYWdlZFdlYlNvY2tldENvbm5lY3Rpb24ge1xuICB0cmFuc3BvcnQ6IFwid3NcIjtcbiAgb25DbG9zZShjYWxsYmFjazogQ2xvc2VIYW5kbGVyKTogdm9pZDtcbiAgb25NZXNzYWdlPEsgZXh0ZW5kcyBrZXlvZiBXZWJTb2NrZXRJbkV2ZW50czxUSW4+PihcbiAgICBldmVudDogSyxcbiAgICBoYW5kbGVyOiBNZXNzYWdlSGFuZGxlcjxXZWJTb2NrZXRJbkV2ZW50czxUSW4+W0tdPixcbiAgKTogdm9pZDtcbiAgcHVibGlzaDxLIGV4dGVuZHMga2V5b2YgV2ViU29ja2V0T3V0RXZlbnRzPFRPdXQ+PihcbiAgICBldmVudDogSyxcbiAgICBkYXRhOiBXZWJTb2NrZXRPdXRFdmVudHM8VE91dD5bS10sXG4gICk6IHZvaWQ7XG4gIHdhaXRGb3JDbG9zZSgpOiBQcm9taXNlPHZvaWQ+O1xuICBqb2luKHJvb21JZDogV2ViU29ja2V0Um9vbUlkKTogdm9pZDtcbiAgbGVhdmUocm9vbUlkOiBXZWJTb2NrZXRSb29tSWQpOiB2b2lkO1xuICBzZXRVc2VySWQodXNlcklkOiBXZWJTb2NrZXRVc2VySWQpOiB2b2lkO1xuICBjbGVhclVzZXJJZCgpOiB2b2lkO1xufVxuXG5leHBvcnQgdHlwZSBBbnlXZWJTb2NrZXRDb25uZWN0aW9uID0gV2ViU29ja2V0Q29ubmVjdGlvbjxXZWJTb2NrZXRFdmVudE1hcCwgV2ViU29ja2V0RXZlbnRNYXA+O1xuXG50eXBlIFBhcnNlZEVudmVsb3BlID0gei5pbmZlcjx0eXBlb2YgV2ViU29ja2V0RW52ZWxvcGVTY2hlbWE+O1xuXG50eXBlIFdlYlNvY2tldENvbm5lY3Rpb25PcHRpb25zPFRPdXQgZXh0ZW5kcyB6LlpvZFJhd1NoYXBlLCBUSW4gZXh0ZW5kcyB6LlpvZFJhd1NoYXBlPiA9IHtcbiAgbmFtZXNwYWNlPzogc3RyaW5nO1xuICBoZWFydGJlYXQ/OiBudW1iZXI7XG4gIGFjdGl2ZT86IGJvb2xlYW47XG4gIG91dEV2ZW50czogei5ab2RPYmplY3Q8VE91dD47XG4gIGluRXZlbnRzOiB6LlpvZE9iamVjdDxUSW4+O1xuICByZWdpc3RyeTogV2ViU29ja2V0UmVnaXN0cnk7XG4gIHRlbGVtZXRyeUNvbnRyb2xsZXI6IFdlYlNvY2tldFRlbGVtZXRyeUNvbnRyb2xsZXI7XG4gIHRyYWNlSWQ/OiBzdHJpbmc7XG4gIHNwYW5JZD86IHN0cmluZztcbiAgcGFyZW50U3BhbklkPzogc3RyaW5nO1xuICBzYW1wbGVkPzogYm9vbGVhbjtcbn07XG5cbmV4cG9ydCB0eXBlIFdlYlNvY2tldFJ1bnRpbWVPcHRpb25zID0ge1xuICBub2RlSWQ/OiBzdHJpbmc7XG4gIHByZXNlbmNlU3RvcmU/OiBXZWJTb2NrZXRQcmVzZW5jZVN0b3JlO1xuICBjbHVzdGVyQnVzPzogV2ViU29ja2V0Q2x1c3RlckJ1cztcbiAgdGVsZW1ldHJ5PzogYm9vbGVhbiB8IFdlYlNvY2tldFRlbGVtZXRyeU9wdGlvbnM7XG59O1xuXG4vLyByZWdpc3RyeeulvCDshozsnKDtlZjqs6AgY29ubmVjdGlvbiDsg53shLEvc2h1dGRvd27snYQg64u064u57ZWoLiBTb25hbXUg7JWg7ZSM66as7LyA7J207IWYIOyImOuqheyjvOq4sOyZgCDqsJnsnbQg7JuA7KeB7J2064+E66GdIOyEpOqzhO2VqFxuZXhwb3J0IGNsYXNzIFdlYlNvY2tldFJ1bnRpbWUge1xuICByZWFkb25seSByZWdpc3RyeTogV2ViU29ja2V0UmVnaXN0cnk7XG4gIHJlYWRvbmx5IHRlbGVtZXRyeUNvbnRyb2xsZXI6IFdlYlNvY2tldFRlbGVtZXRyeUNvbnRyb2xsZXI7XG5cbiAgY29uc3RydWN0b3Iob3B0aW9uczogV2ViU29ja2V0UnVudGltZU9wdGlvbnMgPSB7fSkge1xuICAgIC8vIOu2hOyCsCDtmZjqsr3sl5DshJwg64W465OcIOqwhCDstqnrj4zsnYQg66eJ6riwIOychO2VtCBob3N0bmFtZSArIHBpZOuhnCDrlJTtj7Ttirgg7Iud67OE7J6Q66W8IOunjOuToOuLpC5cbiAgICAvLyDqsJnsnYAg7Zi47Iqk7Yq47JeQIOyXrOufrCDtlITroZzshLjsiqTqsIAg65agIOyeiOyWtOuPhCBwaWTroZwg6rWs67aE65CY66mwLCDroZzqt7gv66mU7Yq466at7JeQ7ISc64+EIOyLneuzhOydtCDsiazsm4BcbiAgICBjb25zdCByZXNvbHZlZE5vZGVJZCA9IG9wdGlvbnMubm9kZUlkID8/IGAke2hvc3RuYW1lKCl9LSR7cHJvY2Vzcy5waWR9YDtcbiAgICB0aGlzLnRlbGVtZXRyeUNvbnRyb2xsZXIgPSBjcmVhdGVXZWJTb2NrZXRUZWxlbWV0cnlDb250cm9sbGVyKG9wdGlvbnMudGVsZW1ldHJ5LCB7XG4gICAgICBydW50aW1lSWQ6IHJhbmRvbVVVSUQoKSxcbiAgICAgIG5vZGVJZDogcmVzb2x2ZWROb2RlSWQsXG4gICAgfSk7XG4gICAgY29uc3QgcmVnaXN0cnlPcHRpb25zOiBXZWJTb2NrZXRSZWdpc3RyeU9wdGlvbnMgPSB7XG4gICAgICBub2RlSWQ6IHJlc29sdmVkTm9kZUlkLFxuICAgICAgcHJlc2VuY2VTdG9yZTogb3B0aW9ucy5wcmVzZW5jZVN0b3JlLFxuICAgICAgY2x1c3RlckJ1czogb3B0aW9ucy5jbHVzdGVyQnVzLFxuICAgICAgdGVsZW1ldHJ5Q29udHJvbGxlcjogdGhpcy50ZWxlbWV0cnlDb250cm9sbGVyLFxuICAgIH07XG4gICAgdGhpcy5yZWdpc3RyeSA9IG5ldyBXZWJTb2NrZXRSZWdpc3RyeShyZWdpc3RyeU9wdGlvbnMpO1xuICB9XG5cbiAgcmVnaXN0ZXJDb25uZWN0aW9uPFRPdXRTY2hlbWEgZXh0ZW5kcyB6LlpvZFJhd1NoYXBlLCBUSW5TY2hlbWEgZXh0ZW5kcyB6LlpvZFJhd1NoYXBlPihcbiAgICBzb2NrZXQ6IFdlYlNvY2tldCxcbiAgICBvcHRpb25zOiBPbWl0PFxuICAgICAgV2ViU29ja2V0Q29ubmVjdGlvbk9wdGlvbnM8VE91dFNjaGVtYSwgVEluU2NoZW1hPixcbiAgICAgIFwicmVnaXN0cnlcIiB8IFwidGVsZW1ldHJ5Q29udHJvbGxlclwiXG4gICAgPixcbiAgKTogV2ViU29ja2V0Q29ubmVjdGlvbjxJbmZlcldlYlNvY2tldEV2ZW50TWFwPFRPdXRTY2hlbWE+LCBJbmZlcldlYlNvY2tldEV2ZW50TWFwPFRJblNjaGVtYT4+IHtcbiAgICByZXR1cm4gbmV3IFdlYlNvY2tldENvbm5lY3Rpb25JbXBsKHNvY2tldCwge1xuICAgICAgLi4ub3B0aW9ucyxcbiAgICAgIHJlZ2lzdHJ5OiB0aGlzLnJlZ2lzdHJ5LFxuICAgICAgdGVsZW1ldHJ5Q29udHJvbGxlcjogdGhpcy50ZWxlbWV0cnlDb250cm9sbGVyLFxuICAgIH0pO1xuICB9XG5cbiAgYWN0aXZhdGVDb25uZWN0aW9uKGNvbm5lY3Rpb25JZDogc3RyaW5nKTogdm9pZCB7XG4gICAgdGhpcy5yZWdpc3RyeS5hY3RpdmF0ZShjb25uZWN0aW9uSWQpO1xuICB9XG5cbiAgYnJvYWRjYXN0KGV2ZW50OiBzdHJpbmcsIGRhdGE6IHVua25vd24sIG5hbWVzcGFjZT86IHN0cmluZyk6IHZvaWQge1xuICAgIHRoaXMucmVnaXN0cnkuYnJvYWRjYXN0KGV2ZW50LCBkYXRhLCBuYW1lc3BhY2UpO1xuICB9XG5cbiAgcHVibGlzaFRvUm9vbShyb29tSWQ6IFdlYlNvY2tldFJvb21JZCwgZXZlbnQ6IHN0cmluZywgZGF0YTogdW5rbm93biwgbmFtZXNwYWNlPzogc3RyaW5nKTogdm9pZCB7XG4gICAgdGhpcy5yZWdpc3RyeS5wdWJsaXNoVG9Sb29tKHJvb21JZCwgZXZlbnQsIGRhdGEsIG5hbWVzcGFjZSk7XG4gIH1cblxuICBwdWJsaXNoVG9Vc2VyKHVzZXJJZDogV2ViU29ja2V0VXNlcklkLCBldmVudDogc3RyaW5nLCBkYXRhOiB1bmtub3duLCBuYW1lc3BhY2U/OiBzdHJpbmcpOiB2b2lkIHtcbiAgICB0aGlzLnJlZ2lzdHJ5LnB1Ymxpc2hUb1VzZXIodXNlcklkLCBldmVudCwgZGF0YSwgbmFtZXNwYWNlKTtcbiAgfVxuXG4gIHB1Ymxpc2hUb0F1ZGllbmNlKGF1ZGllbmNlOiBXZWJTb2NrZXRBdWRpZW5jZSwgZXZlbnQ6IHN0cmluZywgZGF0YTogdW5rbm93bik6IHZvaWQge1xuICAgIHRoaXMucmVnaXN0cnkucHVibGlzaFRvQXVkaWVuY2UoYXVkaWVuY2UsIGV2ZW50LCBkYXRhKTtcbiAgfVxuXG4gIC8vIO2UhOuhnOyEuOyKpCDsooXro4wg7IucIOyCtOyVhOyeiOuKlCDsl7DqsrDsnbQg64Ko7KeAIOyViuuPhOuhnSByZWdpc3RyeeulvCDsiJztmoztlbQg7J286rSEIOyiheujjO2VqFxuICBhc3luYyBzaHV0ZG93bihcbiAgICBjb2RlOiBudW1iZXIgPSBXU19DTE9TRV9DT0RFX0dPSU5HX0FXQVksXG4gICAgcmVhc29uID0gXCJTZXJ2ZXIgc2h1dHRpbmcgZG93blwiLFxuICApOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBhd2FpdCB0aGlzLnJlZ2lzdHJ5LnNodXRkb3duKGNvZGUsIHJlYXNvbik7XG4gICAgYXdhaXQgdGhpcy50ZWxlbWV0cnlDb250cm9sbGVyLnNodXRkb3duKCk7XG4gIH1cbn1cblxuZXhwb3J0IGZ1bmN0aW9uIGNyZWF0ZVdlYlNvY2tldFJ1bnRpbWUob3B0aW9uczogV2ViU29ja2V0UnVudGltZU9wdGlvbnMgPSB7fSk6IFdlYlNvY2tldFJ1bnRpbWUge1xuICByZXR1cm4gbmV3IFdlYlNvY2tldFJ1bnRpbWUob3B0aW9ucyk7XG59XG5cbmNsYXNzIFdlYlNvY2tldENvbm5lY3Rpb25JbXBsPFRPdXRTY2hlbWEgZXh0ZW5kcyB6LlpvZFJhd1NoYXBlLCBUSW5TY2hlbWEgZXh0ZW5kcyB6LlpvZFJhd1NoYXBlPlxuICBpbXBsZW1lbnRzXG4gICAgV2ViU29ja2V0Q29ubmVjdGlvbjxJbmZlcldlYlNvY2tldEV2ZW50TWFwPFRPdXRTY2hlbWE+LCBJbmZlcldlYlNvY2tldEV2ZW50TWFwPFRJblNjaGVtYT4+LFxuICAgIFRlbGVtZXRyeUluc3BlY3RhYmxlQ29ubmVjdGlvbixcbiAgICBUZWxlbWV0cnlDb250ZXh0UHJvdmlkZXJcbntcbiAgcmVhZG9ubHkgaWQgPSByYW5kb21VVUlEKCk7XG4gIHJlYWRvbmx5IHRyYW5zcG9ydCA9IFwid3NcIjtcbiAgcmVhZG9ubHkgbmFtZXNwYWNlOiBzdHJpbmc7XG5cbiAgcHJpdmF0ZSByZWFkb25seSBjbG9zZUNhbGxiYWNrczogQ2xvc2VIYW5kbGVyW10gPSBbXTtcbiAgcHJpdmF0ZSByZWFkb25seSBtZXNzYWdlSGFuZGxlcnMgPSBuZXcgTWFwPHN0cmluZywgQXJyYXk8TWVzc2FnZUhhbmRsZXI8dW5rbm93bj4+PigpO1xuICBwcml2YXRlIHJlYWRvbmx5IHBlbmRpbmdNZXNzYWdlczogUGFyc2VkRW52ZWxvcGVbXSA9IFtdO1xuICBwcml2YXRlIHJlYWRvbmx5IHBlbmRpbmdPdXRib3VuZE1lc3NhZ2VzOiBBcnJheTx7IHBheWxvYWQ6IHN0cmluZzsgZXZlbnQ6IHN0cmluZyB9PiA9IFtdO1xuICBwcml2YXRlIHJlYWRvbmx5IGNsb3NlUHJvbWlzZTogUHJvbWlzZTx2b2lkPjtcbiAgcHJpdmF0ZSByZWFkb25seSByZXNvbHZlQ2xvc2VQcm9taXNlOiAoKSA9PiB2b2lkO1xuICBwcml2YXRlIHJlYWRvbmx5IGhlYXJ0YmVhdE1zOiBudW1iZXI7XG4gIHByaXZhdGUgcmVhZG9ubHkgZXZlbnRTY2hlbWFzSW46IFJlY29yZDxzdHJpbmcsIHouWm9kVHlwZUFueT47XG4gIHByaXZhdGUgcmVhZG9ubHkgZXZlbnRTY2hlbWFzT3V0OiBSZWNvcmQ8c3RyaW5nLCB6LlpvZFR5cGVBbnk+O1xuXG4gIHByaXZhdGUgcmVhZG9ubHkgY29ubmVjdGlvblRyYWNlSWQ/OiBzdHJpbmc7XG4gIHByaXZhdGUgcmVhZG9ubHkgY29ubmVjdGlvblNwYW5JZD86IHN0cmluZztcbiAgcHJpdmF0ZSByZWFkb25seSBjb25uZWN0aW9uUGFyZW50U3BhbklkPzogc3RyaW5nO1xuICBwcml2YXRlIHJlYWRvbmx5IGNvbm5lY3Rpb25TYW1wbGVkPzogYm9vbGVhbjtcbiAgcHJpdmF0ZSByZWFkb25seSBjb25uZWN0aW9uU3RhcnRlZEF0ID0gcGVyZm9ybWFuY2Uubm93KCk7XG5cbiAgLy8gY29ubmVjdGlvbiDsiJjrqoUg64+Z7JWIIOycoOyngOuQmOuKlCDsi53rs4TsnpAuIHNldFVzZXJJZC9jbGVhclVzZXJJZOuhnCDsl4XrjbDsnbTtirjrkJjrqbAgZW1pdCBob3QgcGF0aOyXkOyEnCDrp6TrsoggcmVnaXN0cnkgbG9va3Vw7ZWY7KeAIOyViuuPhOuhnSDsupDsi5ztlahcbiAgcHJpdmF0ZSBfdXNlcklkPzogc3RyaW5nO1xuXG4gIGdldCB1c2VySWQoKTogc3RyaW5nIHwgdW5kZWZpbmVkIHtcbiAgICByZXR1cm4gdGhpcy5fdXNlcklkO1xuICB9XG5cbiAgcHJpdmF0ZSBjbG9zZWRJbnRlcm5hbCA9IGZhbHNlO1xuICBwcml2YXRlIGNsb3NlU3RhcnRlZCA9IGZhbHNlO1xuICBwcml2YXRlIGF3YWl0aW5nUG9uZyA9IGZhbHNlO1xuICBwcml2YXRlIGhlYXJ0YmVhdFRpbWVyOiBSZXR1cm5UeXBlPHR5cGVvZiBzZXRJbnRlcnZhbD4gfCBudWxsID0gbnVsbDtcbiAgcHJpdmF0ZSBtZXNzYWdlUXVldWU6IFByb21pc2U8dm9pZD4gPSBQcm9taXNlLnJlc29sdmUoKTtcbiAgcHJpdmF0ZSBvdXRib3VuZEZsdXNoU2NoZWR1bGVkID0gZmFsc2U7XG5cbiAgY29uc3RydWN0b3IoXG4gICAgcHJpdmF0ZSByZWFkb25seSBzb2NrZXQ6IFdlYlNvY2tldCxcbiAgICBwcml2YXRlIHJlYWRvbmx5IG9wdGlvbnM6IFdlYlNvY2tldENvbm5lY3Rpb25PcHRpb25zPFRPdXRTY2hlbWEsIFRJblNjaGVtYT4sXG4gICkge1xuICAgIHRoaXMubmFtZXNwYWNlID0gb3B0aW9ucy5uYW1lc3BhY2UgPz8gXCJkZWZhdWx0XCI7XG4gICAgdGhpcy5oZWFydGJlYXRNcyA9IG9wdGlvbnMuaGVhcnRiZWF0ID8/IDMwMDAwO1xuICAgIHRoaXMuY29ubmVjdGlvblRyYWNlSWQgPSBvcHRpb25zLnRyYWNlSWQ7XG4gICAgdGhpcy5jb25uZWN0aW9uU3BhbklkID0gb3B0aW9ucy5zcGFuSWQ7XG4gICAgdGhpcy5jb25uZWN0aW9uUGFyZW50U3BhbklkID0gb3B0aW9ucy5wYXJlbnRTcGFuSWQ7XG4gICAgdGhpcy5jb25uZWN0aW9uU2FtcGxlZCA9IG9wdGlvbnMuc2FtcGxlZDtcbiAgICB0aGlzLmV2ZW50U2NoZW1hc0luID0gb3B0aW9ucy5pbkV2ZW50cy5zaGFwZSBhcyB1bmtub3duIGFzIFJlY29yZDxzdHJpbmcsIHouWm9kVHlwZUFueT47XG4gICAgdGhpcy5ldmVudFNjaGVtYXNPdXQgPSBvcHRpb25zLm91dEV2ZW50cy5zaGFwZSBhcyB1bmtub3duIGFzIFJlY29yZDxzdHJpbmcsIHouWm9kVHlwZUFueT47XG5cbiAgICBsZXQgcmVzb2x2ZUNsb3NlUHJvbWlzZSE6ICgpID0+IHZvaWQ7XG4gICAgdGhpcy5jbG9zZVByb21pc2UgPSBuZXcgUHJvbWlzZTx2b2lkPigocmVzb2x2ZSkgPT4ge1xuICAgICAgcmVzb2x2ZUNsb3NlUHJvbWlzZSA9IHJlc29sdmU7XG4gICAgfSk7XG4gICAgdGhpcy5yZXNvbHZlQ2xvc2VQcm9taXNlID0gcmVzb2x2ZUNsb3NlUHJvbWlzZTtcblxuICAgIHRoaXMub3B0aW9ucy5yZWdpc3RyeS5yZWdpc3Rlcih0aGlzLCBvcHRpb25zLmFjdGl2ZSA/PyB0cnVlKTtcbiAgICB0aGlzLnNvY2tldC5vbihcIm1lc3NhZ2VcIiwgdGhpcy5oYW5kbGVNZXNzYWdlKTtcbiAgICB0aGlzLnNvY2tldC5vbihcImNsb3NlXCIsIHRoaXMuaGFuZGxlQ2xvc2UpO1xuICAgIHRoaXMuc29ja2V0Lm9uKFwiZXJyb3JcIiwgdGhpcy5oYW5kbGVFcnJvcik7XG4gICAgdGhpcy5zb2NrZXQub24oXCJwb25nXCIsIHRoaXMuaGFuZGxlUG9uZyk7XG4gICAgdGhpcy5zdGFydEhlYXJ0YmVhdCgpO1xuICB9XG5cbiAgZ2V0IGNsb3NlZCgpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5jbG9zZWRJbnRlcm5hbDtcbiAgfVxuXG4gIG9uQ2xvc2UoY2FsbGJhY2s6IENsb3NlSGFuZGxlcik6IHZvaWQge1xuICAgIHRoaXMuY2xvc2VDYWxsYmFja3MucHVzaChjYWxsYmFjayk7XG4gIH1cblxuICBvbk1lc3NhZ2U8SyBleHRlbmRzIGtleW9mIEluZmVyV2ViU29ja2V0RXZlbnRNYXA8VEluU2NoZW1hPj4oXG4gICAgZXZlbnQ6IEssXG4gICAgaGFuZGxlcjogTWVzc2FnZUhhbmRsZXI8SW5mZXJXZWJTb2NrZXRFdmVudE1hcDxUSW5TY2hlbWE+W0tdPixcbiAgKTogdm9pZCB7XG4gICAgY29uc3QgZXZlbnRLZXkgPSBTdHJpbmcoZXZlbnQpO1xuICAgIGNvbnN0IGhhbmRsZXJzID0gdGhpcy5tZXNzYWdlSGFuZGxlcnMuZ2V0KGV2ZW50S2V5KSA/PyBbXTtcbiAgICBoYW5kbGVycy5wdXNoKGhhbmRsZXIgYXMgTWVzc2FnZUhhbmRsZXI8dW5rbm93bj4pO1xuICAgIHRoaXMubWVzc2FnZUhhbmRsZXJzLnNldChldmVudEtleSwgaGFuZGxlcnMpO1xuICAgIHRoaXMuZmx1c2hQZW5kaW5nTWVzc2FnZXMoZXZlbnRLZXkpO1xuICB9XG5cbiAgcHVibGlzaDxLIGV4dGVuZHMga2V5b2YgSW5mZXJXZWJTb2NrZXRFdmVudE1hcDxUT3V0U2NoZW1hPj4oXG4gICAgZXZlbnQ6IEssXG4gICAgZGF0YTogSW5mZXJXZWJTb2NrZXRFdmVudE1hcDxUT3V0U2NoZW1hPltLXSxcbiAgKTogdm9pZCB7XG4gICAgdGhpcy5wdWJsaXNoVmFsaWRhdGVkKFN0cmluZyhldmVudCksIGRhdGEpO1xuICB9XG5cbiAgcHVibGlzaFVudHlwZWQoZXZlbnQ6IHN0cmluZywgZGF0YTogdW5rbm93bik6IHZvaWQge1xuICAgIHRoaXMucHVibGlzaFZhbGlkYXRlZChldmVudCwgZGF0YSk7XG4gIH1cblxuICB3YWl0Rm9yQ2xvc2UoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgcmV0dXJuIHRoaXMuY2xvc2VQcm9taXNlO1xuICB9XG5cbiAgam9pbihyb29tSWQ6IFdlYlNvY2tldFJvb21JZCk6IHZvaWQge1xuICAgIHRoaXMub3B0aW9ucy5yZWdpc3RyeS5qb2luKHRoaXMuaWQsIHJvb21JZCk7XG4gIH1cblxuICBsZWF2ZShyb29tSWQ6IFdlYlNvY2tldFJvb21JZCk6IHZvaWQge1xuICAgIHRoaXMub3B0aW9ucy5yZWdpc3RyeS5sZWF2ZSh0aGlzLmlkLCByb29tSWQpO1xuICB9XG5cbiAgc2V0VXNlcklkKHVzZXJJZDogV2ViU29ja2V0VXNlcklkKTogdm9pZCB7XG4gICAgdGhpcy5fdXNlcklkID0gU3RyaW5nKHVzZXJJZCk7XG4gICAgdGhpcy5vcHRpb25zLnJlZ2lzdHJ5LnNldFVzZXJJZCh0aGlzLmlkLCB1c2VySWQpO1xuICB9XG5cbiAgY2xlYXJVc2VySWQoKTogdm9pZCB7XG4gICAgdGhpcy5fdXNlcklkID0gdW5kZWZpbmVkO1xuICAgIHRoaXMub3B0aW9ucy5yZWdpc3RyeS5jbGVhclVzZXJJZCh0aGlzLmlkKTtcbiAgfVxuXG4gIGdldFRlbGVtZXRyeVNuYXBzaG90KCk6IFdlYlNvY2tldFRlbGVtZXRyeUNvbm5lY3Rpb25TbmFwc2hvdCB7XG4gICAgcmV0dXJuIHtcbiAgICAgIHBlbmRpbmdJbmJvdW5kTWVzc2FnZXM6IHRoaXMucGVuZGluZ01lc3NhZ2VzLmxlbmd0aCxcbiAgICAgIHBlbmRpbmdPdXRib3VuZE1lc3NhZ2VzOiB0aGlzLnBlbmRpbmdPdXRib3VuZE1lc3NhZ2VzLmxlbmd0aCxcbiAgICAgIHNvY2tldEJ1ZmZlcmVkQnl0ZXM6IHRoaXMuc29ja2V0LnJlYWR5U3RhdGUgPT09IFdTX09QRU4gPyB0aGlzLnNvY2tldC5idWZmZXJlZEFtb3VudCA6IDAsXG4gICAgfTtcbiAgfVxuXG4gIGdldFRlbGVtZXRyeUNvbnRleHQoKTogV2ViU29ja2V0VGVsZW1ldHJ5Q29ubmVjdGlvbkNvbnRleHQge1xuICAgIHJldHVybiB7XG4gICAgICB0cmFjZUlkOiB0aGlzLmNvbm5lY3Rpb25UcmFjZUlkLFxuICAgICAgc3BhbklkOiB0aGlzLmNvbm5lY3Rpb25TcGFuSWQsXG4gICAgICBwYXJlbnRTcGFuSWQ6IHRoaXMuY29ubmVjdGlvblBhcmVudFNwYW5JZCxcbiAgICAgIHNhbXBsZWQ6IHRoaXMuY29ubmVjdGlvblNhbXBsZWQsXG4gICAgfTtcbiAgfVxuXG4gIC8vIOuqqOuToCB0ZWxlbWV0cnkgZW1pdCBzaXRl6rCAIOqzteycoO2VmOuKlCBjb25uZWN0aW9uLWxldmVsIGZpZWxkIOustuydjC5cbiAgLy8g7Zal7ZuEIGNvbm5lY3Rpb24tc2NvcGVkIOyLneuzhOyekChlLmcuIHRlbmFudElkKeqwgCDstpTqsIDrkKAg65WMIO2VnCDqs7Prp4wg7IaQ64yA66m0IOuQqFxuICBwcml2YXRlIHRlbGVtZXRyeUZpZWxkcygpIHtcbiAgICByZXR1cm4ge1xuICAgICAgY29ubmVjdGlvbklkOiB0aGlzLmlkLFxuICAgICAgbmFtZXNwYWNlOiB0aGlzLm5hbWVzcGFjZSxcbiAgICAgIHVzZXJJZDogdGhpcy5fdXNlcklkLFxuICAgICAgdHJhY2VJZDogdGhpcy5jb25uZWN0aW9uVHJhY2VJZCxcbiAgICAgIHNwYW5JZDogdGhpcy5jb25uZWN0aW9uU3BhbklkLFxuICAgICAgcGFyZW50U3BhbklkOiB0aGlzLmNvbm5lY3Rpb25QYXJlbnRTcGFuSWQsXG4gICAgICBzYW1wbGVkOiB0aGlzLmNvbm5lY3Rpb25TYW1wbGVkLFxuICAgIH07XG4gIH1cblxuICBwcml2YXRlIGVtaXRJbmJvdW5kUmVqZWN0ZWQocmVhc29uOiBzdHJpbmcsIGV2ZW50Pzogc3RyaW5nKTogdm9pZCB7XG4gICAgY29uc3QgZmllbGRzID0gdGhpcy50ZWxlbWV0cnlGaWVsZHMoKTtcbiAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgIG5hbWU6IFwid3MubWVzc2FnZS5yZWplY3RlZFwiLFxuICAgICAgbGV2ZWw6IFwid2FyblwiLFxuICAgICAgLi4uZmllbGRzLFxuICAgICAgZGV0YWlsOiBldmVudCAhPT0gdW5kZWZpbmVkID8geyByZWFzb24sIGV2ZW50IH0gOiB7IHJlYXNvbiB9LFxuICAgIH0pO1xuICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLnJlY29yZE1ldHJpYyh7XG4gICAgICBuYW1lOiBcInNvbmFtdS53cy5tZXNzYWdlc1wiLFxuICAgICAga2luZDogXCJjb3VudGVyXCIsXG4gICAgICB2YWx1ZTogMSxcbiAgICAgIHVuaXQ6IFwiMVwiLFxuICAgICAgdGFnczogeyBkaXJlY3Rpb246IFwiaW5ib3VuZFwiLCBvdXRjb21lOiBcInJlamVjdGVkXCIgfSxcbiAgICAgIC4uLmZpZWxkcyxcbiAgICB9KTtcbiAgfVxuXG4gIC8vIHRyYW5zcG9ydCDsooXro4wg64+E7KSRIOyYiOyZuOqwgCDrgpjrj4QgbWFya0Nsb3NlZOqwgCDrsJjrk5zsi5wg7Iuk7ZaJ65CY64+E66GdIHRyeS9maW5hbGx566GcIOqwkOyMiFxuICBjbG9zZShjb2RlPzogbnVtYmVyLCByZWFzb24/OiBzdHJpbmcpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5jbG9zZWRJbnRlcm5hbCB8fCB0aGlzLmNsb3NlU3RhcnRlZCB8fCB0aGlzLnNvY2tldC5yZWFkeVN0YXRlID09PSBXU19DTE9TRUQpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLmNsb3NlU3RhcnRlZCA9IHRydWU7XG4gICAgdHJ5IHtcbiAgICAgIHRoaXMuY2xvc2VUcmFuc3BvcnQoY29kZSwgcmVhc29uKTtcbiAgICB9IGZpbmFsbHkge1xuICAgICAgdGhpcy5tYXJrQ2xvc2VkKGNvZGUsIHJlYXNvbik7XG4gICAgfVxuICB9XG5cbiAgLy8g7J2467CU7Jq065OcIOuplOyLnOyngOulvCDsiJzssKgg7LKY66asIO2BkOyXkCDsmKzrprwuIFNvbmFtdSBlbnZlbG9wZSDqsoDspp0g7IiY7ZaJXG4gIHByaXZhdGUgcmVhZG9ubHkgaGFuZGxlTWVzc2FnZSA9IChyYXc6IHVua25vd24pID0+IHtcbiAgICB0aGlzLmVucXVldWVNZXNzYWdlVGFzayhhc3luYyAoKSA9PiB7XG4gICAgICBjb25zdCB0ZXh0ID0gbm9ybWFsaXplTWVzc2FnZShyYXcpO1xuICAgICAgY29uc3QgcGFyc2VkRW52ZWxvcGUgPSBzYWZlUGFyc2VFbnZlbG9wZSh0ZXh0KTtcbiAgICAgIGlmICghcGFyc2VkRW52ZWxvcGUpIHtcbiAgICAgICAgdGhpcy5lbWl0SW5ib3VuZFJlamVjdGVkKFwiaW52YWxpZFBheWxvYWRcIik7XG4gICAgICAgIHRoaXMuY2xvc2UoV1NfQ0xPU0VfQ09ERV9JTlZBTElEX0ZSQU1FX1BBWUxPQURfREFUQSwgXCJJbnZhbGlkIG1lc3NhZ2UgcGF5bG9hZFwiKTtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgICAgbmFtZTogXCJ3cy5tZXNzYWdlLnJlY2VpdmVkXCIsXG4gICAgICAgIGxldmVsOiBcImRlYnVnXCIsXG4gICAgICAgIC4uLnRoaXMudGVsZW1ldHJ5RmllbGRzKCksXG4gICAgICAgIGRldGFpbDogeyBldmVudDogcGFyc2VkRW52ZWxvcGUuZXZlbnQgfSxcbiAgICAgICAgcGF5bG9hZDogcGFyc2VkRW52ZWxvcGUuZGF0YSxcbiAgICAgIH0pO1xuICAgICAgdGhpcy5vcHRpb25zLnJlZ2lzdHJ5LnRvdWNoKHRoaXMuaWQpO1xuICAgICAgYXdhaXQgdGhpcy5kaXNwYXRjaEVudmVsb3BlKHBhcnNlZEVudmVsb3BlKTtcbiAgICB9KTtcbiAgfTtcblxuICBwcml2YXRlIHJlYWRvbmx5IGhhbmRsZUNsb3NlID0gKGNvZGU/OiBudW1iZXIsIHJlYXNvbj86IEJ1ZmZlciB8IHN0cmluZykgPT4ge1xuICAgIGNvbnN0IHJlYXNvblRleHQgPSB0eXBlb2YgcmVhc29uID09PSBcInN0cmluZ1wiID8gcmVhc29uIDogcmVhc29uPy50b1N0cmluZygpO1xuICAgIHRoaXMubWFya0Nsb3NlZChjb2RlLCByZWFzb25UZXh0KTtcbiAgfTtcblxuICAvLyDshozsvJPsnbQgdHJhbnNwb3J0IGVycm9y66W8IGVtaXTtlZjrqbQg7KaJ7IucIDEwMTEgY2xvc2XroZwg7IiY66C07Iuc7LycIOyDge2DnCDriITrnb3snYQg66eJ7J2MXG4gIHByaXZhdGUgcmVhZG9ubHkgaGFuZGxlRXJyb3IgPSAoKSA9PiB7XG4gICAgdGhpcy5jbG9zZShXU19DTE9TRV9DT0RFX0lOVEVSTkFMX0VSUk9SLCBcIldlYlNvY2tldCB0cmFuc3BvcnQgZXJyb3JcIik7XG4gIH07XG5cbiAgcHJpdmF0ZSByZWFkb25seSBoYW5kbGVQb25nID0gKCkgPT4ge1xuICAgIHRoaXMuYXdhaXRpbmdQb25nID0gZmFsc2U7XG4gICAgdGhpcy5vcHRpb25zLnJlZ2lzdHJ5LnRvdWNoKHRoaXMuaWQpO1xuICB9O1xuXG4gIC8vIGVudmVsb3Bl7J2YIG1ldGEudHJhY2VwYXJlbnTroZzrtoDthLAgdHJhY2UgY29udGV4dOulvCDstpTstpztlahcbiAgLy8gaW52YWxpZCB0cmFjZXBhcmVudOuKlCDsl7DqsrDsnYQg6rGw67aA7ZWY7KeAIOyViuqzoCBkZWJ1ZyDroIjrsqgg6rK96rOg66eMIGVtaXTtlahcbiAgcHJpdmF0ZSByZXNvbHZlTWVzc2FnZVRyYWNlQ29udGV4dChcbiAgICBlbnZlbG9wZTogUGFyc2VkRW52ZWxvcGUsXG4gICk6IFdlYlNvY2tldFRlbGVtZXRyeUNvbm5lY3Rpb25Db250ZXh0IHtcbiAgICBjb25zdCBtZXNzYWdlU3BhbklkID0gZ2VuZXJhdGVTcGFuSWQoKTtcblxuICAgIGlmIChcbiAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmdldFRyYWNlT3B0aW9ucygpLnByb3BhZ2F0ZU1lc3NhZ2VUcmFjZSAmJlxuICAgICAgZW52ZWxvcGUubWV0YT8udHJhY2VwYXJlbnRcbiAgICApIHtcbiAgICAgIGNvbnN0IHBhcnNlZCA9IHBhcnNlVHJhY2VQYXJlbnQoZW52ZWxvcGUubWV0YS50cmFjZXBhcmVudCk7XG4gICAgICBpZiAocGFyc2VkKSB7XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgdHJhY2VJZDogcGFyc2VkLnRyYWNlSWQsXG4gICAgICAgICAgc3BhbklkOiBtZXNzYWdlU3BhbklkLFxuICAgICAgICAgIHBhcmVudFNwYW5JZDogcGFyc2VkLnBhcmVudElkLFxuICAgICAgICAgIHNhbXBsZWQ6IHBhcnNlZC5zYW1wbGVkLFxuICAgICAgICB9O1xuICAgICAgfVxuICAgICAgLy8gaW52YWxpZCB0cmFjZXBhcmVudDogd2FybiBidXQgZG8gbm90IHJlamVjdFxuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgIG5hbWU6IFwid3MudHJhY2UuaW52YWxpZFwiLFxuICAgICAgICBsZXZlbDogXCJkZWJ1Z1wiLFxuICAgICAgICAuLi50aGlzLnRlbGVtZXRyeUZpZWxkcygpLFxuICAgICAgICBkZXRhaWw6IHsgc291cmNlOiBcIm1lc3NhZ2VcIiwgdHJhY2VwYXJlbnQ6IGVudmVsb3BlLm1ldGEudHJhY2VwYXJlbnQgfSxcbiAgICAgIH0pO1xuICAgIH1cblxuICAgIHJldHVybiB7XG4gICAgICB0cmFjZUlkOiB0aGlzLmNvbm5lY3Rpb25UcmFjZUlkLFxuICAgICAgc3BhbklkOiBtZXNzYWdlU3BhbklkLFxuICAgICAgcGFyZW50U3BhbklkOiB0aGlzLmNvbm5lY3Rpb25TcGFuSWQgPz8gdGhpcy5jb25uZWN0aW9uUGFyZW50U3BhbklkLFxuICAgICAgc2FtcGxlZDogdGhpcy5jb25uZWN0aW9uU2FtcGxlZCxcbiAgICB9O1xuICB9XG5cbiAgLy8gZXZlbnQg7KG07J6sIOyXrOu2gCDihpIgc2NoZW1hIOqygOymnSDihpIgaGFuZGxlciDsi6Ttlokg7Iic7Jy866GcIOu2hOq4sO2VqFxuICAvLyBoYW5kbGVy6rCAIOyVhOyngSDrk7HroZ3rkJjsp4Ag7JWK7J2AIOy0iOq4sCDrqZTsi5zsp4DripQg67KE7Y287JeQIOuztOq0gO2WiOuLpOqwgCBvbk1lc3NhZ2Ug65Ox66GdIOyLnCBmbHVzaO2VqFxuICAvLyBoYW5kbGVy64qUIGBhd2FpdGDsnLzroZwg7Iic7LCoIOyLpO2Wie2VtCDtlZwgY29ubmVjdGlvbiDslYjsnZgg66mU7Iuc7KeAIOyInOyEnOulvCDrs7TsnqXtlahcbiAgcHJpdmF0ZSBhc3luYyBkaXNwYXRjaEVudmVsb3BlKGVudmVsb3BlOiBQYXJzZWRFbnZlbG9wZSk6IFByb21pc2U8dm9pZD4ge1xuICAgIGNvbnN0IGhhbmRsZXJzID0gdGhpcy5tZXNzYWdlSGFuZGxlcnMuZ2V0KGVudmVsb3BlLmV2ZW50KTtcbiAgICBjb25zdCBzY2hlbWEgPSB0aGlzLmV2ZW50U2NoZW1hc0luW2VudmVsb3BlLmV2ZW50XTtcblxuICAgIGlmICghc2NoZW1hKSB7XG4gICAgICB0aGlzLmVtaXRJbmJvdW5kUmVqZWN0ZWQoXCJ1bmtub3duRXZlbnRcIiwgZW52ZWxvcGUuZXZlbnQpO1xuICAgICAgdGhpcy5jbG9zZShXU19DTE9TRV9DT0RFX1BPTElDWV9WSU9MQVRJT04sIFwiVW5rbm93biBldmVudFwiKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBwYXJzZWQgPSBzY2hlbWEuc2FmZVBhcnNlKGVudmVsb3BlLmRhdGEpO1xuICAgIGlmICghcGFyc2VkLnN1Y2Nlc3MpIHtcbiAgICAgIHRoaXMuZW1pdEluYm91bmRSZWplY3RlZChcImludmFsaWREYXRhXCIsIGVudmVsb3BlLmV2ZW50KTtcbiAgICAgIHRoaXMuY2xvc2UoV1NfQ0xPU0VfQ09ERV9JTlZBTElEX0ZSQU1FX1BBWUxPQURfREFUQSwgXCJJbnZhbGlkIGV2ZW50IGRhdGFcIik7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgaWYgKCFoYW5kbGVycyB8fCBoYW5kbGVycy5sZW5ndGggPT09IDApIHtcbiAgICAgIGlmICh0aGlzLnBlbmRpbmdNZXNzYWdlcy5sZW5ndGggPj0gTUFYX1BFTkRJTkdfTUVTU0FHRVMpIHtcbiAgICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgICAgbmFtZTogXCJ3cy5tZXNzYWdlLmJ1ZmZlci5kcm9wcGVkXCIsXG4gICAgICAgICAgbGV2ZWw6IFwid2FyblwiLFxuICAgICAgICAgIC4uLnRoaXMudGVsZW1ldHJ5RmllbGRzKCksXG4gICAgICAgICAgZGV0YWlsOiB7IGV2ZW50OiBlbnZlbG9wZS5ldmVudCB9LFxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5wZW5kaW5nTWVzc2FnZXMuc2hpZnQoKTtcbiAgICAgIH1cbiAgICAgIHRoaXMucGVuZGluZ01lc3NhZ2VzLnB1c2goZW52ZWxvcGUpO1xuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgIG5hbWU6IFwid3MubWVzc2FnZS5idWZmZXJlZFwiLFxuICAgICAgICBsZXZlbDogXCJkZWJ1Z1wiLFxuICAgICAgICAuLi50aGlzLnRlbGVtZXRyeUZpZWxkcygpLFxuICAgICAgICBkZXRhaWw6IHsgZXZlbnQ6IGVudmVsb3BlLmV2ZW50IH0sXG4gICAgICB9KTtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCB0cmFjZUN0eCA9IHRoaXMucmVzb2x2ZU1lc3NhZ2VUcmFjZUNvbnRleHQoZW52ZWxvcGUpO1xuICAgIC8vIG1lc3NhZ2UtbGV2ZWwgdHJhY2XripQgY29ubmVjdGlvbi1sZXZlbCB0cmFjZeulvCBvdmVycmlkZe2VqC4gdXNlcklkIC8gY29ubmVjdGlvbklkIC8gbmFtZXNwYWNl64qUIOq3uOuMgOuhnCDsnKDsp4BcbiAgICBjb25zdCBtZXNzYWdlVHJhY2VGaWVsZHMgPSB7XG4gICAgICBjb25uZWN0aW9uSWQ6IHRoaXMuaWQsXG4gICAgICBuYW1lc3BhY2U6IHRoaXMubmFtZXNwYWNlLFxuICAgICAgdXNlcklkOiB0aGlzLl91c2VySWQsXG4gICAgICB0cmFjZUlkOiB0cmFjZUN0eC50cmFjZUlkLFxuICAgICAgc3BhbklkOiB0cmFjZUN0eC5zcGFuSWQsXG4gICAgICBwYXJlbnRTcGFuSWQ6IHRyYWNlQ3R4LnBhcmVudFNwYW5JZCxcbiAgICAgIHNhbXBsZWQ6IHRyYWNlQ3R4LnNhbXBsZWQsXG4gICAgfTtcbiAgICB0cnkge1xuICAgICAgZm9yIChjb25zdCBoYW5kbGVyIG9mIGhhbmRsZXJzKSB7XG4gICAgICAgIGF3YWl0IGhhbmRsZXIocGFyc2VkLmRhdGEsIHRyYWNlQ3R4KTtcbiAgICAgIH1cbiAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICBuYW1lOiBcIndzLm1lc3NhZ2UuZGlzcGF0Y2hlZFwiLFxuICAgICAgICBsZXZlbDogXCJkZWJ1Z1wiLFxuICAgICAgICAuLi5tZXNzYWdlVHJhY2VGaWVsZHMsXG4gICAgICAgIGRldGFpbDogeyBldmVudDogZW52ZWxvcGUuZXZlbnQgfSxcbiAgICAgIH0pO1xuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIucmVjb3JkTWV0cmljKHtcbiAgICAgICAgbmFtZTogXCJzb25hbXUud3MubWVzc2FnZXNcIixcbiAgICAgICAga2luZDogXCJjb3VudGVyXCIsXG4gICAgICAgIHZhbHVlOiAxLFxuICAgICAgICB1bml0OiBcIjFcIixcbiAgICAgICAgdGFnczogeyBkaXJlY3Rpb246IFwiaW5ib3VuZFwiLCBldmVudDogZW52ZWxvcGUuZXZlbnQsIG91dGNvbWU6IFwiYWNjZXB0ZWRcIiB9LFxuICAgICAgICAuLi5tZXNzYWdlVHJhY2VGaWVsZHMsXG4gICAgICB9KTtcbiAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgIG5hbWU6IFwid3MubWVzc2FnZS5mYWlsZWRcIixcbiAgICAgICAgbGV2ZWw6IFwiZXJyb3JcIixcbiAgICAgICAgLi4ubWVzc2FnZVRyYWNlRmllbGRzLFxuICAgICAgICBkZXRhaWw6IHsgZXZlbnQ6IGVudmVsb3BlLmV2ZW50IH0sXG4gICAgICB9KTtcbiAgICAgIHRocm93IGVycm9yO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgZmx1c2hQZW5kaW5nTWVzc2FnZXMoZXZlbnQ6IHN0cmluZyk6IHZvaWQge1xuICAgIGNvbnN0IHJlbWFpbmluZzogUGFyc2VkRW52ZWxvcGVbXSA9IFtdO1xuICAgIGNvbnN0IHRvRmx1c2g6IFBhcnNlZEVudmVsb3BlW10gPSBbXTtcblxuICAgIGZvciAoY29uc3QgbWVzc2FnZSBvZiB0aGlzLnBlbmRpbmdNZXNzYWdlcykge1xuICAgICAgaWYgKG1lc3NhZ2UuZXZlbnQgIT09IGV2ZW50KSB7XG4gICAgICAgIHJlbWFpbmluZy5wdXNoKG1lc3NhZ2UpO1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cblxuICAgICAgdG9GbHVzaC5wdXNoKG1lc3NhZ2UpO1xuICAgIH1cblxuICAgIHRoaXMucGVuZGluZ01lc3NhZ2VzLmxlbmd0aCA9IDA7XG4gICAgdGhpcy5wZW5kaW5nTWVzc2FnZXMucHVzaCguLi5yZW1haW5pbmcpO1xuXG4gICAgZm9yIChjb25zdCBtZXNzYWdlIG9mIHRvRmx1c2gpIHtcbiAgICAgIHRoaXMuZW5xdWV1ZU1lc3NhZ2VUYXNrKGFzeW5jICgpID0+IHtcbiAgICAgICAgYXdhaXQgdGhpcy5kaXNwYXRjaEVudmVsb3BlKG1lc3NhZ2UpO1xuICAgICAgfSk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBwdWJsaXNoVmFsaWRhdGVkKGV2ZW50OiBzdHJpbmcsIGRhdGE6IHVua25vd24pOiB2b2lkIHtcbiAgICBjb25zdCBzY2hlbWEgPSB0aGlzLmV2ZW50U2NoZW1hc091dFtldmVudF07XG4gICAgaWYgKCFzY2hlbWEpIHtcbiAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICBuYW1lOiBcIndzLnB1Ymxpc2gucmVqZWN0ZWRcIixcbiAgICAgICAgbGV2ZWw6IFwiZXJyb3JcIixcbiAgICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgICAgZGV0YWlsOiB7IGV2ZW50LCByZWFzb246IFwidW5rbm93bkV2ZW50XCIgfSxcbiAgICAgIH0pO1xuICAgICAgdGhyb3cgbmV3IEVycm9yKGBVbmtub3duIHdlYnNvY2tldCBldmVudDogJHtldmVudH1gKTtcbiAgICB9XG5cbiAgICBjb25zdCBwYXJzZWQgPSBzY2hlbWEuc2FmZVBhcnNlKGRhdGEpO1xuICAgIGlmICghcGFyc2VkLnN1Y2Nlc3MpIHtcbiAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICBuYW1lOiBcIndzLnB1Ymxpc2gucmVqZWN0ZWRcIixcbiAgICAgICAgbGV2ZWw6IFwiZXJyb3JcIixcbiAgICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgICAgZGV0YWlsOiB7IGV2ZW50LCByZWFzb246IFwiaW52YWxpZFBheWxvYWRcIiB9LFxuICAgICAgfSk7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoYEludmFsaWQgd2Vic29ja2V0IGV2ZW50IHBheWxvYWQ6ICR7ZXZlbnR9YCk7XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuY2xvc2VkSW50ZXJuYWwgfHwgdGhpcy5zb2NrZXQucmVhZHlTdGF0ZSAhPT0gV1NfT1BFTikge1xuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZW1pdCh7XG4gICAgICAgIG5hbWU6IFwid3MucHVibGlzaC5kcm9wcGVkXCIsXG4gICAgICAgIGxldmVsOiBcImRlYnVnXCIsXG4gICAgICAgIC4uLnRoaXMudGVsZW1ldHJ5RmllbGRzKCksXG4gICAgICAgIGRldGFpbDogeyBldmVudCwgcmVhc29uOiBcImNvbm5lY3Rpb25DbG9zZWRcIiB9LFxuICAgICAgfSk7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5lbnF1ZXVlT3V0Ym91bmRNZXNzYWdlKFxuICAgICAgSlNPTi5zdHJpbmdpZnkoe1xuICAgICAgICBldmVudCxcbiAgICAgICAgZGF0YTogcGFyc2VkLmRhdGEsXG4gICAgICB9KSxcbiAgICAgIGV2ZW50LFxuICAgICAgcGFyc2VkLmRhdGEsXG4gICAgKTtcbiAgfVxuXG4gIC8vIGxpc3RlbmVyIO2VtOygnCAvIGhlYXJ0YmVhdCDspJHri6ggLyBwZW5kaW5nIHF1ZXVlIOu5hOybgCAvIHJlZ2lzdHJ5IHVucmVnaXN0ZXIgLyBvbkNsb3NlIOyLpO2WiSAvIHdhaXRGb3JDbG9zZSByZXNvbHZlIOydhCDtlZwg6rOz7JeQIOuqqOyVhCDsm5DsnpDsoIHsnLzroZwg7LKY66as7ZWoXG4gIC8vIGFzeW5jIG9uQ2xvc2XqsIAgcmVqZWN07ZW064+EIHVuaGFuZGxlZCByZWplY3Rpb27snLzroZwg7IOI7KeAIOyViuuPhOuhnSBjYXRjaOuhnCDqsqnrpqztlahcbiAgcHJpdmF0ZSBtYXJrQ2xvc2VkKGNvZGU/OiBudW1iZXIsIF9yZWFzb24/OiBzdHJpbmcpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5jbG9zZWRJbnRlcm5hbCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuY2xvc2VkSW50ZXJuYWwgPSB0cnVlO1xuICAgIHRoaXMuY2xvc2VTdGFydGVkID0gZmFsc2U7XG4gICAgdGhpcy5zdG9wSGVhcnRiZWF0KCk7XG4gICAgY29uc3QgZmllbGRzID0gdGhpcy50ZWxlbWV0cnlGaWVsZHMoKTtcbiAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgIG5hbWU6IFwid3MuY29ubmVjdGlvbi5jbG9zZWRcIixcbiAgICAgIGxldmVsOiBcImluZm9cIixcbiAgICAgIC4uLmZpZWxkcyxcbiAgICB9KTtcbiAgICBpZiAodGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIuZ2V0VHJhY2VPcHRpb25zKCkucmVjb3JkQ29ubmVjdGlvbkxpZmV0aW1lU3Bhbikge1xuICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIucmVjb3JkU3Bhbih7XG4gICAgICAgIG9wZXJhdGlvbk5hbWU6IFwid3MuY29ubmVjdGlvbi5saWZldGltZVwiLFxuICAgICAgICBraW5kOiBcInNlcnZlclwiLFxuICAgICAgICBkdXJhdGlvbk1zOiBwZXJmb3JtYW5jZS5ub3coKSAtIHRoaXMuY29ubmVjdGlvblN0YXJ0ZWRBdCxcbiAgICAgICAgc3RhdHVzOiBkZXJpdmVMaWZldGltZVN0YXR1cyhjb2RlKSxcbiAgICAgICAgLi4uZmllbGRzLFxuICAgICAgfSk7XG4gICAgfVxuICAgIHRoaXMuc29ja2V0Lm9mZihcIm1lc3NhZ2VcIiwgdGhpcy5oYW5kbGVNZXNzYWdlKTtcbiAgICB0aGlzLnNvY2tldC5vZmYoXCJjbG9zZVwiLCB0aGlzLmhhbmRsZUNsb3NlKTtcbiAgICB0aGlzLnNvY2tldC5vZmYoXCJlcnJvclwiLCB0aGlzLmhhbmRsZUVycm9yKTtcbiAgICB0aGlzLnNvY2tldC5vZmYoXCJwb25nXCIsIHRoaXMuaGFuZGxlUG9uZyk7XG4gICAgdGhpcy5hd2FpdGluZ1BvbmcgPSBmYWxzZTtcbiAgICB0aGlzLnBlbmRpbmdNZXNzYWdlcy5sZW5ndGggPSAwO1xuICAgIHRoaXMucGVuZGluZ091dGJvdW5kTWVzc2FnZXMubGVuZ3RoID0gMDtcbiAgICB0aGlzLm9wdGlvbnMucmVnaXN0cnkudW5yZWdpc3Rlcih0aGlzLmlkKTtcbiAgICBmb3IgKGNvbnN0IGNhbGxiYWNrIG9mIHRoaXMuY2xvc2VDYWxsYmFja3Muc3BsaWNlKDApKSB7XG4gICAgICB0cnkge1xuICAgICAgICBjb25zdCByZXN1bHQgPSBjYWxsYmFjaygpO1xuICAgICAgICBpZiAoaXNQcm9taXNlTGlrZShyZXN1bHQpKSB7XG4gICAgICAgICAgdm9pZCByZXN1bHQuY2F0Y2goKCkgPT4ge1xuICAgICAgICAgICAgLy8gYXN5bmMgY2xvc2UgY2FsbGJhY2tzIG11c3Qgbm90IGVzY2FwZSBhcyB1bmhhbmRsZWQgcmVqZWN0aW9uc1xuICAgICAgICAgIH0pO1xuICAgICAgICB9XG4gICAgICB9IGNhdGNoIHtcbiAgICAgICAgLy8gY2xvc2UgY2FsbGJhY2tzIG11c3Qgbm90IGJsb2NrIHRyYW5zcG9ydCBjbGVhbnVwXG4gICAgICB9XG4gICAgfVxuICAgIHRoaXMucmVzb2x2ZUNsb3NlUHJvbWlzZSgpO1xuICB9XG5cbiAgLy8gcG9uZ+ydtCDsmKTsp4Ag7JWK7J2AIOyDge2DnOyXkOyEnCDri6TsnYwgdGlja+ydtCDsmKTrqbQgdGltZW91dCBjbG9zZeuhnCDsspjrpqztlbQgem9tYmllIGNvbm5lY3Rpb27snYQg7KCV66as7ZWoXG4gIHByaXZhdGUgc3RhcnRIZWFydGJlYXQoKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGVhcnRiZWF0TXMgPD0gMCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuaGVhcnRiZWF0VGltZXIgPSBzZXRJbnRlcnZhbCgoKSA9PiB7XG4gICAgICBpZiAodGhpcy5jbG9zZWRJbnRlcm5hbCB8fCB0aGlzLnNvY2tldC5yZWFkeVN0YXRlICE9PSBXU19PUEVOKSB7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cblxuICAgICAgaWYgKHRoaXMuYXdhaXRpbmdQb25nKSB7XG4gICAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICAgIG5hbWU6IFwid3MuaGVhcnRiZWF0LnRpbWVvdXRcIixcbiAgICAgICAgICBsZXZlbDogXCJ3YXJuXCIsXG4gICAgICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgICAgfSk7XG4gICAgICAgIHRoaXMuY2xvc2UoV1NfQ0xPU0VfQ09ERV9HT0lOR19BV0FZLCBcIkhlYXJ0YmVhdCB0aW1lb3V0XCIpO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIHRoaXMuYXdhaXRpbmdQb25nID0gdHJ1ZTtcbiAgICAgIHRoaXMuc29ja2V0LnBpbmcoKTtcbiAgICB9LCB0aGlzLmhlYXJ0YmVhdE1zKTtcbiAgfVxuXG4gIHByaXZhdGUgc3RvcEhlYXJ0YmVhdCgpOiB2b2lkIHtcbiAgICBpZiAoIXRoaXMuaGVhcnRiZWF0VGltZXIpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjbGVhckludGVydmFsKHRoaXMuaGVhcnRiZWF0VGltZXIpO1xuICAgIHRoaXMuaGVhcnRiZWF0VGltZXIgPSBudWxsO1xuICB9XG5cbiAgLy8gY2xvc2XqsIAg7Iuk7Yyo7ZW064+EIHRlcm1pbmF0ZSDtj7TrsLHquYzsp4Ag7Iuc64+E7ZWY6rOgLCDrgZ3rgrQg7Iuk7Yyo7ZWY66m0IG1hcmtDbG9zZWTsl5Ag7IOB7YOcIOygleumrOulvCDsnITsnoTtlahcbiAgcHJpdmF0ZSBjbG9zZVRyYW5zcG9ydChjb2RlPzogbnVtYmVyLCByZWFzb24/OiBzdHJpbmcpOiB2b2lkIHtcbiAgICB0cnkge1xuICAgICAgaWYgKHRoaXMuc29ja2V0LnJlYWR5U3RhdGUgPT09IFdTX09QRU4gfHwgdGhpcy5zb2NrZXQucmVhZHlTdGF0ZSA9PT0gV1NfQ09OTkVDVElORykge1xuICAgICAgICB0aGlzLnNvY2tldC5jbG9zZShjb2RlLCB0cnVuY2F0ZUNsb3NlUmVhc29uKHJlYXNvbikpO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIHRoaXMuc29ja2V0LnRlcm1pbmF0ZSgpO1xuICAgIH0gY2F0Y2gge1xuICAgICAgdHJ5IHtcbiAgICAgICAgdGhpcy5zb2NrZXQudGVybWluYXRlKCk7XG4gICAgICB9IGNhdGNoIHtcbiAgICAgICAgLy8gdHJhbnNwb3J0IGlzIGFscmVhZHkgYnJva2VuOyBzdGF0ZSBjbGVhbnVwIGlzIGhhbmRsZWQgYnkgbWFya0Nsb3NlZCgpXG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgLy8g7J2467CU7Jq065OcIGhhbmRsZXLrpbwgcHJvbWlzZSBjaGFpbuycvOuhnCBzZXJpYWxpemUg7ZWY6rOgLCBoYW5kbGVyIOyYiOyZuOuKlCBjb25uZWN0aW9uLWxvY2FsIDEwMTEgY2xvc2XroZwg7LaV7IaM7ZWoXG4gIHByaXZhdGUgZW5xdWV1ZU1lc3NhZ2VUYXNrKHRhc2s6ICgpID0+IFByb21pc2U8dm9pZD4pOiB2b2lkIHtcbiAgICB0aGlzLm1lc3NhZ2VRdWV1ZSA9IHRoaXMubWVzc2FnZVF1ZXVlXG4gICAgICAudGhlbihhc3luYyAoKSA9PiB7XG4gICAgICAgIGlmICh0aGlzLmNsb3NlZEludGVybmFsKSB7XG4gICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9XG5cbiAgICAgICAgYXdhaXQgdGFzaygpO1xuICAgICAgfSlcbiAgICAgIC5jYXRjaCgoKSA9PiB7XG4gICAgICAgIHRoaXMuY2xvc2UoV1NfQ0xPU0VfQ09ERV9JTlRFUk5BTF9FUlJPUiwgXCJNZXNzYWdlIGhhbmRsaW5nIGZhaWxlZFwiKTtcbiAgICAgIH0pO1xuICB9XG5cbiAgLy8gcXVldWXqsIAg7ZWc6rOE7JeQIOuPhOuLrO2VmOuptCAxMDEz7Jy866GcIOuLq+yVhCDripDrprAg7IaM67mE7J6Q6rCAIOuplOuqqOumrOulvCDrgZ3sl4bsnbQg7J6h7JWE66i57KeAIOuqu+2VmOqyjCDtlahcbiAgLy8gZGF0YSDsnbjsnpDripQgdGVsZW1ldHJ5IHBheWxvYWQgcHJldmlldyDsmqnrj4TroZzrp4wg7IKs7Jqp7ZWY66mwIHBlbmRpbmdPdXRib3VuZE1lc3NhZ2Vz7JeQ64qUIOyggOyepe2VmOyngCDslYrsnYwgKO2BkCDrqZTrqqjrpqwg67O07Zi4KVxuICBwcml2YXRlIGVucXVldWVPdXRib3VuZE1lc3NhZ2UocGF5bG9hZDogc3RyaW5nLCBldmVudDogc3RyaW5nLCBkYXRhOiB1bmtub3duKTogdm9pZCB7XG4gICAgaWYgKHRoaXMucGVuZGluZ091dGJvdW5kTWVzc2FnZXMubGVuZ3RoID49IE1BWF9QRU5ESU5HX09VVEJPVU5EX01FU1NBR0VTKSB7XG4gICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgICAgbmFtZTogXCJ3cy5iYWNrcHJlc3N1cmUub3ZlcmZsb3dcIixcbiAgICAgICAgbGV2ZWw6IFwiZXJyb3JcIixcbiAgICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgIH0pO1xuICAgICAgdGhpcy5jbG9zZShXU19DTE9TRV9DT0RFX1RSWV9BR0FJTl9MQVRFUiwgXCJXZWJTb2NrZXQgYmFja3ByZXNzdXJlIG92ZXJmbG93XCIpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMucGVuZGluZ091dGJvdW5kTWVzc2FnZXMucHVzaCh7IHBheWxvYWQsIGV2ZW50IH0pO1xuICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgbmFtZTogXCJ3cy5wdWJsaXNoLnF1ZXVlZFwiLFxuICAgICAgbGV2ZWw6IFwiZGVidWdcIixcbiAgICAgIC4uLnRoaXMudGVsZW1ldHJ5RmllbGRzKCksXG4gICAgICBkZXRhaWw6IHsgZXZlbnQgfSxcbiAgICAgIHBheWxvYWQ6IGRhdGEsXG4gICAgfSk7XG4gICAgdGhpcy5zY2hlZHVsZU91dGJvdW5kRmx1c2goKTtcbiAgfVxuXG4gIHByaXZhdGUgc2NoZWR1bGVPdXRib3VuZEZsdXNoKGRlbGF5TXM6IG51bWJlciA9IDApOiB2b2lkIHtcbiAgICBpZiAodGhpcy5vdXRib3VuZEZsdXNoU2NoZWR1bGVkIHx8IHRoaXMuY2xvc2VkSW50ZXJuYWwpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLm91dGJvdW5kRmx1c2hTY2hlZHVsZWQgPSB0cnVlO1xuICAgIGNvbnN0IGZsdXNoID0gKCkgPT4ge1xuICAgICAgdGhpcy5vdXRib3VuZEZsdXNoU2NoZWR1bGVkID0gZmFsc2U7XG4gICAgICB0aGlzLmZsdXNoT3V0Ym91bmRNZXNzYWdlcygpO1xuICAgIH07XG5cbiAgICBpZiAoZGVsYXlNcyA+IDApIHtcbiAgICAgIHNldFRpbWVvdXQoZmx1c2gsIGRlbGF5TXMpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHNldEltbWVkaWF0ZShmbHVzaCk7XG4gIH1cblxuICAvLyBidWZmZXJlZEFtb3VudOqwgCDsnoTqs4TsuZjrpbwg64SY7Jy866m0IGZsdXNo66W8IOuvuOukhCBzb2NrZXQg64K067aAIO2BkOqwgCDthLDsp4Dsp4Ag7JWK64+E66GdIGJhY2twcmVzc3VyZeulvCDsobTspJHtlahcbiAgLy8g7ZWcIOuyiOyXkCDrsLDsuZgg64uo7JyE66Gc66eMIHNlbmTtlbQg64+Z6riwIOujqO2UhOqwgCDsnbTrsqTtirgg66Oo7ZSE66W8IOyepeyLnOqwhCDsoJDsnKDtlZjsp4Ag7JWK6rKMIO2VqFxuICBwcml2YXRlIGZsdXNoT3V0Ym91bmRNZXNzYWdlcygpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5jbG9zZWRJbnRlcm5hbCB8fCB0aGlzLnNvY2tldC5yZWFkeVN0YXRlICE9PSBXU19PUEVOKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuc29ja2V0LmJ1ZmZlcmVkQW1vdW50ID4gTUFYX1NPQ0tFVF9CVUZGRVJFRF9BTU9VTlQpIHtcbiAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICBuYW1lOiBcIndzLmJhY2twcmVzc3VyZS5kZWxheWVkXCIsXG4gICAgICAgIGxldmVsOiBcIndhcm5cIixcbiAgICAgICAgLi4udGhpcy50ZWxlbWV0cnlGaWVsZHMoKSxcbiAgICAgIH0pO1xuICAgICAgdGhpcy5zY2hlZHVsZU91dGJvdW5kRmx1c2goT1VUQk9VTkRfUkVUUllfREVMQVlfTVMpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGxldCBzZW50ID0gMDtcbiAgICB3aGlsZSAoXG4gICAgICBzZW50IDwgT1VUQk9VTkRfQkFUQ0hfU0laRSAmJlxuICAgICAgdGhpcy5wZW5kaW5nT3V0Ym91bmRNZXNzYWdlcy5sZW5ndGggPiAwICYmXG4gICAgICB0aGlzLnNvY2tldC5yZWFkeVN0YXRlID09PSBXU19PUEVOXG4gICAgKSB7XG4gICAgICBjb25zdCBuZXh0ID0gdGhpcy5wZW5kaW5nT3V0Ym91bmRNZXNzYWdlcy5zaGlmdCgpO1xuICAgICAgaWYgKCFuZXh0KSB7XG4gICAgICAgIGJyZWFrO1xuICAgICAgfVxuICAgICAgY29uc3QgeyBwYXlsb2FkLCBldmVudCB9ID0gbmV4dDtcblxuICAgICAgY29uc3Qgc3RhcnRlZEF0ID0gcGVyZm9ybWFuY2Uubm93KCk7XG4gICAgICBjb25zdCBmaWVsZHMgPSB0aGlzLnRlbGVtZXRyeUZpZWxkcygpO1xuICAgICAgdHJ5IHtcbiAgICAgICAgdGhpcy5zb2NrZXQuc2VuZChwYXlsb2FkKTtcbiAgICAgICAgY29uc3QgZHVyYXRpb25NcyA9IHBlcmZvcm1hbmNlLm5vdygpIC0gc3RhcnRlZEF0O1xuICAgICAgICB0aGlzLm9wdGlvbnMudGVsZW1ldHJ5Q29udHJvbGxlci5lbWl0KHtcbiAgICAgICAgICBuYW1lOiBcIndzLnB1Ymxpc2guc2VudFwiLFxuICAgICAgICAgIGxldmVsOiBcImRlYnVnXCIsXG4gICAgICAgICAgLi4uZmllbGRzLFxuICAgICAgICAgIGRldGFpbDogeyBldmVudCB9LFxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIucmVjb3JkU3Bhbih7XG4gICAgICAgICAgb3BlcmF0aW9uTmFtZTogXCJ3cy5wdWJsaXNoLnNlbmRcIixcbiAgICAgICAgICBraW5kOiBcInByb2R1Y2VyXCIsXG4gICAgICAgICAgZHVyYXRpb25NcyxcbiAgICAgICAgICBzdGF0dXM6IFwidW5zZXRcIixcbiAgICAgICAgICAuLi5maWVsZHMsXG4gICAgICAgICAgYXR0cmlidXRlczogeyBldmVudCB9LFxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5vcHRpb25zLnRlbGVtZXRyeUNvbnRyb2xsZXIucmVjb3JkTWV0cmljKHtcbiAgICAgICAgICBuYW1lOiBcInNvbmFtdS53cy5wdWJsaXNoZXNcIixcbiAgICAgICAgICBraW5kOiBcImNvdW50ZXJcIixcbiAgICAgICAgICB2YWx1ZTogMSxcbiAgICAgICAgICB1bml0OiBcIjFcIixcbiAgICAgICAgICB0YWdzOiB7IG91dGNvbWU6IFwic2VudFwiLCBldmVudCB9LFxuICAgICAgICAgIC4uLmZpZWxkcyxcbiAgICAgICAgfSk7XG4gICAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgICBjb25zdCBkdXJhdGlvbk1zID0gcGVyZm9ybWFuY2Uubm93KCkgLSBzdGFydGVkQXQ7XG4gICAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLmVtaXQoe1xuICAgICAgICAgIG5hbWU6IFwid3MucHVibGlzaC5mYWlsZWRcIixcbiAgICAgICAgICBsZXZlbDogXCJlcnJvclwiLFxuICAgICAgICAgIC4uLmZpZWxkcyxcbiAgICAgICAgICBkZXRhaWw6IHsgZXZlbnQgfSxcbiAgICAgICAgfSk7XG4gICAgICAgIHRoaXMub3B0aW9ucy50ZWxlbWV0cnlDb250cm9sbGVyLnJlY29yZFNwYW4oe1xuICAgICAgICAgIG9wZXJhdGlvbk5hbWU6IFwid3MucHVibGlzaC5zZW5kXCIsXG4gICAgICAgICAga2luZDogXCJwcm9kdWNlclwiLFxuICAgICAgICAgIGR1cmF0aW9uTXMsXG4gICAgICAgICAgc3RhdHVzOiBcImVycm9yXCIsXG4gICAgICAgICAgLi4uZmllbGRzLFxuICAgICAgICAgIGF0dHJpYnV0ZXM6IHsgZXZlbnQgfSxcbiAgICAgICAgICBlcnJvclR5cGU6IGVycm9yIGluc3RhbmNlb2YgRXJyb3IgPyBlcnJvci5uYW1lIDogdHlwZW9mIGVycm9yLFxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5jbG9zZShXU19DTE9TRV9DT0RFX0lOVEVSTkFMX0VSUk9SLCBcIk91dGJvdW5kIHB1Ymxpc2ggZmFpbGVkXCIpO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIHNlbnQgKz0gMTtcbiAgICAgIGlmICh0aGlzLnNvY2tldC5idWZmZXJlZEFtb3VudCA+IE1BWF9TT0NLRVRfQlVGRkVSRURfQU1PVU5UKSB7XG4gICAgICAgIGJyZWFrO1xuICAgICAgfVxuICAgIH1cblxuICAgIGlmICh0aGlzLnBlbmRpbmdPdXRib3VuZE1lc3NhZ2VzLmxlbmd0aCA+IDApIHtcbiAgICAgIHRoaXMuc2NoZWR1bGVPdXRib3VuZEZsdXNoKFxuICAgICAgICB0aGlzLnNvY2tldC5idWZmZXJlZEFtb3VudCA+IE1BWF9TT0NLRVRfQlVGRkVSRURfQU1PVU5UID8gT1VUQk9VTkRfUkVUUllfREVMQVlfTVMgOiAwLFxuICAgICAgKTtcbiAgICB9XG4gIH1cbn1cblxuZnVuY3Rpb24gbm9ybWFsaXplTWVzc2FnZShyYXc6IHVua25vd24pOiBzdHJpbmcge1xuICBpZiAodHlwZW9mIHJhdyA9PT0gXCJzdHJpbmdcIikge1xuICAgIHJldHVybiByYXc7XG4gIH1cblxuICBpZiAocmF3IGluc3RhbmNlb2YgQnVmZmVyKSB7XG4gICAgcmV0dXJuIHJhdy50b1N0cmluZyhcInV0Zi04XCIpO1xuICB9XG5cbiAgaWYgKHJhdyBpbnN0YW5jZW9mIEFycmF5QnVmZmVyKSB7XG4gICAgcmV0dXJuIEJ1ZmZlci5mcm9tKHJhdykudG9TdHJpbmcoXCJ1dGYtOFwiKTtcbiAgfVxuXG4gIGlmIChBcnJheS5pc0FycmF5KHJhdykpIHtcbiAgICByZXR1cm4gQnVmZmVyLmNvbmNhdChyYXcuZmlsdGVyKChjaHVuayk6IGNodW5rIGlzIEJ1ZmZlciA9PiBjaHVuayBpbnN0YW5jZW9mIEJ1ZmZlcikpLnRvU3RyaW5nKFxuICAgICAgXCJ1dGYtOFwiLFxuICAgICk7XG4gIH1cblxuICByZXR1cm4gSlNPTi5zdHJpbmdpZnkocmF3KTtcbn1cblxuZnVuY3Rpb24gc2FmZVBhcnNlRW52ZWxvcGUocmF3OiBzdHJpbmcpOiBQYXJzZWRFbnZlbG9wZSB8IG51bGwge1xuICB0cnkge1xuICAgIGNvbnN0IHBhcnNlZCA9IEpTT04ucGFyc2UocmF3KSBhcyB1bmtub3duO1xuICAgIGNvbnN0IHZhbGlkYXRlZCA9IFdlYlNvY2tldEVudmVsb3BlU2NoZW1hLnNhZmVQYXJzZShwYXJzZWQpO1xuICAgIHJldHVybiB2YWxpZGF0ZWQuc3VjY2VzcyA/IHZhbGlkYXRlZC5kYXRhIDogbnVsbDtcbiAgfSBjYXRjaCB7XG4gICAgcmV0dXJuIG51bGw7XG4gIH1cbn1cblxuLy8gUkZDIDY0NTXqsIAgY2xvc2UgZnJhbWUgcmVhc29u7J2EIDEyMyBieXRl66GcIOygnO2VnO2VmOuvgOuhnCDstIjqs7zrtoTsnYAg7J6Y6528IOyghOyGoSDsi6TtjKjrpbwg67Cp7KeA7ZWoXG5mdW5jdGlvbiB0cnVuY2F0ZUNsb3NlUmVhc29uKHJlYXNvbj86IHN0cmluZyk6IHN0cmluZyB8IHVuZGVmaW5lZCB7XG4gIGlmICghcmVhc29uKSB7XG4gICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgfVxuXG4gIHJldHVybiBCdWZmZXIuYnl0ZUxlbmd0aChyZWFzb24sIFwidXRmLThcIikgPD0gMTIzXG4gICAgPyByZWFzb25cbiAgICA6IEJ1ZmZlci5mcm9tKHJlYXNvbikuc3ViYXJyYXkoMCwgMTIzKS50b1N0cmluZyhcInV0Zi04XCIpO1xufVxuXG4vLyBjb25uZWN0aW9uIGxpZmV0aW1lIHNwYW7snZggc3RhdHVz66W8IGNsb3NlIGNvZGUg6riw7KSA7Jy866GcIOu2hOq4sO2VqCAoMTAwMC8xMDAxIOygleyDgSDsooXro4wsIOq3uCDsmbgga25vd24gY29kZSBlcnJvciwgY29kZSDrr7jsg4HsnYAgdW5zZXQpXG5mdW5jdGlvbiBkZXJpdmVMaWZldGltZVN0YXR1cyhjb2RlOiBudW1iZXIgfCB1bmRlZmluZWQpOiBcIm9rXCIgfCBcImVycm9yXCIgfCBcInVuc2V0XCIge1xuICBpZiAoY29kZSA9PT0gdW5kZWZpbmVkKSByZXR1cm4gXCJ1bnNldFwiO1xuICBpZiAoY29kZSA9PT0gMTAwMCB8fCBjb2RlID09PSAxMDAxKSByZXR1cm4gXCJva1wiO1xuICByZXR1cm4gXCJlcnJvclwiO1xufVxuIl0sIm1hcHBpbmdz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
|