@pipeline-builder/pipeline-data 4.3.11 → 4.3.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/api/managed-toolchain.d.ts +199 -0
- package/lib/api/managed-toolchain.js +445 -0
- package/lib/api/reporting/ingest.js +52 -12
- package/lib/api/reporting/toolchain-runs.d.ts +162 -0
- package/lib/api/reporting/toolchain-runs.js +268 -0
- package/lib/api/reporting/types.d.ts +17 -1
- package/lib/api/reporting/types.js +1 -1
- package/lib/api/version-references.d.ts +2 -24
- package/lib/api/version-references.js +46 -7
- package/lib/database/drizzle-schema.d.ts +650 -0
- package/lib/database/drizzle-schema.js +11 -1
- package/lib/database/index.d.ts +1 -1
- package/lib/database/index.js +2 -2
- package/lib/database/schema/ecosystem.d.ts +55 -0
- package/lib/database/schema/ecosystem.js +13 -2
- package/lib/database/schema/pipeline.d.ts +19 -0
- package/lib/database/schema/pipeline.js +17 -1
- package/lib/database/schema/toolchain.d.ts +643 -0
- package/lib/database/schema/toolchain.js +102 -0
- package/lib/index.d.ts +2 -0
- package/lib/index.js +5 -1
- package/lib/testing/exports.json +39 -0
- package/package.json +2 -2
|
@@ -13,6 +13,7 @@ import { invalidateOrgReports } from './caches.js';
|
|
|
13
13
|
import { upsertDeployments } from './deploy-rollup.js';
|
|
14
14
|
import { classifyFailure } from './failure-classifier.js';
|
|
15
15
|
import { scrubOptional } from './sql-helpers.js';
|
|
16
|
+
import { deployedToolchainOf, readPlatformDefaultRelease, SELF_MUTATION_ACTION, SELF_MUTATION_STAGE, toolchainActionOf, toolchainOutcomeOf, } from './toolchain-runs.js';
|
|
16
17
|
import { schema } from '../../database/drizzle-schema.js';
|
|
17
18
|
import { withTenantTx } from '../../database/tenancy.js';
|
|
18
19
|
const logger = createLogger('reporting-ingest');
|
|
@@ -26,14 +27,18 @@ function stepKey(pipelineId, stageName, actionName) {
|
|
|
26
27
|
return `${pipelineId}\u0000${stageName}\u0000${actionName}`;
|
|
27
28
|
}
|
|
28
29
|
/**
|
|
29
|
-
* Plugin attribution: the step manifests of
|
|
30
|
-
* event, in ONE read per batch, keyed for
|
|
31
|
-
* post-scrub on both sides (the manifest
|
|
30
|
+
* Plugin attribution AND the deployed toolchain release: the step manifests of
|
|
31
|
+
* every pipeline with an attributable event, in ONE read per batch, keyed for
|
|
32
|
+
* an in-memory join. Names are compared post-scrub on both sides (the manifest
|
|
33
|
+
* stores them scrubbed the same way).
|
|
34
|
+
*
|
|
35
|
+
* The toolchain map is the PLATFORM's record of what was deployed (the
|
|
36
|
+
* manifest's `build-image` entry) — the only source the §7 run stamp may use.
|
|
32
37
|
*/
|
|
33
38
|
async function loadStepPlugins(tx, attributable) {
|
|
34
39
|
const pipelineIds = [...new Set(attributable.map((e) => e.pipelineId))];
|
|
35
40
|
if (pipelineIds.length === 0)
|
|
36
|
-
return new Map();
|
|
41
|
+
return { steps: new Map(), toolchain: new Map() };
|
|
37
42
|
const rows = await tx
|
|
38
43
|
.select({
|
|
39
44
|
pipelineId: schema.pipelineStepManifest.pipelineId,
|
|
@@ -44,10 +49,14 @@ async function loadStepPlugins(tx, attributable) {
|
|
|
44
49
|
pluginPublisherId: schema.pipelineStepManifest.pluginPublisherId,
|
|
45
50
|
pluginName: schema.pipelineStepManifest.pluginName,
|
|
46
51
|
pluginVersion: schema.pipelineStepManifest.pluginVersion,
|
|
52
|
+
stepKey: schema.pipelineStepManifest.stepKey,
|
|
47
53
|
})
|
|
48
54
|
.from(schema.pipelineStepManifest)
|
|
49
55
|
.where(inArray(schema.pipelineStepManifest.pipelineId, pipelineIds));
|
|
50
|
-
return
|
|
56
|
+
return {
|
|
57
|
+
steps: new Map(rows.map((m) => [stepKey(m.pipelineId, m.stageName, m.actionName), m])),
|
|
58
|
+
toolchain: deployedToolchainOf(rows),
|
|
59
|
+
};
|
|
51
60
|
}
|
|
52
61
|
/**
|
|
53
62
|
* Allowance for clock skew between an AWS event's source clock and ours. A real
|
|
@@ -104,7 +113,7 @@ function pbFailureCode(detail) {
|
|
|
104
113
|
const code = failure && typeof failure === 'object' ? failure.code : undefined;
|
|
105
114
|
return typeof code === 'string' && /^[A-Z][A-Z0-9_]{0,63}$/.test(code) ? code : null;
|
|
106
115
|
}
|
|
107
|
-
function toEventRow(event, registry, plugin, keyId) {
|
|
116
|
+
function toEventRow(event, registry, plugin, keyId, toolchainRelease) {
|
|
108
117
|
const detail = event.sourceMessageId !== undefined
|
|
109
118
|
? { ...(event.detail ?? {}), sourceMessageId: event.sourceMessageId }
|
|
110
119
|
: event.detail;
|
|
@@ -142,6 +151,9 @@ function toEventRow(event, registry, plugin, keyId) {
|
|
|
142
151
|
pluginPublisherId: plugin?.pluginPublisherId ?? null,
|
|
143
152
|
pluginName: plugin?.pluginName ?? null,
|
|
144
153
|
pluginVersion: plugin?.pluginVersion ?? null,
|
|
154
|
+
// The managed toolchain release a synth / self-mutation action ran on, from
|
|
155
|
+
// the platform's deployed manifest (never the payload). NULL otherwise.
|
|
156
|
+
toolchainRelease,
|
|
145
157
|
// WHAT KIND of thing broke, classified here rather than at read time: the
|
|
146
158
|
// error text is scrubbed above and eventually swept by retention, so a
|
|
147
159
|
// category derived later would have nothing left to read. NULL for anything
|
|
@@ -174,10 +186,23 @@ function toEventRow(event, registry, plugin, keyId) {
|
|
|
174
186
|
*
|
|
175
187
|
* A non-null environment marks a deploy.
|
|
176
188
|
*/
|
|
177
|
-
function emitIngestMetrics(rows, onMetric) {
|
|
189
|
+
function emitIngestMetrics(rows, onMetric, platformDefaultRelease) {
|
|
178
190
|
for (const r of rows) {
|
|
179
191
|
if (!r.pipelineId)
|
|
180
192
|
continue;
|
|
193
|
+
// Toolchain runs (§7, alerting only): a terminal outcome on a stamped row.
|
|
194
|
+
// Not exclusive — the same action is also a compute measurement below.
|
|
195
|
+
const outcome = r.toolchainRelease ? toolchainOutcomeOf(r.status) : null;
|
|
196
|
+
if (r.toolchainRelease && outcome) {
|
|
197
|
+
onMetric({
|
|
198
|
+
kind: 'toolchain',
|
|
199
|
+
toolchainRelease: r.toolchainRelease,
|
|
200
|
+
// Stamped rows are only ever synth or self-mutation.
|
|
201
|
+
action: r.stageName === SELF_MUTATION_STAGE && r.actionName === SELF_MUTATION_ACTION ? 'self-mutation' : 'synth',
|
|
202
|
+
outcome,
|
|
203
|
+
platformDefaultRelease,
|
|
204
|
+
});
|
|
205
|
+
}
|
|
181
206
|
// Compute consumption: every TERMINAL action, measurable or not. The
|
|
182
207
|
// unmeasurable ones are the point — they are what the coverage ratio counts.
|
|
183
208
|
if (r.eventType === 'ACTION' && TERMINAL_ACTION_STATES.includes(r.status)) {
|
|
@@ -239,7 +264,7 @@ export async function ingestEvents(events, onMetric, caller) {
|
|
|
239
264
|
// Caches are invalidated AFTER the tx resolves: doing it inside held the pg
|
|
240
265
|
// locks open across unrelated cache round-trips. The TTL is 2-5 min, so a
|
|
241
266
|
// fire-and-forget post-commit invalidation is an acceptable trade.
|
|
242
|
-
const { inserted, skipped, unregisteredPipelineIds, affectedOrgs, droppedForeignOrg, droppedInvalidTime, foreignPipelineIds, insertedRows } = await withTenantTx(async (tx) => {
|
|
267
|
+
const { inserted, skipped, unregisteredPipelineIds, affectedOrgs, droppedForeignOrg, droppedInvalidTime, foreignPipelineIds, insertedRows, platformDefaultRelease } = await withTenantTx(async (tx) => {
|
|
243
268
|
// Batch-resolve all unique pipeline ids in one query
|
|
244
269
|
const uniqueIds = [...new Set(events.map(e => e.pipelineId))];
|
|
245
270
|
const registryRows = await tx
|
|
@@ -250,7 +275,7 @@ export async function ingestEvents(events, onMetric, caller) {
|
|
|
250
275
|
.from(schema.pipelineRegistry)
|
|
251
276
|
.where(inArray(schema.pipelineRegistry.pipelineId, uniqueIds));
|
|
252
277
|
const idMap = new Map(registryRows.map(r => [r.pipelineId, r]));
|
|
253
|
-
const stepPlugins = await loadStepPlugins(tx, events.filter((e) => isAttributable(e) && idMap.has(e.pipelineId)));
|
|
278
|
+
const { steps: stepPlugins, toolchain } = await loadStepPlugins(tx, events.filter((e) => isAttributable(e) && idMap.has(e.pipelineId)));
|
|
254
279
|
// Build insert batch (skip events whose pipeline isn't registered)
|
|
255
280
|
const rows = [];
|
|
256
281
|
let skippedLocal = 0;
|
|
@@ -292,9 +317,16 @@ export async function ingestEvents(events, onMetric, caller) {
|
|
|
292
317
|
const step = isAttributable(event) && stageName && actionName
|
|
293
318
|
? stepPlugins.get(stepKey(registry.pipelineId, stageName, actionName))
|
|
294
319
|
: undefined;
|
|
320
|
+
// The toolchain stamp: is this the pipeline's synth / self-mutation
|
|
321
|
+
// action, and which release did the platform deploy it with?
|
|
322
|
+
const deployed = toolchain.get(registry.pipelineId);
|
|
323
|
+
const sameOrgDeployed = deployed && deployed.orgId === registry.orgId ? deployed : undefined;
|
|
324
|
+
const toolchainRelease = toolchainActionOf({ eventType: event.eventType, stageName, actionName }, sameOrgDeployed)
|
|
325
|
+
? sameOrgDeployed.releaseVersion
|
|
326
|
+
: null;
|
|
295
327
|
// Same-org guard: a manifest row is only ever written by the org that
|
|
296
328
|
// owns the pipeline, but the ingest runs cross-tenant, so don't lean on it.
|
|
297
|
-
rows.push(toEventRow(event, registry, step && step.orgId === registry.orgId ? step : undefined, caller?.keyId));
|
|
329
|
+
rows.push(toEventRow(event, registry, step && step.orgId === registry.orgId ? step : undefined, caller?.keyId, toolchainRelease));
|
|
298
330
|
}
|
|
299
331
|
// SQS is at-least-once, so EventBridge can deliver the same state-change
|
|
300
332
|
// twice. `onConflictDoNothing` + the partial unique indexes on
|
|
@@ -311,7 +343,9 @@ export async function ingestEvents(events, onMetric, caller) {
|
|
|
311
343
|
eventType: schema.pipelineEvent.eventType,
|
|
312
344
|
status: schema.pipelineEvent.status,
|
|
313
345
|
stageName: schema.pipelineEvent.stageName,
|
|
346
|
+
actionName: schema.pipelineEvent.actionName,
|
|
314
347
|
environment: schema.pipelineEvent.environment,
|
|
348
|
+
toolchainRelease: schema.pipelineEvent.toolchainRelease,
|
|
315
349
|
// For the per-deploy rollup below: everything `dora_deployments` needs,
|
|
316
350
|
// taken from the rows that ACTUALLY landed so a re-delivery cannot
|
|
317
351
|
// produce a second deploy.
|
|
@@ -342,7 +376,13 @@ export async function ingestEvents(events, onMetric, caller) {
|
|
|
342
376
|
reasons: [...invalidTimeReasons],
|
|
343
377
|
});
|
|
344
378
|
}
|
|
379
|
+
// The platform default, for the alert's baseline gauge — read only when a
|
|
380
|
+
// toolchain run landed, so ordinary batches pay nothing.
|
|
381
|
+
const defaultRelease = landed.some((r) => r.toolchainRelease)
|
|
382
|
+
? await readPlatformDefaultRelease(tx)
|
|
383
|
+
: null;
|
|
345
384
|
return {
|
|
385
|
+
platformDefaultRelease: defaultRelease,
|
|
346
386
|
inserted: landed.length,
|
|
347
387
|
skipped: skippedLocal,
|
|
348
388
|
unregisteredPipelineIds: unregisteredLocal,
|
|
@@ -354,7 +394,7 @@ export async function ingestEvents(events, onMetric, caller) {
|
|
|
354
394
|
};
|
|
355
395
|
});
|
|
356
396
|
if (onMetric)
|
|
357
|
-
emitIngestMetrics(insertedRows, onMetric);
|
|
397
|
+
emitIngestMetrics(insertedRows, onMetric, platformDefaultRelease);
|
|
358
398
|
// Per-deploy rollup. AFTER the events commit and outside their transaction: the
|
|
359
399
|
// events are the durable record and `dora_deployments` is derived from them, so
|
|
360
400
|
// a rollup failure must not roll back an ingest that succeeded. Rebuildable
|
|
@@ -389,4 +429,4 @@ export async function ingestEvents(events, onMetric, caller) {
|
|
|
389
429
|
insertedPipelineIds: [...new Set(insertedRows.map((r) => r.pipelineId).filter((id) => !!id))],
|
|
390
430
|
};
|
|
391
431
|
}
|
|
392
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5nZXN0LmpzIiwic291cmNlcyI6WyIuLi8uLi8uLi9zcmMvYXBpL3JlcG9ydGluZy9pbmdlc3QudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsK0NBQStDO0FBQy9DLHNDQUFzQztBQUV0Qzs7Ozs7O0dBTUc7QUFFSCxPQUFPLEVBQUUsaUJBQWlCLEVBQUUsWUFBWSxFQUFFLFlBQVksRUFBRSxvQkFBb0IsRUFBRSxtQkFBbUIsRUFBRSxNQUFNLDRCQUE0QixDQUFDO0FBQ3RJLE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSxhQUFhLENBQUM7QUFDdEMsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0sYUFBYSxDQUFDO0FBQ25ELE9BQU8sRUFBRSxpQkFBaUIsRUFBRSxNQUFNLG9CQUFvQixDQUFDO0FBQ3ZELE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSx5QkFBeUIsQ0FBQztBQUMxRCxPQUFPLEVBQUUsYUFBYSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFFakQsT0FBTyxFQUFFLE1BQU0sRUFBRSxNQUFNLGtDQUFrQyxDQUFDO0FBQzFELE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSwyQkFBMkIsQ0FBQztBQUd6RCxNQUFNLE1BQU0sR0FBRyxZQUFZLENBQUMsa0JBQWtCLENBQUMsQ0FBQztBQWNoRCxxRUFBcUU7QUFDckUsU0FBUyxjQUFjLENBQUMsQ0FBYztJQUNwQyxPQUFPLENBQUMsQ0FBQyxDQUFDLFNBQVMsS0FBSyxRQUFRLElBQUksQ0FBQyxDQUFDLFNBQVMsS0FBSyxPQUFPLENBQUM7V0FDdkQsQ0FBQyxDQUFDLENBQUMsV0FBVyxLQUFLLGNBQWMsSUFBSSxDQUFDLENBQUMsV0FBVyxLQUFLLFdBQVcsQ0FBQztXQUNuRSxDQUFDLENBQUMsQ0FBQyxDQUFDLFNBQVMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLFVBQVUsQ0FBQztBQUN2QyxDQUFDO0FBRUQsU0FBUyxPQUFPLENBQUMsVUFBa0IsRUFBRSxTQUFpQixFQUFFLFVBQWtCO0lBQ3hF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LEdBQUcsRUFBRSxLQUFLLEVBQUUsWUFBWSxDQUFDLEdBQUcsQ0FBQyxFQUFFLENBQUMsQ0FBQztRQUMvRixDQUFDLENBQUMsQ0FDSCxDQUFDLENBQUM7SUFDTCxDQUFDO0lBRUQsT0FBTztRQUNMLFFBQVE7UUFDUixPQUFPO1FBQ1AsdUJBQXVCO1FBQ3ZCLFlBQVk7UUFDWixpQkFBaUI7UUFDakIsa0JBQWtCO1FBQ2xCLGtCQUFrQjtRQUNsQixvQkFBb0IsRUFBRSxDQUFDLEdBQUcsSUFBSSxHQUFHLENBQUMsWUFBWSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDLFdBQVcsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxDQUFDLEVBQUUsRUFBZ0IsRUFBRSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDO1FBQzdHLG1CQUFtQixFQUFFLENBQUMsR0FBRyxJQUFJLEdBQUcsQ0FBQyxZQUFZLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxFQUFFLEVBQUUsQ0FBQyxDQUFDLENBQUMsVUFBVSxDQUFDLENBQUMsTUFBTSxDQUFDLENBQUMsRUFBRSxFQUFnQixFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUM7S0FDNUcsQ0FBQztBQUNKLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvLyBDb3B5cmlnaHQgMjAyNiBQaXBlbGluZSBCdWlsZGVyIENvbnRyaWJ1dG9yc1xuLy8gU1BEWC1MaWNlbnNlLUlkZW50aWZpZXI6IEFwYWNoZS0yLjBcblxuLyoqXG4gKiBFdmVudCBpbmdlc3Q6IHRoZSBXUklURSBoYWxmIG9mIHJlcG9ydGluZy4gUmVzb2x2ZXMgaW5jb21pbmcgcGlwZWxpbmUgZXZlbnRzXG4gKiBhZ2FpbnN0IHRoZSBwaXBlbGluZSByZWdpc3RyeSwgc2NydWJzIGV2ZXJ5IGZyZWUtZm9ybSBzdHJpbmcsIGJhdGNoLWluc2VydHNcbiAqIHRoZSBtYXRjaGVkIHJvd3MgaWRlbXBvdGVudGx5LCBhbmQgaW52YWxpZGF0ZXMgdGhlIGFmZmVjdGVkIG9yZ3MnIHJlcG9ydFxuICogY2FjaGVzLiBTZXBhcmF0ZSBmcm9tIHRoZSByZXBvcnQgcXVlcmllcyBiZWNhdXNlIHRoaXMgaXMgcmVwb3J0aW5nJ3Mgb25seVxuICogZHVyYWJsZSBwZXJzaXN0ZW5jZSBib3VuZGFyeSDigJQgZXZlcnl0aGluZyBlbHNlIGluIHRoZSBzZXJ2aWNlIG9ubHkgcmVhZHMuXG4gKi9cblxuaW1wb3J0IHsgY29tcHV0ZUNyZWRpdHNGb3IsIGNyZWF0ZUxvZ2dlciwgZXJyb3JNZXNzYWdlLCBub3JtYWxpemVDb21wdXRlVHlwZSwgc2NydWJBd3NJZGVudGlmaWVycyB9IGZyb20gJ0BwaXBlbGluZS1idWlsZGVyL2FwaS1jb3JlJztcbmltcG9ydCB7IGluQXJyYXkgfSBmcm9tICdkcml6emxlLW9ybSc7XG5pbXBvcnQgeyBpbnZhbGlkYXRlT3JnUmVwb3J0cyB9IGZyb20gJy4vY2FjaGVzLmpzJztcbmltcG9ydCB7IHVwc2VydERlcGxveW1lbnRzIH0gZnJvbSAnLi9kZXBsb3ktcm9sbHVwLmpzJztcbmltcG9ydCB7IGNsYXNzaWZ5RmFpbHVyZSB9IGZyb20gJy4vZmFpbHVyZS1jbGFzc2lmaWVyLmpzJztcbmltcG9ydCB7IHNjcnViT3B0aW9uYWwgfSBmcm9tICcuL3NxbC1oZWxwZXJzLmpzJztcbmltcG9ydCB0eXBlIHsgSW5nZXN0Q2FsbGVyLCBJbmdlc3RFdmVudCwgSW5nZXN0TWV0cmljLCBJbmdlc3RSZXN1bHQgfSBmcm9tICcuL3R5cGVzLmpzJztcbmltcG9ydCB7IHNjaGVtYSB9IGZyb20gJy4uLy4uL2RhdGFiYXNlL2RyaXp6bGUtc2NoZW1hLmpzJztcbmltcG9ydCB7IHdpdGhUZW5hbnRUeCB9IGZyb20gJy4uLy4uL2RhdGFiYXNlL3RlbmFuY3kuanMnO1xuaW1wb3J0IHR5cGUgeyBDcnVkVHggfSBmcm9tICcuLi9jcnVkLXNlcnZpY2UuanMnO1xuXG5jb25zdCBsb2dnZXIgPSBjcmVhdGVMb2dnZXIoJ3JlcG9ydGluZy1pbmdlc3QnKTtcblxudHlwZSBQaXBlbGluZUV2ZW50SW5zZXJ0ID0gdHlwZW9mIHNjaGVtYS5waXBlbGluZUV2ZW50LiRpbmZlckluc2VydDtcblxuXG4vKiogVGhlIHBsdWdpbiBhIHBpcGVsaW5lIHN0ZXAgcnVucywgZnJvbSB0aGUgc3RlcCBtYW5pZmVzdCBpdHMgbGFzdCBkZXBsb3kgcmVnaXN0ZXJlZC4gKi9cbmludGVyZmFjZSBTdGVwUGx1Z2luIHtcbiAgb3JnSWQ6IHN0cmluZztcbiAgcGx1Z2luUHVibGlzaGVyOiBzdHJpbmcgfCBudWxsO1xuICBwbHVnaW5QdWJsaXNoZXJJZDogc3RyaW5nIHwgbnVsbDtcbiAgcGx1Z2luTmFtZTogc3RyaW5nIHwgbnVsbDtcbiAgcGx1Z2luVmVyc2lvbjogc3RyaW5nIHwgbnVsbDtcbn1cblxuLyoqIEFuIGFjdGlvbi9idWlsZCBldmVudCB0aGF0IGNhbiBiZSBhdHRyaWJ1dGVkIHRvIGEgcGx1Z2luIHN0ZXAuICovXG5mdW5jdGlvbiBpc0F0dHJpYnV0YWJsZShlOiBJbmdlc3RFdmVudCk6IGJvb2xlYW4ge1xuICByZXR1cm4gKGUuZXZlbnRUeXBlID09PSAnQUNUSU9OJyB8fCBlLmV2ZW50VHlwZSA9PT0gJ0JVSUxEJylcbiAgICAmJiAoZS5ldmVudFNvdXJjZSA9PT0gJ2NvZGVwaXBlbGluZScgfHwgZS5ldmVudFNvdXJjZSA9PT0gJ2NvZGVidWlsZCcpXG4gICAgJiYgISFlLnN0YWdlTmFtZSAmJiAhIWUuYWN0aW9uTmFtZTtcbn1cblxuZnVuY3Rpb24gc3RlcEtleShwaXBlbGluZUlkOiBzdHJpbmcsIHN0YWdlTmFtZTogc3RyaW5nLCBhY3Rpb25OYW1lOiBzdHJpbmcpOiBzdHJpbmcge1xuICByZXR1cm4gYCR7cGlwZWxpbmVJZH1cXHUwMDAwJHtzdGFnZU5hbWV9XFx1MDAwMCR7YWN0aW9uTmFtZX1gO1xufVxuXG4vKipcbiAqIFBsdWdpbiBhdHRyaWJ1dGlvbjogdGhlIHN0ZXAgbWFuaWZlc3RzIG9mIGV2ZXJ5IHBpcGVsaW5lIHdpdGggYW4gYXR0cmlidXRhYmxlXG4gKiBldmVudCwgaW4gT05FIHJlYWQgcGVyIGJhdGNoLCBrZXllZCBmb3IgYW4gaW4tbWVtb3J5IGpvaW4uIE5hbWVzIGFyZSBjb21wYXJlZFxuICogcG9zdC1zY3J1YiBvbiBib3RoIHNpZGVzICh0aGUgbWFuaWZlc3Qgc3RvcmVzIHRoZW0gc2NydWJiZWQgdGhlIHNhbWUgd2F5KS5cbiAqL1xuYXN5bmMgZnVuY3Rpb24gbG9hZFN0ZXBQbHVnaW5zKHR4OiBDcnVkVHgsIGF0dHJpYnV0YWJsZTogSW5nZXN0RXZlbnRbXSk6IFByb21pc2U8TWFwPHN0cmluZywgU3RlcFBsdWdpbj4+IHtcbiAgY29uc3QgcGlwZWxpbmVJZHMgPSBbLi4ubmV3IFNldChhdHRyaWJ1dGFibGUubWFwKChlKSA9PiBlLnBpcGVsaW5lSWQpKV07XG4gIGlmIChwaXBlbGluZUlkcy5sZW5ndGggPT09IDApIHJldHVybiBuZXcgTWFwKCk7XG4gIGNvbnN0IHJvd3MgPSBhd2FpdCB0eFxuICAgIC5zZWxlY3Qoe1xuICAgICAgcGlwZWxpbmVJZDogc2NoZW1hLnBpcGVsaW5lU3RlcE1hbmlmZXN0LnBpcGVsaW5lSWQsXG4gICAgICBvcmdJZDogc2NoZW1hLnBpcGVsaW5lU3RlcE1hbmlmZXN0Lm9yZ0lkLFxuICAgICAgc3RhZ2VOYW1lOiBzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3Quc3RhZ2VOYW1lLFxuICAgICAgYWN0aW9uTmFtZTogc2NoZW1hLnBpcGVsaW5lU3RlcE1hbmlmZXN0LmFjdGlvbk5hbWUsXG4gICAgICBwbHVnaW5QdWJsaXNoZXI6IHNjaGVtYS5waXBlbGluZVN0ZXBNYW5pZmVzdC5wbHVnaW5QdWJsaXNoZXIsXG4gICAgICBwbHVnaW5QdWJsaXNoZXJJZDogc2NoZW1hLnBpcGVsaW5lU3RlcE1hbmlmZXN0LnBsdWdpblB1Ymxpc2hlcklkLFxuICAgICAgcGx1Z2luTmFtZTogc2NoZW1hLnBpcGVsaW5lU3RlcE1hbmlmZXN0LnBsdWdpbk5hbWUsXG4gICAgICBwbHVnaW5WZXJzaW9uOiBzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3QucGx1Z2luVmVyc2lvbixcbiAgICB9KVxuICAgIC5mcm9tKHNjaGVtYS5waXBlbGluZVN0ZXBNYW5pZmVzdClcbiAgICAud2hlcmUoaW5BcnJheShzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3QucGlwZWxpbmVJZCwgcGlwZWxpbmVJZHMpKTtcbiAgcmV0dXJuIG5ldyBNYXAocm93cy5tYXAoKG0pID0+IFtzdGVwS2V5KG0ucGlwZWxpbmVJZCwgbS5zdGFnZU5hbWUsIG0uYWN0aW9uTmFtZSksIG1dKSk7XG59XG5cbi8qKlxuICogQWxsb3dhbmNlIGZvciBjbG9jayBza2V3IGJldHdlZW4gYW4gQVdTIGV2ZW50J3Mgc291cmNlIGNsb2NrIGFuZCBvdXJzLiBBIHJlYWxcbiAqIENvZGVQaXBlbGluZSBldmVudCBjYW4gY2FycnkgYSB0aW1lc3RhbXAgYSBsaXR0bGUgYWhlYWQgb2Ygb3VyIGBub3dgOyB3aXRob3V0XG4gKiBzb21lIHRvbGVyYW5jZSB0aGUgdmFsaWRhdGlvbiBiZWxvdyB3b3VsZCBkcm9wIGhlYWx0aHkgZXZlbnRzIGR1cmluZyBub3JtYWxcbiAqIE5UUCBkcmlmdCwgd2hpY2ggaXMgZmFyIHdvcnNlIHRoYW4gYWRtaXR0aW5nIGEgZmV3IHNlY29uZHMgb2Ygc2tldy5cbiAqL1xuY29uc3QgQ0xPQ0tfU0tFV19UT0xFUkFOQ0VfTVMgPSA1ICogNjAgKiAxMDAwO1xuXG4vKipcbiAqIFdoeSB0aGlzIGV2ZW50J3MgdGltZXN0YW1wcyBhcmUgaW1wb3NzaWJsZSwgb3IgbnVsbCB3aGVuIHRoZXkgYXJlIHVzYWJsZS5cbiAqXG4gKiBDaGVja2VkIGF0IElOR0VTVCDigJQgdGhlIGR1cmFibGUgYm91bmRhcnkg4oCUIHJhdGhlciB0aGFuIGNsYW1wZWQgd2hlbiB0aGUgbWV0cmljc1xuICogYXJlIGNvbXB1dGVkLiBBIG5lZ2F0aXZlIGR1cmF0aW9uIG9yIGEgZnV0dXJlIGRlcGxveSB1c2VkIHRvIGJlIGNsYW1wZWQgdG8gMFxuICogZG93bnN0cmVhbSwgd2hpY2ggcmVwb3J0ZWQgYSBicm9rZW4gY2xvY2sgYXMgYW4gaW5zdGFudCBkZXBsb3kgYW5kIHF1aWV0bHlcbiAqIG1vdmVkIGRlcGxveW1lbnQgZnJlcXVlbmN5LCBjaGFuZ2UtZmFpbHVyZSByYXRlIGFuZCBsZWFkIHRpbWUgZm9yIHRoZSBvcmcuXG4gKlxuICogTk9UIGNoZWNrZWQgaGVyZTogY29tbWl0IHRpbWUgdnMgZGVwbG95IGNvbXBsZXRpb24uIGBjb21taXRfdGltZXN0YW1wYCByaWRlcyB0aGVcbiAqIFBJUEVMSU5FL3NvdXJjZSBldmVudCB3aGlsZSB0aGUgZGVwbG95J3MgYGNvbXBsZXRlZF9hdGAgaXMgb24gYSBzZXBhcmF0ZSBTVEFHRVxuICogcm93LCBqb2luZWQgYnkgYGV4ZWN1dGlvbl9pZGAgb25seSB3aGVuIERPUkEgaXMgcXVlcmllZCDigJQgc28gbm8gc2luZ2xlIGV2ZW50XG4gKiBjYXJyaWVzIGJvdGgsIGFuZCB0aGF0IG9yZGVyaW5nIGNhbiBvbmx5IGJlIGd1YXJkZWQgd2hlcmUgdGhlIHR3byBtZWV0LlxuICovXG5mdW5jdGlvbiBpbnZhbGlkRXZlbnRUaW1lcyhldmVudDogSW5nZXN0RXZlbnQsIG5vd01zOiBudW1iZXIpOiBzdHJpbmcgfCBudWxsIHtcbiAgY29uc3QgY2VpbGluZyA9IG5vd01zICsgQ0xPQ0tfU0tFV19UT0xFUkFOQ0VfTVM7XG4gIGNvbnN0IHBhcnNlZDogQXJyYXk8W3N0cmluZywgbnVtYmVyXT4gPSBbXTtcbiAgZm9yIChjb25zdCBmaWVsZCBvZiBbJ3N0YXJ0ZWRBdCcsICdjb21wbGV0ZWRBdCcsICdjb21taXRUaW1lc3RhbXAnXSBhcyBjb25zdCkge1xuICAgIGNvbnN0IHJhdyA9IGV2ZW50W2ZpZWxkXTtcbiAgICBpZiAocmF3ID09PSB1bmRlZmluZWQgfHwgcmF3ID09PSBudWxsKSBjb250aW51ZTtcbiAgICBjb25zdCBtcyA9IERhdGUucGFyc2UoU3RyaW5nKHJhdykpO1xuICAgIGlmICghTnVtYmVyLmlzRmluaXRlKG1zKSkgcmV0dXJuIGAke2ZpZWxkfSBpcyBub3QgYSBwYXJzZWFibGUgdGltZXN0YW1wYDtcbiAgICBpZiAobXMgPiBjZWlsaW5nKSByZXR1cm4gYCR7ZmllbGR9IGlzIGluIHRoZSBmdXR1cmVgO1xuICAgIHBhcnNlZC5wdXNoKFtmaWVsZCwgbXNdKTtcbiAgfVxuICBjb25zdCBzdGFydGVkID0gcGFyc2VkLmZpbmQoKFtmXSkgPT4gZiA9PT0gJ3N0YXJ0ZWRBdCcpPy5bMV07XG4gIGNvbnN0IGNvbXBsZXRlZCA9IHBhcnNlZC5maW5kKChbZl0pID0+IGYgPT09ICdjb21wbGV0ZWRBdCcpPy5bMV07XG4gIGlmIChzdGFydGVkICE9PSB1bmRlZmluZWQgJiYgY29tcGxldGVkICE9PSB1bmRlZmluZWQgJiYgY29tcGxldGVkIDwgc3RhcnRlZCkge1xuICAgIHJldHVybiAnY29tcGxldGVkQXQgaXMgYmVmb3JlIHN0YXJ0ZWRBdCc7XG4gIH1cbiAgaWYgKGV2ZW50LmR1cmF0aW9uTXMgIT09IHVuZGVmaW5lZCAmJiBldmVudC5kdXJhdGlvbk1zICE9PSBudWxsICYmIGV2ZW50LmR1cmF0aW9uTXMgPCAwKSB7XG4gICAgcmV0dXJuICdkdXJhdGlvbk1zIGlzIG5lZ2F0aXZlJztcbiAgfVxuICByZXR1cm4gbnVsbDtcbn1cblxuLyoqXG4gKiBUaGUgcGVyc2lzdGVkIHJvdyBmb3Igb25lIGluZ2VzdGVkIGV2ZW50LiBUaGlzIGlzIHRoZSBEVVJBQkxFIHBlcnNpc3RlbmNlXG4gKiBib3VuZGFyeTogZXZlcnkgdXNlci9BV1MtZGVyaXZlZCBmcmVlLWZvcm0gc3RyaW5nIGlzIHNjcnViYmVkIGhlcmUsIGFuZFxuICogdGVuYW5jeSBjb21lcyBmcm9tIHRoZSBwaXBlbGluZSByZWdpc3RyeSwgbmV2ZXIgdGhlIGNhbGxlcidzIGNsYWltZWQgb3JnLlxuICovXG4vKiogVGhlIHN5bnRoIHJlZnVzYWwgY29kZSB0aGUgZXZlbnRzIExhbWJkYSBhdHRhY2hlZCAoYGRldGFpbC5wYkZhaWx1cmUuY29kZWApLCBpZiBhbnkuICovXG5mdW5jdGlvbiBwYkZhaWx1cmVDb2RlKGRldGFpbDogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gfCB1bmRlZmluZWQpOiBzdHJpbmcgfCBudWxsIHtcbiAgY29uc3QgZmFpbHVyZSA9IGRldGFpbD8ucGJGYWlsdXJlO1xuICBjb25zdCBjb2RlID0gZmFpbHVyZSAmJiB0eXBlb2YgZmFpbHVyZSA9PT0gJ29iamVjdCcgPyAoZmFpbHVyZSBhcyB7IGNvZGU/OiB1bmtub3duIH0pLmNvZGUgOiB1bmRlZmluZWQ7XG4gIHJldHVybiB0eXBlb2YgY29kZSA9PT0gJ3N0cmluZycgJiYgL15bQS1aXVtBLVowLTlfXXswLDYzfSQvLnRlc3QoY29kZSkgPyBjb2RlIDogbnVsbDtcbn1cblxuZnVuY3Rpb24gdG9FdmVudFJvdyhldmVudDogSW5nZXN0RXZlbnQsIHJlZ2lzdHJ5OiB7IHBpcGVsaW5lSWQ6IHN0cmluZzsgb3JnSWQ6IHN0cmluZyB9LCBwbHVnaW46IFN0ZXBQbHVnaW4gfCB1bmRlZmluZWQsIGtleUlkOiBzdHJpbmcgfCB1bmRlZmluZWQpOiBQaXBlbGluZUV2ZW50SW5zZXJ0IHtcbiAgY29uc3QgZGV0YWlsID0gZXZlbnQuc291cmNlTWVzc2FnZUlkICE9PSB1bmRlZmluZWRcbiAgICA/IHsgLi4uKGV2ZW50LmRldGFpbCA/PyB7fSksIHNvdXJjZU1lc3NhZ2VJZDogZXZlbnQuc291cmNlTWVzc2FnZUlkIH1cbiAgICA6IGV2ZW50LmRldGFpbDtcbiAgcmV0dXJuIHtcbiAgICAvLyByZWdpc3RyeS5waXBlbGluZUlkID09PSBldmVudC5waXBlbGluZUlkOyB0aGUgcmVnaXN0cnkncyBpcyBhbHdheXMgYSByb3dcbiAgICAvLyB0aGF0IGV4aXN0cyAoRkspIGFuZCBpdHMgb3JnSWQgaXMgdGhlIHRydXN0ZWQgdGVuYW50LlxuICAgIHBpcGVsaW5lSWQ6IHJlZ2lzdHJ5LnBpcGVsaW5lSWQsXG4gICAgb3JnSWQ6IHJlZ2lzdHJ5Lm9yZ0lkLFxuICAgIGV2ZW50U291cmNlOiBldmVudC5ldmVudFNvdXJjZSxcbiAgICBldmVudFR5cGU6IGV2ZW50LmV2ZW50VHlwZSxcbiAgICBzdGF0dXM6IGV2ZW50LnN0YXR1cyxcbiAgICAvLyBBbiBBV1MtQVNTSUdORUQgVVVJRCwgbm90IGZyZWUtZm9ybSB0ZXh0OiBpdCBjYW4ndCBjYXJyeSBhbiBhY2NvdW50IGlkLFxuICAgIC8vIGFuZCBzY3J1YmJpbmcgYSAxMi1kaWdpdCBydW4gaW5zaWRlIGl0IHdvdWxkIGNvcnJ1cHQgdGhlIGNvcnJlbGF0aW9uIGtleS5cbiAgICBleGVjdXRpb25JZDogZXZlbnQuZXhlY3V0aW9uSWQsXG4gICAgLy8gVVNFUi1BVVRIT1JFRCBwaXBlbGluZS1zdHJ1Y3R1cmUgbmFtZXMg4oCUIHNhbWUgdW50cnVzdGVkIG9yaWdpbiBhc1xuICAgIC8vIGVycm9yTWVzc2FnZSwgc28gc2NydWJiZWQgKGEgc3RhZ2UgbmFtZWQgd2l0aCBhbiBBUk4gbXVzdCBub3QgcGVyc2lzdCkuXG4gICAgc3RhZ2VOYW1lOiBzY3J1Yk9wdGlvbmFsKGV2ZW50LnN0YWdlTmFtZSksXG4gICAgYWN0aW9uTmFtZTogc2NydWJPcHRpb25hbChldmVudC5hY3Rpb25OYW1lKSxcbiAgICAvLyBIQVJEIENPTlNUUkFJTlQ6IGFuIEFXUyBhY2NvdW50IGlkIG11c3QgTkVWRVIgYmUgcGVyc2lzdGVkLiBGYWlsdXJlIGRldGFpbFxuICAgIC8vIGFuZCBtZXNzYWdlcyByb3V0aW5lbHkgY2FycnkgQVJOcyBhbmQgYmFyZSAxMi1kaWdpdCBhY2NvdW50IGlkcy5cbiAgICBlcnJvck1lc3NhZ2U6IHNjcnViT3B0aW9uYWwoZXZlbnQuZXJyb3JNZXNzYWdlKSxcbiAgICBzdGFydGVkQXQ6IGV2ZW50LnN0YXJ0ZWRBdCA/IG5ldyBEYXRlKGV2ZW50LnN0YXJ0ZWRBdCkgOiB1bmRlZmluZWQsXG4gICAgY29tcGxldGVkQXQ6IGV2ZW50LmNvbXBsZXRlZEF0ID8gbmV3IERhdGUoZXZlbnQuY29tcGxldGVkQXQpIDogdW5kZWZpbmVkLFxuICAgIGR1cmF0aW9uTXM6IGV2ZW50LmR1cmF0aW9uTXMsXG4gICAgLy8gRGVwbG95IGF0dHJpYnV0aW9uIOKAlCBzY3J1YmJlZCBsaWtlIHRoZSBvdGhlciBmcmVlLWZvcm0gc3RyaW5ncy5cbiAgICBjb21taXRTaGE6IHNjcnViT3B0aW9uYWwoZXZlbnQuY29tbWl0U2hhKSxcbiAgICBjb21taXRSZWY6IHNjcnViT3B0aW9uYWwoZXZlbnQuY29tbWl0UmVmKSxcbiAgICBlbnZpcm9ubWVudDogc2NydWJPcHRpb25hbChldmVudC5lbnZpcm9ubWVudCksXG4gICAgLy8gTWVhc3VyZWQgbGVhZCB0aW1lOiB0aGUgb2xkZXN0IHVuc2hpcHBlZCBjb21taXQncyB0aW1lICsgdGhlIGNvdW50LiBBblxuICAgIC8vIFNDTS1kZXJpdmVkIGluc3RhbnQgYW5kIGEgcGxhaW4gaW50ZWdlciDigJQgbm90aGluZyB0byBzY3J1Yi5cbiAgICBjb21taXRUaW1lc3RhbXA6IGV2ZW50LmNvbW1pdFRpbWVzdGFtcCA/IG5ldyBEYXRlKGV2ZW50LmNvbW1pdFRpbWVzdGFtcCkgOiB1bmRlZmluZWQsXG4gICAgY29tbWl0Q291bnQ6IGV2ZW50LmNvbW1pdENvdW50LFxuICAgIC8vIE5VTEwgZm9yIG5vbi1wbHVnaW4gYWN0aW9ucyBhbmQgZm9yIHBpcGVsaW5lcyBkZXBsb3llZCB3aXRob3V0IGEgbWFuaWZlc3QuXG4gICAgcGx1Z2luUHVibGlzaGVyOiBwbHVnaW4/LnBsdWdpblB1Ymxpc2hlciA/PyBudWxsLFxuICAgIHBsdWdpblB1Ymxpc2hlcklkOiBwbHVnaW4/LnBsdWdpblB1Ymxpc2hlcklkID8/IG51bGwsXG4gICAgcGx1Z2luTmFtZTogcGx1Z2luPy5wbHVnaW5OYW1lID8/IG51bGwsXG4gICAgcGx1Z2luVmVyc2lvbjogcGx1Z2luPy5wbHVnaW5WZXJzaW9uID8/IG51bGwsXG4gICAgLy8gV0hBVCBLSU5EIG9mIHRoaW5nIGJyb2tlLCBjbGFzc2lmaWVkIGhlcmUgcmF0aGVyIHRoYW4gYXQgcmVhZCB0aW1lOiB0aGVcbiAgICAvLyBlcnJvciB0ZXh0IGlzIHNjcnViYmVkIGFib3ZlIGFuZCBldmVudHVhbGx5IHN3ZXB0IGJ5IHJldGVudGlvbiwgc28gYVxuICAgIC8vIGNhdGVnb3J5IGRlcml2ZWQgbGF0ZXIgd291bGQgaGF2ZSBub3RoaW5nIGxlZnQgdG8gcmVhZC4gTlVMTCBmb3IgYW55dGhpbmdcbiAgICAvLyB0aGF0IGlzIG5vdCBhIGZhaWx1cmUsIHNvIGl0cyBwcmVzZW5jZSBhbHdheXMgbWVhbnMgXCJ0aGlzIGJyb2tlXCIuXG4gICAgZmFpbHVyZUNhdGVnb3J5OiBjbGFzc2lmeUZhaWx1cmUoe1xuICAgICAgc3RhdHVzOiBldmVudC5zdGF0dXMsXG4gICAgICBlcnJvck1lc3NhZ2U6IHNjcnViT3B0aW9uYWwoZXZlbnQuZXJyb3JNZXNzYWdlKSxcbiAgICAgIGFjdGlvbk5hbWU6IHNjcnViT3B0aW9uYWwoZXZlbnQuYWN0aW9uTmFtZSksXG4gICAgICBzdGFnZU5hbWU6IHNjcnViT3B0aW9uYWwoZXZlbnQuc3RhZ2VOYW1lKSxcbiAgICAgIGZhaWx1cmVDb2RlOiBwYkZhaWx1cmVDb2RlKGV2ZW50LmRldGFpbCksXG4gICAgfSksXG4gICAgLy8gUHJvdmVuYW5jZS4gQm90aCBhcmUgb3BhcXVlIGlkcyDigJQgYW4gQVdTLWFzc2lnbmVkIGV2ZW50IFVVSUQgYW5kIG91ciBvd25cbiAgICAvLyBrZXkgaWQg4oCUIHNvIG5laXRoZXIgY2FuIGNhcnJ5IGFuIGFjY291bnQgaWQgYW5kIG5laXRoZXIgaXMgc2NydWJiZWRcbiAgICAvLyAoc2NydWJiaW5nIGEgZGlnaXQgcnVuIGluc2lkZSBvbmUgd291bGQgY29ycnVwdCB0aGUgY29ycmVsYXRpb24ga2V5KS5cbiAgICBzb3VyY2VFdmVudElkOiBldmVudC5zb3VyY2VFdmVudElkLFxuICAgIGluZ2VzdEtleUlkOiBrZXlJZCxcbiAgICBkZXRhaWw6IGRldGFpbCAhPT0gdW5kZWZpbmVkID8gc2NydWJBd3NJZGVudGlmaWVycyhkZXRhaWwpIDogdW5kZWZpbmVkLFxuICB9O1xufVxuXG4vKipcbiAqIEZhbiB0ZXJtaW5hbCBTVEFHRSBvdXRjb21lcyBhbmQgcGVyLUFDVElPTiBjb21wdXRlIGNvbnN1bXB0aW9uIGludG8gdGhlXG4gKiByb3V0ZSdzIG1ldHJpYyBob29rIChwaXBlbGluZS1kYXRhIGNhbid0IGltcG9ydCBhcGktc2VydmVyJ3MgcmVnaXN0cnkpIGFmdGVyXG4gKiB0aGUgaW5zZXJ0IGNvbW1pdHMuXG4gKlxuICogRHJpdmVuIG9mZiB0aGUgSU5TRVJURUQgcm93cywgc28gYSByZS1kZWxpdmVyZWQgZXZlbnQgdGhlIGRlZHVwIGluZGV4XG4gKiBzd2FsbG93ZWQgaXMgbmV2ZXIgY291bnRlZCB0d2ljZS4gVGhhdCBwcm9wZXJ0eSBpcyBsb2FkLWJlYXJpbmcgZm9yIHRoZVxuICogY29tcHV0ZSBzZXJpZXMgaW4gYSB3YXkgaXQgd2FzIG5vdCBmb3IgdGhlIHN0YWdlIG9uZTogYSBkdXBsaWNhdGVkIHN0YWdlXG4gKiBvdXRjb21lIGRpc3RvcnRzIGEgcmF0ZSwgd2hlcmVhcyBhIGR1cGxpY2F0ZWQgdkNQVS1taW51dGUgZmlndXJlIGlzIGFcbiAqIGRvdWJsZS1jaGFyZ2Ugd2FpdGluZyBmb3IgdGhlIGRheSB0aGUgY2hhcmdlIGlzIHN3aXRjaGVkIG9uLlxuICpcbiAqIEEgbm9uLW51bGwgZW52aXJvbm1lbnQgbWFya3MgYSBkZXBsb3kuXG4gKi9cbmZ1bmN0aW9uIGVtaXRJbmdlc3RNZXRyaWNzKFxuICByb3dzOiBSZWFkb25seUFycmF5PHtcbiAgICBvcmdJZDogc3RyaW5nO1xuICAgIHBpcGVsaW5lSWQ6IHN0cmluZyB8IG51bGw7XG4gICAgZXZlbnRUeXBlOiBzdHJpbmc7XG4gICAgc3RhdHVzOiBzdHJpbmc7XG4gICAgc3RhZ2VOYW1lOiBzdHJpbmcgfCBudWxsO1xuICAgIGVudmlyb25tZW50OiBzdHJpbmcgfCBudWxsO1xuICAgIGR1cmF0aW9uTXM/OiBudW1iZXIgfCBudWxsO1xuICAgIGRldGFpbD86IFJlY29yZDxzdHJpbmcsIHVua25vd24+IHwgbnVsbDtcbiAgfT4sXG4gIG9uTWV0cmljOiAobTogSW5nZXN0TWV0cmljKSA9PiB2b2lkLFxuKTogdm9pZCB7XG4gIGZvciAoY29uc3QgciBvZiByb3dzKSB7XG4gICAgaWYgKCFyLnBpcGVsaW5lSWQpIGNvbnRpbnVlO1xuXG4gICAgLy8gQ29tcHV0ZSBjb25zdW1wdGlvbjogZXZlcnkgVEVSTUlOQUwgYWN0aW9uLCBtZWFzdXJhYmxlIG9yIG5vdC4gVGhlXG4gICAgLy8gdW5tZWFzdXJhYmxlIG9uZXMgYXJlIHRoZSBwb2ludCDigJQgdGhleSBhcmUgd2hhdCB0aGUgY292ZXJhZ2UgcmF0aW8gY291bnRzLlxuICAgIGlmIChyLmV2ZW50VHlwZSA9PT0gJ0FDVElPTicgJiYgVEVSTUlOQUxfQUNUSU9OX1NUQVRFUy5pbmNsdWRlcyhyLnN0YXR1cykpIHtcbiAgICAgIGNvbnN0IGNvbXB1dGVUeXBlID0gbm9ybWFsaXplQ29tcHV0ZVR5cGUoXG4gICAgICAgIHR5cGVvZiByLmRldGFpbD8uY29tcHV0ZVR5cGUgPT09ICdzdHJpbmcnID8gci5kZXRhaWwuY29tcHV0ZVR5cGUgOiBudWxsLFxuICAgICAgKTtcbiAgICAgIGNvbnN0IGR1cmF0aW9uTXMgPSByLmR1cmF0aW9uTXMgPz8gbnVsbDtcbiAgICAgIG9uTWV0cmljKHtcbiAgICAgICAga2luZDogJ2NvbXB1dGUnLFxuICAgICAgICBwaXBlbGluZUlkOiByLnBpcGVsaW5lSWQsXG4gICAgICAgIG9yZ0lkOiByLm9yZ0lkLFxuICAgICAgICBjb21wdXRlVHlwZSxcbiAgICAgICAgZHVyYXRpb25NcyxcbiAgICAgICAgY3JlZGl0czogY29tcHV0ZUNyZWRpdHNGb3IoZHVyYXRpb25NcywgY29tcHV0ZVR5cGUpLFxuICAgICAgfSk7XG4gICAgICBjb250aW51ZTtcbiAgICB9XG5cbiAgICBpZiAoci5ldmVudFR5cGUgIT09ICdTVEFHRScgfHwgKHIuc3RhdHVzICE9PSAnU1VDQ0VFREVEJyAmJiByLnN0YXR1cyAhPT0gJ0ZBSUxFRCcpKSBjb250aW51ZTtcbiAgICBvbk1ldHJpYyh7XG4gICAgICBraW5kOiAnc3RhZ2UnLFxuICAgICAgcGlwZWxpbmVJZDogci5waXBlbGluZUlkLFxuICAgICAgb3JnSWQ6IHIub3JnSWQsXG4gICAgICBzdGFnZTogci5zdGFnZU5hbWUgPz8gJycsXG4gICAgICBlbnZpcm9ubWVudDogci5lbnZpcm9ubWVudCA/PyBudWxsLFxuICAgICAgcmVzdWx0OiByLnN0YXR1cyA9PT0gJ1NVQ0NFRURFRCcgPyAnc3VjY2VlZGVkJyA6ICdmYWlsZWQnLFxuICAgIH0pO1xuICB9XG59XG5cbi8qKiBBY3Rpb24gc3RhdGVzIHRoYXQgbWVhbiB0aGUgYWN0aW9uIGlzIG92ZXIgYW5kIGl0cyBjb25zdW1wdGlvbiBpcyBmaW5hbC4gKi9cbmNvbnN0IFRFUk1JTkFMX0FDVElPTl9TVEFURVM6IHJlYWRvbmx5IHN0cmluZ1tdID0gWydTVUNDRUVERUQnLCAnRkFJTEVEJywgJ1NUT1BQRUQnXTtcblxuLyoqXG4gKiBSZXNvbHZlIGluY29taW5nIGV2ZW50cyBhZ2FpbnN0IHRoZSBwaXBlbGluZSByZWdpc3RyeSwgYmF0Y2gtaW5zZXJ0IHRoZVxuICogbWF0Y2hlZCBvbmVzLCBhbmQgaW52YWxpZGF0ZSByZXBvcnRpbmcgY2FjaGVzIGZvciBhZmZlY3RlZCBvcmdzLlxuICogRXZlbnRzIGZvciB1bnJlZ2lzdGVyZWQgcGlwZWxpbmUgaWRzIGFyZSBkcm9wcGVkIChhbmQgbG9nZ2VkIGF0IFdBUk5cbiAqIHdpdGggc2FtcGxlIGlkcyBzbyBhbiBvcGVyYXRvciBjYW4gc2VlIHdoZW4gRXZlbnRCcmlkZ2UgaXMgZGVsaXZlcmluZ1xuICogZXZlbnRzIGZvciBwaXBlbGluZXMgdGhhdCBoYXZlbid0IGNhbGxlZCBQT1NUIC9waXBlbGluZXMvcmVnaXN0cnkgeWV0KS5cbiAqXG4gKiBSZXR1cm5zIGNvdW50cyArIGEgc2FtcGxlIG9mIHVucmVnaXN0ZXJlZCBwaXBlbGluZSBpZHMgZm9yIG9ic2VydmFiaWxpdHkuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBpbmdlc3RFdmVudHMoXG4gIGV2ZW50czogSW5nZXN0RXZlbnRbXSxcbiAgb25NZXRyaWM/OiAobTogSW5nZXN0TWV0cmljKSA9PiB2b2lkLFxuICBjYWxsZXI/OiBJbmdlc3RDYWxsZXIsXG4pOiBQcm9taXNlPEluZ2VzdFJlc3VsdD4ge1xuICAvLyBURU5BTkNZLiBBbiBldmVudCdzIG9yZyBjb21lcyBmcm9tIHRoZSBwaXBlbGluZSBSRUdJU1RSWSwgbm90IHRoZSB0b2tlbiwgc29cbiAgLy8gdGhlIHNjb3BlIGNoZWNrIGFsb25lIGxldCBhbnkgYHJlcG9ydGluZzppbmdlc3RgIGhvbGRlciBwb3N0IGV2ZW50cyBmb3JcbiAgLy8gYW5vdGhlciBvcmcncyBwaXBlbGluZSBpZCBhbmQgaGF2ZSB0aGVtIGF0dHJpYnV0ZWQgdGhlcmUuIGBjYWxsZXJgIGNhcnJpZXNcbiAgLy8gdGhlIG9yZyBpZHMgdGhpcyB0b2tlbiBtYXkgd3JpdGUgZm9yOyBhbnl0aGluZyBlbHNlIGlzIGRyb3BwZWQgYmVsb3cuXG4gIC8vXG4gIC8vIGBjYWxsZXJgIGlzIG9wdGlvbmFsIG9ubHkgc28gaW4tcHJvY2VzcyBjYWxsZXJzIHRoYXQgYWxyZWFkeSBydW5cbiAgLy8gY3Jvc3MtdGVuYW50ICh0ZXN0cywgYmFja2ZpbGxzKSBrZWVwIHdvcmtpbmcg4oCUIGFuIEFCU0VOVCBjYWxsZXIgbWVhbnMgXCJub1xuICAvLyByZXN0cmljdGlvblwiLCBhbmQgdGhlIHJvdXRlIGFsd2F5cyBzdXBwbGllcyBvbmUuIEEgY2FsbGVyIHdpdGggYW4gRU1QVFlcbiAgLy8gYWxsb3ctbGlzdCBhbmQgbm8gY3Jvc3NUZW5hbnQgZmxhZyB0aGVyZWZvcmUgZHJvcHMgZXZlcnl0aGluZywgd2hpY2ggaXMgdGhlXG4gIC8vIHJpZ2h0IGFuc3dlciB3aGVuIHRoZSByb3V0ZSBjb3VsZCBub3QgZXN0YWJsaXNoIHdobyBpcyB3cml0aW5nLlxuICBjb25zdCB1bnJlc3RyaWN0ZWQgPSBjYWxsZXIgPT09IHVuZGVmaW5lZCB8fCBjYWxsZXIuY3Jvc3NUZW5hbnQgPT09IHRydWU7XG4gIGNvbnN0IGFsbG93ZWQgPSBuZXcgU2V0KGNhbGxlcj8uYWxsb3dlZE9yZ0lkcyA/PyBbXSk7XG4gIC8vIE11bHRpLW9yZyBiYXRjaCBpbnNlcnQ6IHRoZSBjYWxsZXIgcmVzb2x2ZXMgdG8gbXVsdGlwbGUgb3JncyB2aWEgdGhlXG4gIC8vIHBpcGVsaW5lLXJlZ2lzdHJ5IGxvb2t1cCBiZWxvdywgc28gdGhlIHJvdXRlIGxheWVyIE1VU1QgZXN0YWJsaXNoIGFcbiAgLy8gYHJ1bldpdGhUZW5hbnRDb250ZXh0KHsgaXNTdXBlckFkbWluOiB0cnVlIH0sIC4uLilgIHNjb3BlIGJlZm9yZSBjYWxsaW5nXG4gIC8vIHRoaXMgZnVuY3Rpb24uIFVuZGVyIEZPUkNFJ2QgUkxTLCBhIHNpbmdsZSB0eCB3aXRoIGBhcHAub3JnX2lkID0gPG9uZVxuICAvLyBvcmc+YCBjb3VsZCBvbmx5IHdyaXRlIGV2ZW50cyBmb3IgdGhhdCBvcmc7IGJ5cGFzcyB2aWEgc3lzYWRtaW4gaXNcbiAgLy8gdGhlIHJpZ2h0IGdhdGUgZm9yIHRoaXMgc2VydmVyLWludGVybmFsIGNyb3NzLXRlbmFudCBlbmRwb2ludC4gU2VlXG4gIC8vIGFwaS9yZXBvcnRpbmcvc3JjL3JvdXRlcy9ldmVudC1pbmdlc3QudHMgZm9yIHRoZSB3cmFwcGVyLlxuICAvLyBDYWNoZXMgYXJlIGludmFsaWRhdGVkIEFGVEVSIHRoZSB0eCByZXNvbHZlczogZG9pbmcgaXQgaW5zaWRlIGhlbGQgdGhlIHBnXG4gIC8vIGxvY2tzIG9wZW4gYWNyb3NzIHVucmVsYXRlZCBjYWNoZSByb3VuZC10cmlwcy4gVGhlIFRUTCBpcyAyLTUgbWluLCBzbyBhXG4gIC8vIGZpcmUtYW5kLWZvcmdldCBwb3N0LWNvbW1pdCBpbnZhbGlkYXRpb24gaXMgYW4gYWNjZXB0YWJsZSB0cmFkZS5cbiAgY29uc3QgeyBpbnNlcnRlZCwgc2tpcHBlZCwgdW5yZWdpc3RlcmVkUGlwZWxpbmVJZHMsIGFmZmVjdGVkT3JncywgZHJvcHBlZEZvcmVpZ25PcmcsIGRyb3BwZWRJbnZhbGlkVGltZSwgZm9yZWlnblBpcGVsaW5lSWRzLCBpbnNlcnRlZFJvd3MgfSA9IGF3YWl0IHdpdGhUZW5hbnRUeChhc3luYyAodHgpID0+IHtcbiAgICAvLyBCYXRjaC1yZXNvbHZlIGFsbCB1bmlxdWUgcGlwZWxpbmUgaWRzIGluIG9uZSBxdWVyeVxuICAgIGNvbnN0IHVuaXF1ZUlkcyA9IFsuLi5uZXcgU2V0KGV2ZW50cy5tYXAoZSA9PiBlLnBpcGVsaW5lSWQpKV07XG4gICAgY29uc3QgcmVnaXN0cnlSb3dzID0gYXdhaXQgdHhcbiAgICAgIC5zZWxlY3Qoe1xuICAgICAgICBwaXBlbGluZUlkOiBzY2hlbWEucGlwZWxpbmVSZWdpc3RyeS5waXBlbGluZUlkLFxuICAgICAgICBvcmdJZDogc2NoZW1hLnBpcGVsaW5lUmVnaXN0cnkub3JnSWQsXG4gICAgICB9KVxuICAgICAgLmZyb20oc2NoZW1hLnBpcGVsaW5lUmVnaXN0cnkpXG4gICAgICAud2hlcmUoaW5BcnJheShzY2hlbWEucGlwZWxpbmVSZWdpc3RyeS5waXBlbGluZUlkLCB1bmlxdWVJZHMpKTtcblxuICAgIGNvbnN0IGlkTWFwID0gbmV3IE1hcChyZWdpc3RyeVJvd3MubWFwKHIgPT4gW3IucGlwZWxpbmVJZCwgcl0pKTtcbiAgICBjb25zdCBzdGVwUGx1Z2lucyA9IGF3YWl0IGxvYWRTdGVwUGx1Z2lucyh0eCwgZXZlbnRzLmZpbHRlcigoZSkgPT4gaXNBdHRyaWJ1dGFibGUoZSkgJiYgaWRNYXAuaGFzKGUucGlwZWxpbmVJZCkpKTtcblxuICAgIC8vIEJ1aWxkIGluc2VydCBiYXRjaCAoc2tpcCBldmVudHMgd2hvc2UgcGlwZWxpbmUgaXNuJ3QgcmVnaXN0ZXJlZClcbiAgICBjb25zdCByb3dzOiBQaXBlbGluZUV2ZW50SW5zZXJ0W10gPSBbXTtcbiAgICBsZXQgc2tpcHBlZExvY2FsID0gMDtcbiAgICBsZXQgZm9yZWlnbkxvY2FsID0gMDtcbiAgICBsZXQgaW52YWxpZFRpbWVMb2NhbCA9IDA7XG4gICAgY29uc3QgaW52YWxpZFRpbWVSZWFzb25zID0gbmV3IFNldDxzdHJpbmc+KCk7XG4gICAgY29uc3QgZm9yZWlnbk9yZ0lkcyA9IG5ldyBTZXQ8c3RyaW5nPigpO1xuICAgIGNvbnN0IGZvcmVpZ25QaXBlbGluZUlkc0xvY2FsID0gbmV3IFNldDxzdHJpbmc+KCk7XG4gICAgY29uc3QgdW5yZWdpc3RlcmVkTG9jYWw6IHN0cmluZ1tdID0gW107XG4gICAgLy8gT25lIGBub3dgIGZvciB0aGUgd2hvbGUgYmF0Y2g6IHBlci1ldmVudCBjbG9ja3Mgd291bGQgbGV0IGFuIGV2ZW50IHBhc3Mgb3JcbiAgICAvLyBmYWlsIGRlcGVuZGluZyBvbiB3aGVyZSBpdCBzYXQgaW4gdGhlIGxvb3AuXG4gICAgY29uc3Qgbm93TXMgPSBEYXRlLm5vdygpO1xuXG4gICAgZm9yIChjb25zdCBldmVudCBvZiBldmVudHMpIHtcbiAgICAgIGNvbnN0IHJlZ2lzdHJ5ID0gaWRNYXAuZ2V0KGV2ZW50LnBpcGVsaW5lSWQpO1xuICAgICAgaWYgKCFyZWdpc3RyeSkge1xuICAgICAgICBza2lwcGVkTG9jYWwrKztcbiAgICAgICAgdW5yZWdpc3RlcmVkTG9jYWwucHVzaChldmVudC5waXBlbGluZUlkKTtcbiAgICAgICAgY29udGludWU7XG4gICAgICB9XG4gICAgICAvLyBUaGUgcGlwZWxpbmUgcmVzb2x2ZXMgdG8gYW4gb3JnIHRoaXMgY2FsbGVyIG1heSBub3Qgd3JpdGUgZm9yLiBDb3VudGVkXG4gICAgICAvLyBzZXBhcmF0ZWx5IGZyb20gYHNraXBwZWRgIChhbiB1bnJlZ2lzdGVyZWQgaWQgaXMgYSBwcm9kdWNlciBydW5uaW5nXG4gICAgICAvLyBhaGVhZCBvZiByZWdpc3RyYXRpb247IHRoaXMgaXMgYSB0ZW5hbmN5IHJlZnVzYWwpIGFuZCBuZXZlciBpbnNlcnRlZC5cbiAgICAgIGlmICghdW5yZXN0cmljdGVkICYmICFhbGxvd2VkLmhhcyhyZWdpc3RyeS5vcmdJZCkpIHtcbiAgICAgICAgZm9yZWlnbkxvY2FsKys7XG4gICAgICAgIGZvcmVpZ25PcmdJZHMuYWRkKHJlZ2lzdHJ5Lm9yZ0lkKTtcbiAgICAgICAgZm9yZWlnblBpcGVsaW5lSWRzTG9jYWwuYWRkKGV2ZW50LnBpcGVsaW5lSWQpO1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cbiAgICAgIC8vIEltcG9zc2libGUgdGltZXN0YW1wcyBhcmUgcmVmdXNlZCBhdCB0aGUgYm91bmRhcnksIHNvIG5vIGRvd25zdHJlYW1cbiAgICAgIC8vIG1ldHJpYyBoYXMgdG8gY2xhbXAgYSBuZWdhdGl2ZSBnYXAgYW5kIGNhbGwgaXQgemVyby5cbiAgICAgIGNvbnN0IGJhZFRpbWUgPSBpbnZhbGlkRXZlbnRUaW1lcyhldmVudCwgbm93TXMpO1xuICAgICAgaWYgKGJhZFRpbWUpIHtcbiAgICAgICAgaW52YWxpZFRpbWVMb2NhbCsrO1xuICAgICAgICBpbnZhbGlkVGltZVJlYXNvbnMuYWRkKGJhZFRpbWUpO1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cbiAgICAgIGNvbnN0IHN0YWdlTmFtZSA9IHNjcnViT3B0aW9uYWwoZXZlbnQuc3RhZ2VOYW1lKTtcbiAgICAgIGNvbnN0IGFjdGlvbk5hbWUgPSBzY3J1Yk9wdGlvbmFsKGV2ZW50LmFjdGlvbk5hbWUpO1xuICAgICAgY29uc3Qgc3RlcCA9IGlzQXR0cmlidXRhYmxlKGV2ZW50KSAmJiBzdGFnZU5hbWUgJiYgYWN0aW9uTmFtZVxuICAgICAgICA/IHN0ZXBQbHVnaW5zLmdldChzdGVwS2V5KHJlZ2lzdHJ5LnBpcGVsaW5lSWQsIHN0YWdlTmFtZSwgYWN0aW9uTmFtZSkpXG4gICAgICAgIDogdW5kZWZpbmVkO1xuICAgICAgLy8gU2FtZS1vcmcgZ3VhcmQ6IGEgbWFuaWZlc3Qgcm93IGlzIG9ubHkgZXZlciB3cml0dGVuIGJ5IHRoZSBvcmcgdGhhdFxuICAgICAgLy8gb3ducyB0aGUgcGlwZWxpbmUsIGJ1dCB0aGUgaW5nZXN0IHJ1bnMgY3Jvc3MtdGVuYW50LCBzbyBkb24ndCBsZWFuIG9uIGl0LlxuICAgICAgcm93cy5wdXNoKHRvRXZlbnRSb3coZXZlbnQsIHJlZ2lzdHJ5LCBzdGVwICYmIHN0ZXAub3JnSWQgPT09IHJlZ2lzdHJ5Lm9yZ0lkID8gc3RlcCA6IHVuZGVmaW5lZCwgY2FsbGVyPy5rZXlJZCkpO1xuICAgIH1cblxuICAgIC8vIFNRUyBpcyBhdC1sZWFzdC1vbmNlLCBzbyBFdmVudEJyaWRnZSBjYW4gZGVsaXZlciB0aGUgc2FtZSBzdGF0ZS1jaGFuZ2VcbiAgICAvLyB0d2ljZS4gYG9uQ29uZmxpY3REb05vdGhpbmdgICsgdGhlIHBhcnRpYWwgdW5pcXVlIGluZGV4ZXMgb25cbiAgICAvLyAocGlwZWxpbmVfaWQsIGV4ZWN1dGlvbl9pZCwgZXZlbnRfdHlwZSwgc3RhdHVzLCBzdGFnZV9uYW1lLCBhY3Rpb25fbmFtZSlcbiAgICAvLyBhbmQgb24gc291cmNlX2V2ZW50X2lkICh0aGUgRXZlbnRCcmlkZ2UgaWQsIHdoZW4gcHJlc2VudCkgbWFrZVxuICAgIC8vIHJlLWRlbGl2ZXJ5IGlkZW1wb3RlbnQuIGByZXR1cm5pbmdgIGdpdmVzIHRoZSBSRUFMIGluc2VydGVkIHNldCBzb1xuICAgIC8vIGNvdW50cywgbWV0cmljcyBhbmQgY2FjaGUgaW52YWxpZGF0aW9uIGFsbCBpZ25vcmUgZHVwbGljYXRlcy5cbiAgICBjb25zdCBsYW5kZWQgPSByb3dzLmxlbmd0aCA+IDBcbiAgICAgID8gYXdhaXQgdHguaW5zZXJ0KHNjaGVtYS5waXBlbGluZUV2ZW50KS52YWx1ZXMocm93cylcbiAgICAgICAgLm9uQ29uZmxpY3REb05vdGhpbmcoKVxuICAgICAgICAucmV0dXJuaW5nKHtcbiAgICAgICAgICBvcmdJZDogc2NoZW1hLnBpcGVsaW5lRXZlbnQub3JnSWQsXG4gICAgICAgICAgcGlwZWxpbmVJZDogc2NoZW1hLnBpcGVsaW5lRXZlbnQucGlwZWxpbmVJZCxcbiAgICAgICAgICBldmVudFR5cGU6IHNjaGVtYS5waXBlbGluZUV2ZW50LmV2ZW50VHlwZSxcbiAgICAgICAgICBzdGF0dXM6IHNjaGVtYS5waXBlbGluZUV2ZW50LnN0YXR1cyxcbiAgICAgICAgICBzdGFnZU5hbWU6IHNjaGVtYS5waXBlbGluZUV2ZW50LnN0YWdlTmFtZSxcbiAgICAgICAgICBlbnZpcm9ubWVudDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuZW52aXJvbm1lbnQsXG4gICAgICAgICAgLy8gRm9yIHRoZSBwZXItZGVwbG95IHJvbGx1cCBiZWxvdzogZXZlcnl0aGluZyBgZG9yYV9kZXBsb3ltZW50c2AgbmVlZHMsXG4gICAgICAgICAgLy8gdGFrZW4gZnJvbSB0aGUgcm93cyB0aGF0IEFDVFVBTExZIGxhbmRlZCBzbyBhIHJlLWRlbGl2ZXJ5IGNhbm5vdFxuICAgICAgICAgIC8vIHByb2R1Y2UgYSBzZWNvbmQgZGVwbG95LlxuICAgICAgICAgIGV4ZWN1dGlvbklkOiBzY2hlbWEucGlwZWxpbmVFdmVudC5leGVjdXRpb25JZCxcbiAgICAgICAgICBjb21taXRTaGE6IHNjaGVtYS5waXBlbGluZUV2ZW50LmNvbW1pdFNoYSxcbiAgICAgICAgICBjb21taXRUaW1lc3RhbXA6IHNjaGVtYS5waXBlbGluZUV2ZW50LmNvbW1pdFRpbWVzdGFtcCxcbiAgICAgICAgICBjb21taXRDb3VudDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuY29tbWl0Q291bnQsXG4gICAgICAgICAgY29tcGxldGVkQXQ6IHNjaGVtYS5waXBlbGluZUV2ZW50LmNvbXBsZXRlZEF0LFxuICAgICAgICAgIHN0YXJ0ZWRBdDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuc3RhcnRlZEF0LFxuICAgICAgICAgIGNyZWF0ZWRBdDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuY3JlYXRlZEF0LFxuICAgICAgICAgIGRldGFpbDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuZGV0YWlsLFxuICAgICAgICAgIHNvdXJjZUV2ZW50SWQ6IHNjaGVtYS5waXBlbGluZUV2ZW50LnNvdXJjZUV2ZW50SWQsXG4gICAgICAgIH0pXG4gICAgICA6IFtdO1xuXG4gICAgLy8gTG9nIGluc2lkZSB0aGUgdHggc2NvcGUgd2hpbGUgdGhlIG9yZyBzZXQgaXMgaW4gaGFuZC4gV0FSTiwgbm90IGVycm9yOlxuICAgIC8vIGEgbWlzcm91dGVkIHByb2R1Y2VyIGlzIHRoZSBjb21tb24gY2F1c2UsIGJ1dCB0aGUgc2FtZSBsaW5lIGlzIHRoZSBvbmx5XG4gICAgLy8gc2lnbmFsIG9mIGFuIGluamVjdGlvbiBhdHRlbXB0LCBzbyBpdCBuYW1lcyB0aGUgb3JncyBpdCByZWZ1c2VkLlxuICAgIGlmIChmb3JlaWduTG9jYWwgPiAwKSB7XG4gICAgICBsb2dnZXIud2FybignRHJvcHBlZCBpbmdlc3QgZXZlbnRzIGZvciBvcmdzIHRoZSBjYWxsZXIgbWF5IG5vdCB3cml0ZSBmb3InLCB7XG4gICAgICAgIGRyb3BwZWQ6IGZvcmVpZ25Mb2NhbCxcbiAgICAgICAgZm9yZWlnbk9yZ0lkczogWy4uLmZvcmVpZ25PcmdJZHNdLFxuICAgICAgICBhbGxvd2VkT3JnSWRzOiBbLi4uYWxsb3dlZF0sXG4gICAgICB9KTtcbiAgICB9XG5cbiAgICBpZiAoaW52YWxpZFRpbWVMb2NhbCA+IDApIHtcbiAgICAgIGxvZ2dlci53YXJuKCdEcm9wcGVkIGluZ2VzdCBldmVudHMgd2l0aCBpbXBvc3NpYmxlIHRpbWVzdGFtcHMnLCB7XG4gICAgICAgIGRyb3BwZWQ6IGludmFsaWRUaW1lTG9jYWwsXG4gICAgICAgIHJlYXNvbnM6IFsuLi5pbnZhbGlkVGltZVJlYXNvbnNdLFxuICAgICAgfSk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgIGluc2VydGVkOiBsYW5kZWQubGVuZ3RoLFxuICAgICAgc2tpcHBlZDogc2tpcHBlZExvY2FsLFxuICAgICAgdW5yZWdpc3RlcmVkUGlwZWxpbmVJZHM6IHVucmVnaXN0ZXJlZExvY2FsLFxuICAgICAgYWZmZWN0ZWRPcmdzOiBbLi4ubmV3IFNldChsYW5kZWQubWFwKHIgPT4gci5vcmdJZCkpXSxcbiAgICAgIGRyb3BwZWRGb3JlaWduT3JnOiBmb3JlaWduTG9jYWwsXG4gICAgICBkcm9wcGVkSW52YWxpZFRpbWU6IGludmFsaWRUaW1lTG9jYWwsXG4gICAgICBmb3JlaWduUGlwZWxpbmVJZHM6IFsuLi5mb3JlaWduUGlwZWxpbmVJZHNMb2NhbF0sXG4gICAgICBpbnNlcnRlZFJvd3M6IGxhbmRlZCxcbiAgICB9O1xuICB9KTtcblxuICBpZiAob25NZXRyaWMpIGVtaXRJbmdlc3RNZXRyaWNzKGluc2VydGVkUm93cywgb25NZXRyaWMpO1xuXG4gIC8vIFBlci1kZXBsb3kgcm9sbHVwLiBBRlRFUiB0aGUgZXZlbnRzIGNvbW1pdCBhbmQgb3V0c2lkZSB0aGVpciB0cmFuc2FjdGlvbjogdGhlXG4gIC8vIGV2ZW50cyBhcmUgdGhlIGR1cmFibGUgcmVjb3JkIGFuZCBgZG9yYV9kZXBsb3ltZW50c2AgaXMgZGVyaXZlZCBmcm9tIHRoZW0sIHNvXG4gIC8vIGEgcm9sbHVwIGZhaWx1cmUgbXVzdCBub3Qgcm9sbCBiYWNrIGFuIGluZ2VzdCB0aGF0IHN1Y2NlZWRlZC4gUmVidWlsZGFibGVcbiAgLy8gZWl0aGVyIHdheS4gYHVwc2VydERlcGxveW1lbnRzYCBuZXZlciB0aHJvd3MgZm9yIHRoYXQgcmVhc29uLlxuICBhd2FpdCB1cHNlcnREZXBsb3ltZW50cyhpbnNlcnRlZFJvd3MpO1xuXG4gIC8vIFN1cmZhY2UgdGhlIHNpbGVudCBza2lwOiBhbiB1bnJlZ2lzdGVyZWQgcGlwZWxpbmUgaWQgdXN1YWxseSBtZWFucyB0aGVcbiAgLy8gcGlwZWxpbmUgaGFzbid0IGNhbGxlZCBQT1NUIC9waXBlbGluZXMvcmVnaXN0cnkgeWV0IChvciBpdHNcbiAgLy8gcGIucGlwZWxpbmUtaWQgdGFnIGlzIG1pc3NpbmcvdW5yZWFkYWJsZSBieSB0aGUgTGFtYmRhKS4gTG9nZ2luZyBpdFxuICAvLyBtYWtlcyBhIGJyb2tlbiBqb2luIHZpc2libGUgaW5zdGVhZCBvZiBsb29raW5nIGxpa2UgXCJubyBhY3Rpdml0eVwiLlxuICBpZiAodW5yZWdpc3RlcmVkUGlwZWxpbmVJZHMubGVuZ3RoID4gMCkge1xuICAgIGxvZ2dlci53YXJuKCdQaXBlbGluZSBldmVudHMgc2tpcHBlZDogcGlwZWxpbmUgaWQgbm90IGZvdW5kIGluIHJlZ2lzdHJ5Jywge1xuICAgICAgY291bnQ6IHVucmVnaXN0ZXJlZFBpcGVsaW5lSWRzLmxlbmd0aCxcbiAgICAgIHNhbXBsZTogdW5yZWdpc3RlcmVkUGlwZWxpbmVJZHMuc2xpY2UoMCwgMyksXG4gICAgfSk7XG4gIH1cblxuICAvLyBQb3N0LWNvbW1pdCBjYWNoZSBpbnZhbGlkYXRpb24uIEZpcmUtYW5kLWZvcmdldCB3aXRoIGxvZ2dpbmcg4oCUIFRUTCBpc1xuICAvLyBzaG9ydCBlbm91Z2ggdGhhdCBhIG1pc3NlZCBpbnZhbGlkYXRpb24gc2VsZi1oZWFscy5cbiAgaWYgKGFmZmVjdGVkT3Jncy5sZW5ndGggPiAwKSB7XG4gICAgdm9pZCBQcm9taXNlLmFsbChhZmZlY3RlZE9yZ3MubWFwKChvcmcpID0+XG4gICAgICBpbnZhbGlkYXRlT3JnUmVwb3J0cyhvcmcpLmNhdGNoKChlcnIpID0+IHtcbiAgICAgICAgbG9nZ2VyLndhcm4oJ1JlcG9ydGluZyBjYWNoZSBpbnZhbGlkYXRpb24gZmFpbGVkJywgeyBvcmdJZDogb3JnLCBlcnJvcjogZXJyb3JNZXNzYWdlKGVycikgfSk7XG4gICAgICB9KSxcbiAgICApKTtcbiAgfVxuXG4gIHJldHVybiB7XG4gICAgaW5zZXJ0ZWQsXG4gICAgc2tpcHBlZCxcbiAgICB1bnJlZ2lzdGVyZWRQaXBlbGluZUlkcyxcbiAgICBhZmZlY3RlZE9yZ3MsXG4gICAgZHJvcHBlZEZvcmVpZ25PcmcsXG4gICAgZHJvcHBlZEludmFsaWRUaW1lLFxuICAgIGZvcmVpZ25QaXBlbGluZUlkcyxcbiAgICBpbnNlcnRlZEV4ZWN1dGlvbklkczogWy4uLm5ldyBTZXQoaW5zZXJ0ZWRSb3dzLm1hcCgocikgPT4gci5leGVjdXRpb25JZCkuZmlsdGVyKChpZCk6IGlkIGlzIHN0cmluZyA9PiAhIWlkKSldLFxuICAgIGluc2VydGVkUGlwZWxpbmVJZHM6IFsuLi5uZXcgU2V0KGluc2VydGVkUm93cy5tYXAoKHIpID0+IHIucGlwZWxpbmVJZCkuZmlsdGVyKChpZCk6IGlkIGlzIHN0cmluZyA9PiAhIWlkKSldLFxuICB9O1xufVxuIl19
|
|
432
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5nZXN0LmpzIiwic291cmNlcyI6WyIuLi8uLi8uLi9zcmMvYXBpL3JlcG9ydGluZy9pbmdlc3QudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsK0NBQStDO0FBQy9DLHNDQUFzQztBQUV0Qzs7Ozs7O0dBTUc7QUFFSCxPQUFPLEVBQUUsaUJBQWlCLEVBQUUsWUFBWSxFQUFFLFlBQVksRUFBRSxvQkFBb0IsRUFBRSxtQkFBbUIsRUFBRSxNQUFNLDRCQUE0QixDQUFDO0FBQ3RJLE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSxhQUFhLENBQUM7QUFDdEMsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0sYUFBYSxDQUFDO0FBQ25ELE9BQU8sRUFBRSxpQkFBaUIsRUFBRSxNQUFNLG9CQUFvQixDQUFDO0FBQ3ZELE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSx5QkFBeUIsQ0FBQztBQUMxRCxPQUFPLEVBQUUsYUFBYSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFDakQsT0FBTyxFQUNMLG1CQUFtQixFQUFFLDBCQUEwQixFQUFFLG9CQUFvQixFQUFFLG1CQUFtQixFQUFFLGlCQUFpQixFQUM3RyxrQkFBa0IsR0FDbkIsTUFBTSxxQkFBcUIsQ0FBQztBQUU3QixPQUFPLEVBQUUsTUFBTSxFQUFFLE1BQU0sa0NBQWtDLENBQUM7QUFDMUQsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLDJCQUEyQixDQUFDO0FBR3pELE1BQU0sTUFBTSxHQUFHLFlBQVksQ0FBQyxrQkFBa0IsQ0FBQyxDQUFDO0FBY2hELHFFQUFxRTtBQUNyRSxTQUFTLGNBQWMsQ0FBQyxDQUFjO0lBQ3BDLE9BQU8sQ0FBQyxDQUFDLENBQUMsU0FBUyxLQUFLLFFBQVEsSUFBSSxDQUFDLENBQUMsU0FBUyxLQUFLLE9BQU8sQ0FBQztXQUN2RCxDQUFDLENBQUMsQ0FBQyxXQUFXLEtBQUssY0FBYyxJQUFJLENBQUMsQ0FBQyxXQUFXLEtBQUssV0FBVyxDQUFDO1dBQ25FLENBQUMsQ0FBQyxDQUFDLENB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Q0FBQyxDQUFDLEVBQUUsRUFBZ0IsRUFBRSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDO1FBQzdHLG1CQUFtQixFQUFFLENBQUMsR0FBRyxJQUFJLEdBQUcsQ0FBQyxZQUFZLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxFQUFFLEVBQUUsQ0FBQyxDQUFDLENBQUMsVUFBVSxDQUFDLENBQUMsTUFBTSxDQUFDLENBQUMsRUFBRSxFQUFnQixFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUM7S0FDNUcsQ0FBQztBQUNKLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvLyBDb3B5cmlnaHQgMjAyNiBQaXBlbGluZSBCdWlsZGVyIENvbnRyaWJ1dG9yc1xuLy8gU1BEWC1MaWNlbnNlLUlkZW50aWZpZXI6IEFwYWNoZS0yLjBcblxuLyoqXG4gKiBFdmVudCBpbmdlc3Q6IHRoZSBXUklURSBoYWxmIG9mIHJlcG9ydGluZy4gUmVzb2x2ZXMgaW5jb21pbmcgcGlwZWxpbmUgZXZlbnRzXG4gKiBhZ2FpbnN0IHRoZSBwaXBlbGluZSByZWdpc3RyeSwgc2NydWJzIGV2ZXJ5IGZyZWUtZm9ybSBzdHJpbmcsIGJhdGNoLWluc2VydHNcbiAqIHRoZSBtYXRjaGVkIHJvd3MgaWRlbXBvdGVudGx5LCBhbmQgaW52YWxpZGF0ZXMgdGhlIGFmZmVjdGVkIG9yZ3MnIHJlcG9ydFxuICogY2FjaGVzLiBTZXBhcmF0ZSBmcm9tIHRoZSByZXBvcnQgcXVlcmllcyBiZWNhdXNlIHRoaXMgaXMgcmVwb3J0aW5nJ3Mgb25seVxuICogZHVyYWJsZSBwZXJzaXN0ZW5jZSBib3VuZGFyeSDigJQgZXZlcnl0aGluZyBlbHNlIGluIHRoZSBzZXJ2aWNlIG9ubHkgcmVhZHMuXG4gKi9cblxuaW1wb3J0IHsgY29tcHV0ZUNyZWRpdHNGb3IsIGNyZWF0ZUxvZ2dlciwgZXJyb3JNZXNzYWdlLCBub3JtYWxpemVDb21wdXRlVHlwZSwgc2NydWJBd3NJZGVudGlmaWVycyB9IGZyb20gJ0BwaXBlbGluZS1idWlsZGVyL2FwaS1jb3JlJztcbmltcG9ydCB7IGluQXJyYXkgfSBmcm9tICdkcml6emxlLW9ybSc7XG5pbXBvcnQgeyBpbnZhbGlkYXRlT3JnUmVwb3J0cyB9IGZyb20gJy4vY2FjaGVzLmpzJztcbmltcG9ydCB7IHVwc2VydERlcGxveW1lbnRzIH0gZnJvbSAnLi9kZXBsb3ktcm9sbHVwLmpzJztcbmltcG9ydCB7IGNsYXNzaWZ5RmFpbHVyZSB9IGZyb20gJy4vZmFpbHVyZS1jbGFzc2lmaWVyLmpzJztcbmltcG9ydCB7IHNjcnViT3B0aW9uYWwgfSBmcm9tICcuL3NxbC1oZWxwZXJzLmpzJztcbmltcG9ydCB7XG4gIGRlcGxveWVkVG9vbGNoYWluT2YsIHJlYWRQbGF0Zm9ybURlZmF1bHRSZWxlYXNlLCBTRUxGX01VVEFUSU9OX0FDVElPTiwgU0VMRl9NVVRBVElPTl9TVEFHRSwgdG9vbGNoYWluQWN0aW9uT2YsXG4gIHRvb2xjaGFpbk91dGNvbWVPZiwgdHlwZSBEZXBsb3llZFRvb2xjaGFpbixcbn0gZnJvbSAnLi90b29sY2hhaW4tcnVucy5qcyc7XG5pbXBvcnQgdHlwZSB7IEluZ2VzdENhbGxlciwgSW5nZXN0RXZlbnQsIEluZ2VzdE1ldHJpYywgSW5nZXN0UmVzdWx0IH0gZnJvbSAnLi90eXBlcy5qcyc7XG5pbXBvcnQgeyBzY2hlbWEgfSBmcm9tICcuLi8uLi9kYXRhYmFzZS9kcml6emxlLXNjaGVtYS5qcyc7XG5pbXBvcnQgeyB3aXRoVGVuYW50VHggfSBmcm9tICcuLi8uLi9kYXRhYmFzZS90ZW5hbmN5LmpzJztcbmltcG9ydCB0eXBlIHsgQ3J1ZFR4IH0gZnJvbSAnLi4vY3J1ZC1zZXJ2aWNlLmpzJztcblxuY29uc3QgbG9nZ2VyID0gY3JlYXRlTG9nZ2VyKCdyZXBvcnRpbmctaW5nZXN0Jyk7XG5cbnR5cGUgUGlwZWxpbmVFdmVudEluc2VydCA9IHR5cGVvZiBzY2hlbWEucGlwZWxpbmVFdmVudC4kaW5mZXJJbnNlcnQ7XG5cblxuLyoqIFRoZSBwbHVnaW4gYSBwaXBlbGluZSBzdGVwIHJ1bnMsIGZyb20gdGhlIHN0ZXAgbWFuaWZlc3QgaXRzIGxhc3QgZGVwbG95IHJlZ2lzdGVyZWQuICovXG5pbnRlcmZhY2UgU3RlcFBsdWdpbiB7XG4gIG9yZ0lkOiBzdHJpbmc7XG4gIHBsdWdpblB1Ymxpc2hlcjogc3RyaW5nIHwgbnVsbDtcbiAgcGx1Z2luUHVibGlzaGVySWQ6IHN0cmluZyB8IG51bGw7XG4gIHBsdWdpbk5hbWU6IHN0cmluZyB8IG51bGw7XG4gIHBsdWdpblZlcnNpb246IHN0cmluZyB8IG51bGw7XG59XG5cbi8qKiBBbiBhY3Rpb24vYnVpbGQgZXZlbnQgdGhhdCBjYW4gYmUgYXR0cmlidXRlZCB0byBhIHBsdWdpbiBzdGVwLiAqL1xuZnVuY3Rpb24gaXNBdHRyaWJ1dGFibGUoZTogSW5nZXN0RXZlbnQpOiBib29sZWFuIHtcbiAgcmV0dXJuIChlLmV2ZW50VHlwZSA9PT0gJ0FDVElPTicgfHwgZS5ldmVudFR5cGUgPT09ICdCVUlMRCcpXG4gICAgJiYgKGUuZXZlbnRTb3VyY2UgPT09ICdjb2RlcGlwZWxpbmUnIHx8IGUuZXZlbnRTb3VyY2UgPT09ICdjb2RlYnVpbGQnKVxuICAgICYmICEhZS5zdGFnZU5hbWUgJiYgISFlLmFjdGlvbk5hbWU7XG59XG5cbmZ1bmN0aW9uIHN0ZXBLZXkocGlwZWxpbmVJZDogc3RyaW5nLCBzdGFnZU5hbWU6IHN0cmluZywgYWN0aW9uTmFtZTogc3RyaW5nKTogc3RyaW5nIHtcbiAgcmV0dXJuIGAke3BpcGVsaW5lSWR9XFx1MDAwMCR7c3RhZ2VOYW1lfVxcdTAwMDAke2FjdGlvbk5hbWV9YDtcbn1cblxuLyoqXG4gKiBQbHVnaW4gYXR0cmlidXRpb24gQU5EIHRoZSBkZXBsb3llZCB0b29sY2hhaW4gcmVsZWFzZTogdGhlIHN0ZXAgbWFuaWZlc3RzIG9mXG4gKiBldmVyeSBwaXBlbGluZSB3aXRoIGFuIGF0dHJpYnV0YWJsZSBldmVudCwgaW4gT05FIHJlYWQgcGVyIGJhdGNoLCBrZXllZCBmb3JcbiAqIGFuIGluLW1lbW9yeSBqb2luLiBOYW1lcyBhcmUgY29tcGFyZWQgcG9zdC1zY3J1YiBvbiBib3RoIHNpZGVzICh0aGUgbWFuaWZlc3RcbiAqIHN0b3JlcyB0aGVtIHNjcnViYmVkIHRoZSBzYW1lIHdheSkuXG4gKlxuICogVGhlIHRvb2xjaGFpbiBtYXAgaXMgdGhlIFBMQVRGT1JNJ3MgcmVjb3JkIG9mIHdoYXQgd2FzIGRlcGxveWVkICh0aGVcbiAqIG1hbmlmZXN0J3MgYGJ1aWxkLWltYWdlYCBlbnRyeSkg4oCUIHRoZSBvbmx5IHNvdXJjZSB0aGUgwqc3IHJ1biBzdGFtcCBtYXkgdXNlLlxuICovXG5hc3luYyBmdW5jdGlvbiBsb2FkU3RlcFBsdWdpbnModHg6IENydWRUeCwgYXR0cmlidXRhYmxlOiBJbmdlc3RFdmVudFtdKTogUHJvbWlzZTx7IHN0ZXBzOiBNYXA8c3RyaW5nLCBTdGVwUGx1Z2luPjsgdG9vbGNoYWluOiBNYXA8c3RyaW5nLCBEZXBsb3llZFRvb2xjaGFpbj4gfT4ge1xuICBjb25zdCBwaXBlbGluZUlkcyA9IFsuLi5uZXcgU2V0KGF0dHJpYnV0YWJsZS5tYXAoKGUpID0+IGUucGlwZWxpbmVJZCkpXTtcbiAgaWYgKHBpcGVsaW5lSWRzLmxlbmd0aCA9PT0gMCkgcmV0dXJuIHsgc3RlcHM6IG5ldyBNYXAoKSwgdG9vbGNoYWluOiBuZXcgTWFwKCkgfTtcbiAgY29uc3Qgcm93cyA9IGF3YWl0IHR4XG4gICAgLnNlbGVjdCh7XG4gICAgICBwaXBlbGluZUlkOiBzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3QucGlwZWxpbmVJZCxcbiAgICAgIG9yZ0lkOiBzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3Qub3JnSWQsXG4gICAgICBzdGFnZU5hbWU6IHNjaGVtYS5waXBlbGluZVN0ZXBNYW5pZmVzdC5zdGFnZU5hbWUsXG4gICAgICBhY3Rpb25OYW1lOiBzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3QuYWN0aW9uTmFtZSxcbiAgICAgIHBsdWdpblB1Ymxpc2hlcjogc2NoZW1hLnBpcGVsaW5lU3RlcE1hbmlmZXN0LnBsdWdpblB1Ymxpc2hlcixcbiAgICAgIHBsdWdpblB1Ymxpc2hlcklkOiBzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3QucGx1Z2luUHVibGlzaGVySWQsXG4gICAgICBwbHVnaW5OYW1lOiBzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3QucGx1Z2luTmFtZSxcbiAgICAgIHBsdWdpblZlcnNpb246IHNjaGVtYS5waXBlbGluZVN0ZXBNYW5pZmVzdC5wbHVnaW5WZXJzaW9uLFxuICAgICAgc3RlcEtleTogc2NoZW1hLnBpcGVsaW5lU3RlcE1hbmlmZXN0LnN0ZXBLZXksXG4gICAgfSlcbiAgICAuZnJvbShzY2hlbWEucGlwZWxpbmVTdGVwTWFuaWZlc3QpXG4gICAgLndoZXJlKGluQXJyYXkoc2NoZW1hLnBpcGVsaW5lU3RlcE1hbmlmZXN0LnBpcGVsaW5lSWQsIHBpcGVsaW5lSWRzKSk7XG4gIHJldHVybiB7XG4gICAgc3RlcHM6IG5ldyBNYXAocm93cy5tYXAoKG0pID0+IFtzdGVwS2V5KG0ucGlwZWxpbmVJZCwgbS5zdGFnZU5hbWUsIG0uYWN0aW9uTmFtZSksIG1dKSksXG4gICAgdG9vbGNoYWluOiBkZXBsb3llZFRvb2xjaGFpbk9mKHJvd3MpLFxuICB9O1xufVxuXG4vKipcbiAqIEFsbG93YW5jZSBmb3IgY2xvY2sgc2tldyBiZXR3ZWVuIGFuIEFXUyBldmVudCdzIHNvdXJjZSBjbG9jayBhbmQgb3Vycy4gQSByZWFsXG4gKiBDb2RlUGlwZWxpbmUgZXZlbnQgY2FuIGNhcnJ5IGEgdGltZXN0YW1wIGEgbGl0dGxlIGFoZWFkIG9mIG91ciBgbm93YDsgd2l0aG91dFxuICogc29tZSB0b2xlcmFuY2UgdGhlIHZhbGlkYXRpb24gYmVsb3cgd291bGQgZHJvcCBoZWFsdGh5IGV2ZW50cyBkdXJpbmcgbm9ybWFsXG4gKiBOVFAgZHJpZnQsIHdoaWNoIGlzIGZhciB3b3JzZSB0aGFuIGFkbWl0dGluZyBhIGZldyBzZWNvbmRzIG9mIHNrZXcuXG4gKi9cbmNvbnN0IENMT0NLX1NLRVdfVE9MRVJBTkNFX01TID0gNSAqIDYwICogMTAwMDtcblxuLyoqXG4gKiBXaHkgdGhpcyBldmVudCdzIHRpbWVzdGFtcHMgYXJlIGltcG9zc2libGUsIG9yIG51bGwgd2hlbiB0aGV5IGFyZSB1c2FibGUuXG4gKlxuICogQ2hlY2tlZCBhdCBJTkdFU1Qg4oCUIHRoZSBkdXJhYmxlIGJvdW5kYXJ5IOKAlCByYXRoZXIgdGhhbiBjbGFtcGVkIHdoZW4gdGhlIG1ldHJpY3NcbiAqIGFyZSBjb21wdXRlZC4gQSBuZWdhdGl2ZSBkdXJhdGlvbiBvciBhIGZ1dHVyZSBkZXBsb3kgdXNlZCB0byBiZSBjbGFtcGVkIHRvIDBcbiAqIGRvd25zdHJlYW0sIHdoaWNoIHJlcG9ydGVkIGEgYnJva2VuIGNsb2NrIGFzIGFuIGluc3RhbnQgZGVwbG95IGFuZCBxdWlldGx5XG4gKiBtb3ZlZCBkZXBsb3ltZW50IGZyZXF1ZW5jeSwgY2hhbmdlLWZhaWx1cmUgcmF0ZSBhbmQgbGVhZCB0aW1lIGZvciB0aGUgb3JnLlxuICpcbiAqIE5PVCBjaGVja2VkIGhlcmU6IGNvbW1pdCB0aW1lIHZzIGRlcGxveSBjb21wbGV0aW9uLiBgY29tbWl0X3RpbWVzdGFtcGAgcmlkZXMgdGhlXG4gKiBQSVBFTElORS9zb3VyY2UgZXZlbnQgd2hpbGUgdGhlIGRlcGxveSdzIGBjb21wbGV0ZWRfYXRgIGlzIG9uIGEgc2VwYXJhdGUgU1RBR0VcbiAqIHJvdywgam9pbmVkIGJ5IGBleGVjdXRpb25faWRgIG9ubHkgd2hlbiBET1JBIGlzIHF1ZXJpZWQg4oCUIHNvIG5vIHNpbmdsZSBldmVudFxuICogY2FycmllcyBib3RoLCBhbmQgdGhhdCBvcmRlcmluZyBjYW4gb25seSBiZSBndWFyZGVkIHdoZXJlIHRoZSB0d28gbWVldC5cbiAqL1xuZnVuY3Rpb24gaW52YWxpZEV2ZW50VGltZXMoZXZlbnQ6IEluZ2VzdEV2ZW50LCBub3dNczogbnVtYmVyKTogc3RyaW5nIHwgbnVsbCB7XG4gIGNvbnN0IGNlaWxpbmcgPSBub3dNcyArIENMT0NLX1NLRVdfVE9MRVJBTkNFX01TO1xuICBjb25zdCBwYXJzZWQ6IEFycmF5PFtzdHJpbmcsIG51bWJlcl0+ID0gW107XG4gIGZvciAoY29uc3QgZmllbGQgb2YgWydzdGFydGVkQXQnLCAnY29tcGxldGVkQXQnLCAnY29tbWl0VGltZXN0YW1wJ10gYXMgY29uc3QpIHtcbiAgICBjb25zdCByYXcgPSBldmVudFtmaWVsZF07XG4gICAgaWYgKHJhdyA9PT0gdW5kZWZpbmVkIHx8IHJhdyA9PT0gbnVsbCkgY29udGludWU7XG4gICAgY29uc3QgbXMgPSBEYXRlLnBhcnNlKFN0cmluZyhyYXcpKTtcbiAgICBpZiAoIU51bWJlci5pc0Zpbml0ZShtcykpIHJldHVybiBgJHtmaWVsZH0gaXMgbm90IGEgcGFyc2VhYmxlIHRpbWVzdGFtcGA7XG4gICAgaWYgKG1zID4gY2VpbGluZykgcmV0dXJuIGAke2ZpZWxkfSBpcyBpbiB0aGUgZnV0dXJlYDtcbiAgICBwYXJzZWQucHVzaChbZmllbGQsIG1zXSk7XG4gIH1cbiAgY29uc3Qgc3RhcnRlZCA9IHBhcnNlZC5maW5kKChbZl0pID0+IGYgPT09ICdzdGFydGVkQXQnKT8uWzFdO1xuICBjb25zdCBjb21wbGV0ZWQgPSBwYXJzZWQuZmluZCgoW2ZdKSA9PiBmID09PSAnY29tcGxldGVkQXQnKT8uWzFdO1xuICBpZiAoc3RhcnRlZCAhPT0gdW5kZWZpbmVkICYmIGNvbXBsZXRlZCAhPT0gdW5kZWZpbmVkICYmIGNvbXBsZXRlZCA8IHN0YXJ0ZWQpIHtcbiAgICByZXR1cm4gJ2NvbXBsZXRlZEF0IGlzIGJlZm9yZSBzdGFydGVkQXQnO1xuICB9XG4gIGlmIChldmVudC5kdXJhdGlvbk1zICE9PSB1bmRlZmluZWQgJiYgZXZlbnQuZHVyYXRpb25NcyAhPT0gbnVsbCAmJiBldmVudC5kdXJhdGlvbk1zIDwgMCkge1xuICAgIHJldHVybiAnZHVyYXRpb25NcyBpcyBuZWdhdGl2ZSc7XG4gIH1cbiAgcmV0dXJuIG51bGw7XG59XG5cbi8qKlxuICogVGhlIHBlcnNpc3RlZCByb3cgZm9yIG9uZSBpbmdlc3RlZCBldmVudC4gVGhpcyBpcyB0aGUgRFVSQUJMRSBwZXJzaXN0ZW5jZVxuICogYm91bmRhcnk6IGV2ZXJ5IHVzZXIvQVdTLWRlcml2ZWQgZnJlZS1mb3JtIHN0cmluZyBpcyBzY3J1YmJlZCBoZXJlLCBhbmRcbiAqIHRlbmFuY3kgY29tZXMgZnJvbSB0aGUgcGlwZWxpbmUgcmVnaXN0cnksIG5ldmVyIHRoZSBjYWxsZXIncyBjbGFpbWVkIG9yZy5cbiAqL1xuLyoqIFRoZSBzeW50aCByZWZ1c2FsIGNvZGUgdGhlIGV2ZW50cyBMYW1iZGEgYXR0YWNoZWQgKGBkZXRhaWwucGJGYWlsdXJlLmNvZGVgKSwgaWYgYW55LiAqL1xuZnVuY3Rpb24gcGJGYWlsdXJlQ29kZShkZXRhaWw6IFJlY29yZDxzdHJpbmcsIHVua25vd24+IHwgdW5kZWZpbmVkKTogc3RyaW5nIHwgbnVsbCB7XG4gIGNvbnN0IGZhaWx1cmUgPSBkZXRhaWw/LnBiRmFpbHVyZTtcbiAgY29uc3QgY29kZSA9IGZhaWx1cmUgJiYgdHlwZW9mIGZhaWx1cmUgPT09ICdvYmplY3QnID8gKGZhaWx1cmUgYXMgeyBjb2RlPzogdW5rbm93biB9KS5jb2RlIDogdW5kZWZpbmVkO1xuICByZXR1cm4gdHlwZW9mIGNvZGUgPT09ICdzdHJpbmcnICYmIC9eW0EtWl1bQS1aMC05X117MCw2M30kLy50ZXN0KGNvZGUpID8gY29kZSA6IG51bGw7XG59XG5cbmZ1bmN0aW9uIHRvRXZlbnRSb3coXG4gIGV2ZW50OiBJbmdlc3RFdmVudCxcbiAgcmVnaXN0cnk6IHsgcGlwZWxpbmVJZDogc3RyaW5nOyBvcmdJZDogc3RyaW5nIH0sXG4gIHBsdWdpbjogU3RlcFBsdWdpbiB8IHVuZGVmaW5lZCxcbiAga2V5SWQ6IHN0cmluZyB8IHVuZGVmaW5lZCxcbiAgdG9vbGNoYWluUmVsZWFzZTogc3RyaW5nIHwgbnVsbCxcbik6IFBpcGVsaW5lRXZlbnRJbnNlcnQge1xuICBjb25zdCBkZXRhaWwgPSBldmVudC5zb3VyY2VNZXNzYWdlSWQgIT09IHVuZGVmaW5lZFxuICAgID8geyAuLi4oZXZlbnQuZGV0YWlsID8/IHt9KSwgc291cmNlTWVzc2FnZUlkOiBldmVudC5zb3VyY2VNZXNzYWdlSWQgfVxuICAgIDogZXZlbnQuZGV0YWlsO1xuICByZXR1cm4ge1xuICAgIC8vIHJlZ2lzdHJ5LnBpcGVsaW5lSWQgPT09IGV2ZW50LnBpcGVsaW5lSWQ7IHRoZSByZWdpc3RyeSdzIGlzIGFsd2F5cyBhIHJvd1xuICAgIC8vIHRoYXQgZXhpc3RzIChGSykgYW5kIGl0cyBvcmdJZCBpcyB0aGUgdHJ1c3RlZCB0ZW5hbnQuXG4gICAgcGlwZWxpbmVJZDogcmVnaXN0cnkucGlwZWxpbmVJZCxcbiAgICBvcmdJZDogcmVnaXN0cnkub3JnSWQsXG4gICAgZXZlbnRTb3VyY2U6IGV2ZW50LmV2ZW50U291cmNlLFxuICAgIGV2ZW50VHlwZTogZXZlbnQuZXZlbnRUeXBlLFxuICAgIHN0YXR1czogZXZlbnQuc3RhdHVzLFxuICAgIC8vIEFuIEFXUy1BU1NJR05FRCBVVUlELCBub3QgZnJlZS1mb3JtIHRleHQ6IGl0IGNhbid0IGNhcnJ5IGFuIGFjY291bnQgaWQsXG4gICAgLy8gYW5kIHNjcnViYmluZyBhIDEyLWRpZ2l0IHJ1biBpbnNpZGUgaXQgd291bGQgY29ycnVwdCB0aGUgY29ycmVsYXRpb24ga2V5LlxuICAgIGV4ZWN1dGlvbklkOiBldmVudC5leGVjdXRpb25JZCxcbiAgICAvLyBVU0VSLUFVVEhPUkVEIHBpcGVsaW5lLXN0cnVjdHVyZSBuYW1lcyDigJQgc2FtZSB1bnRydXN0ZWQgb3JpZ2luIGFzXG4gICAgLy8gZXJyb3JNZXNzYWdlLCBzbyBzY3J1YmJlZCAoYSBzdGFnZSBuYW1lZCB3aXRoIGFuIEFSTiBtdXN0IG5vdCBwZXJzaXN0KS5cbiAgICBzdGFnZU5hbWU6IHNjcnViT3B0aW9uYWwoZXZlbnQuc3RhZ2VOYW1lKSxcbiAgICBhY3Rpb25OYW1lOiBzY3J1Yk9wdGlvbmFsKGV2ZW50LmFjdGlvbk5hbWUpLFxuICAgIC8vIEhBUkQgQ09OU1RSQUlOVDogYW4gQVdTIGFjY291bnQgaWQgbXVzdCBORVZFUiBiZSBwZXJzaXN0ZWQuIEZhaWx1cmUgZGV0YWlsXG4gICAgLy8gYW5kIG1lc3NhZ2VzIHJvdXRpbmVseSBjYXJyeSBBUk5zIGFuZCBiYXJlIDEyLWRpZ2l0IGFjY291bnQgaWRzLlxuICAgIGVycm9yTWVzc2FnZTogc2NydWJPcHRpb25hbChldmVudC5lcnJvck1lc3NhZ2UpLFxuICAgIHN0YXJ0ZWRBdDogZXZlbnQuc3RhcnRlZEF0ID8gbmV3IERhdGUoZXZlbnQuc3RhcnRlZEF0KSA6IHVuZGVmaW5lZCxcbiAgICBjb21wbGV0ZWRBdDogZXZlbnQuY29tcGxldGVkQXQgPyBuZXcgRGF0ZShldmVudC5jb21wbGV0ZWRBdCkgOiB1bmRlZmluZWQsXG4gICAgZHVyYXRpb25NczogZXZlbnQuZHVyYXRpb25NcyxcbiAgICAvLyBEZXBsb3kgYXR0cmlidXRpb24g4oCUIHNjcnViYmVkIGxpa2UgdGhlIG90aGVyIGZyZWUtZm9ybSBzdHJpbmdzLlxuICAgIGNvbW1pdFNoYTogc2NydWJPcHRpb25hbChldmVudC5jb21taXRTaGEpLFxuICAgIGNvbW1pdFJlZjogc2NydWJPcHRpb25hbChldmVudC5jb21taXRSZWYpLFxuICAgIGVudmlyb25tZW50OiBzY3J1Yk9wdGlvbmFsKGV2ZW50LmVudmlyb25tZW50KSxcbiAgICAvLyBNZWFzdXJlZCBsZWFkIHRpbWU6IHRoZSBvbGRlc3QgdW5zaGlwcGVkIGNvbW1pdCdzIHRpbWUgKyB0aGUgY291bnQuIEFuXG4gICAgLy8gU0NNLWRlcml2ZWQgaW5zdGFudCBhbmQgYSBwbGFpbiBpbnRlZ2VyIOKAlCBub3RoaW5nIHRvIHNjcnViLlxuICAgIGNvbW1pdFRpbWVzdGFtcDogZXZlbnQuY29tbWl0VGltZXN0YW1wID8gbmV3IERhdGUoZXZlbnQuY29tbWl0VGltZXN0YW1wKSA6IHVuZGVmaW5lZCxcbiAgICBjb21taXRDb3VudDogZXZlbnQuY29tbWl0Q291bnQsXG4gICAgLy8gTlVMTCBmb3Igbm9uLXBsdWdpbiBhY3Rpb25zIGFuZCBmb3IgcGlwZWxpbmVzIGRlcGxveWVkIHdpdGhvdXQgYSBtYW5pZmVzdC5cbiAgICBwbHVnaW5QdWJsaXNoZXI6IHBsdWdpbj8ucGx1Z2luUHVibGlzaGVyID8/IG51bGwsXG4gICAgcGx1Z2luUHVibGlzaGVySWQ6IHBsdWdpbj8ucGx1Z2luUHVibGlzaGVySWQgPz8gbnVsbCxcbiAgICBwbHVnaW5OYW1lOiBwbHVnaW4/LnBsdWdpbk5hbWUgPz8gbnVsbCxcbiAgICBwbHVnaW5WZXJzaW9uOiBwbHVnaW4/LnBsdWdpblZlcnNpb24gPz8gbnVsbCxcbiAgICAvLyBUaGUgbWFuYWdlZCB0b29sY2hhaW4gcmVsZWFzZSBhIHN5bnRoIC8gc2VsZi1tdXRhdGlvbiBhY3Rpb24gcmFuIG9uLCBmcm9tXG4gICAgLy8gdGhlIHBsYXRmb3JtJ3MgZGVwbG95ZWQgbWFuaWZlc3QgKG5ldmVyIHRoZSBwYXlsb2FkKS4gTlVMTCBvdGhlcndpc2UuXG4gICAgdG9vbGNoYWluUmVsZWFzZSxcbiAgICAvLyBXSEFUIEtJTkQgb2YgdGhpbmcgYnJva2UsIGNsYXNzaWZpZWQgaGVyZSByYXRoZXIgdGhhbiBhdCByZWFkIHRpbWU6IHRoZVxuICAgIC8vIGVycm9yIHRleHQgaXMgc2NydWJiZWQgYWJvdmUgYW5kIGV2ZW50dWFsbHkgc3dlcHQgYnkgcmV0ZW50aW9uLCBzbyBhXG4gICAgLy8gY2F0ZWdvcnkgZGVyaXZlZCBsYXRlciB3b3VsZCBoYXZlIG5vdGhpbmcgbGVmdCB0byByZWFkLiBOVUxMIGZvciBhbnl0aGluZ1xuICAgIC8vIHRoYXQgaXMgbm90IGEgZmFpbHVyZSwgc28gaXRzIHByZXNlbmNlIGFsd2F5cyBtZWFucyBcInRoaXMgYnJva2VcIi5cbiAgICBmYWlsdXJlQ2F0ZWdvcnk6IGNsYXNzaWZ5RmFpbHVyZSh7XG4gICAgICBzdGF0dXM6IGV2ZW50LnN0YXR1cyxcbiAgICAgIGVycm9yTWVzc2FnZTogc2NydWJPcHRpb25hbChldmVudC5lcnJvck1lc3NhZ2UpLFxuICAgICAgYWN0aW9uTmFtZTogc2NydWJPcHRpb25hbChldmVudC5hY3Rpb25OYW1lKSxcbiAgICAgIHN0YWdlTmFtZTogc2NydWJPcHRpb25hbChldmVudC5zdGFnZU5hbWUpLFxuICAgICAgZmFpbHVyZUNvZGU6IHBiRmFpbHVyZUNvZGUoZXZlbnQuZGV0YWlsKSxcbiAgICB9KSxcbiAgICAvLyBQcm92ZW5hbmNlLiBCb3RoIGFyZSBvcGFxdWUgaWRzIOKAlCBhbiBBV1MtYXNzaWduZWQgZXZlbnQgVVVJRCBhbmQgb3VyIG93blxuICAgIC8vIGtleSBpZCDigJQgc28gbmVpdGhlciBjYW4gY2FycnkgYW4gYWNjb3VudCBpZCBhbmQgbmVpdGhlciBpcyBzY3J1YmJlZFxuICAgIC8vIChzY3J1YmJpbmcgYSBkaWdpdCBydW4gaW5zaWRlIG9uZSB3b3VsZCBjb3JydXB0IHRoZSBjb3JyZWxhdGlvbiBrZXkpLlxuICAgIHNvdXJjZUV2ZW50SWQ6IGV2ZW50LnNvdXJjZUV2ZW50SWQsXG4gICAgaW5nZXN0S2V5SWQ6IGtleUlkLFxuICAgIGRldGFpbDogZGV0YWlsICE9PSB1bmRlZmluZWQgPyBzY3J1YkF3c0lkZW50aWZpZXJzKGRldGFpbCkgOiB1bmRlZmluZWQsXG4gIH07XG59XG5cbi8qKlxuICogRmFuIHRlcm1pbmFsIFNUQUdFIG91dGNvbWVzIGFuZCBwZXItQUNUSU9OIGNvbXB1dGUgY29uc3VtcHRpb24gaW50byB0aGVcbiAqIHJvdXRlJ3MgbWV0cmljIGhvb2sgKHBpcGVsaW5lLWRhdGEgY2FuJ3QgaW1wb3J0IGFwaS1zZXJ2ZXIncyByZWdpc3RyeSkgYWZ0ZXJcbiAqIHRoZSBpbnNlcnQgY29tbWl0cy5cbiAqXG4gKiBEcml2ZW4gb2ZmIHRoZSBJTlNFUlRFRCByb3dzLCBzbyBhIHJlLWRlbGl2ZXJlZCBldmVudCB0aGUgZGVkdXAgaW5kZXhcbiAqIHN3YWxsb3dlZCBpcyBuZXZlciBjb3VudGVkIHR3aWNlLiBUaGF0IHByb3BlcnR5IGlzIGxvYWQtYmVhcmluZyBmb3IgdGhlXG4gKiBjb21wdXRlIHNlcmllcyBpbiBhIHdheSBpdCB3YXMgbm90IGZvciB0aGUgc3RhZ2Ugb25lOiBhIGR1cGxpY2F0ZWQgc3RhZ2VcbiAqIG91dGNvbWUgZGlzdG9ydHMgYSByYXRlLCB3aGVyZWFzIGEgZHVwbGljYXRlZCB2Q1BVLW1pbnV0ZSBmaWd1cmUgaXMgYVxuICogZG91YmxlLWNoYXJnZSB3YWl0aW5nIGZvciB0aGUgZGF5IHRoZSBjaGFyZ2UgaXMgc3dpdGNoZWQgb24uXG4gKlxuICogQSBub24tbnVsbCBlbnZpcm9ubWVudCBtYXJrcyBhIGRlcGxveS5cbiAqL1xuZnVuY3Rpb24gZW1pdEluZ2VzdE1ldHJpY3MoXG4gIHJvd3M6IFJlYWRvbmx5QXJyYXk8e1xuICAgIG9yZ0lkOiBzdHJpbmc7XG4gICAgcGlwZWxpbmVJZDogc3RyaW5nIHwgbnVsbDtcbiAgICBldmVudFR5cGU6IHN0cmluZztcbiAgICBzdGF0dXM6IHN0cmluZztcbiAgICBzdGFnZU5hbWU6IHN0cmluZyB8IG51bGw7XG4gICAgYWN0aW9uTmFtZT86IHN0cmluZyB8IG51bGw7XG4gICAgZW52aXJvbm1lbnQ6IHN0cmluZyB8IG51bGw7XG4gICAgZHVyYXRpb25Ncz86IG51bWJlciB8IG51bGw7XG4gICAgZGV0YWlsPzogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gfCBudWxsO1xuICAgIHRvb2xjaGFpblJlbGVhc2U/OiBzdHJpbmcgfCBudWxsO1xuICB9PixcbiAgb25NZXRyaWM6IChtOiBJbmdlc3RNZXRyaWMpID0+IHZvaWQsXG4gIHBsYXRmb3JtRGVmYXVsdFJlbGVhc2U6IHN0cmluZyB8IG51bGwsXG4pOiB2b2lkIHtcbiAgZm9yIChjb25zdCByIG9mIHJvd3MpIHtcbiAgICBpZiAoIXIucGlwZWxpbmVJZCkgY29udGludWU7XG5cbiAgICAvLyBUb29sY2hhaW4gcnVucyAowqc3LCBhbGVydGluZyBvbmx5KTogYSB0ZXJtaW5hbCBvdXRjb21lIG9uIGEgc3RhbXBlZCByb3cuXG4gICAgLy8gTm90IGV4Y2x1c2l2ZSDigJQgdGhlIHNhbWUgYWN0aW9uIGlzIGFsc28gYSBjb21wdXRlIG1lYXN1cmVtZW50IGJlbG93LlxuICAgIGNvbnN0IG91dGNvbWUgPSByLnRvb2xjaGFpblJlbGVhc2UgPyB0b29sY2hhaW5PdXRjb21lT2Yoci5zdGF0dXMpIDogbnVsbDtcbiAgICBpZiAoci50b29sY2hhaW5SZWxlYXNlICYmIG91dGNvbWUpIHtcbiAgICAgIG9uTWV0cmljKHtcbiAgICAgICAga2luZDogJ3Rvb2xjaGFpbicsXG4gICAgICAgIHRvb2xjaGFpblJlbGVhc2U6IHIudG9vbGNoYWluUmVsZWFzZSxcbiAgICAgICAgLy8gU3RhbXBlZCByb3dzIGFyZSBvbmx5IGV2ZXIgc3ludGggb3Igc2VsZi1tdXRhdGlvbi5cbiAgICAgICAgYWN0aW9uOiByLnN0YWdlTmFtZSA9PT0gU0VMRl9NVVRBVElPTl9TVEFHRSAmJiByLmFjdGlvbk5hbWUgPT09IFNFTEZfTVVUQVRJT05fQUNUSU9OID8gJ3NlbGYtbXV0YXRpb24nIDogJ3N5bnRoJyxcbiAgICAgICAgb3V0Y29tZSxcbiAgICAgICAgcGxhdGZvcm1EZWZhdWx0UmVsZWFzZSxcbiAgICAgIH0pO1xuICAgIH1cblxuICAgIC8vIENvbXB1dGUgY29uc3VtcHRpb246IGV2ZXJ5IFRFUk1JTkFMIGFjdGlvbiwgbWVhc3VyYWJsZSBvciBub3QuIFRoZVxuICAgIC8vIHVubWVhc3VyYWJsZSBvbmVzIGFyZSB0aGUgcG9pbnQg4oCUIHRoZXkgYXJlIHdoYXQgdGhlIGNvdmVyYWdlIHJhdGlvIGNvdW50cy5cbiAgICBpZiAoci5ldmVudFR5cGUgPT09ICdBQ1RJT04nICYmIFRFUk1JTkFMX0FDVElPTl9TVEFURVMuaW5jbHVkZXMoci5zdGF0dXMpKSB7XG4gICAgICBjb25zdCBjb21wdXRlVHlwZSA9IG5vcm1hbGl6ZUNvbXB1dGVUeXBlKFxuICAgICAgICB0eXBlb2Ygci5kZXRhaWw/LmNvbXB1dGVUeXBlID09PSAnc3RyaW5nJyA/IHIuZGV0YWlsLmNvbXB1dGVUeXBlIDogbnVsbCxcbiAgICAgICk7XG4gICAgICBjb25zdCBkdXJhdGlvbk1zID0gci5kdXJhdGlvbk1zID8/IG51bGw7XG4gICAgICBvbk1ldHJpYyh7XG4gICAgICAgIGtpbmQ6ICdjb21wdXRlJyxcbiAgICAgICAgcGlwZWxpbmVJZDogci5waXBlbGluZUlkLFxuICAgICAgICBvcmdJZDogci5vcmdJZCxcbiAgICAgICAgY29tcHV0ZVR5cGUsXG4gICAgICAgIGR1cmF0aW9uTXMsXG4gICAgICAgIGNyZWRpdHM6IGNvbXB1dGVDcmVkaXRzRm9yKGR1cmF0aW9uTXMsIGNvbXB1dGVUeXBlKSxcbiAgICAgIH0pO1xuICAgICAgY29udGludWU7XG4gICAgfVxuXG4gICAgaWYgKHIuZXZlbnRUeXBlICE9PSAnU1RBR0UnIHx8IChyLnN0YXR1cyAhPT0gJ1NVQ0NFRURFRCcgJiYgci5zdGF0dXMgIT09ICdGQUlMRUQnKSkgY29udGludWU7XG4gICAgb25NZXRyaWMoe1xuICAgICAga2luZDogJ3N0YWdlJyxcbiAgICAgIHBpcGVsaW5lSWQ6IHIucGlwZWxpbmVJZCxcbiAgICAgIG9yZ0lkOiByLm9yZ0lkLFxuICAgICAgc3RhZ2U6IHIuc3RhZ2VOYW1lID8/ICcnLFxuICAgICAgZW52aXJvbm1lbnQ6IHIuZW52aXJvbm1lbnQgPz8gbnVsbCxcbiAgICAgIHJlc3VsdDogci5zdGF0dXMgPT09ICdTVUNDRUVERUQnID8gJ3N1Y2NlZWRlZCcgOiAnZmFpbGVkJyxcbiAgICB9KTtcbiAgfVxufVxuXG4vKiogQWN0aW9uIHN0YXRlcyB0aGF0IG1lYW4gdGhlIGFjdGlvbiBpcyBvdmVyIGFuZCBpdHMgY29uc3VtcHRpb24gaXMgZmluYWwuICovXG5jb25zdCBURVJNSU5BTF9BQ1RJT05fU1RBVEVTOiByZWFkb25seSBzdHJpbmdbXSA9IFsnU1VDQ0VFREVEJywgJ0ZBSUxFRCcsICdTVE9QUEVEJ107XG5cbi8qKlxuICogUmVzb2x2ZSBpbmNvbWluZyBldmVudHMgYWdhaW5zdCB0aGUgcGlwZWxpbmUgcmVnaXN0cnksIGJhdGNoLWluc2VydCB0aGVcbiAqIG1hdGNoZWQgb25lcywgYW5kIGludmFsaWRhdGUgcmVwb3J0aW5nIGNhY2hlcyBmb3IgYWZmZWN0ZWQgb3Jncy5cbiAqIEV2ZW50cyBmb3IgdW5yZWdpc3RlcmVkIHBpcGVsaW5lIGlkcyBhcmUgZHJvcHBlZCAoYW5kIGxvZ2dlZCBhdCBXQVJOXG4gKiB3aXRoIHNhbXBsZSBpZHMgc28gYW4gb3BlcmF0b3IgY2FuIHNlZSB3aGVuIEV2ZW50QnJpZGdlIGlzIGRlbGl2ZXJpbmdcbiAqIGV2ZW50cyBmb3IgcGlwZWxpbmVzIHRoYXQgaGF2ZW4ndCBjYWxsZWQgUE9TVCAvcGlwZWxpbmVzL3JlZ2lzdHJ5IHlldCkuXG4gKlxuICogUmV0dXJucyBjb3VudHMgKyBhIHNhbXBsZSBvZiB1bnJlZ2lzdGVyZWQgcGlwZWxpbmUgaWRzIGZvciBvYnNlcnZhYmlsaXR5LlxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gaW5nZXN0RXZlbnRzKFxuICBldmVudHM6IEluZ2VzdEV2ZW50W10sXG4gIG9uTWV0cmljPzogKG06IEluZ2VzdE1ldHJpYykgPT4gdm9pZCxcbiAgY2FsbGVyPzogSW5nZXN0Q2FsbGVyLFxuKTogUHJvbWlzZTxJbmdlc3RSZXN1bHQ+IHtcbiAgLy8gVEVOQU5DWS4gQW4gZXZlbnQncyBvcmcgY29tZXMgZnJvbSB0aGUgcGlwZWxpbmUgUkVHSVNUUlksIG5vdCB0aGUgdG9rZW4sIHNvXG4gIC8vIHRoZSBzY29wZSBjaGVjayBhbG9uZSBsZXQgYW55IGByZXBvcnRpbmc6aW5nZXN0YCBob2xkZXIgcG9zdCBldmVudHMgZm9yXG4gIC8vIGFub3RoZXIgb3JnJ3MgcGlwZWxpbmUgaWQgYW5kIGhhdmUgdGhlbSBhdHRyaWJ1dGVkIHRoZXJlLiBgY2FsbGVyYCBjYXJyaWVzXG4gIC8vIHRoZSBvcmcgaWRzIHRoaXMgdG9rZW4gbWF5IHdyaXRlIGZvcjsgYW55dGhpbmcgZWxzZSBpcyBkcm9wcGVkIGJlbG93LlxuICAvL1xuICAvLyBgY2FsbGVyYCBpcyBvcHRpb25hbCBvbmx5IHNvIGluLXByb2Nlc3MgY2FsbGVycyB0aGF0IGFscmVhZHkgcnVuXG4gIC8vIGNyb3NzLXRlbmFudCAodGVzdHMsIGJhY2tmaWxscykga2VlcCB3b3JraW5nIOKAlCBhbiBBQlNFTlQgY2FsbGVyIG1lYW5zIFwibm9cbiAgLy8gcmVzdHJpY3Rpb25cIiwgYW5kIHRoZSByb3V0ZSBhbHdheXMgc3VwcGxpZXMgb25lLiBBIGNhbGxlciB3aXRoIGFuIEVNUFRZXG4gIC8vIGFsbG93LWxpc3QgYW5kIG5vIGNyb3NzVGVuYW50IGZsYWcgdGhlcmVmb3JlIGRyb3BzIGV2ZXJ5dGhpbmcsIHdoaWNoIGlzIHRoZVxuICAvLyByaWdodCBhbnN3ZXIgd2hlbiB0aGUgcm91dGUgY291bGQgbm90IGVzdGFibGlzaCB3aG8gaXMgd3JpdGluZy5cbiAgY29uc3QgdW5yZXN0cmljdGVkID0gY2FsbGVyID09PSB1bmRlZmluZWQgfHwgY2FsbGVyLmNyb3NzVGVuYW50ID09PSB0cnVlO1xuICBjb25zdCBhbGxvd2VkID0gbmV3IFNldChjYWxsZXI/LmFsbG93ZWRPcmdJZHMgPz8gW10pO1xuICAvLyBNdWx0aS1vcmcgYmF0Y2ggaW5zZXJ0OiB0aGUgY2FsbGVyIHJlc29sdmVzIHRvIG11bHRpcGxlIG9yZ3MgdmlhIHRoZVxuICAvLyBwaXBlbGluZS1yZWdpc3RyeSBsb29rdXAgYmVsb3csIHNvIHRoZSByb3V0ZSBsYXllciBNVVNUIGVzdGFibGlzaCBhXG4gIC8vIGBydW5XaXRoVGVuYW50Q29udGV4dCh7IGlzU3VwZXJBZG1pbjogdHJ1ZSB9LCAuLi4pYCBzY29wZSBiZWZvcmUgY2FsbGluZ1xuICAvLyB0aGlzIGZ1bmN0aW9uLiBVbmRlciBGT1JDRSdkIFJMUywgYSBzaW5nbGUgdHggd2l0aCBgYXBwLm9yZ19pZCA9IDxvbmVcbiAgLy8gb3JnPmAgY291bGQgb25seSB3cml0ZSBldmVudHMgZm9yIHRoYXQgb3JnOyBieXBhc3MgdmlhIHN5c2FkbWluIGlzXG4gIC8vIHRoZSByaWdodCBnYXRlIGZvciB0aGlzIHNlcnZlci1pbnRlcm5hbCBjcm9zcy10ZW5hbnQgZW5kcG9pbnQuIFNlZVxuICAvLyBhcGkvcmVwb3J0aW5nL3NyYy9yb3V0ZXMvZXZlbnQtaW5nZXN0LnRzIGZvciB0aGUgd3JhcHBlci5cbiAgLy8gQ2FjaGVzIGFyZSBpbnZhbGlkYXRlZCBBRlRFUiB0aGUgdHggcmVzb2x2ZXM6IGRvaW5nIGl0IGluc2lkZSBoZWxkIHRoZSBwZ1xuICAvLyBsb2NrcyBvcGVuIGFjcm9zcyB1bnJlbGF0ZWQgY2FjaGUgcm91bmQtdHJpcHMuIFRoZSBUVEwgaXMgMi01IG1pbiwgc28gYVxuICAvLyBmaXJlLWFuZC1mb3JnZXQgcG9zdC1jb21taXQgaW52YWxpZGF0aW9uIGlzIGFuIGFjY2VwdGFibGUgdHJhZGUuXG4gIGNvbnN0IHsgaW5zZXJ0ZWQsIHNraXBwZWQsIHVucmVnaXN0ZXJlZFBpcGVsaW5lSWRzLCBhZmZlY3RlZE9yZ3MsIGRyb3BwZWRGb3JlaWduT3JnLCBkcm9wcGVkSW52YWxpZFRpbWUsIGZvcmVpZ25QaXBlbGluZUlkcywgaW5zZXJ0ZWRSb3dzLCBwbGF0Zm9ybURlZmF1bHRSZWxlYXNlIH0gPSBhd2FpdCB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB7XG4gICAgLy8gQmF0Y2gtcmVzb2x2ZSBhbGwgdW5pcXVlIHBpcGVsaW5lIGlkcyBpbiBvbmUgcXVlcnlcbiAgICBjb25zdCB1bmlxdWVJZHMgPSBbLi4ubmV3IFNldChldmVudHMubWFwKGUgPT4gZS5waXBlbGluZUlkKSldO1xuICAgIGNvbnN0IHJlZ2lzdHJ5Um93cyA9IGF3YWl0IHR4XG4gICAgICAuc2VsZWN0KHtcbiAgICAgICAgcGlwZWxpbmVJZDogc2NoZW1hLnBpcGVsaW5lUmVnaXN0cnkucGlwZWxpbmVJZCxcbiAgICAgICAgb3JnSWQ6IHNjaGVtYS5waXBlbGluZVJlZ2lzdHJ5Lm9yZ0lkLFxuICAgICAgfSlcbiAgICAgIC5mcm9tKHNjaGVtYS5waXBlbGluZVJlZ2lzdHJ5KVxuICAgICAgLndoZXJlKGluQXJyYXkoc2NoZW1hLnBpcGVsaW5lUmVnaXN0cnkucGlwZWxpbmVJZCwgdW5pcXVlSWRzKSk7XG5cbiAgICBjb25zdCBpZE1hcCA9IG5ldyBNYXAocmVnaXN0cnlSb3dzLm1hcChyID0+IFtyLnBpcGVsaW5lSWQsIHJdKSk7XG4gICAgY29uc3QgeyBzdGVwczogc3RlcFBsdWdpbnMsIHRvb2xjaGFpbiB9ID0gYXdhaXQgbG9hZFN0ZXBQbHVnaW5zKHR4LCBldmVudHMuZmlsdGVyKChlKSA9PiBpc0F0dHJpYnV0YWJsZShlKSAmJiBpZE1hcC5oYXMoZS5waXBlbGluZUlkKSkpO1xuXG4gICAgLy8gQnVpbGQgaW5zZXJ0IGJhdGNoIChza2lwIGV2ZW50cyB3aG9zZSBwaXBlbGluZSBpc24ndCByZWdpc3RlcmVkKVxuICAgIGNvbnN0IHJvd3M6IFBpcGVsaW5lRXZlbnRJbnNlcnRbXSA9IFtdO1xuICAgIGxldCBza2lwcGVkTG9jYWwgPSAwO1xuICAgIGxldCBmb3JlaWduTG9jYWwgPSAwO1xuICAgIGxldCBpbnZhbGlkVGltZUxvY2FsID0gMDtcbiAgICBjb25zdCBpbnZhbGlkVGltZVJlYXNvbnMgPSBuZXcgU2V0PHN0cmluZz4oKTtcbiAgICBjb25zdCBmb3JlaWduT3JnSWRzID0gbmV3IFNldDxzdHJpbmc+KCk7XG4gICAgY29uc3QgZm9yZWlnblBpcGVsaW5lSWRzTG9jYWwgPSBuZXcgU2V0PHN0cmluZz4oKTtcbiAgICBjb25zdCB1bnJlZ2lzdGVyZWRMb2NhbDogc3RyaW5nW10gPSBbXTtcbiAgICAvLyBPbmUgYG5vd2AgZm9yIHRoZSB3aG9sZSBiYXRjaDogcGVyLWV2ZW50IGNsb2NrcyB3b3VsZCBsZXQgYW4gZXZlbnQgcGFzcyBvclxuICAgIC8vIGZhaWwgZGVwZW5kaW5nIG9uIHdoZXJlIGl0IHNhdCBpbiB0aGUgbG9vcC5cbiAgICBjb25zdCBub3dNcyA9IERhdGUubm93KCk7XG5cbiAgICBmb3IgKGNvbnN0IGV2ZW50IG9mIGV2ZW50cykge1xuICAgICAgY29uc3QgcmVnaXN0cnkgPSBpZE1hcC5nZXQoZXZlbnQucGlwZWxpbmVJZCk7XG4gICAgICBpZiAoIXJlZ2lzdHJ5KSB7XG4gICAgICAgIHNraXBwZWRMb2NhbCsrO1xuICAgICAgICB1bnJlZ2lzdGVyZWRMb2NhbC5wdXNoKGV2ZW50LnBpcGVsaW5lSWQpO1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cbiAgICAgIC8vIFRoZSBwaXBlbGluZSByZXNvbHZlcyB0byBhbiBvcmcgdGhpcyBjYWxsZXIgbWF5IG5vdCB3cml0ZSBmb3IuIENvdW50ZWRcbiAgICAgIC8vIHNlcGFyYXRlbHkgZnJvbSBgc2tpcHBlZGAgKGFuIHVucmVnaXN0ZXJlZCBpZCBpcyBhIHByb2R1Y2VyIHJ1bm5pbmdcbiAgICAgIC8vIGFoZWFkIG9mIHJlZ2lzdHJhdGlvbjsgdGhpcyBpcyBhIHRlbmFuY3kgcmVmdXNhbCkgYW5kIG5ldmVyIGluc2VydGVkLlxuICAgICAgaWYgKCF1bnJlc3RyaWN0ZWQgJiYgIWFsbG93ZWQuaGFzKHJlZ2lzdHJ5Lm9yZ0lkKSkge1xuICAgICAgICBmb3JlaWduTG9jYWwrKztcbiAgICAgICAgZm9yZWlnbk9yZ0lkcy5hZGQocmVnaXN0cnkub3JnSWQpO1xuICAgICAgICBmb3JlaWduUGlwZWxpbmVJZHNMb2NhbC5hZGQoZXZlbnQucGlwZWxpbmVJZCk7XG4gICAgICAgIGNvbnRpbnVlO1xuICAgICAgfVxuICAgICAgLy8gSW1wb3NzaWJsZSB0aW1lc3RhbXBzIGFyZSByZWZ1c2VkIGF0IHRoZSBib3VuZGFyeSwgc28gbm8gZG93bnN0cmVhbVxuICAgICAgLy8gbWV0cmljIGhhcyB0byBjbGFtcCBhIG5lZ2F0aXZlIGdhcCBhbmQgY2FsbCBpdCB6ZXJvLlxuICAgICAgY29uc3QgYmFkVGltZSA9IGludmFsaWRFdmVudFRpbWVzKGV2ZW50LCBub3dNcyk7XG4gICAgICBpZiAoYmFkVGltZSkge1xuICAgICAgICBpbnZhbGlkVGltZUxvY2FsKys7XG4gICAgICAgIGludmFsaWRUaW1lUmVhc29ucy5hZGQoYmFkVGltZSk7XG4gICAgICAgIGNvbnRpbnVlO1xuICAgICAgfVxuICAgICAgY29uc3Qgc3RhZ2VOYW1lID0gc2NydWJPcHRpb25hbChldmVudC5zdGFnZU5hbWUpO1xuICAgICAgY29uc3QgYWN0aW9uTmFtZSA9IHNjcnViT3B0aW9uYWwoZXZlbnQuYWN0aW9uTmFtZSk7XG4gICAgICBjb25zdCBzdGVwID0gaXNBdHRyaWJ1dGFibGUoZXZlbnQpICYmIHN0YWdlTmFtZSAmJiBhY3Rpb25OYW1lXG4gICAgICAgID8gc3RlcFBsdWdpbnMuZ2V0KHN0ZXBLZXkocmVnaXN0cnkucGlwZWxpbmVJZCwgc3RhZ2VOYW1lLCBhY3Rpb25OYW1lKSlcbiAgICAgICAgOiB1bmRlZmluZWQ7XG4gICAgICAvLyBUaGUgdG9vbGNoYWluIHN0YW1wOiBpcyB0aGlzIHRoZSBwaXBlbGluZSdzIHN5bnRoIC8gc2VsZi1tdXRhdGlvblxuICAgICAgLy8gYWN0aW9uLCBhbmQgd2hpY2ggcmVsZWFzZSBkaWQgdGhlIHBsYXRmb3JtIGRlcGxveSBpdCB3aXRoP1xuICAgICAgY29uc3QgZGVwbG95ZWQgPSB0b29sY2hhaW4uZ2V0KHJlZ2lzdHJ5LnBpcGVsaW5lSWQpO1xuICAgICAgY29uc3Qgc2FtZU9yZ0RlcGxveWVkID0gZGVwbG95ZWQgJiYgZGVwbG95ZWQub3JnSWQgPT09IHJlZ2lzdHJ5Lm9yZ0lkID8gZGVwbG95ZWQgOiB1bmRlZmluZWQ7XG4gICAgICBjb25zdCB0b29sY2hhaW5SZWxlYXNlID0gdG9vbGNoYWluQWN0aW9uT2YoeyBldmVudFR5cGU6IGV2ZW50LmV2ZW50VHlwZSwgc3RhZ2VOYW1lLCBhY3Rpb25OYW1lIH0sIHNhbWVPcmdEZXBsb3llZClcbiAgICAgICAgPyBzYW1lT3JnRGVwbG95ZWQhLnJlbGVhc2VWZXJzaW9uXG4gICAgICAgIDogbnVsbDtcbiAgICAgIC8vIFNhbWUtb3JnIGd1YXJkOiBhIG1hbmlmZXN0IHJvdyBpcyBvbmx5IGV2ZXIgd3JpdHRlbiBieSB0aGUgb3JnIHRoYXRcbiAgICAgIC8vIG93bnMgdGhlIHBpcGVsaW5lLCBidXQgdGhlIGluZ2VzdCBydW5zIGNyb3NzLXRlbmFudCwgc28gZG9uJ3QgbGVhbiBvbiBpdC5cbiAgICAgIHJvd3MucHVzaCh0b0V2ZW50Um93KGV2ZW50LCByZWdpc3RyeSwgc3RlcCAmJiBzdGVwLm9yZ0lkID09PSByZWdpc3RyeS5vcmdJZCA/IHN0ZXAgOiB1bmRlZmluZWQsIGNhbGxlcj8ua2V5SWQsIHRvb2xjaGFpblJlbGVhc2UpKTtcbiAgICB9XG5cbiAgICAvLyBTUVMgaXMgYXQtbGVhc3Qtb25jZSwgc28gRXZlbnRCcmlkZ2UgY2FuIGRlbGl2ZXIgdGhlIHNhbWUgc3RhdGUtY2hhbmdlXG4gICAgLy8gdHdpY2UuIGBvbkNvbmZsaWN0RG9Ob3RoaW5nYCArIHRoZSBwYXJ0aWFsIHVuaXF1ZSBpbmRleGVzIG9uXG4gICAgLy8gKHBpcGVsaW5lX2lkLCBleGVjdXRpb25faWQsIGV2ZW50X3R5cGUsIHN0YXR1cywgc3RhZ2VfbmFtZSwgYWN0aW9uX25hbWUpXG4gICAgLy8gYW5kIG9uIHNvdXJjZV9ldmVudF9pZCAodGhlIEV2ZW50QnJpZGdlIGlkLCB3aGVuIHByZXNlbnQpIG1ha2VcbiAgICAvLyByZS1kZWxpdmVyeSBpZGVtcG90ZW50LiBgcmV0dXJuaW5nYCBnaXZlcyB0aGUgUkVBTCBpbnNlcnRlZCBzZXQgc29cbiAgICAvLyBjb3VudHMsIG1ldHJpY3MgYW5kIGNhY2hlIGludmFsaWRhdGlvbiBhbGwgaWdub3JlIGR1cGxpY2F0ZXMuXG4gICAgY29uc3QgbGFuZGVkID0gcm93cy5sZW5ndGggPiAwXG4gICAgICA/IGF3YWl0IHR4Lmluc2VydChzY2hlbWEucGlwZWxpbmVFdmVudCkudmFsdWVzKHJvd3MpXG4gICAgICAgIC5vbkNvbmZsaWN0RG9Ob3RoaW5nKClcbiAgICAgICAgLnJldHVybmluZyh7XG4gICAgICAgICAgb3JnSWQ6IHNjaGVtYS5waXBlbGluZUV2ZW50Lm9yZ0lkLFxuICAgICAgICAgIHBpcGVsaW5lSWQ6IHNjaGVtYS5waXBlbGluZUV2ZW50LnBpcGVsaW5lSWQsXG4gICAgICAgICAgZXZlbnRUeXBlOiBzY2hlbWEucGlwZWxpbmVFdmVudC5ldmVudFR5cGUsXG4gICAgICAgICAgc3RhdHVzOiBzY2hlbWEucGlwZWxpbmVFdmVudC5zdGF0dXMsXG4gICAgICAgICAgc3RhZ2VOYW1lOiBzY2hlbWEucGlwZWxpbmVFdmVudC5zdGFnZU5hbWUsXG4gICAgICAgICAgYWN0aW9uTmFtZTogc2NoZW1hLnBpcGVsaW5lRXZlbnQuYWN0aW9uTmFtZSxcbiAgICAgICAgICBlbnZpcm9ubWVudDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuZW52aXJvbm1lbnQsXG4gICAgICAgICAgdG9vbGNoYWluUmVsZWFzZTogc2NoZW1hLnBpcGVsaW5lRXZlbnQudG9vbGNoYWluUmVsZWFzZSxcbiAgICAgICAgICAvLyBGb3IgdGhlIHBlci1kZXBsb3kgcm9sbHVwIGJlbG93OiBldmVyeXRoaW5nIGBkb3JhX2RlcGxveW1lbnRzYCBuZWVkcyxcbiAgICAgICAgICAvLyB0YWtlbiBmcm9tIHRoZSByb3dzIHRoYXQgQUNUVUFMTFkgbGFuZGVkIHNvIGEgcmUtZGVsaXZlcnkgY2Fubm90XG4gICAgICAgICAgLy8gcHJvZHVjZSBhIHNlY29uZCBkZXBsb3kuXG4gICAgICAgICAgZXhlY3V0aW9uSWQ6IHNjaGVtYS5waXBlbGluZUV2ZW50LmV4ZWN1dGlvbklkLFxuICAgICAgICAgIGNvbW1pdFNoYTogc2NoZW1hLnBpcGVsaW5lRXZlbnQuY29tbWl0U2hhLFxuICAgICAgICAgIGNvbW1pdFRpbWVzdGFtcDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuY29tbWl0VGltZXN0YW1wLFxuICAgICAgICAgIGNvbW1pdENvdW50OiBzY2hlbWEucGlwZWxpbmVFdmVudC5jb21taXRDb3VudCxcbiAgICAgICAgICBjb21wbGV0ZWRBdDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuY29tcGxldGVkQXQsXG4gICAgICAgICAgc3RhcnRlZEF0OiBzY2hlbWEucGlwZWxpbmVFdmVudC5zdGFydGVkQXQsXG4gICAgICAgICAgY3JlYXRlZEF0OiBzY2hlbWEucGlwZWxpbmVFdmVudC5jcmVhdGVkQXQsXG4gICAgICAgICAgZGV0YWlsOiBzY2hlbWEucGlwZWxpbmVFdmVudC5kZXRhaWwsXG4gICAgICAgICAgc291cmNlRXZlbnRJZDogc2NoZW1hLnBpcGVsaW5lRXZlbnQuc291cmNlRXZlbnRJZCxcbiAgICAgICAgfSlcbiAgICAgIDogW107XG5cbiAgICAvLyBMb2cgaW5zaWRlIHRoZSB0eCBzY29wZSB3aGlsZSB0aGUgb3JnIHNldCBpcyBpbiBoYW5kLiBXQVJOLCBub3QgZXJyb3I6XG4gICAgLy8gYSBtaXNyb3V0ZWQgcHJvZHVjZXIgaXMgdGhlIGNvbW1vbiBjYXVzZSwgYnV0IHRoZSBzYW1lIGxpbmUgaXMgdGhlIG9ubHlcbiAgICAvLyBzaWduYWwgb2YgYW4gaW5qZWN0aW9uIGF0dGVtcHQsIHNvIGl0IG5hbWVzIHRoZSBvcmdzIGl0IHJlZnVzZWQuXG4gICAgaWYgKGZvcmVpZ25Mb2NhbCA+IDApIHtcbiAgICAgIGxvZ2dlci53YXJuKCdEcm9wcGVkIGluZ2VzdCBldmVudHMgZm9yIG9yZ3MgdGhlIGNhbGxlciBtYXkgbm90IHdyaXRlIGZvcicsIHtcbiAgICAgICAgZHJvcHBlZDogZm9yZWlnbkxvY2FsLFxuICAgICAgICBmb3JlaWduT3JnSWRzOiBbLi4uZm9yZWlnbk9yZ0lkc10sXG4gICAgICAgIGFsbG93ZWRPcmdJZHM6IFsuLi5hbGxvd2VkXSxcbiAgICAgIH0pO1xuICAgIH1cblxuICAgIGlmIChpbnZhbGlkVGltZUxvY2FsID4gMCkge1xuICAgICAgbG9nZ2VyLndhcm4oJ0Ryb3BwZWQgaW5nZXN0IGV2ZW50cyB3aXRoIGltcG9zc2libGUgdGltZXN0YW1wcycsIHtcbiAgICAgICAgZHJvcHBlZDogaW52YWxpZFRpbWVMb2NhbCxcbiAgICAgICAgcmVhc29uczogWy4uLmludmFsaWRUaW1lUmVhc29uc10sXG4gICAgICB9KTtcbiAgICB9XG5cbiAgICAvLyBUaGUgcGxhdGZvcm0gZGVmYXVsdCwgZm9yIHRoZSBhbGVydCdzIGJhc2VsaW5lIGdhdWdlIOKAlCByZWFkIG9ubHkgd2hlbiBhXG4gICAgLy8gdG9vbGNoYWluIHJ1biBsYW5kZWQsIHNvIG9yZGluYXJ5IGJhdGNoZXMgcGF5IG5vdGhpbmcuXG4gICAgY29uc3QgZGVmYXVsdFJlbGVhc2UgPSBsYW5kZWQuc29tZSgocikgPT4gci50b29sY2hhaW5SZWxlYXNlKVxuICAgICAgPyBhd2FpdCByZWFkUGxhdGZvcm1EZWZhdWx0UmVsZWFzZSh0eClcbiAgICAgIDogbnVsbDtcblxuICAgIHJldHVybiB7XG4gICAgICBwbGF0Zm9ybURlZmF1bHRSZWxlYXNlOiBkZWZhdWx0UmVsZWFzZSxcbiAgICAgIGluc2VydGVkOiBsYW5kZWQubGVuZ3RoLFxuICAgICAgc2tpcHBlZDogc2tpcHBlZExvY2FsLFxuICAgICAgdW5yZWdpc3RlcmVkUGlwZWxpbmVJZHM6IHVucmVnaXN0ZXJlZExvY2FsLFxuICAgICAgYWZmZWN0ZWRPcmdzOiBbLi4ubmV3IFNldChsYW5kZWQubWFwKHIgPT4gci5vcmdJZCkpXSxcbiAgICAgIGRyb3BwZWRGb3JlaWduT3JnOiBmb3JlaWduTG9jYWwsXG4gICAgICBkcm9wcGVkSW52YWxpZFRpbWU6IGludmFsaWRUaW1lTG9jYWwsXG4gICAgICBmb3JlaWduUGlwZWxpbmVJZHM6IFsuLi5mb3JlaWduUGlwZWxpbmVJZHNMb2NhbF0sXG4gICAgICBpbnNlcnRlZFJvd3M6IGxhbmRlZCxcbiAgICB9O1xuICB9KTtcblxuICBpZiAob25NZXRyaWMpIGVtaXRJbmdlc3RNZXRyaWNzKGluc2VydGVkUm93cywgb25NZXRyaWMsIHBsYXRmb3JtRGVmYXVsdFJlbGVhc2UpO1xuXG4gIC8vIFBlci1kZXBsb3kgcm9sbHVwLiBBRlRFUiB0aGUgZXZlbnRzIGNvbW1pdCBhbmQgb3V0c2lkZSB0aGVpciB0cmFuc2FjdGlvbjogdGhlXG4gIC8vIGV2ZW50cyBhcmUgdGhlIGR1cmFibGUgcmVjb3JkIGFuZCBgZG9yYV9kZXBsb3ltZW50c2AgaXMgZGVyaXZlZCBmcm9tIHRoZW0sIHNvXG4gIC8vIGEgcm9sbHVwIGZhaWx1cmUgbXVzdCBub3Qgcm9sbCBiYWNrIGFuIGluZ2VzdCB0aGF0IHN1Y2NlZWRlZC4gUmVidWlsZGFibGVcbiAgLy8gZWl0aGVyIHdheS4gYHVwc2VydERlcGxveW1lbnRzYCBuZXZlciB0aHJvd3MgZm9yIHRoYXQgcmVhc29uLlxuICBhd2FpdCB1cHNlcnREZXBsb3ltZW50cyhpbnNlcnRlZFJvd3MpO1xuXG4gIC8vIFN1cmZhY2UgdGhlIHNpbGVudCBza2lwOiBhbiB1bnJlZ2lzdGVyZWQgcGlwZWxpbmUgaWQgdXN1YWxseSBtZWFucyB0aGVcbiAgLy8gcGlwZWxpbmUgaGFzbid0IGNhbGxlZCBQT1NUIC9waXBlbGluZXMvcmVnaXN0cnkgeWV0IChvciBpdHNcbiAgLy8gcGIucGlwZWxpbmUtaWQgdGFnIGlzIG1pc3NpbmcvdW5yZWFkYWJsZSBieSB0aGUgTGFtYmRhKS4gTG9nZ2luZyBpdFxuICAvLyBtYWtlcyBhIGJyb2tlbiBqb2luIHZpc2libGUgaW5zdGVhZCBvZiBsb29raW5nIGxpa2UgXCJubyBhY3Rpdml0eVwiLlxuICBpZiAodW5yZWdpc3RlcmVkUGlwZWxpbmVJZHMubGVuZ3RoID4gMCkge1xuICAgIGxvZ2dlci53YXJuKCdQaXBlbGluZSBldmVudHMgc2tpcHBlZDogcGlwZWxpbmUgaWQgbm90IGZvdW5kIGluIHJlZ2lzdHJ5Jywge1xuICAgICAgY291bnQ6IHVucmVnaXN0ZXJlZFBpcGVsaW5lSWRzLmxlbmd0aCxcbiAgICAgIHNhbXBsZTogdW5yZWdpc3RlcmVkUGlwZWxpbmVJZHMuc2xpY2UoMCwgMyksXG4gICAgfSk7XG4gIH1cblxuICAvLyBQb3N0LWNvbW1pdCBjYWNoZSBpbnZhbGlkYXRpb24uIEZpcmUtYW5kLWZvcmdldCB3aXRoIGxvZ2dpbmcg4oCUIFRUTCBpc1xuICAvLyBzaG9ydCBlbm91Z2ggdGhhdCBhIG1pc3NlZCBpbnZhbGlkYXRpb24gc2VsZi1oZWFscy5cbiAgaWYgKGFmZmVjdGVkT3Jncy5sZW5ndGggPiAwKSB7XG4gICAgdm9pZCBQcm9taXNlLmFsbChhZmZlY3RlZE9yZ3MubWFwKChvcmcpID0+XG4gICAgICBpbnZhbGlkYXRlT3JnUmVwb3J0cyhvcmcpLmNhdGNoKChlcnIpID0+IHtcbiAgICAgICAgbG9nZ2VyLndhcm4oJ1JlcG9ydGluZyBjYWNoZSBpbnZhbGlkYXRpb24gZmFpbGVkJywgeyBvcmdJZDogb3JnLCBlcnJvcjogZXJyb3JNZXNzYWdlKGVycikgfSk7XG4gICAgICB9KSxcbiAgICApKTtcbiAgfVxuXG4gIHJldHVybiB7XG4gICAgaW5zZXJ0ZWQsXG4gICAgc2tpcHBlZCxcbiAgICB1bnJlZ2lzdGVyZWRQaXBlbGluZUlkcyxcbiAgICBhZmZlY3RlZE9yZ3MsXG4gICAgZHJvcHBlZEZvcmVpZ25PcmcsXG4gICAgZHJvcHBlZEludmFsaWRUaW1lLFxuICAgIGZvcmVpZ25QaXBlbGluZUlkcyxcbiAgICBpbnNlcnRlZEV4ZWN1dGlvbklkczogWy4uLm5ldyBTZXQoaW5zZXJ0ZWRSb3dzLm1hcCgocikgPT4gci5leGVjdXRpb25JZCkuZmlsdGVyKChpZCk6IGlkIGlzIHN0cmluZyA9PiAhIWlkKSldLFxuICAgIGluc2VydGVkUGlwZWxpbmVJZHM6IFsuLi5uZXcgU2V0KGluc2VydGVkUm93cy5tYXAoKHIpID0+IHIucGlwZWxpbmVJZCkuZmlsdGVyKChpZCk6IGlkIGlzIHN0cmluZyA9PiAhIWlkKSldLFxuICB9O1xufVxuIl19
|
|
@@ -0,0 +1,162 @@
|
|
|
1
|
+
import { type SqlExecutor } from '../../database/pg-result.js';
|
|
2
|
+
/** The two toolchain actions a release is judged on. */
|
|
3
|
+
export type ToolchainAction = 'synth' | 'self-mutation';
|
|
4
|
+
/** Terminal toolchain outcomes; anything else (STARTED, CANCELED, ABANDONED…) says nothing about the toolchain. */
|
|
5
|
+
export type ToolchainOutcome = 'succeeded' | 'failed';
|
|
6
|
+
/**
|
|
7
|
+
* CDK Pipelines' self-mutation action: a fixed stage and action name
|
|
8
|
+
* (`aws-cdk-lib/pipelines/lib/codepipeline/codepipeline.js`).
|
|
9
|
+
*/
|
|
10
|
+
export declare const SELF_MUTATION_STAGE = "UpdatePipeline";
|
|
11
|
+
export declare const SELF_MUTATION_ACTION = "SelfMutate";
|
|
12
|
+
/**
|
|
13
|
+
* The synth step's `stepKey` in the step manifest (`pluginStepLabel(null, …)`).
|
|
14
|
+
* The synth ACTION's name is a generated id, so it is identified by the
|
|
15
|
+
* manifest row carrying this key — the names the built pipeline really used.
|
|
16
|
+
*/
|
|
17
|
+
export declare const SYNTH_STEP_KEY = "synth";
|
|
18
|
+
/**
|
|
19
|
+
* The `build-image` entry's plugin: the release's bootstrap half. The entry is
|
|
20
|
+
* the manifest's non-step row under `step_key` {@link BUILD_IMAGE_STEP_KEY}
|
|
21
|
+
* (api-core `BUILD_IMAGE_MANIFEST_*`), and its `plugin_version` IS the release.
|
|
22
|
+
*/
|
|
23
|
+
export declare const BUILD_IMAGE_PLUGIN = "pipeline-bootstrap";
|
|
24
|
+
/** A manifest row, as {@link deployedToolchainOf} reads it. */
|
|
25
|
+
export interface ToolchainManifestRow {
|
|
26
|
+
pipelineId: string;
|
|
27
|
+
orgId: string;
|
|
28
|
+
stageName: string;
|
|
29
|
+
actionName: string;
|
|
30
|
+
pluginPublisher: string | null;
|
|
31
|
+
pluginName: string | null;
|
|
32
|
+
pluginVersion: string | null;
|
|
33
|
+
stepKey?: string | null;
|
|
34
|
+
}
|
|
35
|
+
/** One pipeline's deployed toolchain, from its manifest. */
|
|
36
|
+
export interface DeployedToolchain {
|
|
37
|
+
orgId: string;
|
|
38
|
+
/** The release its `build-image` entry records. */
|
|
39
|
+
releaseVersion: string;
|
|
40
|
+
/** The synth action as the built pipeline names it; null when the manifest has no synth row. */
|
|
41
|
+
synth: {
|
|
42
|
+
stageName: string;
|
|
43
|
+
actionName: string;
|
|
44
|
+
} | null;
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Each pipeline's deployed toolchain, from its manifest rows. A pipeline
|
|
48
|
+
* whose manifest records no `build-image` entry (deployed before releases, or
|
|
49
|
+
* a placeholder bootstrap) has none, and its actions are not stamped. Only an
|
|
50
|
+
* OWN-ORG row (no publisher) counts: a managed name can never be a listing.
|
|
51
|
+
*/
|
|
52
|
+
export declare function deployedToolchainOf(rows: readonly ToolchainManifestRow[]): Map<string, DeployedToolchain>;
|
|
53
|
+
/**
|
|
54
|
+
* Which toolchain action (if any) an ACTION event is, given its pipeline's
|
|
55
|
+
* deployed toolchain. Names are compared post-scrub, as the manifest stores them.
|
|
56
|
+
*/
|
|
57
|
+
export declare function toolchainActionOf(event: {
|
|
58
|
+
eventType: string;
|
|
59
|
+
stageName?: string | null;
|
|
60
|
+
actionName?: string | null;
|
|
61
|
+
}, deployed: DeployedToolchain | undefined): ToolchainAction | null;
|
|
62
|
+
/** The terminal outcome of a status, or null for a non-terminal / non-judging one. */
|
|
63
|
+
export declare function toolchainOutcomeOf(status: string): ToolchainOutcome | null;
|
|
64
|
+
/** The gate's thresholds (set on the console, Phase 5). */
|
|
65
|
+
export interface CanaryGateParams {
|
|
66
|
+
/** N: counted synth runs required. */
|
|
67
|
+
minRuns: number;
|
|
68
|
+
/** M: distinct orgs required. */
|
|
69
|
+
minOrgs: number;
|
|
70
|
+
/** T: the release's failure rate may exceed the default's by at most this many percentage points. */
|
|
71
|
+
maxFailurePointsAboveDefault: number;
|
|
72
|
+
}
|
|
73
|
+
export declare const DEFAULT_CANARY_GATE: Readonly<CanaryGateParams>;
|
|
74
|
+
/** One org's terminal synth outcomes on the candidate, NEWEST first. */
|
|
75
|
+
export interface OrgRuns {
|
|
76
|
+
orgId: string;
|
|
77
|
+
outcomes: readonly ToolchainOutcome[];
|
|
78
|
+
}
|
|
79
|
+
export interface CanaryGateInput {
|
|
80
|
+
releaseVersion: string;
|
|
81
|
+
candidate: readonly OrgRuns[];
|
|
82
|
+
/** The current platform default's synth runs over the same window (uncapped). */
|
|
83
|
+
baseline: {
|
|
84
|
+
releaseVersion: string | null;
|
|
85
|
+
runs: number;
|
|
86
|
+
failures: number;
|
|
87
|
+
};
|
|
88
|
+
params?: Partial<CanaryGateParams>;
|
|
89
|
+
}
|
|
90
|
+
export type CanaryGateShortfall = 'runs' | 'orgs' | 'failure-rate';
|
|
91
|
+
/** The gate's verdict and every number behind it — what the console shows. */
|
|
92
|
+
export interface CanaryGateResult {
|
|
93
|
+
passed: boolean;
|
|
94
|
+
releaseVersion: string;
|
|
95
|
+
params: CanaryGateParams;
|
|
96
|
+
/** ceil(N / M): the most runs any one org contributes. */
|
|
97
|
+
perOrgCap: number;
|
|
98
|
+
/** Runs counted toward N, after the per-org cap. */
|
|
99
|
+
countedRuns: number;
|
|
100
|
+
/** Every terminal synth run on the release, before the cap. */
|
|
101
|
+
totalRuns: number;
|
|
102
|
+
/** Distinct orgs with at least one counted run. */
|
|
103
|
+
orgs: number;
|
|
104
|
+
/** Failures among the counted runs. */
|
|
105
|
+
failures: number;
|
|
106
|
+
/** Percent (0–100) over the counted runs; null with none. */
|
|
107
|
+
failureRate: number | null;
|
|
108
|
+
baselineReleaseVersion: string | null;
|
|
109
|
+
baselineRuns: number;
|
|
110
|
+
/** Percent (0–100); 0 when the default has no runs in the window (the strict reading). */
|
|
111
|
+
baselineFailureRate: number;
|
|
112
|
+
/** failureRate − baselineFailureRate, in points; null with no counted runs. */
|
|
113
|
+
pointsAboveDefault: number | null;
|
|
114
|
+
/** Which thresholds were not met (empty when passed). */
|
|
115
|
+
shortfalls: CanaryGateShortfall[];
|
|
116
|
+
}
|
|
117
|
+
/** The per-org contribution cap: ceil(N / M). */
|
|
118
|
+
export declare function canaryPerOrgCap(params: Pick<CanaryGateParams, 'minRuns' | 'minOrgs'>): number;
|
|
119
|
+
/**
|
|
120
|
+
* The canary gate: at least N counted synth runs across at least M orgs, and a
|
|
121
|
+
* failure rate within T points of the current default's. Each org counts its
|
|
122
|
+
* most recent `ceil(N / M)` runs only — toward N AND toward the failure rate,
|
|
123
|
+
* so one org can neither satisfy N alone nor dominate the rate. Being BETTER
|
|
124
|
+
* than the default never fails the gate.
|
|
125
|
+
*/
|
|
126
|
+
export declare function evaluateCanaryGate(input: CanaryGateInput): CanaryGateResult;
|
|
127
|
+
/**
|
|
128
|
+
* Evaluate the canary gate for `releaseVersion` against `baselineReleaseVersion`
|
|
129
|
+
* (the current platform default; null when none) from the stamped rows.
|
|
130
|
+
*
|
|
131
|
+
* Window: since the release was registered (`toolchain_release.created_at`),
|
|
132
|
+
* for both the candidate and the default, so the two rates are contemporaneous.
|
|
133
|
+
* Only terminal (SUCCEEDED / FAILED) SYNTH runs count; self-mutation is not
|
|
134
|
+
* part of the gate (§6 counts synth runs).
|
|
135
|
+
*
|
|
136
|
+
* Reads every org's rows: run it ELEVATED (the plugin service's toolchain tx
|
|
137
|
+
* is). The candidate read is bounded at `ceil(N/M)` rows per org.
|
|
138
|
+
*/
|
|
139
|
+
export declare function readCanaryGate(db: SqlExecutor, releaseVersion: string, baselineReleaseVersion: string | null, params?: Partial<CanaryGateParams>): Promise<CanaryGateResult>;
|
|
140
|
+
export interface AffectedOrg {
|
|
141
|
+
orgId: string;
|
|
142
|
+
/** Pipelines in this org on the release whose latest synth failed. */
|
|
143
|
+
pipelines: number;
|
|
144
|
+
pipelineIds: string[];
|
|
145
|
+
}
|
|
146
|
+
export interface AffectedPipelines {
|
|
147
|
+
releaseVersion: string;
|
|
148
|
+
totalPipelines: number;
|
|
149
|
+
orgs: AffectedOrg[];
|
|
150
|
+
}
|
|
151
|
+
/**
|
|
152
|
+
* Pipelines whose DEPLOYED release is `releaseVersion` (their manifest's
|
|
153
|
+
* `build-image` entry) and whose LATEST terminal synth run failed, grouped by
|
|
154
|
+
* org — the console's Affected view and the "Notify affected owners" target
|
|
155
|
+
* set. A pipeline whose latest synth succeeded has healed and is not listed.
|
|
156
|
+
*
|
|
157
|
+
* Elevated read: it spans every org. Callers show the system-org operator
|
|
158
|
+
* counts, and notify each org about its own pipelines only.
|
|
159
|
+
*/
|
|
160
|
+
export declare function readAffectedPipelines(db: SqlExecutor, releaseVersion: string): Promise<AffectedPipelines>;
|
|
161
|
+
/** The current platform default (elevated read), or null. */
|
|
162
|
+
export declare function readPlatformDefaultRelease(db: SqlExecutor): Promise<string | null>;
|