@pipeline-builder/pipeline-data 3.4.85 → 3.4.87
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/crud-service.d.ts +49 -6
- package/lib/api/crud-service.js +92 -24
- package/lib/api/query-builders.js +57 -26
- package/lib/api/reporting-service.d.ts +3 -3
- package/lib/api/reporting-service.js +19 -13
- package/lib/database/drizzle-schema.d.ts +50 -6188
- package/lib/database/drizzle-schema.js +20 -954
- package/lib/database/postgres-connection.d.ts +0 -1
- package/lib/database/postgres-connection.js +1 -6
- package/lib/database/schema/alert.d.ts +554 -0
- package/lib/database/schema/alert.js +120 -0
- package/lib/database/schema/compliance.d.ts +3284 -0
- package/lib/database/schema/compliance.js +348 -0
- package/lib/database/schema/dashboard.d.ts +457 -0
- package/lib/database/schema/dashboard.js +120 -0
- package/lib/database/schema/message.d.ts +379 -0
- package/lib/database/schema/message.js +95 -0
- package/lib/database/schema/pipeline.d.ts +868 -0
- package/lib/database/schema/pipeline.js +166 -0
- package/lib/database/schema/plugin.d.ts +617 -0
- package/lib/database/schema/plugin.js +134 -0
- package/lib/database/tenancy.d.ts +5 -0
- package/lib/database/tenancy.js +6 -3
- package/package.json +2 -2
|
@@ -82,7 +82,7 @@ export interface PaginatedResult<T> {
|
|
|
82
82
|
* protected buildConditions(filter, orgId) { return buildPipelineConditions(filter, orgId); }
|
|
83
83
|
* protected getSortColumn(sortBy) { return sortColumnMap[sortBy] ?? null; }
|
|
84
84
|
* protected getProjectColumn() { return schema.pipeline.project; }
|
|
85
|
-
* protected getOrgColumn() { return schema.pipeline.
|
|
85
|
+
* protected getOrgColumn() { return schema.pipeline.orgId; }
|
|
86
86
|
* }
|
|
87
87
|
* ```
|
|
88
88
|
*/
|
|
@@ -99,12 +99,20 @@ export declare abstract class CrudService<TEntity extends BaseEntity, TFilter, T
|
|
|
99
99
|
protected abstract getSortColumn(sortBy: string): AnyColumn | null;
|
|
100
100
|
/** Get the project column for setDefault scoping (null if entity has no project scope) */
|
|
101
101
|
protected abstract getProjectColumn(): AnyColumn | null;
|
|
102
|
-
/**
|
|
102
|
+
/**
|
|
103
|
+
* Get the tenant org-id column. Used both to scope `setDefault` and to pin
|
|
104
|
+
* every write (update/delete/bulkDelete) to the caller's own org — so it MUST
|
|
105
|
+
* be the tenant `orgId` column, not a display/name column.
|
|
106
|
+
*/
|
|
103
107
|
protected abstract getOrgColumn(): AnyColumn;
|
|
104
108
|
/** Get the unique constraint columns for onConflictDoUpdate */
|
|
105
109
|
protected abstract get conflictTarget(): AnyColumn[];
|
|
106
110
|
private readonly _logger;
|
|
107
|
-
|
|
111
|
+
constructor();
|
|
112
|
+
/** Build conditions for a single entity by ID.
|
|
113
|
+
* `parentOrgId` widens visibility to a parent org's public rows (org → team
|
|
114
|
+
* hierarchy) — same opt-in semantics as `find`/`findPaginated`. Omitted by the
|
|
115
|
+
* write path (`writeConditions`), which must stay own-org scoped. */
|
|
108
116
|
private idConditions;
|
|
109
117
|
/**
|
|
110
118
|
* Conditions for a MUTATION (update/delete) of a single entity.
|
|
@@ -135,6 +143,18 @@ export declare abstract class CrudService<TEntity extends BaseEntity, TFilter, T
|
|
|
135
143
|
* run under sysadmin context — the access-control WHERE clause (own + parent +
|
|
136
144
|
* system public, built server-side from a trusted JWT claim) is then the
|
|
137
145
|
* authoritative tenancy gate. Without `parentOrgId` it stays RLS-scoped.
|
|
146
|
+
*
|
|
147
|
+
* INVARIANT (why the sysadmin bypass is safe): the WHERE clause is always
|
|
148
|
+
* server-built by `buildConditions(filter, orgId, parentOrgId)` from values
|
|
149
|
+
* derived from the validated JWT (`orgId` = active org, `parentOrgId` = the
|
|
150
|
+
* active org's parent). None of them is a raw user-supplied predicate, so the
|
|
151
|
+
* bypass only ever widens the read to the caller's own subtree + system public
|
|
152
|
+
* rows — it can NOT be steered at an arbitrary org. NOTE: this does remove the
|
|
153
|
+
* RLS backstop for the widened read; a single-GUC `app.org_id` can't express
|
|
154
|
+
* the "own OR parent OR system" set the policy would need, so replacing the
|
|
155
|
+
* bypass would require a tenancy-layer change (e.g. a multi-org RLS policy).
|
|
156
|
+
* Deferred deliberately — do not swap this for a blanket bypass without
|
|
157
|
+
* re-checking the WHERE is still fully server-built.
|
|
138
158
|
*/
|
|
139
159
|
private runRead;
|
|
140
160
|
find(filter: Partial<TFilter>, orgId?: string, parentOrgId?: string): Promise<TEntity[]>;
|
|
@@ -156,15 +176,24 @@ export declare abstract class CrudService<TEntity extends BaseEntity, TFilter, T
|
|
|
156
176
|
*
|
|
157
177
|
* @param filter - Filter criteria
|
|
158
178
|
* @param orgId - User's organization ID (optional — omit for anonymous/system-public-only access)
|
|
179
|
+
* @param parentOrgId - Org → team hierarchy: widen the count to the parent org's
|
|
180
|
+
* public rows. MUST mirror `find`/`findPaginated`'s widening (same
|
|
181
|
+
* `buildConditions` args + sysadmin-scoped read via `runRead`) so a paged
|
|
182
|
+
* list's `total` matches the rows a widened `find()` returns — otherwise the
|
|
183
|
+
* count omits the parent's rows and reports a narrower total than the data set.
|
|
159
184
|
*/
|
|
160
|
-
count(filter: Partial<TFilter>, orgId?: string): Promise<number>;
|
|
185
|
+
count(filter: Partial<TFilter>, orgId?: string, parentOrgId?: string): Promise<number>;
|
|
161
186
|
/**
|
|
162
187
|
* Find a single entity by ID
|
|
163
188
|
*
|
|
164
189
|
* @param id - Entity ID
|
|
165
190
|
* @param orgId - User's organization ID (optional — omit for anonymous/system-public-only access)
|
|
191
|
+
* @param parentOrgId - Org → team hierarchy: widen visibility to the parent
|
|
192
|
+
* org's public rows (so a team can fetch a parent's public entity by id).
|
|
193
|
+
* Same opt-in + sysadmin-scoped read as `find`/`findPaginated`; the
|
|
194
|
+
* access-control WHERE clause is the authoritative tenancy gate.
|
|
166
195
|
*/
|
|
167
|
-
findById(id: string, orgId?: string): Promise<TEntity | null>;
|
|
196
|
+
findById(id: string, orgId?: string, parentOrgId?: string): Promise<TEntity | null>;
|
|
168
197
|
/**
|
|
169
198
|
* Defense-in-depth tenant stamp. RLS is in owner-bypass mode, so the app layer
|
|
170
199
|
* is the only tenant gate on writes. A NON-sysadmin caller may only write into
|
|
@@ -201,9 +230,23 @@ export declare abstract class CrudService<TEntity extends BaseEntity, TFilter, T
|
|
|
201
230
|
* Uses upsert (onConflictDoUpdate) — all rows are inserted in one query per chunk.
|
|
202
231
|
* Chunks of 100 to stay within PostgreSQL parameter limits.
|
|
203
232
|
*/
|
|
233
|
+
/**
|
|
234
|
+
* Build the `onConflictDoUpdate` SET for a bulk upsert. Unlike a single-row
|
|
235
|
+
* create (which can spread the one row's data), a batched insert has many rows,
|
|
236
|
+
* so each updatable column is written from `excluded.*` (the would-be-inserted
|
|
237
|
+
* value) — otherwise an existing row's fields are silently discarded and only
|
|
238
|
+
* timestamps bump. Skips identity/immutable (`id`, `createdAt`, `createdBy`)
|
|
239
|
+
* and the conflict-target columns; `updatedAt`/`updatedBy` get the fresh values.
|
|
240
|
+
*/
|
|
241
|
+
private buildBulkUpsertSet;
|
|
204
242
|
bulkCreate(items: TInsert[], userId: string): Promise<TEntity[]>;
|
|
205
243
|
/**
|
|
206
244
|
* Soft-delete multiple entities by IDs in a single batch operation.
|
|
207
245
|
*/
|
|
208
|
-
bulkDelete(ids: string[], orgId: string, userId: string
|
|
246
|
+
bulkDelete(ids: string[], orgId: string, userId: string,
|
|
247
|
+
/** When true, only PRIVATE records are deleted — mirrors the single-delete
|
|
248
|
+
* `requirePublicAccess` gate so a non-sysadmin can't bulk-delete public
|
|
249
|
+
* (shared/sysadmin-managed) records. No-op for entities without an
|
|
250
|
+
* `accessModifier` column. Callers pass `!isSystemAdmin(req)`. */
|
|
251
|
+
restrictToPrivate?: boolean): Promise<TEntity[]>;
|
|
209
252
|
}
|
package/lib/api/crud-service.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
// Copyright 2026 Pipeline Builder Contributors
|
|
2
2
|
// SPDX-License-Identifier: Apache-2.0
|
|
3
3
|
import { NotFoundError, createLogger } from '@pipeline-builder/api-core';
|
|
4
|
-
import { SQL, eq, and, asc, desc, sql, inArray } from 'drizzle-orm';
|
|
4
|
+
import { SQL, eq, and, asc, desc, sql, inArray, getTableColumns } from 'drizzle-orm';
|
|
5
5
|
import { withTenantTx, runWithTenantContext, getTenantContext } from '../database/tenancy.js';
|
|
6
6
|
/** Pagination defaults — read from env to match CoreConstants in pipeline-core. */
|
|
7
7
|
const DEFAULT_PAGE_LIMIT = parseInt(process.env.DEFAULT_PAGE_LIMIT || '100', 10);
|
|
@@ -48,15 +48,27 @@ export function drizzleCount(rows) {
|
|
|
48
48
|
* protected buildConditions(filter, orgId) { return buildPipelineConditions(filter, orgId); }
|
|
49
49
|
* protected getSortColumn(sortBy) { return sortColumnMap[sortBy] ?? null; }
|
|
50
50
|
* protected getProjectColumn() { return schema.pipeline.project; }
|
|
51
|
-
* protected getOrgColumn() { return schema.pipeline.
|
|
51
|
+
* protected getOrgColumn() { return schema.pipeline.orgId; }
|
|
52
52
|
* }
|
|
53
53
|
* ```
|
|
54
54
|
*/
|
|
55
55
|
export class CrudService {
|
|
56
56
|
_logger = createLogger('crud-service');
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
57
|
+
constructor() {
|
|
58
|
+
// Fail fast if a subclass doesn't expose a tenant org column. The write
|
|
59
|
+
// paths (writeConditions / bulkDelete) pin mutations to the caller's own
|
|
60
|
+
// org through it; a missing column would silently drop that guard — a
|
|
61
|
+
// cross-tenant fail-open — so assert its presence up front.
|
|
62
|
+
if (this.getOrgColumn() == null) {
|
|
63
|
+
throw new Error(`${this.constructor.name}: getOrgColumn() must return the tenant org column`);
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
/** Build conditions for a single entity by ID.
|
|
67
|
+
* `parentOrgId` widens visibility to a parent org's public rows (org → team
|
|
68
|
+
* hierarchy) — same opt-in semantics as `find`/`findPaginated`. Omitted by the
|
|
69
|
+
* write path (`writeConditions`), which must stay own-org scoped. */
|
|
70
|
+
idConditions(id, orgId, parentOrgId) {
|
|
71
|
+
return this.buildConditions({ id }, orgId, parentOrgId);
|
|
60
72
|
}
|
|
61
73
|
/**
|
|
62
74
|
* Conditions for a MUTATION (update/delete) of a single entity.
|
|
@@ -70,9 +82,11 @@ export class CrudService {
|
|
|
70
82
|
*/
|
|
71
83
|
writeConditions(id, orgId) {
|
|
72
84
|
const conditions = this.idConditions(id, orgId);
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
85
|
+
// Pin the mutation to the caller's own org via the tenant column
|
|
86
|
+
// (getOrgColumn, asserted non-null in the constructor) — consistent with
|
|
87
|
+
// setDefault and without the old silent fail-open when the property was absent.
|
|
88
|
+
if (orgId)
|
|
89
|
+
conditions.push(eq(this.getOrgColumn(), orgId));
|
|
76
90
|
return conditions;
|
|
77
91
|
}
|
|
78
92
|
// Lifecycle hooks — override in subclasses to react to mutations
|
|
@@ -95,6 +109,18 @@ export class CrudService {
|
|
|
95
109
|
* run under sysadmin context — the access-control WHERE clause (own + parent +
|
|
96
110
|
* system public, built server-side from a trusted JWT claim) is then the
|
|
97
111
|
* authoritative tenancy gate. Without `parentOrgId` it stays RLS-scoped.
|
|
112
|
+
*
|
|
113
|
+
* INVARIANT (why the sysadmin bypass is safe): the WHERE clause is always
|
|
114
|
+
* server-built by `buildConditions(filter, orgId, parentOrgId)` from values
|
|
115
|
+
* derived from the validated JWT (`orgId` = active org, `parentOrgId` = the
|
|
116
|
+
* active org's parent). None of them is a raw user-supplied predicate, so the
|
|
117
|
+
* bypass only ever widens the read to the caller's own subtree + system public
|
|
118
|
+
* rows — it can NOT be steered at an arbitrary org. NOTE: this does remove the
|
|
119
|
+
* RLS backstop for the widened read; a single-GUC `app.org_id` can't express
|
|
120
|
+
* the "own OR parent OR system" set the policy would need, so replacing the
|
|
121
|
+
* bypass would require a tenancy-layer change (e.g. a multi-org RLS policy).
|
|
122
|
+
* Deferred deliberately — do not swap this for a blanket bypass without
|
|
123
|
+
* re-checking the WHERE is still fully server-built.
|
|
98
124
|
*/
|
|
99
125
|
runRead(parentOrgId, fn) {
|
|
100
126
|
return parentOrgId ? runWithTenantContext({ isSuperAdmin: true }, fn) : fn();
|
|
@@ -200,13 +226,18 @@ export class CrudService {
|
|
|
200
226
|
*
|
|
201
227
|
* @param filter - Filter criteria
|
|
202
228
|
* @param orgId - User's organization ID (optional — omit for anonymous/system-public-only access)
|
|
229
|
+
* @param parentOrgId - Org → team hierarchy: widen the count to the parent org's
|
|
230
|
+
* public rows. MUST mirror `find`/`findPaginated`'s widening (same
|
|
231
|
+
* `buildConditions` args + sysadmin-scoped read via `runRead`) so a paged
|
|
232
|
+
* list's `total` matches the rows a widened `find()` returns — otherwise the
|
|
233
|
+
* count omits the parent's rows and reports a narrower total than the data set.
|
|
203
234
|
*/
|
|
204
|
-
async count(filter, orgId) {
|
|
205
|
-
const conditions = this.buildConditions(filter, orgId);
|
|
206
|
-
const [result] = await withTenantTx(async (tx) => tx
|
|
235
|
+
async count(filter, orgId, parentOrgId) {
|
|
236
|
+
const conditions = this.buildConditions(filter, orgId, parentOrgId);
|
|
237
|
+
const [result] = await this.runRead(parentOrgId, () => withTenantTx(async (tx) => tx
|
|
207
238
|
.select({ count: sql `count(*)::int` })
|
|
208
239
|
.from(this.schema)
|
|
209
|
-
.where(and(...conditions)).then(r => drizzleCount(r)));
|
|
240
|
+
.where(and(...conditions)).then(r => drizzleCount(r))));
|
|
210
241
|
return result?.count || 0;
|
|
211
242
|
}
|
|
212
243
|
/**
|
|
@@ -214,14 +245,18 @@ export class CrudService {
|
|
|
214
245
|
*
|
|
215
246
|
* @param id - Entity ID
|
|
216
247
|
* @param orgId - User's organization ID (optional — omit for anonymous/system-public-only access)
|
|
248
|
+
* @param parentOrgId - Org → team hierarchy: widen visibility to the parent
|
|
249
|
+
* org's public rows (so a team can fetch a parent's public entity by id).
|
|
250
|
+
* Same opt-in + sysadmin-scoped read as `find`/`findPaginated`; the
|
|
251
|
+
* access-control WHERE clause is the authoritative tenancy gate.
|
|
217
252
|
*/
|
|
218
|
-
async findById(id, orgId) {
|
|
219
|
-
const conditions = this.idConditions(id, orgId);
|
|
220
|
-
const results = await withTenantTx(async (tx) => tx
|
|
253
|
+
async findById(id, orgId, parentOrgId) {
|
|
254
|
+
const conditions = this.idConditions(id, orgId, parentOrgId);
|
|
255
|
+
const results = await this.runRead(parentOrgId, () => withTenantTx(async (tx) => tx
|
|
221
256
|
.select()
|
|
222
257
|
.from(this.schema)
|
|
223
258
|
.where(and(...conditions))
|
|
224
|
-
.limit(1).then(r => drizzleRows(r)));
|
|
259
|
+
.limit(1).then(r => drizzleRows(r))));
|
|
225
260
|
return results[0] || null;
|
|
226
261
|
}
|
|
227
262
|
// Mutation operations
|
|
@@ -401,12 +436,40 @@ export class CrudService {
|
|
|
401
436
|
* Uses upsert (onConflictDoUpdate) — all rows are inserted in one query per chunk.
|
|
402
437
|
* Chunks of 100 to stay within PostgreSQL parameter limits.
|
|
403
438
|
*/
|
|
439
|
+
/**
|
|
440
|
+
* Build the `onConflictDoUpdate` SET for a bulk upsert. Unlike a single-row
|
|
441
|
+
* create (which can spread the one row's data), a batched insert has many rows,
|
|
442
|
+
* so each updatable column is written from `excluded.*` (the would-be-inserted
|
|
443
|
+
* value) — otherwise an existing row's fields are silently discarded and only
|
|
444
|
+
* timestamps bump. Skips identity/immutable (`id`, `createdAt`, `createdBy`)
|
|
445
|
+
* and the conflict-target columns; `updatedAt`/`updatedBy` get the fresh values.
|
|
446
|
+
*/
|
|
447
|
+
buildBulkUpsertSet(now, user) {
|
|
448
|
+
const conflictNames = new Set(this.conflictTarget.map((c) => c.name));
|
|
449
|
+
const set = {};
|
|
450
|
+
for (const [key, col] of Object.entries(getTableColumns(this.schema))) {
|
|
451
|
+
const name = col.name;
|
|
452
|
+
if (key === 'id' || key === 'createdAt' || key === 'createdBy' || conflictNames.has(name))
|
|
453
|
+
continue;
|
|
454
|
+
if (key === 'updatedAt') {
|
|
455
|
+
set[key] = now;
|
|
456
|
+
continue;
|
|
457
|
+
}
|
|
458
|
+
if (key === 'updatedBy') {
|
|
459
|
+
set[key] = user;
|
|
460
|
+
continue;
|
|
461
|
+
}
|
|
462
|
+
set[key] = sql `excluded.${sql.identifier(name)}`;
|
|
463
|
+
}
|
|
464
|
+
return set;
|
|
465
|
+
}
|
|
404
466
|
async bulkCreate(items, userId) {
|
|
405
467
|
if (items.length === 0)
|
|
406
468
|
return [];
|
|
407
469
|
const CHUNK_SIZE = 100;
|
|
408
470
|
const now = new Date();
|
|
409
471
|
const user = userId || 'system';
|
|
472
|
+
const conflictSet = this.buildBulkUpsertSet(now, user);
|
|
410
473
|
const results = await withTenantTx(async (tx) => {
|
|
411
474
|
const allCreated = [];
|
|
412
475
|
for (let i = 0; i < items.length; i += CHUNK_SIZE) {
|
|
@@ -421,10 +484,7 @@ export class CrudService {
|
|
|
421
484
|
.values(values)
|
|
422
485
|
.onConflictDoUpdate({
|
|
423
486
|
target: this.conflictTarget,
|
|
424
|
-
set:
|
|
425
|
-
updatedAt: now,
|
|
426
|
-
updatedBy: user,
|
|
427
|
-
},
|
|
487
|
+
set: conflictSet,
|
|
428
488
|
})
|
|
429
489
|
.returning().then(r => drizzleRows(r));
|
|
430
490
|
allCreated.push(...created);
|
|
@@ -439,7 +499,12 @@ export class CrudService {
|
|
|
439
499
|
/**
|
|
440
500
|
* Soft-delete multiple entities by IDs in a single batch operation.
|
|
441
501
|
*/
|
|
442
|
-
async bulkDelete(ids, orgId, userId
|
|
502
|
+
async bulkDelete(ids, orgId, userId,
|
|
503
|
+
/** When true, only PRIVATE records are deleted — mirrors the single-delete
|
|
504
|
+
* `requirePublicAccess` gate so a non-sysadmin can't bulk-delete public
|
|
505
|
+
* (shared/sysadmin-managed) records. No-op for entities without an
|
|
506
|
+
* `accessModifier` column. Callers pass `!isSystemAdmin(req)`. */
|
|
507
|
+
restrictToPrivate = false) {
|
|
443
508
|
if (ids.length === 0)
|
|
444
509
|
return [];
|
|
445
510
|
const now = new Date();
|
|
@@ -447,11 +512,14 @@ export class CrudService {
|
|
|
447
512
|
// Owner-scope the bulk soft-delete: buildConditions also matches system/other
|
|
448
513
|
// -org PUBLIC rows, so without the strict orgId pin a tenant could delete
|
|
449
514
|
// shared records by id. (See writeConditions.)
|
|
450
|
-
const
|
|
515
|
+
const accessCol = this.schema.accessModifier;
|
|
451
516
|
const conditions = [
|
|
452
517
|
inArray(this.schema.id, ids),
|
|
453
518
|
...this.buildConditions({}, orgId),
|
|
454
|
-
|
|
519
|
+
// Tenant column (getOrgColumn, asserted non-null) — consistent with
|
|
520
|
+
// writeConditions; no silent fail-open when the property is absent.
|
|
521
|
+
...(orgId ? [eq(this.getOrgColumn(), orgId)] : []),
|
|
522
|
+
...(restrictToPrivate && accessCol ? [eq(accessCol, 'private')] : []),
|
|
455
523
|
];
|
|
456
524
|
const deleted = await withTenantTx(async (tx) => tx
|
|
457
525
|
.update(this.schema)
|
|
@@ -468,4 +536,4 @@ export class CrudService {
|
|
|
468
536
|
return deleted;
|
|
469
537
|
}
|
|
470
538
|
}
|
|
471
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY3J1ZC1zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL2FwaS9jcnVkLXNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsK0NBQStDO0FBQy9DLHNDQUFzQztBQUV0QyxPQUFPLEVBQUUsYUFBYSxFQUFFLFlBQVksRUFBRSxNQUFNLDRCQUE0QixDQUFDO0FBQ3pFLE9BQU8sRUFBRSxHQUFHLEVBQUUsRUFBRSxFQUFFLEdBQUcsRUFBRSxHQUFHLEVBQUUsSUFBSSxFQUFFLEdBQUcsRUFBRSxPQUFPLEVBQUUsTUFBTSxhQUFhLENBQUM7QUFHcEUsT0FBTyxFQUFFLFlBQVksRUFBRSxvQkFBb0IsRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLHdCQUF3QixDQUFDO0FBRTlGLG1GQUFtRjtBQUNuRixNQUFNLGtCQUFrQixHQUFHLFFBQVEsQ0FBQyxPQUFPLENBQUMsR0FBRyxDQUFDLGtCQUFrQixJQUFJLEtBQUssRUFBRSxFQUFFLENBQUMsQ0FBQztBQUNqRixNQUFNLGNBQWMsR0FBRyxRQUFRLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxjQUFjLElBQUksTUFBTSxFQUFFLEVBQUUsQ0FBQyxDQUFDO0FBRTFFOzs7OztHQUtHO0FBQ0gsTUFBTSxVQUFVLFdBQVcsQ0FBSSxJQUFhO0lBQzFDLE9BQU8sSUFBVyxDQUFDO0FBQ3JCLENBQUM7QUFFRCx3RUFBd0U7QUFDeEUsTUFBTSxVQUFVLFlBQVksQ0FBQyxJQUFhO0lBQ3hDLE9BQU8sSUFBMkIsQ0FBQztBQUNyQyxDQUFDO0FBOENEOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztHQWdDRztBQUNILE1BQU0sT0FBZ0IsV0FBVztJQTRCZCxPQUFPLEdBQUcsWUFBWSxDQUFDLGNBQWMsQ0FBQyxDQUFDO0lBRXhELGtEQUFrRDtJQUMxQyxZQUFZLENBQUMsRUFBVSxFQUFFLEtBQWM7UUFDN0MsT0FBTyxJQUFJLENBQUMsZUFBZSxDQUFDLEVBQUUsRUFBRSxFQUFpQyxFQUFFLEtBQUssQ0FBQyxDQUFDO0lBQzVFLENBQUM7SUFFRDs7Ozs7Ozs7O09BU0c7SUFDSyxlQUFlLENBQUMsRUFBVSxFQUFFLEtBQWM7UUFDaEQsTUFBTSxVQUFVLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxFQUFFLEVBQUUsS0FBSyxDQUFDLENBQUM7UUFDaEQsTUFBTSxNQUFNLEdBQUksSUFBSSxDQUFDLE1BQWMsQ0FBQyxLQUE4QixDQUFDO1FBQ25FLElBQUksS0FBSyxJQUFJLE1BQU07WUFBRSxVQUFVLENBQUMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxNQUFNLEVBQUUsS0FBSyxDQUFDLENBQUMsQ0FBQztRQUN4RCxPQUFPLFVBQVUsQ0FBQztJQUNwQixDQUFDO0lBRUQsaUVBQWlFO0lBQ2pFLDJFQUEyRTtJQUUzRSwyQ0FBMkM7SUFDakMsS0FBSyxDQUFDLGFBQWEsQ0FBQyxPQUFnQixFQUFFLE9BQWUsSUFBa0IsQ0FBQztJQUVsRix3Q0FBd0M7SUFDOUIsS0FBSyxDQUFDLGFBQWEsQ0FBQyxHQUFXLEVBQUUsT0FBZ0IsRUFBRSxPQUFlLElBQWtCLENBQUM7SUFFL0YsNkNBQTZDO0lBQ25DLEtBQUssQ0FBQyxhQUFhLENBQUMsR0FBVyxFQUFFLE9BQWdCLEVBQUUsT0FBZSxJQUFrQixDQUFDO0lBRS9GOzs7OztPQUtHO0lBQ0g7Ozs7OztPQU1HO0lBQ0ssT0FBTyxDQUFJLFdBQStCLEVBQUUsRUFBb0I7UUFDdEUsT0FBTyxXQUFXLENBQUMsQ0FBQyxDQUFDLG9CQUFvQixDQUFDLEVBQUUsWUFBWSxFQUFFLElBQUksRUFBRSxFQUFFLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFLEVBQUUsQ0FBQztJQUMvRSxDQUFDO0lBRUQsS0FBSyxDQUFDLElBQUksQ0FBQyxNQUF3QixFQUFFLEtBQWMsRUFBRSxXQUFvQjtRQUN2RSxNQUFNLFVBQVUsR0FBRyxJQUFJLENBQUMsZUFBZSxDQUFDLE1BQU0sRUFBRSxLQUFLLEVBQUUsV0FBVyxDQUFDLENBQUM7UUFFcEUsT0FBTyxJQUFJLENBQUMsT0FBTyxDQUFDLFdBQVcsRUFBRSxHQUFHLEVBQUUsQ0FBQyxZQUFZLENBQUMsS0FBSyxFQUFFLEVBQUUsRUFBRSxFQUFFLENBQUMsRUFBRTthQUNqRSxNQUFNLEVBQUU7YUFDUixJQUFJLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQzthQUNqQixLQUFLLENBQUMsR0FBRyxDQUFDLEdBQUcsVUFBVSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxXQUFXLENBQVUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFDcEUsQ0FBQztJQUVEOzs7Ozs7T0FNRztJQUNILEtBQUssQ0FBQyxhQUFhLENBQ2pCLE1BQXdCLEVBQ3hCLEtBQWMsRUFDZCxVQUF3QixFQUFFLEVBQzFCLFdBQW9CO1FBRXBCLE1BQU0sRUFBRSxLQUFLLEVBQUUsUUFBUSxHQUFHLGtCQUFrQixFQUFFLE1BQU0sR0FBRyxDQUFDLEVBQUUsTUFBTSxFQUFFLFNBQVMsR0FBRyxLQUFLLEVBQUUsWUFBWSxHQUFHLEtBQUssRUFBRSxNQUFNLEVBQUUsTUFBTSxFQUFFLEdBQUcsT0FBTyxDQUFDO1FBQ3RJLE1BQU0sS0FBSyxHQUFHLElBQUksQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxDQUFDLEVBQUUsUUFBUSxDQUFDLEVBQUUsY0FBYyxDQUFDLENBQUM7UUFFOUQscUVBQXFFO1FBQ3JFLE1BQU0sU0FBUyxHQUFHLENBQUMsQ0FBQyxDQUFDLE1BQU0sSUFBSSxNQUFNLENBQUMsQ0FBQztRQUV2QyxNQUFNLFVBQVUsR0FBRyxJQUFJLENBQUMsZUFBZSxDQUFDLE1BQU0sRUFBRSxLQUFLLEVBQUUsV0FBVyxDQUFDLENBQUM7UUFFcEUsa0VBQWtFO1FBQ2xFLElBQUksU0FBUyxFQUFFLENBQUM7WUFDZCxNQUFNLFVBQVUsR0FBRyxJQUFJLENBQUMsYUFBYSxDQUFDLE1BQU0sQ0FBQyxDQUFDO1lBQzlDLElBQUksVUFBVSxFQUFFLENBQUM7Z0JBQ2YsTUFBTSxFQUFFLEdBQUcsU0FBUyxLQUFLLE1BQU07b0JBQzdCLENBQUMsQ0FBQyxHQUFHLENBQUEsR0FBRyxVQUFVLE1BQU0sTUFBTSxFQUFFO29CQUNoQyxDQUFDLENBQUMsR0FBRyxDQUFBLEdBQUcsVUFBVSxNQUFNLE1BQU0sRUFBRSxDQUFDO2dCQUNuQyxVQUFVLENBQUMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxDQUFDO1lBQ3RCLENBQUM7UUFDSCxDQUFDO1FBRUQsaUVBQWlFO1FBQ2pFLHdFQUF3RTtRQUN4RSxvRUFBb0U7UUFDcEUseUVBQXlFO1FBQ3pFLDBFQUEwRTtRQUMxRSxPQUFPLElBQUksQ0FBQyxPQUFPLENBQUMsV0FBVyxFQUFFLEdBQUcsRUFBRSxDQUFDLFlBQVksQ0FBQyxLQUFLLEVBQUUsRUFBRSxFQUFFLEVBQUU7WUFDL0QsMkRBQTJEO1lBQzNELE1BQU0sVUFBVSxHQUFHLE1BQU0sQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLGdCQUFnQixDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUMsQ0FBQyxTQUFTLENBQUM7WUFDdEUsSUFBSSxLQUFLLEdBQUcsVUFBVTtnQkFDcEIsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxNQUFNLENBQUMsVUFBaUIsQ0FBQyxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxHQUFHLFVBQVUsQ0FBQyxDQUFDO2dCQUMxRSxDQUFDLENBQUMsRUFBRSxDQUFDLE1BQU0sRUFBRSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxHQUFHLFVBQVUsQ0FBQyxDQUFDLENBQUM7WUFFNUQsSUFBSSxNQUFNLEVBQUUsQ0FBQztnQkFDWCxNQUFNLFVBQVUsR0FBRyxJQUFJLENBQUMsYUFBYSxDQUFDLE1BQU0sQ0FBQyxDQUFDO2dCQUM5QyxJQUFJLFVBQVUsRUFBRSxDQUFDO29CQUNmLEtBQUssR0FBRyxLQUFLLENBQUMsT0FBTyxDQUFDLFNBQVMsS0FBSyxNQUFNLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxVQUFVLENBQUMsQ0FBQyxDQUFDLENBQUMsR0FBRyxDQUFDLFVBQVUsQ0FBQyxDQUFRLENBQUM7Z0JBQzFGLENBQUM7WUFDSCxDQUFDO1lBRUQsbURBQW1EO1lBQ25ELE1BQU0sZUFBZSxHQUFHLFNBQVMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxNQUFNLENBQUM7WUFDL0MsTUFBTSxJQUFJLEdBQUcsTUFBTSxLQUFLO2lCQUNyQixLQUFLLENBQUMsS0FBSyxHQUFHLENBQUMsQ0FBQztpQkFDaEIsTUFBTSxDQUFDLGVBQWUsQ0FBQyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLFdBQVcsQ0FBVSxDQUFDLENBQUMsQ0FBQyxDQUFDO1lBRTlELE1BQU0sT0FBTyxHQUFHLElBQUksQ0FBQyxNQUFNLEdBQUcsS0FBSyxDQUFDO1lBQ3BDLE1BQU0sSUFBSSxHQUFHLE9BQU8sQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDLEVBQUUsS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQztZQUVuRCxNQUFNLE1BQU0sR0FBNkIsRUFBRSxJQUFJLEVBQUUsS0FBSyxFQUFFLE1BQU0sRUFBRSxlQUFlLEVBQUUsT0FBTyxFQUFFLENBQUM7WUFFM0YseURBQXlEO1lBQ3pELElBQUksSUFBSSxDQUFDLE1BQU0sR0FBRyxDQUFDLElBQUksTUFBTSxFQUFFLENBQUM7Z0JBQzlCLE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsTUFBTSxHQUFHLENBQUMsQ0FBNEIsQ0FBQztnQkFDbEUsTUFBTSxXQUFXLEdBQUcsUUFBUSxDQUFDLE1BQU0sQ0FBQyxDQUFDO2dCQUNyQyxJQUFJLFdBQVcsS0FBSyxTQUFTLEVBQUUsQ0FBQztvQkFDOUIsTUFBTSxDQUFDLFVBQVUsR0FBRyxXQUFXLFlBQVksSUFBSSxDQUFDLENBQUMsQ0FBQyxXQUFXLENBQUMsV0FBVyxFQUFFLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxXQUFXLENBQUMsQ0FBQztnQkFDcEcsQ0FBQztZQUNILENBQUM7WUFFRCwwRUFBMEU7WUFDMUUsb0VBQW9FO1lBQ3BFLElBQUksWUFBWSxFQUFFLENBQUM7Z0JBQ2pCLE1BQU0sY0FBYyxHQUFHLElBQUksQ0FBQyxlQUFlLENBQUMsTUFBTSxFQUFFLEtBQUssRUFBRSxXQUFXLENBQUMsQ0FBQztnQkFDeEUsTUFBTSxDQUFDLFdBQVcsQ0FBQyxHQUFHLE1BQU0sRUFBRTtxQkFDM0IsTUFBTSxDQUFDLEVBQUUsS0FBSyxFQUFFLEdBQUcsQ0FBUSxlQUFlLEVBQUUsQ0FBQztxQkFDN0MsSUFBSSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUM7cUJBQ2pCLEtBQUssQ0FBQyxHQUFHLENBQUMsR0FBRyxjQUFjLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLFlBQVksQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO2dCQUM1RCxNQUFNLENBQUMsS0FBSyxHQUFHLFdBQVcsRUFBRSxLQUFLLElBQUksQ0FBQyxDQUFDO1lBQ3pDLENBQUM7WUFFRCxPQUFPLE1BQU0sQ0FBQztRQUNoQixDQUFDLENBQUMsQ0FBQyxDQUFDO0lBQ04sQ0FBQztJQUVEOzs7T0FHRztJQUNLLGdCQUFnQixDQUFDLE1BQWdCO1FBQ3ZDLElBQUksTUFBTSxDQUFDLE1BQU0sS0FBSyxDQUFDO1lBQUUsT0FBTyxTQUFTLENBQUM7UUFFMUMsTUFBTSxPQUFPLEdBQTRCLEVBQUUsQ0FBQztRQUM1Qyx3Q0FBd0M7UUFDeEMsT0FBTyxDQUFDLEVBQUUsR0FBSSxJQUFJLENBQUMsTUFBYyxDQUFDLEVBQUUsQ0FBQztRQUVyQyxLQUFLLE1BQU0sS0FBSyxJQUFJLE1BQU0sRUFBRSxDQUFDO1lBQzNCLElBQUksS0FBSyxLQUFLLElBQUk7Z0JBQUUsU0FBUyxDQUFDLG1CQUFtQjtZQUNqRCxNQUFNLEdBQUcsR0FBSSxJQUFJLENBQUMsTUFBYyxDQUFDLEtBQUssQ0FBQyxDQUFDO1lBQ3hDLElBQUksR0FBRztnQkFBRSxPQUFPLENBQUMsS0FBSyxDQUFDLEdBQUcsR0FBRyxDQUFDO1FBQ2hDLENBQUM7UUFFRCwrQ0FBK0M7UUFDL0MsT0FBTyxPQUFPLENBQUM7SUFDakIsQ0FBQztJQUVEOzs7OztPQUtHO0lBQ0gsS0FBSyxDQUFDLEtBQUssQ0FBQyxNQUF3QixFQUFFLEtBQWM7UUFDbEQsTUFBTSxVQUFVLEdBQUcsSUFBSSxDQUFDLGVBQWUsQ0FBQyxNQUFNLEVBQUUsS0FBSyxDQUFDLENBQUM7UUFFdkQsTUFBTSxDQUFDLE1BQU0sQ0FBQyxHQUFHLE1BQU0sWUFBWSxDQUFDLEtBQUssRUFBRSxFQUFFLEVBQUUsRUFBRSxDQUFDLEVBQUU7YUFDakQsTUFBTSxDQUFDLEVBQUUsS0FBSyxFQUFFLEdBQUcsQ0FBUSxlQUFlLEVBQUUsQ0FBQzthQUM3QyxJQUFJLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQzthQUNqQixLQUFLLENBQUMsR0FBRyxDQUFDLEdBQUcsVUFBVSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxZQUFZLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBRXpELE9BQU8sTUFBTSxFQUFFLEtBQUssSUFBSSxDQUFDLENBQUM7SUFDNUIsQ0FBQztJQUVEOzs7OztPQUtHO0lBQ0gsS0FBSyxDQUFDLFFBQVEsQ0FBQyxFQUFVLEVBQUUsS0FBYztRQUN2QyxNQUFNLFVBQVUsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLEVBQUUsRUFBRSxLQUFLLENBQUMsQ0FBQztRQUVoRCxNQUFNLE9BQU8sR0FBRyxNQUFNLFlBQVksQ0FBQyxLQUFLLEVBQUUsRUFBRSxFQUFFLEVBQUUsQ0FBQyxFQUFFO2FBQ2hELE1BQU0sRUFBRTthQUNSLElBQUksQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDO2FBQ2pCLEtBQUssQ0FBQyxHQUFHLENBQUMsR0FBRyxVQUFVLENBQUMsQ0FBQzthQUN6QixLQUFLLENBQUMsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsV0FBVyxDQUFVLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQztRQUVoRCxPQUFPLE9BQU8sQ0FBQyxDQUFDLENBQUMsSUFBSSxJQUFJLENBQUM7SUFDNUIsQ0FBQztJQUVELHNCQUFzQjtJQUV0Qjs7Ozs7OztPQU9HO0lBQ08sWUFBWSxDQUFDLElBQWE7UUFDbEMsTUFBTSxHQUFHLEdBQUcsZ0JBQWdCLEVBQUUsQ0FBQztRQUMvQixNQUFNLENBQUMsR0FBRyxJQUErQixDQUFDO1FBQzFDLElBQUksR0FBRyxJQUFJLENBQUMsR0FBRyxDQUFDLFlBQVksSUFBSSxHQUFHLENBQUMsS0FBSyxJQUFJLE9BQU8sSUFBSSxDQUFDLElBQUksQ0FBQyxDQUFDLEtBQUssS0FBSyxHQUFHLENBQUMsS0FBSyxFQUFFLENBQUM7WUFDbkYsSUFBSSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsOERBQThELEVBQUU7Z0JBQ2hGLFFBQVEsRUFBRSxDQUFDLENBQUMsS0FBSyxFQUFFLFFBQVEsRUFBRSxHQUFHLENBQUMsS0FBSzthQUN2QyxDQUFDLENBQUM7WUFDSCxPQUFPLEVBQUUsR0FBRyxDQUFDLEVBQUUsS0FBSyxFQUFFLEdBQUcsQ0FBQyxLQUFLLEVBQWEsQ0FBQztRQUMvQyxDQUFDO1FBQ0QsT0FBTyxJQUFJLENBQUM7SUFDZCxDQUFDO0lBRUQ7O09BRUc7SUFDSCxLQUFLLENBQUMsTUFBTSxDQUFDLElBQWEsRUFBRSxNQUFjO1FBQ3hDLE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDekMsTUFBTSxDQUFDLE9BQU8sQ0FBQyxHQUFHLE1BQU0sWUFBWSxDQUFDLEtBQUssRUFBRSxFQUFFLEVBQUUsRUFBRSxDQUFDLEVBQUU7YUFDbEQsTUFBTSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUM7YUFDbkIsTUFBTSxDQUFDO1lBQ04sR0FBRyxRQUFRO1lBQ1gsU0FBUyxFQUFFLE1BQU0sSUFBSSxRQUFRO1lBQzdCLFNBQVMsRUFBRSxNQUFNLElBQUksUUFBUTtTQUN2QixDQUFDO2FBQ1Isa0JBQWtCLENBQUM7WUFDbEIsTUFBTSxFQUFFLElBQUksQ0FBQyxjQUFxQjtZQUNsQyxHQUFHLEVBQUU7Z0JBQ0gsR0FBRyxRQUFRO2dCQUNYLFNBQVMsRUFBRSxJQUFJLElBQUksRUFBRTtnQkFDckIsU0FBUyxFQUFFLE1BQU0sSUFBSSxRQUFRO2FBQ3ZCO1NBQ1QsQ0FBQzthQUNELFNBQVMsRUFBRSxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLFdBQVcsQ0FBVSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFFbkQsdUVBQXVFO1FBQ3ZFLHlFQUF5RTtRQUN6RSxvRUFBb0U7UUFDcEUsc0VBQXNFO1FBQ3RFLElBQUksQ0FBQztZQUNILE1BQU0sSUFBSSxDQUFDLGFBQWEsQ0FBQyxPQUFPLEVBQUUsTUFBTSxDQUFDLENBQUM7UUFDNUMsQ0FBQztRQUFDLE9BQU8sR0FBRyxFQUFFLENBQUM7WUFDYixJQUFJLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyx1QkFBdUIsRUFBRSxFQUFFLEtBQUssRUFBRSxNQUFNLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQyxDQUFDO1FBQ3JFLENBQUM7UUFFRCxPQUFPLE9BQU8sQ0FBQztJQUNqQixDQUFDO0lBRUQ7O09BRUc7SUFDSCxLQUFLLENBQUMsTUFBTSxDQUNWLEVBQVUsRUFDVixJQUFzQixFQUN0QixLQUFhLEVBQ2IsTUFBYztRQUVkLE1BQU0sVUFBVSxHQUFHLElBQUksQ0FBQyxlQUFlLENBQUMsRUFBRSxFQUFFLEtBQUssQ0FBQyxDQUFDO1FBRW5ELE1BQU0sQ0FBQyxPQUFPLENBQUMsR0FBRyxNQUFNLFlBQVksQ0FBQyxLQUFLLEVBQUUsRUFBRSxFQUFFLEVBQUUsQ0FBQyxFQUFFO2FBQ2xELE1BQU0sQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDO2FBQ25CLEdBQUcsQ0FBQztZQUNILEdBQUcsSUFBSTtZQUNQLFNBQVMsRUFBRSxJQUFJLElBQUksRUFBRTtZQUNyQixTQUFTLEVBQUUsTUFBTSxJQUFJLFFBQVE7U0FDdkIsQ0FBQzthQUNSLEtBQUssQ0FBQyxHQUFHLENBQUMsR0FBRyxVQUFVLENBQUMsQ0FBQzthQUN6QixTQUFTLEVBQUUsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxXQUFXLENBQVUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBRW5ELElBQUksT0FBTyxFQUFFLENBQUM7WUFDWixJQUFJLENBQUM7Z0JBQ0gsTUFBTSxJQUFJLENBQUMsYUFBYSxDQUFDLEVBQUUsRUFBRSxPQUFPLEVBQUUsTUFBTSxDQUFDLENBQUM7WUFDaEQsQ0FBQztZQUFDLE9BQU8sR0FBRyxFQUFFLENBQUM7Z0JBQ2IsSUFBSSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsdUJBQXVCLEVBQUUsRUFBRSxLQUFLLEVBQUUsTUFBTSxDQUFDLEdBQUcsQ0FBQyxFQUFFLENBQUMsQ0FBQztZQUNyRSxDQUFDO1FBQ0gsQ0FBQztRQUVELE9BQU8sT0FBTyxJQUFJLElBQUksQ0FBQztJQUN6QixDQUFDO0lBRUQ7O09BRUc7SUFDSCxLQUFLLENBQUMsTUFBTSxDQUFDLEVBQVUsRUFBRSxLQUFhLEVBQUUsTUFBYztRQUNwRCxNQUFNLFVBQVUsR0FBRyxJQUFJLENBQUMsZUFBZSxDQUFDLEVBQUUsRUFBRSxLQUFLLENBQUMsQ0FBQztRQUVuRCxNQUFNLENBQUMsT0FBTyxDQUFDLEdBQUcsTUFBTSxZQUFZLENBQUMsS0FBSyxFQUFFLEVBQUUsRUFBRSxFQUFFLENBQUMsRUFBRTthQUNsRCxNQUFNLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQzthQUNuQixHQUFHLENBQUM7WUFDSCxRQUFRLEVBQUUsS0FBSztZQUNmLFNBQVMsRUFBRSxJQUFJLElBQUksRUFBRTtZQUNyQixTQUFTLEVBQUUsTUFBTSxJQUFJLFFBQVE7WUFDN0IsU0FBUyxFQUFFLElBQUksSUFBSSxFQUFFO1lBQ3JCLFNBQVMsRUFBRSxNQUFNLElBQUksUUFBUTtTQUN2QixDQUFDO2FBQ1IsS0FBSyxDQUFDLEdBQUcsQ0FBQyxHQUFHLFVBQVUsQ0FBQyxDQUFDO2FBQ3pCLFNBQVMsRUFBRSxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLFdBQVcsQ0FBVSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFFbkQsSUFBSSxPQUFPLEVBQUUsQ0FBQztZQUNaLElBQUksQ0FBQztnQkFDSCxNQUFNLElBQUksQ0FBQyxhQUFhLENBQUMsRUFBRSxFQUFFLE9BQU8sRUFBRSxNQUFNLENBQUMsQ0FBQztZQUNoRCxDQUFDO1lBQUMsT0FBTyxHQUFHLEVBQUUsQ0FBQztnQkFDYixJQUFJLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyx1QkFBdUIsRUFBRSxFQUFFLEtBQUssRUFBRSxNQUFNLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQyxDQUFDO1lBQ3JFLENBQUM7UUFDSCxDQUFDO1FBRUQsT0FBTyxPQUFPLElBQUksSUFBSSxDQUFDO0lBQ3pCLENBQUM7SUFFRDs7OztPQUlHO0lBQ0gsS0FBSyxDQUFDLFVBQVUsQ0FDZCxPQUFlLEVBQ2YsR0FBVyxFQUNYLEVBQVUsRUFDVixNQUFjO1FBRWQsOEVBQThFO1FBQzlFLDBFQUEwRTtRQUMxRSxxRUFBcUU7UUFDckUsTUFBTSxHQUFHLEdBQUcsZ0JBQWdCLEVBQUUsQ0FBQztRQUMvQixJQUFJLEdBQUcsSUFBSSxDQUFDLEdBQUcsQ0FBQyxZQUFZLElBQUksR0FBRyxDQUFDLEtBQUs7WUFBRSxHQUFHLEdBQUcsR0FBRyxDQUFDLEtBQUssQ0FBQztRQUMzRCxPQUFPLFlBQVksQ0FBQyxLQUFLLEVBQUUsRUFBRSxFQUFFLEVBQUU7WUFDL0IsTUFBTSxTQUFTLEdBQUcsSUFBSSxDQUFDLFlBQVksRUFBRSxDQUFDO1lBQ3RDLE1BQU0sYUFBYSxHQUFHLElBQUksQ0FBQyxnQkFBZ0IsRUFBRSxDQUFDO1lBRTlDLGlEQUFpRDtZQUNqRCxNQUFNLGVBQWUsR0FBRztnQkFDdEIsRUFBRSxDQUFDLFNBQVMsRUFBRSxHQUFHLENBQUM7Z0JBQ2xCLEVBQUUsQ0FBRSxJQUFJLENBQUMsTUFBYyxDQUFDLFNBQVMsRUFBRSxJQUFJLENBQUM7YUFDekMsQ0FBQztZQUNGLElBQUksYUFBYSxFQUFFLENBQUM7Z0JBQ2xCLGVBQWUsQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLGFBQWEsRUFBRSxPQUFPLENBQUMsQ0FBQyxDQUFDO1lBQ25ELENBQUM7WUFFRCxnRkFBZ0Y7WUFDaEYsTUFBTSxFQUFFLENBQUMsT0FBTyxDQUNkLEdBQUcsQ0FBQSxrQkFBa0IsSUFBSSxDQUFDLE1BQU07b0JBQ3BCLFNBQVMsTUFBTSxHQUFHO29CQUNqQixJQUFJLENBQUMsTUFBYyxDQUFDLFNBQVM7Y0FDcEMsYUFBYSxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUEsT0FBTyxhQUFhLE1BQU0sT0FBTyxFQUFFLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQSxFQUFFO3VCQUNyRCxDQUNoQixDQUFDO1lBRUYsNENBQTRDO1lBQzVDLE1BQU0sRUFBRTtpQkFDTCxNQUFNLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQztpQkFDbkIsR0FBRyxDQUFDO2dCQUNILFNBQVMsRUFBRSxLQUFLO2dCQUNoQixTQUFTLEVBQUUsSUFBSSxJQUFJLEVBQUU7Z0JBQ3JCLFNBQVMsRUFBRSxNQUFNLElBQUksUUFBUTthQUN2QixDQUFDO2lCQUNSLEtBQUssQ0FBQyxHQUFHLENBQUMsR0FBRyxlQUFlLENBQUMsQ0FBQyxDQUFDO1lBRWxDLHNDQUFzQztZQUN0QyxNQUFNLENBQUMsT0FBTyxDQUFDLEdBQUcsTUFBTSxFQUFFO2lCQUN2QixNQUFNLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQztpQkFDbkIsR0FBRyxDQUFDO2dCQUNILFNBQVMsRUFBRSxJQUFJO2dCQUNmLFNBQVMsRUFBRSxJQUFJLElBQUksRUFBRTtnQkFDckIsU0FBUyxFQUFFLE1BQU0sSUFBSSxRQUFRO2FBQ3ZCLENBQUM7aUJBQ1IsS0FBSyxDQUNKLEdBQUcsQ0FDRCxFQUFFLENBQUUsSUFBSSxDQUFDLE1BQWMsQ0FBQyxFQUFFLEVBQUUsRUFBRSxDQUFDLEVBQy9CLEVBQUUsQ0FBQyxTQUFTLEVBQUUsR0FBRyxDQUFDLENBQ25CLENBQ0Y7aUJBQ0EsU0FBUyxFQUFFLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsV0FBVyxDQUFVLENBQUMsQ0FBQyxDQUFDLENBQUM7WUFFbEQsSUFBSSxDQUFDLE9BQU8sRUFBRSxDQUFDO2dCQUNiLE1BQU0sSUFBSSxhQUFhLENBQUMsa0JBQWtCLEVBQUUsWUFBWSxDQUFDLENBQUM7WUFDNUQsQ0FBQztZQUVELE9BQU8sT0FBTyxDQUFDO1FBQ2pCLENBQUMsQ0FBQyxDQUFDO0lBQ0wsQ0FBQztJQUVEOztPQUVHO0lBQ0gsS0FBSyxDQUFDLFVBQVUsQ0FDZCxNQUF3QixFQUN4QixJQUFzQixFQUN0QixLQUFhLEVBQ2IsTUFBYztRQUVkLE1BQU0sVUFBVSxHQUFHLElBQUksQ0FBQyxlQUFlLENBQUMsTUFBTSxFQUFFLEtBQUssQ0FBQyxDQUFDO1FBRXZELE9BQU8sWUFBWSxDQUFDLEtBQUssRUFBRSxFQUFFLEVBQUUsRUFBRSxDQUFDLEVBQUU7YUFDakMsTUFBTSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUM7YUFDbkIsR0FBRyxDQUFDO1lBQ0gsR0FBRyxJQUFJO1lBQ1AsU0FBUyxFQUFFLElBQUksSUFBSSxFQUFFO1lBQ3JCLFNBQVMsRUFBRSxNQUFNLElBQUksUUFBUTtTQUN2QixDQUFDO2FBQ1IsS0FBSyxDQUFDLEdBQUcsQ0FBQyxHQUFHLFVBQVUsQ0FBQyxDQUFDO2FBQ3pCLFNBQVMsRUFBRSxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLFdBQVcsQ0FBVSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFDckQsQ0FBQztJQUVEOzs7O09BSUc7SUFDSCxLQUFLLENBQUMsVUFBVSxDQUFDLEtBQWdCLEVBQUUsTUFBYztRQUMvQyxJQUFJLEtBQUssQ0FBQyxNQUFNLEtBQUssQ0FBQztZQUFFLE9BQU8sRUFBRSxDQUFDO1FBRWxDLE1BQU0sVUFBVSxHQUFHLEdBQUcsQ0FBQztRQUN2QixNQUFNLEdBQUcsR0FBRyxJQUFJLElBQUksRUFBRSxDQUFDO1FBQ3ZCLE1BQU0sSUFBSSxHQUFHLE1BQU0sSUFBSSxRQUFRLENBQUM7UUFFaEMsTUFBTSxPQUFPLEdBQUcsTUFBTSxZQUFZLENBQUMsS0FBSyxFQUFFLEVBQUUsRUFBRSxFQUFFO1lBQzlDLE1BQU0sVUFBVSxHQUFjLEVBQUUsQ0FBQztZQUVqQyxLQUFLLElBQUksQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDLEdBQUcsS0FBSyxDQUFDLE1BQU0sRUFBRSxDQUFDLElBQUksVUFBVSxFQUFFLENBQUM7Z0JBQ2xELE1BQU0sS0FBSyxHQUFHLEtBQUssQ0FBQyxLQUFLLENBQUMsQ0FBQyxFQUFFLENBQUMsR0FBRyxVQUFVLENBQUMsQ0FBQztnQkFDN0MsTUFBTSxNQUFNLEdBQUcsS0FBSyxDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLENBQUM7b0JBQ2hDLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUM7b0JBQzFCLFNBQVMsRUFBRSxJQUFJO29CQUNmLFNBQVMsRUFBRSxJQUFJO2lCQUNSLENBQUEsQ0FBQyxDQUFDO2dCQUVYLE1BQU0sT0FBTyxHQUFHLE1BQU0sRUFBRTtxQkFDckIsTUFBTSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUM7cUJBQ25CLE1BQU0sQ0FBQyxNQUFNLENBQUM7cUJBQ2Qsa0JBQWtCLENBQUM7b0JBQ2xCLE1BQU0sRUFBRSxJQUFJLENBQUMsY0FBcUI7b0JBQ2xDLEdBQUcsRUFBRTt3QkFDSCxTQUFTLEVBQUUsR0FBRzt3QkFDZCxTQUFTLEVBQUUsSUFBSTtxQkFDVDtpQkFDVCxDQUFDO3FCQUNELFNBQVMsRUFBRSxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLFdBQVcsQ0FBVSxDQUFDLENBQUMsQ0FBQyxDQUFDO2dCQUVsRCxVQUFVLENBQUMsSUFBSSxDQUFDLEdBQUcsT0FBTyxDQUFDLENBQUM7WUFDOUIsQ0FBQztZQUVELE9BQU8sVUFBVSxDQUFDO1FBQ3BCLENBQUMsQ0FBQyxDQUFDO1FBRUgsdUVBQXVFO1FBQ3ZFLDREQUE0RDtRQUM1RCxNQUFNLE9BQU8sQ0FBQyxHQUFHLENBQ2YsT0FBTyxDQUFDLEdBQUcsQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUNuQixJQUFJLENBQUMsYUFBYSxDQUFDLE1BQU0sRUFBRSxNQUFNLENBQUMsQ0FBQyxLQUFLLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FDN0MsSUFBSSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsdUJBQXVCLEVBQUUsRUFBRSxLQUFLLEVBQUUsTUFBTSxDQUFDLEdBQUcsQ0FBQyxFQUFFLENBQUMsQ0FDbkUsQ0FDRixDQUNGLENBQUM7UUFFRixPQUFPLE9BQU8sQ0FBQztJQUNqQixDQUFDO0lBRUQ7O09BRUc7SUFDSCxLQUFLLENBQUMsVUFBVSxDQUNkLEdBQWEsRUFDYixLQUFhLEVBQ2IsTUFBYztRQUVkLElBQUksR0FBRyxDQUFDLE1BQU0sS0FBSyxDQUFDO1lBQUUsT0FBTyxFQUFFLENBQUM7UUFFaEMsTUFBTSxHQUFHLEdBQUcsSUFBSSxJQUFJLEVBQUUsQ0FBQztRQUN2QixNQUFNLElBQUksR0FBRyxNQUFNLElBQUksUUFBUSxDQUFDO1FBQ2hDLDhFQUE4RTtRQUM5RSwwRUFBMEU7UUFDMUUsK0NBQStDO1FBQy9DLE1BQU0sTUFBTSxHQUFJLElBQUksQ0FBQyxNQUFjLENBQUMsS0FBOEIsQ0FBQztRQUNuRSxNQUFNLFVBQVUsR0FBRztZQUNqQixPQUFPLENBQUUsSUFBSSxDQUFDLE1BQWMsQ0FBQyxFQUFFLEVBQUUsR0FBRyxDQUFDO1lBQ3JDLEdBQUcsSUFBSSxDQUFDLGVBQWUsQ0FBQyxFQUFzQixFQUFFLEtBQUssQ0FBQztZQUN0RCxHQUFHLENBQUMsS0FBSyxJQUFJLE1BQU0sQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsTUFBTSxFQUFFLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQztTQUNoRCxDQUFDO1FBRUYsTUFBTSxPQUFPLEdBQUcsTUFBTSxZQUFZLENBQUMsS0FBSyxFQUFFLEVBQUUsRUFBRSxFQUFFLENBQUMsRUFBRTthQUNoRCxNQUFNLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQzthQUNuQixHQUFHLENBQUM7WUFDSCxRQUFRLEVBQUUsS0FBSztZQUNmLFNBQVMsRUFBRSxHQUFHO1lBQ2QsU0FBUyxFQUFFLElBQUk7WUFDZixTQUFTLEVBQUUsR0FBRztZQUNkLFNBQVMsRUFBRSxJQUFJO1NBQ1QsQ0FBQzthQUNSLEtBQUssQ0FBQyxHQUFHLENBQUMsR0FBRyxVQUFVLENBQUMsQ0FBQzthQUN6QixTQUFTLEVBQUUsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxXQUFXLENBQVUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBRW5ELE1BQU0sT0FBTyxDQUFDLEdBQUcsQ0FDZixPQUFPLENBQUMsR0FBRyxDQUFDLE1BQU0sQ0FBQyxFQUFFLENBQ25CLElBQUksQ0FBQyxhQUFhLENBQUMsTUFBTSxDQUFDLEVBQUUsRUFBRSxNQUFNLEVBQUUsTUFBTSxDQUFDLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxFQUFFLENBQ3hELElBQUksQ0FBQyxPQUFPLENBQUMsSUFBSSxDQUFDLHVCQUF1QixFQUFFLEVBQUUsS0FBSyxFQUFFLE1BQU0sQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDLENBQ25FLENBQ0YsQ0FDRixDQUFDO1FBRUYsT0FBTyxPQUFPLENBQUM7SUFDakIsQ0FBQztDQUNGIiwic291cmNlc0NvbnRlbnQiOlsiLy8gQ29weXJpZ2h0IDIwMjYgUGlwZWxpbmUgQnVpbGRlciBDb250cmlidXRvcnNcbi8vIFNQRFgtTGljZW5zZS1JZGVudGlmaWVyOiBBcGFjaGUtMi4wXG5cbmltcG9ydCB7IE5vdEZvdW5kRXJyb3IsIGNyZWF0ZUxvZ2dlciB9IGZyb20gJ0BwaXBlbGluZS1idWlsZGVyL2FwaS1jb3JlJztcbmltcG9ydCB7IFNRTCwgZXEsIGFuZCwgYXNjLCBkZXNjLCBzcWwsIGluQXJyYXkgfSBmcm9tICdkcml6emxlLW9ybSc7XG5pbXBvcnQgdHlwZSB7IEFueUNvbHVtbiB9IGZyb20gJ2RyaXp6bGUtb3JtL2NvbHVtbic7XG5pbXBvcnQgdHlwZSB7IFBnVGFibGUgfSBmcm9tICdkcml6emxlLW9ybS9wZy1jb3JlJztcbmltcG9ydCB7IHdpdGhUZW5hbnRUeCwgcnVuV2l0aFRlbmFudENvbnRleHQsIGdldFRlbmFudENvbnRleHQgfSBmcm9tICcuLi9kYXRhYmFzZS90ZW5hbmN5LmpzJztcblxuLyoqIFBhZ2luYXRpb24gZGVmYXVsdHMg4oCUIHJlYWQgZnJvbSBlbnYgdG8gbWF0Y2ggQ29yZUNvbnN0YW50cyBpbiBwaXBlbGluZS1jb3JlLiAqL1xuY29uc3QgREVGQVVMVF9QQUdFX0xJTUlUID0gcGFyc2VJbnQocHJvY2Vzcy5lbnYuREVGQVVMVF9QQUdFX0xJTUlUIHx8ICcxMDAnLCAxMCk7XG5jb25zdCBNQVhfUEFHRV9MSU1JVCA9IHBhcnNlSW50KHByb2Nlc3MuZW52Lk1BWF9QQUdFX0xJTUlUIHx8ICcxMDAwJywgMTApO1xuXG4vKipcbiAqIENhc3QgRHJpenpsZSBxdWVyeSByZXN1bHRzIHRvIGEgdHlwZWQgYXJyYXkuXG4gKiBEcml6emxlJ3MgZ2VuZXJpYyByZXR1cm4gdHlwZSAoYFBnU2VsZWN0QmFzZTwuLi4+YCkgZG9lc24ndCBuYXJyb3cgdG8gb3VyXG4gKiBlbnRpdHkgZ2VuZXJpY3MsIHNvIGFuIGV4cGxpY2l0IGNhc3QgaXMgbmVlZGVkLiBDZW50cmFsaXNlZCBoZXJlIHNvIGV2ZXJ5XG4gKiBjYWxsLXNpdGUgc3RheXMgb25lLWxpbmVyIGNsZWFuIGFuZCB0aGUgY2FzdCBpcyBkb2N1bWVudGVkIGluIG9uZSBwbGFjZS5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGRyaXp6bGVSb3dzPFQ+KHJvd3M6IHVua25vd24pOiBUW10ge1xuICByZXR1cm4gcm93cyBhcyBUW107XG59XG5cbi8qKiBDYXN0IGEgRHJpenpsZSBhZ2dyZWdhdGUgcmVzdWx0IHRvIGV4dHJhY3QgYFt7IGNvdW50OiBudW1iZXIgfV1gLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGRyaXp6bGVDb3VudChyb3dzOiB1bmtub3duKTogW3sgY291bnQ6IG51bWJlciB9XSB7XG4gIHJldHVybiByb3dzIGFzIFt7IGNvdW50OiBudW1iZXIgfV07XG59XG5cbi8qKlxuICogQmFzZSBpbnRlcmZhY2UgZm9yIGVudGl0aWVzIHdpdGggY29tbW9uIGZpZWxkc1xuICovXG5leHBvcnQgaW50ZXJmYWNlIEJhc2VFbnRpdHkge1xuICBpZDogc3RyaW5nO1xuICBvcmdJZDogc3RyaW5nO1xuICBpc0RlZmF1bHQ6IGJvb2xlYW47XG4gIGNyZWF0ZWRBdDogRGF0ZTtcbiAgdXBkYXRlZEF0OiBEYXRlO1xuICBjcmVhdGVkQnk6IHN0cmluZztcbiAgdXBkYXRlZEJ5OiBzdHJpbmc7XG4gIFtrZXk6IHN0cmluZ106IHVua25vd247XG59XG5cbi8qKlxuICogUGFnaW5hdGlvbiBhbmQgc29ydGluZyBvcHRpb25zXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgUXVlcnlPcHRpb25zIHtcbiAgbGltaXQ/OiBudW1iZXI7XG4gIG9mZnNldD86IG51bWJlcjtcbiAgc29ydEJ5Pzogc3RyaW5nO1xuICBzb3J0T3JkZXI/OiAnYXNjJyB8ICdkZXNjJztcbiAgLyoqIFdoZW4gdHJ1ZSwgcnVucyBhIHNlcGFyYXRlIENPVU5UKCopIHF1ZXJ5IHRvIGluY2x1ZGUgZXhhY3QgdG90YWwuIERlZmF1bHQ6IGZhbHNlLiAqL1xuICBpbmNsdWRlVG90YWw/OiBib29sZWFuO1xuICAvKiogQ3Vyc29yLWJhc2VkIHBhZ2luYXRpb246IGZldGNoIHJvd3MgYWZ0ZXIgdGhpcyBjdXJzb3IgdmFsdWUgKHVzZXMgc29ydEJ5IGNvbHVtbikuICovXG4gIGN1cnNvcj86IHN0cmluZztcbiAgLyoqIFNwYXJzZSBmaWVsZHNldDogY29sdW1uIG5hbWVzIHRvIHNlbGVjdC4gUmV0dXJucyBhbGwgY29sdW1ucyB3aGVuIG9taXR0ZWQuICovXG4gIGZpZWxkcz86IHN0cmluZ1tdO1xufVxuXG4vKipcbiAqIFBhZ2luYXRlZCByZXN1bHQgd2l0aCBtZXRhZGF0YVxuICovXG5leHBvcnQgaW50ZXJmYWNlIFBhZ2luYXRlZFJlc3VsdDxUPiB7XG4gIGRhdGE6IFRbXTtcbiAgLyoqIFRvdGFsIGNvdW50IG9mIG1hdGNoaW5nIGVudGl0aWVzLiBPbmx5IHByZXNlbnQgd2hlbiBpbmNsdWRlVG90YWwgaXMgdHJ1ZS4gKi9cbiAgdG90YWw/OiBudW1iZXI7XG4gIGxpbWl0OiBudW1iZXI7XG4gIG9mZnNldDogbnVtYmVyO1xuICBoYXNNb3JlOiBib29sZWFuO1xuICAvKiogQ3Vyc29yIHBvaW50aW5nIHRvIHRoZSBsYXN0IGl0ZW0sIGZvciBjdXJzb3ItYmFzZWQgcGFnaW5hdGlvbi4gKi9cbiAgbmV4dEN1cnNvcj86IHN0cmluZztcbn1cblxuLyoqXG4gKiBBYnN0cmFjdCBDUlVEIHNlcnZpY2Ugd2l0aCBtdWx0aS10ZW5hbnQgYWNjZXNzIGNvbnRyb2wgYW5kIHBhZ2luYXRpb24uXG4gKlxuICogU3ViY2xhc3NlcyBiaW5kIHRvIGEgc3BlY2lmaWMgRHJpenpsZSB0YWJsZSBieSBpbXBsZW1lbnRpbmcgYHNjaGVtYWAsXG4gKiBgYnVpbGRDb25kaXRpb25zYCwgYGdldFNvcnRDb2x1bW5gLCBhbmQgdGhlIG9yZy9wcm9qZWN0LWNvbHVtbiBhY2Nlc3NvcnMuXG4gKlxuICogQHR5cGVQYXJhbSBURW50aXR5IC0gRW50aXR5IHR5cGUgZXh0ZW5kaW5nIEJhc2VFbnRpdHlcbiAqIEB0eXBlUGFyYW0gVEZpbHRlciAtIEZpbHRlciB0eXBlIGZvciBxdWVyeSBwYXJhbWV0ZXJzXG4gKiBAdHlwZVBhcmFtIFRJbnNlcnQgLSBJbnNlcnQgRFRPIHR5cGVcbiAqIEB0eXBlUGFyYW0gVFVwZGF0ZSAtIFVwZGF0ZSBEVE8gdHlwZVxuICpcbiAqICoqQSBub3RlIG9uIHRoZSB0eXBlIGNhc3RzLioqIERyaXp6bGUncyByb3cgdHlwZXMgYXJlIGluZmVycmVkIGZyb21cbiAqIGBwZ1RhYmxlKC4uLilgIGFuZCBkb24ndCBnZW5lcmljYWxseSBuYXJyb3cgdGhyb3VnaCB0aGUgYWJzdHJhY3QgYHNjaGVtYWBcbiAqIGdldHRlciwgc28gdGhlIGJhc2UgY2xhc3MgY2FzdHMgcXVlcnkgcmVzdWx0cyB0byBgVEVudGl0eWAgYW5kIGJhY2suIFRoZVxuICogY2FzdCBpcyAqbm90KiBhIHJ1bnRpbWUgc2FmZXR5IGd1YXJhbnRlZSDigJQgaXQgcmVsaWVzIG9uIGVhY2ggc3ViY2xhc3NcbiAqIHBhc3NpbmcgdGhlIG1hdGNoaW5nIGVudGl0eSB0eXBlLiBPcmctc2NvcGluZyBpcyBlbmZvcmNlZCBieSBldmVyeVxuICogc3ViY2xhc3MncyBgYnVpbGRDb25kaXRpb25zYCBpbmplY3RpbmcgYFdIRVJFIG9yZ19pZCA9ICQxYDsgdGhpcyBjbGFzc1xuICogZG9lcyBub3QgYWRkIHRoYXQgZmlsdGVyIGl0c2VsZi5cbiAqXG4gKiAqKkVycm9yIHBvbGljeS4qKiBFcnJvcnMgcHJvcGFnYXRlIHVwIHRvIHRoZSByb3V0ZS1sZXZlbCBoYW5kbGVyXG4gKiAoYHdpdGhSb3V0ZWApOyBubyBjYXRjaC1hbmQtc3dhbGxvdyBoZXJlLlxuICpcbiAqIEBleGFtcGxlXG4gKiBgYGB0eXBlc2NyaXB0XG4gKiBjbGFzcyBQaXBlbGluZVNlcnZpY2UgZXh0ZW5kcyBDcnVkU2VydmljZTxQaXBlbGluZSwgUGlwZWxpbmVGaWx0ZXIsIFBpcGVsaW5lSW5zZXJ0LCBQaXBlbGluZVVwZGF0ZT4ge1xuICogICBwcm90ZWN0ZWQgZ2V0IHNjaGVtYSgpIHsgcmV0dXJuIHNjaGVtYS5waXBlbGluZTsgfVxuICogICBwcm90ZWN0ZWQgYnVpbGRDb25kaXRpb25zKGZpbHRlciwgb3JnSWQpIHsgcmV0dXJuIGJ1aWxkUGlwZWxpbmVDb25kaXRpb25zKGZpbHRlciwgb3JnSWQpOyB9XG4gKiAgIHByb3RlY3RlZCBnZXRTb3J0Q29sdW1uKHNvcnRCeSkgeyByZXR1cm4gc29ydENvbHVtbk1hcFtzb3J0QnldID8/IG51bGw7IH1cbiAqICAgcHJvdGVjdGVkIGdldFByb2plY3RDb2x1bW4oKSB7IHJldHVybiBzY2hlbWEucGlwZWxpbmUucHJvamVjdDsgfVxuICogICBwcm90ZWN0ZWQgZ2V0T3JnQ29sdW1uKCkgeyByZXR1cm4gc2NoZW1hLnBpcGVsaW5lLm9yZ2FuaXphdGlvbjsgfVxuICogfVxuICogYGBgXG4gKi9cbmV4cG9ydCBhYnN0cmFjdCBjbGFzcyBDcnVkU2VydmljZTxcbiAgVEVudGl0eSBleHRlbmRzIEJhc2VFbnRpdHksXG4gIFRGaWx0ZXIsXG4gIFRJbnNlcnQsXG4gIFRVcGRhdGUsXG4+IHtcbiAgLyoqIERyaXp6bGUgc2NoZW1hIHRhYmxlIGZvciB0aGlzIGVudGl0eSAqL1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgZ2V0IHNjaGVtYSgpOiBQZ1RhYmxlO1xuXG4gIC8qKlxuICAgKiBCdWlsZCBTUUwgY29uZGl0aW9ucyBmb3IgZmlsdGVyaW5nIGVudGl0aWVzLlxuICAgKiBgcGFyZW50T3JnSWRgIChvcmcg4oaSIHRlYW0gaGllcmFyY2h5KSBpcyBvcHRpb25hbCBhbmQgb25seSBob25vcmVkIGJ5XG4gICAqIHNlcnZpY2VzIHRoYXQgb3B0IGludG8gcGFyZW50LWluaGVyaXRlZCB2aXNpYmlsaXR5IChlLmcuIHBsdWdpbnMpLlxuICAgKi9cbiAgcHJvdGVjdGVkIGFic3RyYWN0IGJ1aWxkQ29uZGl0aW9ucyhmaWx0ZXI6IFBhcnRpYWw8VEZpbHRlcj4sIG9yZ0lkPzogc3RyaW5nLCBwYXJlbnRPcmdJZD86IHN0cmluZyk6IFNRTFtdO1xuXG4gIC8qKiBHZXQgdGhlIHNjaGVtYSBjb2x1bW4gZm9yIHNvcnRpbmcgYnkgZmllbGQgbmFtZSAqL1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgZ2V0U29ydENvbHVtbihzb3J0Qnk6IHN0cmluZyk6IEFueUNvbHVtbiB8IG51bGw7XG5cbiAgLyoqIEdldCB0aGUgcHJvamVjdCBjb2x1bW4gZm9yIHNldERlZmF1bHQgc2NvcGluZyAobnVsbCBpZiBlbnRpdHkgaGFzIG5vIHByb2plY3Qgc2NvcGUpICovXG4gIHByb3RlY3RlZCBhYnN0cmFjdCBnZXRQcm9qZWN0Q29sdW1uKCk6IEFueUNvbHVtbiB8IG51bGw7XG5cbiAgLyoqIEdldCB0aGUgb3JnYW5pemF0aW9uIGNvbHVtbiBmb3Igc2V0RGVmYXVsdCBzY29waW5nICovXG4gIHByb3RlY3RlZCBhYnN0cmFjdCBnZXRPcmdDb2x1bW4oKTogQW55Q29sdW1uO1xuXG4gIC8qKiBHZXQgdGhlIHVuaXF1ZSBjb25zdHJhaW50IGNvbHVtbnMgZm9yIG9uQ29uZmxpY3REb1VwZGF0ZSAqL1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgZ2V0IGNvbmZsaWN0VGFyZ2V0KCk6IEFueUNvbHVtbltdO1xuXG4gIHByaXZhdGUgcmVhZG9ubHkgX2xvZ2dlciA9IGNyZWF0ZUxvZ2dlcignY3J1ZC1zZXJ2aWNlJyk7XG5cbiAgLyoqIEJ1aWxkIGNvbmRpdGlvbnMgZm9yIGEgc2luZ2xlIGVudGl0eSBieSBJRC4gKi9cbiAgcHJpdmF0ZSBpZENvbmRpdGlvbnMoaWQ6IHN0cmluZywgb3JnSWQ/OiBzdHJpbmcpOiBTUUxbXSB7XG4gICAgcmV0dXJuIHRoaXMuYnVpbGRDb25kaXRpb25zKHsgaWQgfSBhcyB1bmtub3duIGFzIFBhcnRpYWw8VEZpbHRlcj4sIG9yZ0lkKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDb25kaXRpb25zIGZvciBhIE1VVEFUSU9OICh1cGRhdGUvZGVsZXRlKSBvZiBhIHNpbmdsZSBlbnRpdHkuXG4gICAqXG4gICAqIGBpZENvbmRpdGlvbnNgIHJldXNlcyB0aGUgUkVBRCBhY2Nlc3MtY29udHJvbCBjbGF1c2UsIHdoaWNoIGFsc28gbWF0Y2hlc1xuICAgKiBzeXN0ZW0tb3JnIC8gb3RoZXItb3JnIFBVQkxJQyByZWNvcmRzIOKAlCBzbyB3aXRob3V0IGFuIGV4dHJhIG93bmVyc2hpcCBwaW4gYW55XG4gICAqIHRlbmFudCBjb3VsZCB1cGRhdGUgb3Igc29mdC1kZWxldGUgYW5vdGhlciBvcmcncyAob3IgdGhlIHN5c3RlbSBvcmcncykgcHVibGljXG4gICAqIHJlY29yZHMuIEFORCBhIHN0cmljdCBgb3JnSWQgPT09IGNhbGxlcmAgcHJlZGljYXRlOiB0aGUgcmVhZCBjbGF1c2Unc1xuICAgKiBwdWJsaWMtT1IgYnJhbmNoIHJlcXVpcmVzIGBvcmdfaWQgPSAnc3lzdGVtJ2AsIHdoaWNoIHRoZW4gY2FuJ3QgYmUgc2F0aXNmaWVkLFxuICAgKiBsZWF2aW5nIG9ubHkgb3duLW9yZyByb3dzLiBvcmdJZC1sZXNzIChzeXNhZG1pbikgY29udGV4dCBrZWVwcyBmdWxsIGFjY2Vzcy5cbiAgICovXG4gIHByaXZhdGUgd3JpdGVDb25kaXRpb25zKGlkOiBzdHJpbmcsIG9yZ0lkPzogc3RyaW5nKTogU1FMW10ge1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSB0aGlzLmlkQ29uZGl0aW9ucyhpZCwgb3JnSWQpO1xuICAgIGNvbnN0IG9yZ0NvbCA9ICh0aGlzLnNjaGVtYSBhcyBhbnkpLm9yZ0lkIGFzIEFueUNvbHVtbiB8IHVuZGVmaW5lZDtcbiAgICBpZiAob3JnSWQgJiYgb3JnQ29sKSBjb25kaXRpb25zLnB1c2goZXEob3JnQ29sLCBvcmdJZCkpO1xuICAgIHJldHVybiBjb25kaXRpb25zO1xuICB9XG5cbiAgLy8gTGlmZWN5Y2xlIGhvb2tzIOKAlCBvdmVycmlkZSBpbiBzdWJjbGFzc2VzIHRvIHJlYWN0IHRvIG11dGF0aW9uc1xuICAvLyBUaGVzZSBhcmUgZmlyZS1hbmQtZm9yZ2V0OiBlcnJvcnMgYXJlIGxvZ2dlZCBidXQgbmV2ZXIgYmxvY2sgdGhlIGNhbGxlci5cblxuICAvKiogQ2FsbGVkIGFmdGVyIGEgbmV3IGVudGl0eSBpcyBjcmVhdGVkICovXG4gIHByb3RlY3RlZCBhc3luYyBvbkFmdGVyQ3JlYXRlKF9lbnRpdHk6IFRFbnRpdHksIF91c2VySWQ6IHN0cmluZyk6IFByb21pc2U8dm9pZD4ge31cblxuICAvKiogQ2FsbGVkIGFmdGVyIGFuIGVudGl0eSBpcyB1cGRhdGVkICovXG4gIHByb3RlY3RlZCBhc3luYyBvbkFmdGVyVXBkYXRlKF9pZDogc3RyaW5nLCBfZW50aXR5OiBURW50aXR5LCBfdXNlcklkOiBzdHJpbmcpOiBQcm9taXNlPHZvaWQ+IHt9XG5cbiAgLyoqIENhbGxlZCBhZnRlciBhbiBlbnRpdHkgaXMgc29mdC1kZWxldGVkICovXG4gIHByb3RlY3RlZCBhc3luYyBvbkFmdGVyRGVsZXRlKF9pZDogc3RyaW5nLCBfZW50aXR5OiBURW50aXR5LCBfdXNlcklkOiBzdHJpbmcpOiBQcm9taXNlPHZvaWQ+IHt9XG5cbiAgLyoqXG4gICAqIEZpbmQgZW50aXRpZXMgbWF0Y2hpbmcgZmlsdGVyIGNyaXRlcmlhXG4gICAqXG4gICAqIEBwYXJhbSBmaWx0ZXIgLSBGaWx0ZXIgY3JpdGVyaWFcbiAgICogQHBhcmFtIG9yZ0lkIC0gVXNlcidzIG9yZ2FuaXphdGlvbiBJRCAob3B0aW9uYWwg4oCUIG9taXQgZm9yIGFub255bW91cy9zeXN0ZW0tcHVibGljLW9ubHkgYWNjZXNzKVxuICAgKi9cbiAgLyoqXG4gICAqIE9yZyDihpIgdGVhbSBoaWVyYXJjaHk6IHdoZW4gYSByZWFkIGlzIHdpZGVuZWQgdG8gYSBwYXJlbnQgb3JnIChgcGFyZW50T3JnSWRgXG4gICAqIHNldCksIHRoZSBwYXJlbnQncyByb3dzIGFyZSBvdXRzaWRlIHRoZSBjYWxsZXIncyBSTFMgc2NvcGUsIHNvIHRoZSByZWFkIG11c3RcbiAgICogcnVuIHVuZGVyIHN5c2FkbWluIGNvbnRleHQg4oCUIHRoZSBhY2Nlc3MtY29udHJvbCBXSEVSRSBjbGF1c2UgKG93biArIHBhcmVudCArXG4gICAqIHN5c3RlbSBwdWJsaWMsIGJ1aWx0IHNlcnZlci1zaWRlIGZyb20gYSB0cnVzdGVkIEpXVCBjbGFpbSkgaXMgdGhlbiB0aGVcbiAgICogYXV0aG9yaXRhdGl2ZSB0ZW5hbmN5IGdhdGUuIFdpdGhvdXQgYHBhcmVudE9yZ0lkYCBpdCBzdGF5cyBSTFMtc2NvcGVkLlxuICAgKi9cbiAgcHJpdmF0ZSBydW5SZWFkPFQ+KHBhcmVudE9yZ0lkOiBzdHJpbmcgfCB1bmRlZmluZWQsIGZuOiAoKSA9PiBQcm9taXNlPFQ+KTogUHJvbWlzZTxUPiB7XG4gICAgcmV0dXJuIHBhcmVudE9yZ0lkID8gcnVuV2l0aFRlbmFudENvbnRleHQoeyBpc1N1cGVyQWRtaW46IHRydWUgfSwgZm4pIDogZm4oKTtcbiAgfVxuXG4gIGFzeW5jIGZpbmQoZmlsdGVyOiBQYXJ0aWFsPFRGaWx0ZXI+LCBvcmdJZD86IHN0cmluZywgcGFyZW50T3JnSWQ/OiBzdHJpbmcpOiBQcm9taXNlPFRFbnRpdHlbXT4ge1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSB0aGlzLmJ1aWxkQ29uZGl0aW9ucyhmaWx0ZXIsIG9yZ0lkLCBwYXJlbnRPcmdJZCk7XG5cbiAgICByZXR1cm4gdGhpcy5ydW5SZWFkKHBhcmVudE9yZ0lkLCAoKSA9PiB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB0eFxuICAgICAgLnNlbGVjdCgpXG4gICAgICAuZnJvbSh0aGlzLnNjaGVtYSlcbiAgICAgIC53aGVyZShhbmQoLi4uY29uZGl0aW9ucykpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSkpKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBGaW5kIGVudGl0aWVzIHdpdGggcGFnaW5hdGlvbiBhbmQgc29ydGluZ1xuICAgKlxuICAgKiBAcGFyYW0gZmlsdGVyIC0gRmlsdGVyIGNyaXRlcmlhXG4gICAqIEBwYXJhbSBvcmdJZCAtIFVzZXIncyBvcmdhbml6YXRpb24gSUQgKG9wdGlvbmFsIOKAlCBvbWl0IGZvciBhbm9ueW1vdXMvc3lzdGVtLXB1YmxpYy1vbmx5IGFjY2VzcylcbiAgICogQHBhcmFtIG9wdGlvbnMgLSBQYWdpbmF0aW9uIGFuZCBzb3J0aW5nIG9wdGlvbnNcbiAgICovXG4gIGFzeW5jIGZpbmRQYWdpbmF0ZWQoXG4gICAgZmlsdGVyOiBQYXJ0aWFsPFRGaWx0ZXI+LFxuICAgIG9yZ0lkPzogc3RyaW5nLFxuICAgIG9wdGlvbnM6IFF1ZXJ5T3B0aW9ucyA9IHt9LFxuICAgIHBhcmVudE9yZ0lkPzogc3RyaW5nLFxuICApOiBQcm9taXNlPFBhZ2luYXRlZFJlc3VsdDxURW50aXR5Pj4ge1xuICAgIGNvbnN0IHsgbGltaXQ6IHJhd0xpbWl0ID0gREVGQVVMVF9QQUdFX0xJTUlULCBvZmZzZXQgPSAwLCBzb3J0QnksIHNvcnRPcmRlciA9ICdhc2MnLCBpbmNsdWRlVG90YWwgPSBmYWxzZSwgY3Vyc29yLCBmaWVsZHMgfSA9IG9wdGlvbnM7XG4gICAgY29uc3QgbGltaXQgPSBNYXRoLm1pbihNYXRoLm1heCgxLCByYXdMaW1pdCksIE1BWF9QQUdFX0xJTUlUKTtcblxuICAgIC8vIEN1cnNvciBhbmQgb2Zmc2V0IGFyZSBtdXR1YWxseSBleGNsdXNpdmUg4oCUIGN1cnNvciB0YWtlcyBwcmVjZWRlbmNlXG4gICAgY29uc3QgdXNlQ3Vyc29yID0gISEoY3Vyc29yICYmIHNvcnRCeSk7XG5cbiAgICBjb25zdCBjb25kaXRpb25zID0gdGhpcy5idWlsZENvbmRpdGlvbnMoZmlsdGVyLCBvcmdJZCwgcGFyZW50T3JnSWQpO1xuXG4gICAgLy8gQ3Vyc29yLWJhc2VkIHBhZ2luYXRpb246IGFkZCBXSEVSRSBjbGF1c2UgZm9yIGtleXNldCBwYWdpbmF0aW9uXG4gICAgaWYgKHVzZUN1cnNvcikge1xuICAgICAgY29uc3Qgc29ydENvbHVtbiA9IHRoaXMuZ2V0U29ydENvbHVtbihzb3J0QnkpO1xuICAgICAgaWYgKHNvcnRDb2x1bW4pIHtcbiAgICAgICAgY29uc3Qgb3AgPSBzb3J0T3JkZXIgPT09ICdkZXNjJ1xuICAgICAgICAgID8gc3FsYCR7c29ydENvbHVtbn0gPCAke2N1cnNvcn1gXG4gICAgICAgICAgOiBzcWxgJHtzb3J0Q29sdW1ufSA+ICR7Y3Vyc29yfWA7XG4gICAgICAgIGNvbmRpdGlvbnMucHVzaChvcCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gV3JhcCB0aGUgd2hvbGUgcGFnaW5hdGVkIHJlYWQgKFNFTEVDVCArIG9wdGlvbmFsIENPVU5UKSBpbiBvbmVcbiAgICAvLyB0ZW5hbnQgdHguIEJvdGggcXVlcmllcyBhcmUgdmlzaWJpbGl0eS1zY29wZWQgYnkgdGhlIHNhbWUgUkxTIHBvbGljeSxcbiAgICAvLyBhbmQgcGlubmluZyB0aGVtIHRvIGEgc2luZ2xlIHR4IGtlZXBzIHRoZSBgYXBwLm9yZ19pZGAgR1VDIHN0YWJsZVxuICAgIC8vIGJldHdlZW4gdGhlbS4gV2hlbiB3aWRlbmluZyB0byBhIHBhcmVudCBvcmcsIHRoZSB3aG9sZSByZWFkIHJ1bnMgdW5kZXJcbiAgICAvLyBzeXNhZG1pbiBjb250ZXh0IChzZWUgcnVuUmVhZCkgc28gdGhlIGFjY2Vzcy1jb250cm9sIFdIRVJFIGlzIHRoZSBnYXRlLlxuICAgIHJldHVybiB0aGlzLnJ1blJlYWQocGFyZW50T3JnSWQsICgpID0+IHdpdGhUZW5hbnRUeChhc3luYyAodHgpID0+IHtcbiAgICAgIC8vIEJ1aWxkIFNFTEVDVCDigJQgc3BhcnNlIGZpZWxkc2V0IHdoZW4gZmllbGRzIGFyZSBzcGVjaWZpZWRcbiAgICAgIGNvbnN0IHNlbGVjdFNwZWMgPSBmaWVsZHMgPyB0aGlzLmJ1aWxkRmllbGRTZWxlY3QoZmllbGRzKSA6IHVuZGVmaW5lZDtcbiAgICAgIGxldCBxdWVyeSA9IHNlbGVjdFNwZWNcbiAgICAgICAgPyB0eC5zZWxlY3Qoc2VsZWN0U3BlYyBhcyBhbnkpLmZyb20odGhpcy5zY2hlbWEpLndoZXJlKGFuZCguLi5jb25kaXRpb25zKSlcbiAgICAgICAgOiB0eC5zZWxlY3QoKS5mcm9tKHRoaXMuc2NoZW1hKS53aGVyZShhbmQoLi4uY29uZGl0aW9ucykpO1xuXG4gICAgICBpZiAoc29ydEJ5KSB7XG4gICAgICAgIGNvbnN0IHNvcnRDb2x1bW4gPSB0aGlzLmdldFNvcnRDb2x1bW4oc29ydEJ5KTtcbiAgICAgICAgaWYgKHNvcnRDb2x1bW4pIHtcbiAgICAgICAgICBxdWVyeSA9IHF1ZXJ5Lm9yZGVyQnkoc29ydE9yZGVyID09PSAnZGVzYycgPyBkZXNjKHNvcnRDb2x1bW4pIDogYXNjKHNvcnRDb2x1bW4pKSBhcyBhbnk7XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgLy8gRmV0Y2ggbGltaXQrMSB0byBkZXRlY3QgaGFzTW9yZSB3aXRob3V0IENPVU5UKCopXG4gICAgICBjb25zdCBlZmZlY3RpdmVPZmZzZXQgPSB1c2VDdXJzb3IgPyAwIDogb2Zmc2V0O1xuICAgICAgY29uc3Qgcm93cyA9IGF3YWl0IHF1ZXJ5XG4gICAgICAgIC5saW1pdChsaW1pdCArIDEpXG4gICAgICAgIC5vZmZzZXQoZWZmZWN0aXZlT2Zmc2V0KS50aGVuKHIgPT4gZHJpenpsZVJvd3M8VEVudGl0eT4ocikpO1xuXG4gICAgICBjb25zdCBoYXNNb3JlID0gcm93cy5sZW5ndGggPiBsaW1pdDtcbiAgICAgIGNvbnN0IGRhdGEgPSBoYXNNb3JlID8gcm93cy5zbGljZSgwLCBsaW1pdCkgOiByb3dzO1xuXG4gICAgICBjb25zdCByZXN1bHQ6IFBhZ2luYXRlZFJlc3VsdDxURW50aXR5PiA9IHsgZGF0YSwgbGltaXQsIG9mZnNldDogZWZmZWN0aXZlT2Zmc2V0LCBoYXNNb3JlIH07XG5cbiAgICAgIC8vIFByb3ZpZGUgbmV4dCBjdXJzb3IgZnJvbSBsYXN0IGl0ZW0ncyBzb3J0IGNvbHVtbiB2YWx1ZVxuICAgICAgaWYgKGRhdGEubGVuZ3RoID4gMCAmJiBzb3J0QnkpIHtcbiAgICAgICAgY29uc3QgbGFzdEl0ZW0gPSBkYXRhW2RhdGEubGVuZ3RoIC0gMV0gYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG4gICAgICAgIGNvbnN0IGN1cnNvclZhbHVlID0gbGFzdEl0ZW1bc29ydEJ5XTtcbiAgICAgICAgaWYgKGN1cnNvclZhbHVlICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICByZXN1bHQubmV4dEN1cnNvciA9IGN1cnNvclZhbHVlIGluc3RhbmNlb2YgRGF0ZSA/IGN1cnNvclZhbHVlLnRvSVNPU3RyaW5nKCkgOiBTdHJpbmcoY3Vyc29yVmFsdWUpO1xuICAgICAgICB9XG4gICAgICB9XG5cbiAgICAgIC8vIE9ubHkgcnVuIHRoZSBDT1VOVCgqKSBxdWVyeSB3aGVuIHRoZSBjYWxsZXIgZXhwbGljaXRseSBuZWVkcyB0aGUgdG90YWwuXG4gICAgICAvLyBNdXN0IGluY2x1ZGUgcGFyZW50T3JnSWQgc28gYHRvdGFsYCBtYXRjaGVzIHRoZSB3aWRlbmVkIGRhdGEgc2V0LlxuICAgICAgaWYgKGluY2x1ZGVUb3RhbCkge1xuICAgICAgICBjb25zdCBiYXNlQ29uZGl0aW9ucyA9IHRoaXMuYnVpbGRDb25kaXRpb25zKGZpbHRlciwgb3JnSWQsIHBhcmVudE9yZ0lkKTtcbiAgICAgICAgY29uc3QgW2NvdW50UmVzdWx0XSA9IGF3YWl0IHR4XG4gICAgICAgICAgLnNlbGVjdCh7IGNvdW50OiBzcWw8bnVtYmVyPmBjb3VudCgqKTo6aW50YCB9KVxuICAgICAgICAgIC5mcm9tKHRoaXMuc2NoZW1hKVxuICAgICAgICAgIC53aGVyZShhbmQoLi4uYmFzZUNvbmRpdGlvbnMpKS50aGVuKHIgPT4gZHJpenpsZUNvdW50KHIpKTtcbiAgICAgICAgcmVzdWx0LnRvdGFsID0gY291bnRSZXN1bHQ/LmNvdW50IHx8IDA7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiByZXN1bHQ7XG4gICAgfSkpO1xuICB9XG5cbiAgLyoqXG4gICAqIEJ1aWxkIGEgY29sdW1uIHNlbGVjdGlvbiBtYXAgZm9yIHNwYXJzZSBmaWVsZHNldHMuXG4gICAqIEZhbGxzIGJhY2sgdG8gZnVsbCBzZWxlY3QgaWYgbm8gbWF0Y2hpbmcgY29sdW1ucyBmb3VuZC5cbiAgICovXG4gIHByaXZhdGUgYnVpbGRGaWVsZFNlbGVjdChmaWVsZHM6IHN0cmluZ1tdKTogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gfCB1bmRlZmluZWQge1xuICAgIGlmIChmaWVsZHMubGVuZ3RoID09PSAwKSByZXR1cm4gdW5kZWZpbmVkO1xuXG4gICAgY29uc3QgY29sdW1uczogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gPSB7fTtcbiAgICAvLyBBbHdheXMgaW5jbHVkZSBpZCBmb3IgZW50aXR5IGlkZW50aXR5XG4gICAgY29sdW1ucy5pZCA9ICh0aGlzLnNjaGVtYSBhcyBhbnkpLmlkO1xuXG4gICAgZm9yIChjb25zdCBmaWVsZCBvZiBmaWVsZHMpIHtcbiAgICAgIGlmIChmaWVsZCA9PT0gJ2lkJykgY29udGludWU7IC8vIEFscmVhZHkgaW5jbHVkZWRcbiAgICAgIGNvbnN0IGNvbCA9ICh0aGlzLnNjaGVtYSBhcyBhbnkpW2ZpZWxkXTtcbiAgICAgIGlmIChjb2wpIGNvbHVtbnNbZmllbGRdID0gY29sO1xuICAgIH1cblxuICAgIC8vIEF0IG1pbmltdW0gd2UnbGwgaGF2ZSB7IGlkIH0sIHdoaWNoIGlzIHZhbGlkXG4gICAgcmV0dXJuIGNvbHVtbnM7XG4gIH1cblxuICAvKipcbiAgICogQ291bnQgZW50aXRpZXMgbWF0Y2hpbmcgZmlsdGVyIGNyaXRlcmlhXG4gICAqXG4gICAqIEBwYXJhbSBmaWx0ZXIgLSBGaWx0ZXIgY3JpdGVyaWFcbiAgICogQHBhcmFtIG9yZ0lkIC0gVXNlcidzIG9yZ2FuaXphdGlvbiBJRCAob3B0aW9uYWwg4oCUIG9taXQgZm9yIGFub255bW91cy9zeXN0ZW0tcHVibGljLW9ubHkgYWNjZXNzKVxuICAgKi9cbiAgYXN5bmMgY291bnQoZmlsdGVyOiBQYXJ0aWFsPFRGaWx0ZXI+LCBvcmdJZD86IHN0cmluZyk6IFByb21pc2U8bnVtYmVyPiB7XG4gICAgY29uc3QgY29uZGl0aW9ucyA9IHRoaXMuYnVpbGRDb25kaXRpb25zKGZpbHRlciwgb3JnSWQpO1xuXG4gICAgY29uc3QgW3Jlc3VsdF0gPSBhd2FpdCB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB0eFxuICAgICAgLnNlbGVjdCh7IGNvdW50OiBzcWw8bnVtYmVyPmBjb3VudCgqKTo6aW50YCB9KVxuICAgICAgLmZyb20odGhpcy5zY2hlbWEpXG4gICAgICAud2hlcmUoYW5kKC4uLmNvbmRpdGlvbnMpKS50aGVuKHIgPT4gZHJpenpsZUNvdW50KHIpKSk7XG5cbiAgICByZXR1cm4gcmVzdWx0Py5jb3VudCB8fCAwO1xuICB9XG5cbiAgLyoqXG4gICAqIEZpbmQgYSBzaW5nbGUgZW50aXR5IGJ5IElEXG4gICAqXG4gICAqIEBwYXJhbSBpZCAtIEVudGl0eSBJRFxuICAgKiBAcGFyYW0gb3JnSWQgLSBVc2VyJ3Mgb3JnYW5pemF0aW9uIElEIChvcHRpb25hbCDigJQgb21pdCBmb3IgYW5vbnltb3VzL3N5c3RlbS1wdWJsaWMtb25seSBhY2Nlc3MpXG4gICAqL1xuICBhc3luYyBmaW5kQnlJZChpZDogc3RyaW5nLCBvcmdJZD86IHN0cmluZyk6IFByb21pc2U8VEVudGl0eSB8IG51bGw+IHtcbiAgICBjb25zdCBjb25kaXRpb25zID0gdGhpcy5pZENvbmRpdGlvbnMoaWQsIG9yZ0lkKTtcblxuICAgIGNvbnN0IHJlc3VsdHMgPSBhd2FpdCB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB0eFxuICAgICAgLnNlbGVjdCgpXG4gICAgICAuZnJvbSh0aGlzLnNjaGVtYSlcbiAgICAgIC53aGVyZShhbmQoLi4uY29uZGl0aW9ucykpXG4gICAgICAubGltaXQoMSkudGhlbihyID0+IGRyaXp6bGVSb3dzPFRFbnRpdHk+KHIpKSk7XG5cbiAgICByZXR1cm4gcmVzdWx0c1swXSB8fCBudWxsO1xuICB9XG5cbiAgLy8gTXV0YXRpb24gb3BlcmF0aW9uc1xuXG4gIC8qKlxuICAgKiBEZWZlbnNlLWluLWRlcHRoIHRlbmFudCBzdGFtcC4gUkxTIGlzIGluIG93bmVyLWJ5cGFzcyBtb2RlLCBzbyB0aGUgYXBwIGxheWVyXG4gICAqIGlzIHRoZSBvbmx5IHRlbmFudCBnYXRlIG9uIHdyaXRlcy4gQSBOT04tc3lzYWRtaW4gY2FsbGVyIG1heSBvbmx5IHdyaXRlIGludG9cbiAgICogaXRzIE9XTiBvcmcsIHNvIG92ZXJ3cml0ZSBhbnkgY2FsbGVyLXN1cHBsaWVkIGBvcmdJZGAgd2l0aCB0aGUgdHJ1c3RlZFxuICAgKiB0ZW5hbnQtY29udGV4dCBvcmcg4oCUIGEgcm91dGUgdGhhdCBmb3J3YXJkcyBhIGZvcmdlZCBgZGF0YS5vcmdJZGAgdGhlbiBjYW4ndFxuICAgKiBjcm9zcyB0ZW5hbnRzLiBTeXNhZG1pbiAoYW5kIG91dC1vZi1jb250ZXh0IHdvcmtlci9zeXN0ZW0gcGF0aHMpIGtlZXAgdGhlXG4gICAqIHN1cHBsaWVkIG9yZywgbWF0Y2hpbmcgdGhlIFJMUyBwb2xpY3kgYGN1cnJlbnRfaXNfc3lzYWRtaW4oKSBPUiBvcmdfaWQgPSBjdXJyZW50X29yZ19pZCgpYC5cbiAgICovXG4gIHByb3RlY3RlZCBlbmZvcmNlT3JnSWQoZGF0YTogVEluc2VydCk6IFRJbnNlcnQge1xuICAgIGNvbnN0IGN0eCA9IGdldFRlbmFudENvbnRleHQoKTtcbiAgICBjb25zdCBkID0gZGF0YSBhcyBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcbiAgICBpZiAoY3R4ICYmICFjdHguaXNTdXBlckFkbWluICYmIGN0eC5vcmdJZCAmJiAnb3JnSWQnIGluIGQgJiYgZC5vcmdJZCAhPT0gY3R4Lm9yZ0lkKSB7XG4gICAgICB0aGlzLl9sb2dnZXIud2FybignQ3J1ZFNlcnZpY2U6IG92ZXJyaWRpbmcgY2FsbGVyIG9yZ0lkIHdpdGggdGVuYW50LWNvbnRleHQgb3JnJywge1xuICAgICAgICBzdXBwbGllZDogZC5vcmdJZCwgZW5mb3JjZWQ6IGN0eC5vcmdJZCxcbiAgICAgIH0pO1xuICAgICAgcmV0dXJuIHsgLi4uZCwgb3JnSWQ6IGN0eC5vcmdJZCB9IGFzIFRJbnNlcnQ7XG4gICAgfVxuICAgIHJldHVybiBkYXRhO1xuICB9XG5cbiAgLyoqXG4gICAqIENyZWF0ZSBhIG5ldyBlbnRpdHlcbiAgICovXG4gIGFzeW5jIGNyZWF0ZShkYXRhOiBUSW5zZXJ0LCB1c2VySWQ6IHN0cmluZyk6IFByb21pc2U8VEVudGl0eT4ge1xuICAgIGNvbnN0IHNhZmVEYXRhID0gdGhpcy5lbmZvcmNlT3JnSWQoZGF0YSk7XG4gICAgY29uc3QgW2NyZWF0ZWRdID0gYXdhaXQgd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4gdHhcbiAgICAgIC5pbnNlcnQodGhpcy5zY2hlbWEpXG4gICAgICAudmFsdWVzKHtcbiAgICAgICAgLi4uc2FmZURhdGEsXG4gICAgICAgIGNyZWF0ZWRCeTogdXNlcklkIHx8ICdzeXN0ZW0nLFxuICAgICAgICB1cGRhdGVkQnk6IHVzZXJJZCB8fCAnc3lzdGVtJyxcbiAgICAgIH0gYXMgYW55KVxuICAgICAgLm9uQ29uZmxpY3REb1VwZGF0ZSh7XG4gICAgICAgIHRhcmdldDogdGhpcy5jb25mbGljdFRhcmdldCBhcyBhbnksXG4gICAgICAgIHNldDoge1xuICAgICAgICAgIC4uLnNhZmVEYXRhLFxuICAgICAgICAgIHVwZGF0ZWRBdDogbmV3IERhdGUoKSxcbiAgICAgICAgICB1cGRhdGVkQnk6IHVzZXJJZCB8fCAnc3lzdGVtJyxcbiAgICAgICAgfSBhcyBhbnksXG4gICAgICB9KVxuICAgICAgLnJldHVybmluZygpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSkpO1xuXG4gICAgLy8gQXdhaXRlZCBpbnRlbnRpb25hbGx5OiBjYWNoZSBpbnZhbGlkYXRpb24gaGFwcGVucyBpbiB0aGUgaG9vaywgYW5kIGFcbiAgICAvLyBmaXJlLWFuZC1mb3JnZXQgcGF0dGVybiBsZXRzIGEgc3Vic2VxdWVudCByZWFkIGluc2lkZSB0aGUgc2FtZSByZXF1ZXN0XG4gICAgLy8gcmV0dXJuIHRoZSBzdGFsZSBwcmUtd3JpdGUgZW50cnkuIFRoZSBob29rIGlzIGV4cGVjdGVkIHRvIGJlIGZhc3RcbiAgICAvLyAoc2luZ2xlIFJlZGlzIG9wKTsgc2xvdyBob29rcyBzaG91bGQgcnVuIHRoZWlyIG93biBiYWNrZ3JvdW5kIHdvcmsuXG4gICAgdHJ5IHtcbiAgICAgIGF3YWl0IHRoaXMub25BZnRlckNyZWF0ZShjcmVhdGVkLCB1c2VySWQpO1xuICAgIH0gY2F0Y2ggKGVycikge1xuICAgICAgdGhpcy5fbG9nZ2VyLndhcm4oJ0xpZmVjeWNsZSBob29rIGZhaWxlZCcsIHsgZXJyb3I6IFN0cmluZyhlcnIpIH0pO1xuICAgIH1cblxuICAgIHJldHVybiBjcmVhdGVkO1xuICB9XG5cbiAgLyoqXG4gICAqIFVwZGF0ZSBhbiBleGlzdGluZyBlbnRpdHlcbiAgICovXG4gIGFzeW5jIHVwZGF0ZShcbiAgICBpZDogc3RyaW5nLFxuICAgIGRhdGE6IFBhcnRpYWw8VFVwZGF0ZT4sXG4gICAgb3JnSWQ6IHN0cmluZyxcbiAgICB1c2VySWQ6IHN0cmluZyxcbiAgKTogUHJvbWlzZTxURW50aXR5IHwgbnVsbD4ge1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSB0aGlzLndyaXRlQ29uZGl0aW9ucyhpZCwgb3JnSWQpO1xuXG4gICAgY29uc3QgW3VwZGF0ZWRdID0gYXdhaXQgd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4gdHhcbiAgICAgIC51cGRhdGUodGhpcy5zY2hlbWEpXG4gICAgICAuc2V0KHtcbiAgICAgICAgLi4uZGF0YSxcbiAgICAgICAgdXBkYXRlZEF0OiBuZXcgRGF0ZSgpLFxuICAgICAgICB1cGRhdGVkQnk6IHVzZXJJZCB8fCAnc3lzdGVtJyxcbiAgICAgIH0gYXMgYW55KVxuICAgICAgLndoZXJlKGFuZCguLi5jb25kaXRpb25zKSlcbiAgICAgIC5yZXR1cm5pbmcoKS50aGVuKHIgPT4gZHJpenpsZVJvd3M8VEVudGl0eT4ocikpKTtcblxuICAgIGlmICh1cGRhdGVkKSB7XG4gICAgICB0cnkge1xuICAgICAgICBhd2FpdCB0aGlzLm9uQWZ0ZXJVcGRhdGUoaWQsIHVwZGF0ZWQsIHVzZXJJZCk7XG4gICAgICB9IGNhdGNoIChlcnIpIHtcbiAgICAgICAgdGhpcy5fbG9nZ2VyLndhcm4oJ0xpZmVjeWNsZSBob29rIGZhaWxlZCcsIHsgZXJyb3I6IFN0cmluZyhlcnIpIH0pO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiB1cGRhdGVkIHx8IG51bGw7XG4gIH1cblxuICAvKipcbiAgICogRGVsZXRlIGFuIGVudGl0eSAoc29mdCBkZWxldGUgYnkgc2V0dGluZyBpc0FjdGl2ZSA9IGZhbHNlKVxuICAgKi9cbiAgYXN5bmMgZGVsZXRlKGlkOiBzdHJpbmcsIG9yZ0lkOiBzdHJpbmcsIHVzZXJJZDogc3RyaW5nKTogUHJvbWlzZTxURW50aXR5IHwgbnVsbD4ge1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSB0aGlzLndyaXRlQ29uZGl0aW9ucyhpZCwgb3JnSWQpO1xuXG4gICAgY29uc3QgW2RlbGV0ZWRdID0gYXdhaXQgd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4gdHhcbiAgICAgIC51cGRhdGUodGhpcy5zY2hlbWEpXG4gICAgICAuc2V0KHtcbiAgICAgICAgaXNBY3RpdmU6IGZhbHNlLFxuICAgICAgICB1cGRhdGVkQXQ6IG5ldyBEYXRlKCksXG4gICAgICAgIHVwZGF0ZWRCeTogdXNlcklkIHx8ICdzeXN0ZW0nLFxuICAgICAgICBkZWxldGVkQXQ6IG5ldyBEYXRlKCksXG4gICAgICAgIGRlbGV0ZWRCeTogdXNlcklkIHx8ICdzeXN0ZW0nLFxuICAgICAgfSBhcyBhbnkpXG4gICAgICAud2hlcmUoYW5kKC4uLmNvbmRpdGlvbnMpKVxuICAgICAgLnJldHVybmluZygpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSkpO1xuXG4gICAgaWYgKGRlbGV0ZWQpIHtcbiAgICAgIHRyeSB7XG4gICAgICAgIGF3YWl0IHRoaXMub25BZnRlckRlbGV0ZShpZCwgZGVsZXRlZCwgdXNlcklkKTtcbiAgICAgIH0gY2F0Y2ggKGVycikge1xuICAgICAgICB0aGlzLl9sb2dnZXIud2FybignTGlmZWN5Y2xlIGhvb2sgZmFpbGVkJywgeyBlcnJvcjogU3RyaW5nKGVycikgfSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIGRlbGV0ZWQgfHwgbnVsbDtcbiAgfVxuXG4gIC8qKlxuICAgKiBTZXQgYW4gZW50aXR5IGFzIHRoZSBkZWZhdWx0IGZvciBhIHByb2plY3Qvb3JnYW5pemF0aW9uIHNjb3BlLlxuICAgKiBNYXJrcyBhbGwgb3RoZXIgZW50aXRpZXMgYXMgbm9uLWRlZmF1bHQsIHRoZW4gc2V0cyB0aGUgc3BlY2lmaWVkIGVudGl0eS5cbiAgICogVXNlcyBhIHRyYW5zYWN0aW9uIHRvIGVuc3VyZSBhdG9taWNpdHkuXG4gICAqL1xuICBhc3luYyBzZXREZWZhdWx0KFxuICAgIHByb2plY3Q6IHN0cmluZyxcbiAgICBvcmc6IHN0cmluZyxcbiAgICBpZDogc3RyaW5nLFxuICAgIHVzZXJJZDogc3RyaW5nLFxuICApOiBQcm9taXNlPFRFbnRpdHk+IHtcbiAgICAvLyBBIG5vbi1zeXNhZG1pbiBtYXkgb25seSBmbGlwIGRlZmF1bHRzIHdpdGhpbiBpdHMgT1dOIG9yZyDigJQgcGluIHRoZSBzY29wZSB0b1xuICAgIC8vIHRoZSB0cnVzdGVkIHRlbmFudCBjb250ZXh0IHNvIGEgZm9yd2FyZGVkIGBvcmdgIGFyZyBjYW4ndCB0b3VjaCBhbm90aGVyXG4gICAgLy8gdGVuYW50J3MgZGVmYXVsdHMgKFJMUyBpcyBpbiBvd25lci1ieXBhc3MgbW9kZTsgdGhpcyBpcyB0aGUgZ2F0ZSkuXG4gICAgY29uc3QgY3R4ID0gZ2V0VGVuYW50Q29udGV4dCgpO1xuICAgIGlmIChjdHggJiYgIWN0eC5pc1N1cGVyQWRtaW4gJiYgY3R4Lm9yZ0lkKSBvcmcgPSBjdHgub3JnSWQ7XG4gICAgcmV0dXJuIHdpdGhUZW5hbnRUeChhc3luYyAodHgpID0+IHtcbiAgICAgIGNvbnN0IG9yZ0NvbHVtbiA9IHRoaXMuZ2V0T3JnQ29sdW1uKCk7XG4gICAgICBjb25zdCBwcm9qZWN0Q29sdW1uID0gdGhpcy5nZXRQcm9qZWN0Q29sdW1uKCk7XG5cbiAgICAgIC8vIEJ1aWxkIHNjb3BpbmcgY29uZGl0aW9ucyBmb3IgY2xlYXJpbmcgZGVmYXVsdHNcbiAgICAgIGNvbnN0IHNjb3BlQ29uZGl0aW9ucyA9IFtcbiAgICAgICAgZXEob3JnQ29sdW1uLCBvcmcpLFxuICAgICAgICBlcSgodGhpcy5zY2hlbWEgYXMgYW55KS5pc0RlZmF1bHQsIHRydWUpLFxuICAgICAgXTtcbiAgICAgIGlmIChwcm9qZWN0Q29sdW1uKSB7XG4gICAgICAgIHNjb3BlQ29uZGl0aW9ucy5wdXNoKGVxKHByb2plY3RDb2x1bW4sIHByb2plY3QpKTtcbiAgICAgIH1cblxuICAgICAgLy8gTG9jayBleGlzdGluZyBkZWZhdWx0cyB3aXRoIEZPUiBVUERBVEUgdG8gcHJldmVudCBjb25jdXJyZW50IHNldERlZmF1bHQgcmFjZXNcbiAgICAgIGF3YWl0IHR4LmV4ZWN1dGUoXG4gICAgICAgIHNxbGBTRUxFQ1QgaWQgRlJPTSAke3RoaXMuc2NoZW1hfVxuICAgICAgICAgICAgV0hFUkUgJHtvcmdDb2x1bW59ID0gJHtvcmd9XG4gICAgICAgICAgICAgIEFORCAkeyh0aGlzLnNjaGVtYSBhcyBhbnkpLmlzRGVmYXVsdH0gPSB0cnVlXG4gICAgICAgICAgICAke3Byb2plY3RDb2x1bW4gPyBzcWxgQU5EICR7cHJvamVjdENvbHVtbn0gPSAke3Byb2plY3R9YCA6IHNxbGBgfVxuICAgICAgICAgICAgRk9SIFVQREFURWAsXG4gICAgICApO1xuXG4gICAgICAvLyBNYXJrIGFsbCBlbnRpdGllcyBpbiBzY29wZSBhcyBub24tZGVmYXVsdFxuICAgICAgYXdhaXQgdHhcbiAgICAgICAgLnVwZGF0ZSh0aGlzLnNjaGVtYSlcbiAgICAgICAgLnNldCh7XG4gICAgICAgICAgaXNEZWZhdWx0OiBmYWxzZSxcbiAgICAgICAgICB1cGRhdGVkQXQ6IG5ldyBEYXRlKCksXG4gICAgICAgICAgdXBkYXRlZEJ5OiB1c2VySWQgfHwgJ3N5c3RlbScsXG4gICAgICAgIH0gYXMgYW55KVxuICAgICAgICAud2hlcmUoYW5kKC4uLnNjb3BlQ29uZGl0aW9ucykpO1xuXG4gICAgICAvLyBTZXQgdGhlIHNwZWNpZmllZCBlbnRpdHkgYXMgZGVmYXVsdFxuICAgICAgY29uc3QgW3VwZGF0ZWRdID0gYXdhaXQgdHhcbiAgICAgICAgLnVwZGF0ZSh0aGlzLnNjaGVtYSlcbiAgICAgICAgLnNldCh7XG4gICAgICAgICAgaXNEZWZhdWx0OiB0cnVlLFxuICAgICAgICAgIHVwZGF0ZWRBdDogbmV3IERhdGUoKSxcbiAgICAgICAgICB1cGRhdGVkQnk6IHVzZXJJZCB8fCAnc3lzdGVtJyxcbiAgICAgICAgfSBhcyBhbnkpXG4gICAgICAgIC53aGVyZShcbiAgICAgICAgICBhbmQoXG4gICAgICAgICAgICBlcSgodGhpcy5zY2hlbWEgYXMgYW55KS5pZCwgaWQpLFxuICAgICAgICAgICAgZXEob3JnQ29sdW1uLCBvcmcpLFxuICAgICAgICAgICksXG4gICAgICAgIClcbiAgICAgICAgLnJldHVybmluZygpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSk7XG5cbiAgICAgIGlmICghdXBkYXRlZCkge1xuICAgICAgICB0aHJvdyBuZXcgTm90Rm91bmRFcnJvcihgRW50aXR5IHdpdGggaWQgJHtpZH0gbm90IGZvdW5kYCk7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiB1cGRhdGVkO1xuICAgIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIFVwZGF0ZSBtdWx0aXBsZSBlbnRpdGllcyBtYXRjaGluZyBmaWx0ZXJcbiAgICovXG4gIGFzeW5jIHVwZGF0ZU1hbnkoXG4gICAgZmlsdGVyOiBQYXJ0aWFsPFRGaWx0ZXI+LFxuICAgIGRhdGE6IFBhcnRpYWw8VFVwZGF0ZT4sXG4gICAgb3JnSWQ6IHN0cmluZyxcbiAgICB1c2VySWQ6IHN0cmluZyxcbiAgKTogUHJvbWlzZTxURW50aXR5W10+IHtcbiAgICBjb25zdCBjb25kaXRpb25zID0gdGhpcy5idWlsZENvbmRpdGlvbnMoZmlsdGVyLCBvcmdJZCk7XG5cbiAgICByZXR1cm4gd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4gdHhcbiAgICAgIC51cGRhdGUodGhpcy5zY2hlbWEpXG4gICAgICAuc2V0KHtcbiAgICAgICAgLi4uZGF0YSxcbiAgICAgICAgdXBkYXRlZEF0OiBuZXcgRGF0ZSgpLFxuICAgICAgICB1cGRhdGVkQnk6IHVzZXJJZCB8fCAnc3lzdGVtJyxcbiAgICAgIH0gYXMgYW55KVxuICAgICAgLndoZXJlKGFuZCguLi5jb25kaXRpb25zKSlcbiAgICAgIC5yZXR1cm5pbmcoKS50aGVuKHIgPT4gZHJpenpsZVJvd3M8VEVudGl0eT4ocikpKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDcmVhdGUgbXVsdGlwbGUgZW50aXRpZXMgaW4gYSBzaW5nbGUgYmF0Y2ggaW5zZXJ0LlxuICAgKiBVc2VzIHVwc2VydCAob25Db25mbGljdERvVXBkYXRlKSDigJQgYWxsIHJvd3MgYXJlIGluc2VydGVkIGluIG9uZSBxdWVyeSBwZXIgY2h1bmsuXG4gICAqIENodW5rcyBvZiAxMDAgdG8gc3RheSB3aXRoaW4gUG9zdGdyZVNRTCBwYXJhbWV0ZXIgbGltaXRzLlxuICAgKi9cbiAgYXN5bmMgYnVsa0NyZWF0ZShpdGVtczogVEluc2VydFtdLCB1c2VySWQ6IHN0cmluZyk6IFByb21pc2U8VEVudGl0eVtdPiB7XG4gICAgaWYgKGl0ZW1zLmxlbmd0aCA9PT0gMCkgcmV0dXJuIFtdO1xuXG4gICAgY29uc3QgQ0hVTktfU0laRSA9IDEwMDtcbiAgICBjb25zdCBub3cgPSBuZXcgRGF0ZSgpO1xuICAgIGNvbnN0IHVzZXIgPSB1c2VySWQgfHwgJ3N5c3RlbSc7XG5cbiAgICBjb25zdCByZXN1bHRzID0gYXdhaXQgd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4ge1xuICAgICAgY29uc3QgYWxsQ3JlYXRlZDogVEVudGl0eVtdID0gW107XG5cbiAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgaXRlbXMubGVuZ3RoOyBpICs9IENIVU5LX1NJWkUpIHtcbiAgICAgICAgY29uc3QgY2h1bmsgPSBpdGVtcy5zbGljZShpLCBpICsgQ0hVTktfU0laRSk7XG4gICAgICAgIGNvbnN0IHZhbHVlcyA9IGNodW5rLm1hcChkYXRhID0+ICh7XG4gICAgICAgICAgLi4udGhpcy5lbmZvcmNlT3JnSWQoZGF0YSksXG4gICAgICAgICAgY3JlYXRlZEJ5OiB1c2VyLFxuICAgICAgICAgIHVwZGF0ZWRCeTogdXNlcixcbiAgICAgICAgfSBhcyBhbnkpKTtcblxuICAgICAgICBjb25zdCBjcmVhdGVkID0gYXdhaXQgdHhcbiAgICAgICAgICAuaW5zZXJ0KHRoaXMuc2NoZW1hKVxuICAgICAgICAgIC52YWx1ZXModmFsdWVzKVxuICAgICAgICAgIC5vbkNvbmZsaWN0RG9VcGRhdGUoe1xuICAgICAgICAgICAgdGFyZ2V0OiB0aGlzLmNvbmZsaWN0VGFyZ2V0IGFzIGFueSxcbiAgICAgICAgICAgIHNldDoge1xuICAgICAgICAgICAgICB1cGRhdGVkQXQ6IG5vdyxcbiAgICAgICAgICAgICAgdXBkYXRlZEJ5OiB1c2VyLFxuICAgICAgICAgICAgfSBhcyBhbnksXG4gICAgICAgICAgfSlcbiAgICAgICAgICAucmV0dXJuaW5nKCkudGhlbihyID0+IGRyaXp6bGVSb3dzPFRFbnRpdHk+KHIpKTtcblxuICAgICAgICBhbGxDcmVhdGVkLnB1c2goLi4uY3JlYXRlZCk7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiBhbGxDcmVhdGVkO1xuICAgIH0pO1xuXG4gICAgLy8gUnVuIGhvb2tzIGluIHBhcmFsbGVsIGJ1dCBhd2FpdCBhbGwgYmVmb3JlIHJldHVybmluZyBzbyBhIHN1YnNlcXVlbnRcbiAgICAvLyByZWFkIGluIHRoZSBzYW1lIHJlcXVlc3Qgc2VlcyBhIGNvaGVyZW50IHBvc3Qtd3JpdGUgdmlldy5cbiAgICBhd2FpdCBQcm9taXNlLmFsbChcbiAgICAgIHJlc3VsdHMubWFwKGVudGl0eSA9PlxuICAgICAgICB0aGlzLm9uQWZ0ZXJDcmVhdGUoZW50aXR5LCB1c2VySWQpLmNhdGNoKGVyciA9PlxuICAgICAgICAgIHRoaXMuX2xvZ2dlci53YXJuKCdMaWZlY3ljbGUgaG9vayBmYWlsZWQnLCB7IGVycm9yOiBTdHJpbmcoZXJyKSB9KSxcbiAgICAgICAgKSxcbiAgICAgICksXG4gICAgKTtcblxuICAgIHJldHVybiByZXN1bHRzO1xuICB9XG5cbiAgLyoqXG4gICAqIFNvZnQtZGVsZXRlIG11bHRpcGxlIGVudGl0aWVzIGJ5IElEcyBpbiBhIHNpbmdsZSBiYXRjaCBvcGVyYXRpb24uXG4gICAqL1xuICBhc3luYyBidWxrRGVsZXRlKFxuICAgIGlkczogc3RyaW5nW10sXG4gICAgb3JnSWQ6IHN0cmluZyxcbiAgICB1c2VySWQ6IHN0cmluZyxcbiAgKTogUHJvbWlzZTxURW50aXR5W10+IHtcbiAgICBpZiAoaWRzLmxlbmd0aCA9PT0gMCkgcmV0dXJuIFtdO1xuXG4gICAgY29uc3Qgbm93ID0gbmV3IERhdGUoKTtcbiAgICBjb25zdCB1c2VyID0gdXNlcklkIHx8ICdzeXN0ZW0nO1xuICAgIC8vIE93bmVyLXNjb3BlIHRoZSBidWxrIHNvZnQtZGVsZXRlOiBidWlsZENvbmRpdGlvbnMgYWxzbyBtYXRjaGVzIHN5c3RlbS9vdGhlclxuICAgIC8vIC1vcmcgUFVCTElDIHJvd3MsIHNvIHdpdGhvdXQgdGhlIHN0cmljdCBvcmdJZCBwaW4gYSB0ZW5hbnQgY291bGQgZGVsZXRlXG4gICAgLy8gc2hhcmVkIHJlY29yZHMgYnkgaWQuIChTZWUgd3JpdGVDb25kaXRpb25zLilcbiAgICBjb25zdCBvcmdDb2wgPSAodGhpcy5zY2hlbWEgYXMgYW55KS5vcmdJZCBhcyBBbnlDb2x1bW4gfCB1bmRlZmluZWQ7XG4gICAgY29uc3QgY29uZGl0aW9ucyA9IFtcbiAgICAgIGluQXJyYXkoKHRoaXMuc2NoZW1hIGFzIGFueSkuaWQsIGlkcyksXG4gICAgICAuLi50aGlzLmJ1aWxkQ29uZGl0aW9ucyh7fSBhcyBQYXJ0aWFsPFRGaWx0ZXI+LCBvcmdJZCksXG4gICAgICAuLi4ob3JnSWQgJiYgb3JnQ29sID8gW2VxKG9yZ0NvbCwgb3JnSWQpXSA6IFtdKSxcbiAgICBdO1xuXG4gICAgY29uc3QgZGVsZXRlZCA9IGF3YWl0IHdpdGhUZW5hbnRUeChhc3luYyAodHgpID0+IHR4XG4gICAgICAudXBkYXRlKHRoaXMuc2NoZW1hKVxuICAgICAgLnNldCh7XG4gICAgICAgIGlzQWN0aXZlOiBmYWxzZSxcbiAgICAgICAgdXBkYXRlZEF0OiBub3csXG4gICAgICAgIHVwZGF0ZWRCeTogdXNlcixcbiAgICAgICAgZGVsZXRlZEF0OiBub3csXG4gICAgICAgIGRlbGV0ZWRCeTogdXNlcixcbiAgICAgIH0gYXMgYW55KVxuICAgICAgLndoZXJlKGFuZCguLi5jb25kaXRpb25zKSlcbiAgICAgIC5yZXR1cm5pbmcoKS50aGVuKHIgPT4gZHJpenpsZVJvd3M8VEVudGl0eT4ocikpKTtcblxuICAgIGF3YWl0IFByb21pc2UuYWxsKFxuICAgICAgZGVsZXRlZC5tYXAoZW50aXR5ID0+XG4gICAgICAgIHRoaXMub25BZnRlckRlbGV0ZShlbnRpdHkuaWQsIGVudGl0eSwgdXNlcklkKS5jYXRjaChlcnIgPT5cbiAgICAgICAgICB0aGlzLl9sb2dnZXIud2FybignTGlmZWN5Y2xlIGhvb2sgZmFpbGVkJywgeyBlcnJvcjogU3RyaW5nKGVycikgfSksXG4gICAgICAgICksXG4gICAgICApLFxuICAgICk7XG5cbiAgICByZXR1cm4gZGVsZXRlZDtcbiAgfVxufVxuIl19
|
|
539
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY3J1ZC1zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL2FwaS9jcnVkLXNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsK0NBQStDO0FBQy9DLHNDQUFzQztBQUV0QyxPQUFPLEVBQUUsYUFBYSxFQUFFLFlBQVksRUFBRSxNQUFNLDRCQUE0QixDQUFDO0FBQ3pFLE9BQU8sRUFBRSxHQUFHLEVBQUUsRUFBRSxFQUFFLEdBQUcsRUFBRSxHQUFHLEVBQUUsSUFBSSxFQUFFLEdBQUcsRUFBRSxPQUFPLEVBQUUsZUFBZSxFQUFFLE1BQU0sYUFBYSxDQUFDO0FBR3JGLE9BQU8sRUFBRSxZQUFZLEVBQUUsb0JBQW9CLEVBQUUsZ0JBQWdCLEVBQUUsTUFBTSx3QkFBd0IsQ0FBQztBQUU5RixtRkFBbUY7QUFDbkYsTUFBTSxrQkFBa0IsR0FBRyxRQUFRLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxrQkFBa0IsSUFBSSxLQUFLLEVBQUUsRUFBRSxDQUFDLENBQUM7QUFDakYsTUFBTSxjQUFjLEdBQUcsUUFBUSxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsY0FBYyxJQUFJLE1BQU0sRUFBRSxFQUFFLENBQUMsQ0FBQztBQUUxRTs7Ozs7R0FLRztBQUNILE1BQU0sVUFBVSxXQUFXLENBQUksSUFBYTtJQUMxQyxPQUFPLElBQVcsQ0FBQztBQUNyQixDQUFDO0FBRUQsd0VBQXdFO0FBQ3hFLE1BQU0sVUFBVSxZQUFZLENBQUMsSUFBYTtJQUN4QyxPQUFPLElBQTJCLENBQUM7QUFDckMsQ0FBQztBQThDRDs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7R0FnQ0c7QUFDSCxNQUFNLE9BQWdCLFdBQVc7SUFnQ2QsT0FBTyxHQUFHLFlBQVksQ0FBQyxjQUFjLENBQUMsQ0FBQztJQUV4RDtRQUNFLHdFQUF3RTtRQUN4RSx5RUFBeUU7UUFDekUsc0VBQXNFO1FBQ3RFLDREQUE0RDtRQUM1RCxJQUFJLElBQUksQ0FB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SyxDQUFDLEdBQUcsQ0FBQyxFQUFFLENBQ3hELElBQUksQ0FBQyxPQUFPLENBQUMsSUFBSSxDQUFDLHVCQUF1QixFQUFFLEVBQUUsS0FBSyxFQUFFLE1BQU0sQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDLENBQ25FLENBQ0YsQ0FDRixDQUFDO1FBRUYsT0FBTyxPQUFPLENBQUM7SUFDakIsQ0FBQztDQUNGIiwic291cmNlc0NvbnRlbnQiOlsiLy8gQ29weXJpZ2h0IDIwMjYgUGlwZWxpbmUgQnVpbGRlciBDb250cmlidXRvcnNcbi8vIFNQRFgtTGljZW5zZS1JZGVudGlmaWVyOiBBcGFjaGUtMi4wXG5cbmltcG9ydCB7IE5vdEZvdW5kRXJyb3IsIGNyZWF0ZUxvZ2dlciB9IGZyb20gJ0BwaXBlbGluZS1idWlsZGVyL2FwaS1jb3JlJztcbmltcG9ydCB7IFNRTCwgZXEsIGFuZCwgYXNjLCBkZXNjLCBzcWwsIGluQXJyYXksIGdldFRhYmxlQ29sdW1ucyB9IGZyb20gJ2RyaXp6bGUtb3JtJztcbmltcG9ydCB0eXBlIHsgQW55Q29sdW1uIH0gZnJvbSAnZHJpenpsZS1vcm0vY29sdW1uJztcbmltcG9ydCB0eXBlIHsgUGdUYWJsZSB9IGZyb20gJ2RyaXp6bGUtb3JtL3BnLWNvcmUnO1xuaW1wb3J0IHsgd2l0aFRlbmFudFR4LCBydW5XaXRoVGVuYW50Q29udGV4dCwgZ2V0VGVuYW50Q29udGV4dCB9IGZyb20gJy4uL2RhdGFiYXNlL3RlbmFuY3kuanMnO1xuXG4vKiogUGFnaW5hdGlvbiBkZWZhdWx0cyDigJQgcmVhZCBmcm9tIGVudiB0byBtYXRjaCBDb3JlQ29uc3RhbnRzIGluIHBpcGVsaW5lLWNvcmUuICovXG5jb25zdCBERUZBVUxUX1BBR0VfTElNSVQgPSBwYXJzZUludChwcm9jZXNzLmVudi5ERUZBVUxUX1BBR0VfTElNSVQgfHwgJzEwMCcsIDEwKTtcbmNvbnN0IE1BWF9QQUdFX0xJTUlUID0gcGFyc2VJbnQocHJvY2Vzcy5lbnYuTUFYX1BBR0VfTElNSVQgfHwgJzEwMDAnLCAxMCk7XG5cbi8qKlxuICogQ2FzdCBEcml6emxlIHF1ZXJ5IHJlc3VsdHMgdG8gYSB0eXBlZCBhcnJheS5cbiAqIERyaXp6bGUncyBnZW5lcmljIHJldHVybiB0eXBlIChgUGdTZWxlY3RCYXNlPC4uLj5gKSBkb2Vzbid0IG5hcnJvdyB0byBvdXJcbiAqIGVudGl0eSBnZW5lcmljcywgc28gYW4gZXhwbGljaXQgY2FzdCBpcyBuZWVkZWQuIENlbnRyYWxpc2VkIGhlcmUgc28gZXZlcnlcbiAqIGNhbGwtc2l0ZSBzdGF5cyBvbmUtbGluZXIgY2xlYW4gYW5kIHRoZSBjYXN0IGlzIGRvY3VtZW50ZWQgaW4gb25lIHBsYWNlLlxuICovXG5leHBvcnQgZnVuY3Rpb24gZHJpenpsZVJvd3M8VD4ocm93czogdW5rbm93bik6IFRbXSB7XG4gIHJldHVybiByb3dzIGFzIFRbXTtcbn1cblxuLyoqIENhc3QgYSBEcml6emxlIGFnZ3JlZ2F0ZSByZXN1bHQgdG8gZXh0cmFjdCBgW3sgY291bnQ6IG51bWJlciB9XWAuICovXG5leHBvcnQgZnVuY3Rpb24gZHJpenpsZUNvdW50KHJvd3M6IHVua25vd24pOiBbeyBjb3VudDogbnVtYmVyIH1dIHtcbiAgcmV0dXJuIHJvd3MgYXMgW3sgY291bnQ6IG51bWJlciB9XTtcbn1cblxuLyoqXG4gKiBCYXNlIGludGVyZmFjZSBmb3IgZW50aXRpZXMgd2l0aCBjb21tb24gZmllbGRzXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgQmFzZUVudGl0eSB7XG4gIGlkOiBzdHJpbmc7XG4gIG9yZ0lkOiBzdHJpbmc7XG4gIGlzRGVmYXVsdDogYm9vbGVhbjtcbiAgY3JlYXRlZEF0OiBEYXRlO1xuICB1cGRhdGVkQXQ6IERhdGU7XG4gIGNyZWF0ZWRCeTogc3RyaW5nO1xuICB1cGRhdGVkQnk6IHN0cmluZztcbiAgW2tleTogc3RyaW5nXTogdW5rbm93bjtcbn1cblxuLyoqXG4gKiBQYWdpbmF0aW9uIGFuZCBzb3J0aW5nIG9wdGlvbnNcbiAqL1xuZXhwb3J0IGludGVyZmFjZSBRdWVyeU9wdGlvbnMge1xuICBsaW1pdD86IG51bWJlcjtcbiAgb2Zmc2V0PzogbnVtYmVyO1xuICBzb3J0Qnk/OiBzdHJpbmc7XG4gIHNvcnRPcmRlcj86ICdhc2MnIHwgJ2Rlc2MnO1xuICAvKiogV2hlbiB0cnVlLCBydW5zIGEgc2VwYXJhdGUgQ09VTlQoKikgcXVlcnkgdG8gaW5jbHVkZSBleGFjdCB0b3RhbC4gRGVmYXVsdDogZmFsc2UuICovXG4gIGluY2x1ZGVUb3RhbD86IGJvb2xlYW47XG4gIC8qKiBDdXJzb3ItYmFzZWQgcGFnaW5hdGlvbjogZmV0Y2ggcm93cyBhZnRlciB0aGlzIGN1cnNvciB2YWx1ZSAodXNlcyBzb3J0QnkgY29sdW1uKS4gKi9cbiAgY3Vyc29yPzogc3RyaW5nO1xuICAvKiogU3BhcnNlIGZpZWxkc2V0OiBjb2x1bW4gbmFtZXMgdG8gc2VsZWN0LiBSZXR1cm5zIGFsbCBjb2x1bW5zIHdoZW4gb21pdHRlZC4gKi9cbiAgZmllbGRzPzogc3RyaW5nW107XG59XG5cbi8qKlxuICogUGFnaW5hdGVkIHJlc3VsdCB3aXRoIG1ldGFkYXRhXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgUGFnaW5hdGVkUmVzdWx0PFQ+IHtcbiAgZGF0YTogVFtdO1xuICAvKiogVG90YWwgY291bnQgb2YgbWF0Y2hpbmcgZW50aXRpZXMuIE9ubHkgcHJlc2VudCB3aGVuIGluY2x1ZGVUb3RhbCBpcyB0cnVlLiAqL1xuICB0b3RhbD86IG51bWJlcjtcbiAgbGltaXQ6IG51bWJlcjtcbiAgb2Zmc2V0OiBudW1iZXI7XG4gIGhhc01vcmU6IGJvb2xlYW47XG4gIC8qKiBDdXJzb3IgcG9pbnRpbmcgdG8gdGhlIGxhc3QgaXRlbSwgZm9yIGN1cnNvci1iYXNlZCBwYWdpbmF0aW9uLiAqL1xuICBuZXh0Q3Vyc29yPzogc3RyaW5nO1xufVxuXG4vKipcbiAqIEFic3RyYWN0IENSVUQgc2VydmljZSB3aXRoIG11bHRpLXRlbmFudCBhY2Nlc3MgY29udHJvbCBhbmQgcGFnaW5hdGlvbi5cbiAqXG4gKiBTdWJjbGFzc2VzIGJpbmQgdG8gYSBzcGVjaWZpYyBEcml6emxlIHRhYmxlIGJ5IGltcGxlbWVudGluZyBgc2NoZW1hYCxcbiAqIGBidWlsZENvbmRpdGlvbnNgLCBgZ2V0U29ydENvbHVtbmAsIGFuZCB0aGUgb3JnL3Byb2plY3QtY29sdW1uIGFjY2Vzc29ycy5cbiAqXG4gKiBAdHlwZVBhcmFtIFRFbnRpdHkgLSBFbnRpdHkgdHlwZSBleHRlbmRpbmcgQmFzZUVudGl0eVxuICogQHR5cGVQYXJhbSBURmlsdGVyIC0gRmlsdGVyIHR5cGUgZm9yIHF1ZXJ5IHBhcmFtZXRlcnNcbiAqIEB0eXBlUGFyYW0gVEluc2VydCAtIEluc2VydCBEVE8gdHlwZVxuICogQHR5cGVQYXJhbSBUVXBkYXRlIC0gVXBkYXRlIERUTyB0eXBlXG4gKlxuICogKipBIG5vdGUgb24gdGhlIHR5cGUgY2FzdHMuKiogRHJpenpsZSdzIHJvdyB0eXBlcyBhcmUgaW5mZXJyZWQgZnJvbVxuICogYHBnVGFibGUoLi4uKWAgYW5kIGRvbid0IGdlbmVyaWNhbGx5IG5hcnJvdyB0aHJvdWdoIHRoZSBhYnN0cmFjdCBgc2NoZW1hYFxuICogZ2V0dGVyLCBzbyB0aGUgYmFzZSBjbGFzcyBjYXN0cyBxdWVyeSByZXN1bHRzIHRvIGBURW50aXR5YCBhbmQgYmFjay4gVGhlXG4gKiBjYXN0IGlzICpub3QqIGEgcnVudGltZSBzYWZldHkgZ3VhcmFudGVlIOKAlCBpdCByZWxpZXMgb24gZWFjaCBzdWJjbGFzc1xuICogcGFzc2luZyB0aGUgbWF0Y2hpbmcgZW50aXR5IHR5cGUuIE9yZy1zY29waW5nIGlzIGVuZm9yY2VkIGJ5IGV2ZXJ5XG4gKiBzdWJjbGFzcydzIGBidWlsZENvbmRpdGlvbnNgIGluamVjdGluZyBgV0hFUkUgb3JnX2lkID0gJDFgOyB0aGlzIGNsYXNzXG4gKiBkb2VzIG5vdCBhZGQgdGhhdCBmaWx0ZXIgaXRzZWxmLlxuICpcbiAqICoqRXJyb3IgcG9saWN5LioqIEVycm9ycyBwcm9wYWdhdGUgdXAgdG8gdGhlIHJvdXRlLWxldmVsIGhhbmRsZXJcbiAqIChgd2l0aFJvdXRlYCk7IG5vIGNhdGNoLWFuZC1zd2FsbG93IGhlcmUuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHR5cGVzY3JpcHRcbiAqIGNsYXNzIFBpcGVsaW5lU2VydmljZSBleHRlbmRzIENydWRTZXJ2aWNlPFBpcGVsaW5lLCBQaXBlbGluZUZpbHRlciwgUGlwZWxpbmVJbnNlcnQsIFBpcGVsaW5lVXBkYXRlPiB7XG4gKiAgIHByb3RlY3RlZCBnZXQgc2NoZW1hKCkgeyByZXR1cm4gc2NoZW1hLnBpcGVsaW5lOyB9XG4gKiAgIHByb3RlY3RlZCBidWlsZENvbmRpdGlvbnMoZmlsdGVyLCBvcmdJZCkgeyByZXR1cm4gYnVpbGRQaXBlbGluZUNvbmRpdGlvbnMoZmlsdGVyLCBvcmdJZCk7IH1cbiAqICAgcHJvdGVjdGVkIGdldFNvcnRDb2x1bW4oc29ydEJ5KSB7IHJldHVybiBzb3J0Q29sdW1uTWFwW3NvcnRCeV0gPz8gbnVsbDsgfVxuICogICBwcm90ZWN0ZWQgZ2V0UHJvamVjdENvbHVtbigpIHsgcmV0dXJuIHNjaGVtYS5waXBlbGluZS5wcm9qZWN0OyB9XG4gKiAgIHByb3RlY3RlZCBnZXRPcmdDb2x1bW4oKSB7IHJldHVybiBzY2hlbWEucGlwZWxpbmUub3JnSWQ7IH1cbiAqIH1cbiAqIGBgYFxuICovXG5leHBvcnQgYWJzdHJhY3QgY2xhc3MgQ3J1ZFNlcnZpY2U8XG4gIFRFbnRpdHkgZXh0ZW5kcyBCYXNlRW50aXR5LFxuICBURmlsdGVyLFxuICBUSW5zZXJ0LFxuICBUVXBkYXRlLFxuPiB7XG4gIC8qKiBEcml6emxlIHNjaGVtYSB0YWJsZSBmb3IgdGhpcyBlbnRpdHkgKi9cbiAgcHJvdGVjdGVkIGFic3RyYWN0IGdldCBzY2hlbWEoKTogUGdUYWJsZTtcblxuICAvKipcbiAgICogQnVpbGQgU1FMIGNvbmRpdGlvbnMgZm9yIGZpbHRlcmluZyBlbnRpdGllcy5cbiAgICogYHBhcmVudE9yZ0lkYCAob3JnIOKGkiB0ZWFtIGhpZXJhcmNoeSkgaXMgb3B0aW9uYWwgYW5kIG9ubHkgaG9ub3JlZCBieVxuICAgKiBzZXJ2aWNlcyB0aGF0IG9wdCBpbnRvIHBhcmVudC1pbmhlcml0ZWQgdmlzaWJpbGl0eSAoZS5nLiBwbHVnaW5zKS5cbiAgICovXG4gIHByb3RlY3RlZCBhYnN0cmFjdCBidWlsZENvbmRpdGlvbnMoZmlsdGVyOiBQYXJ0aWFsPFRGaWx0ZXI+LCBvcmdJZD86IHN0cmluZywgcGFyZW50T3JnSWQ/OiBzdHJpbmcpOiBTUUxbXTtcblxuICAvKiogR2V0IHRoZSBzY2hlbWEgY29sdW1uIGZvciBzb3J0aW5nIGJ5IGZpZWxkIG5hbWUgKi9cbiAgcHJvdGVjdGVkIGFic3RyYWN0IGdldFNvcnRDb2x1bW4oc29ydEJ5OiBzdHJpbmcpOiBBbnlDb2x1bW4gfCBudWxsO1xuXG4gIC8qKiBHZXQgdGhlIHByb2plY3QgY29sdW1uIGZvciBzZXREZWZhdWx0IHNjb3BpbmcgKG51bGwgaWYgZW50aXR5IGhhcyBubyBwcm9qZWN0IHNjb3BlKSAqL1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgZ2V0UHJvamVjdENvbHVtbigpOiBBbnlDb2x1bW4gfCBudWxsO1xuXG4gIC8qKlxuICAgKiBHZXQgdGhlIHRlbmFudCBvcmctaWQgY29sdW1uLiBVc2VkIGJvdGggdG8gc2NvcGUgYHNldERlZmF1bHRgIGFuZCB0byBwaW5cbiAgICogZXZlcnkgd3JpdGUgKHVwZGF0ZS9kZWxldGUvYnVsa0RlbGV0ZSkgdG8gdGhlIGNhbGxlcidzIG93biBvcmcg4oCUIHNvIGl0IE1VU1RcbiAgICogYmUgdGhlIHRlbmFudCBgb3JnSWRgIGNvbHVtbiwgbm90IGEgZGlzcGxheS9uYW1lIGNvbHVtbi5cbiAgICovXG4gIHByb3RlY3RlZCBhYnN0cmFjdCBnZXRPcmdDb2x1bW4oKTogQW55Q29sdW1uO1xuXG4gIC8qKiBHZXQgdGhlIHVuaXF1ZSBjb25zdHJhaW50IGNvbHVtbnMgZm9yIG9uQ29uZmxpY3REb1VwZGF0ZSAqL1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgZ2V0IGNvbmZsaWN0VGFyZ2V0KCk6IEFueUNvbHVtbltdO1xuXG4gIHByaXZhdGUgcmVhZG9ubHkgX2xvZ2dlciA9IGNyZWF0ZUxvZ2dlcignY3J1ZC1zZXJ2aWNlJyk7XG5cbiAgY29uc3RydWN0b3IoKSB7XG4gICAgLy8gRmFpbCBmYXN0IGlmIGEgc3ViY2xhc3MgZG9lc24ndCBleHBvc2UgYSB0ZW5hbnQgb3JnIGNvbHVtbi4gVGhlIHdyaXRlXG4gICAgLy8gcGF0aHMgKHdyaXRlQ29uZGl0aW9ucyAvIGJ1bGtEZWxldGUpIHBpbiBtdXRhdGlvbnMgdG8gdGhlIGNhbGxlcidzIG93blxuICAgIC8vIG9yZyB0aHJvdWdoIGl0OyBhIG1pc3NpbmcgY29sdW1uIHdvdWxkIHNpbGVudGx5IGRyb3AgdGhhdCBndWFyZCDigJQgYVxuICAgIC8vIGNyb3NzLXRlbmFudCBmYWlsLW9wZW4g4oCUIHNvIGFzc2VydCBpdHMgcHJlc2VuY2UgdXAgZnJvbnQuXG4gICAgaWYgKHRoaXMuZ2V0T3JnQ29sdW1uKCkgPT0gbnVsbCkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKGAke3RoaXMuY29uc3RydWN0b3IubmFtZX06IGdldE9yZ0NvbHVtbigpIG11c3QgcmV0dXJuIHRoZSB0ZW5hbnQgb3JnIGNvbHVtbmApO1xuICAgIH1cbiAgfVxuXG4gIC8qKiBCdWlsZCBjb25kaXRpb25zIGZvciBhIHNpbmdsZSBlbnRpdHkgYnkgSUQuXG4gICAqICBgcGFyZW50T3JnSWRgIHdpZGVucyB2aXNpYmlsaXR5IHRvIGEgcGFyZW50IG9yZydzIHB1YmxpYyByb3dzIChvcmcg4oaSIHRlYW1cbiAgICogIGhpZXJhcmNoeSkg4oCUIHNhbWUgb3B0LWluIHNlbWFudGljcyBhcyBgZmluZGAvYGZpbmRQYWdpbmF0ZWRgLiBPbWl0dGVkIGJ5IHRoZVxuICAgKiAgd3JpdGUgcGF0aCAoYHdyaXRlQ29uZGl0aW9uc2ApLCB3aGljaCBtdXN0IHN0YXkgb3duLW9yZyBzY29wZWQuICovXG4gIHByaXZhdGUgaWRDb25kaXRpb25zKGlkOiBzdHJpbmcsIG9yZ0lkPzogc3RyaW5nLCBwYXJlbnRPcmdJZD86IHN0cmluZyk6IFNRTFtdIHtcbiAgICByZXR1cm4gdGhpcy5idWlsZENvbmRpdGlvbnMoeyBpZCB9IGFzIHVua25vd24gYXMgUGFydGlhbDxURmlsdGVyPiwgb3JnSWQsIHBhcmVudE9yZ0lkKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDb25kaXRpb25zIGZvciBhIE1VVEFUSU9OICh1cGRhdGUvZGVsZXRlKSBvZiBhIHNpbmdsZSBlbnRpdHkuXG4gICAqXG4gICAqIGBpZENvbmRpdGlvbnNgIHJldXNlcyB0aGUgUkVBRCBhY2Nlc3MtY29udHJvbCBjbGF1c2UsIHdoaWNoIGFsc28gbWF0Y2hlc1xuICAgKiBzeXN0ZW0tb3JnIC8gb3RoZXItb3JnIFBVQkxJQyByZWNvcmRzIOKAlCBzbyB3aXRob3V0IGFuIGV4dHJhIG93bmVyc2hpcCBwaW4gYW55XG4gICAqIHRlbmFudCBjb3VsZCB1cGRhdGUgb3Igc29mdC1kZWxldGUgYW5vdGhlciBvcmcncyAob3IgdGhlIHN5c3RlbSBvcmcncykgcHVibGljXG4gICAqIHJlY29yZHMuIEFORCBhIHN0cmljdCBgb3JnSWQgPT09IGNhbGxlcmAgcHJlZGljYXRlOiB0aGUgcmVhZCBjbGF1c2Unc1xuICAgKiBwdWJsaWMtT1IgYnJhbmNoIHJlcXVpcmVzIGBvcmdfaWQgPSAnc3lzdGVtJ2AsIHdoaWNoIHRoZW4gY2FuJ3QgYmUgc2F0aXNmaWVkLFxuICAgKiBsZWF2aW5nIG9ubHkgb3duLW9yZyByb3dzLiBvcmdJZC1sZXNzIChzeXNhZG1pbikgY29udGV4dCBrZWVwcyBmdWxsIGFjY2Vzcy5cbiAgICovXG4gIHByaXZhdGUgd3JpdGVDb25kaXRpb25zKGlkOiBzdHJpbmcsIG9yZ0lkPzogc3RyaW5nKTogU1FMW10ge1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSB0aGlzLmlkQ29uZGl0aW9ucyhpZCwgb3JnSWQpO1xuICAgIC8vIFBpbiB0aGUgbXV0YXRpb24gdG8gdGhlIGNhbGxlcidzIG93biBvcmcgdmlhIHRoZSB0ZW5hbnQgY29sdW1uXG4gICAgLy8gKGdldE9yZ0NvbHVtbiwgYXNzZXJ0ZWQgbm9uLW51bGwgaW4gdGhlIGNvbnN0cnVjdG9yKSDigJQgY29uc2lzdGVudCB3aXRoXG4gICAgLy8gc2V0RGVmYXVsdCBhbmQgd2l0aG91dCB0aGUgb2xkIHNpbGVudCBmYWlsLW9wZW4gd2hlbiB0aGUgcHJvcGVydHkgd2FzIGFic2VudC5cbiAgICBpZiAob3JnSWQpIGNvbmRpdGlvbnMucHVzaChlcSh0aGlzLmdldE9yZ0NvbHVtbigpLCBvcmdJZCkpO1xuICAgIHJldHVybiBjb25kaXRpb25zO1xuICB9XG5cbiAgLy8gTGlmZWN5Y2xlIGhvb2tzIOKAlCBvdmVycmlkZSBpbiBzdWJjbGFzc2VzIHRvIHJlYWN0IHRvIG11dGF0aW9uc1xuICAvLyBUaGVzZSBhcmUgZmlyZS1hbmQtZm9yZ2V0OiBlcnJvcnMgYXJlIGxvZ2dlZCBidXQgbmV2ZXIgYmxvY2sgdGhlIGNhbGxlci5cblxuICAvKiogQ2FsbGVkIGFmdGVyIGEgbmV3IGVudGl0eSBpcyBjcmVhdGVkICovXG4gIHByb3RlY3RlZCBhc3luYyBvbkFmdGVyQ3JlYXRlKF9lbnRpdHk6IFRFbnRpdHksIF91c2VySWQ6IHN0cmluZyk6IFByb21pc2U8dm9pZD4ge31cblxuICAvKiogQ2FsbGVkIGFmdGVyIGFuIGVudGl0eSBpcyB1cGRhdGVkICovXG4gIHByb3RlY3RlZCBhc3luYyBvbkFmdGVyVXBkYXRlKF9pZDogc3RyaW5nLCBfZW50aXR5OiBURW50aXR5LCBfdXNlcklkOiBzdHJpbmcpOiBQcm9taXNlPHZvaWQ+IHt9XG5cbiAgLyoqIENhbGxlZCBhZnRlciBhbiBlbnRpdHkgaXMgc29mdC1kZWxldGVkICovXG4gIHByb3RlY3RlZCBhc3luYyBvbkFmdGVyRGVsZXRlKF9pZDogc3RyaW5nLCBfZW50aXR5OiBURW50aXR5LCBfdXNlcklkOiBzdHJpbmcpOiBQcm9taXNlPHZvaWQ+IHt9XG5cbiAgLyoqXG4gICAqIEZpbmQgZW50aXRpZXMgbWF0Y2hpbmcgZmlsdGVyIGNyaXRlcmlhXG4gICAqXG4gICAqIEBwYXJhbSBmaWx0ZXIgLSBGaWx0ZXIgY3JpdGVyaWFcbiAgICogQHBhcmFtIG9yZ0lkIC0gVXNlcidzIG9yZ2FuaXphdGlvbiBJRCAob3B0aW9uYWwg4oCUIG9taXQgZm9yIGFub255bW91cy9zeXN0ZW0tcHVibGljLW9ubHkgYWNjZXNzKVxuICAgKi9cbiAgLyoqXG4gICAqIE9yZyDihpIgdGVhbSBoaWVyYXJjaHk6IHdoZW4gYSByZWFkIGlzIHdpZGVuZWQgdG8gYSBwYXJlbnQgb3JnIChgcGFyZW50T3JnSWRgXG4gICAqIHNldCksIHRoZSBwYXJlbnQncyByb3dzIGFyZSBvdXRzaWRlIHRoZSBjYWxsZXIncyBSTFMgc2NvcGUsIHNvIHRoZSByZWFkIG11c3RcbiAgICogcnVuIHVuZGVyIHN5c2FkbWluIGNvbnRleHQg4oCUIHRoZSBhY2Nlc3MtY29udHJvbCBXSEVSRSBjbGF1c2UgKG93biArIHBhcmVudCArXG4gICAqIHN5c3RlbSBwdWJsaWMsIGJ1aWx0IHNlcnZlci1zaWRlIGZyb20gYSB0cnVzdGVkIEpXVCBjbGFpbSkgaXMgdGhlbiB0aGVcbiAgICogYXV0aG9yaXRhdGl2ZSB0ZW5hbmN5IGdhdGUuIFdpdGhvdXQgYHBhcmVudE9yZ0lkYCBpdCBzdGF5cyBSTFMtc2NvcGVkLlxuICAgKlxuICAgKiBJTlZBUklBTlQgKHdoeSB0aGUgc3lzYWRtaW4gYnlwYXNzIGlzIHNhZmUpOiB0aGUgV0hFUkUgY2xhdXNlIGlzIGFsd2F5c1xuICAgKiBzZXJ2ZXItYnVpbHQgYnkgYGJ1aWxkQ29uZGl0aW9ucyhmaWx0ZXIsIG9yZ0lkLCBwYXJlbnRPcmdJZClgIGZyb20gdmFsdWVzXG4gICAqIGRlcml2ZWQgZnJvbSB0aGUgdmFsaWRhdGVkIEpXVCAoYG9yZ0lkYCA9IGFjdGl2ZSBvcmcsIGBwYXJlbnRPcmdJZGAgPSB0aGVcbiAgICogYWN0aXZlIG9yZydzIHBhcmVudCkuIE5vbmUgb2YgdGhlbSBpcyBhIHJhdyB1c2VyLXN1cHBsaWVkIHByZWRpY2F0ZSwgc28gdGhlXG4gICAqIGJ5cGFzcyBvbmx5IGV2ZXIgd2lkZW5zIHRoZSByZWFkIHRvIHRoZSBjYWxsZXIncyBvd24gc3VidHJlZSArIHN5c3RlbSBwdWJsaWNcbiAgICogcm93cyDigJQgaXQgY2FuIE5PVCBiZSBzdGVlcmVkIGF0IGFuIGFyYml0cmFyeSBvcmcuIE5PVEU6IHRoaXMgZG9lcyByZW1vdmUgdGhlXG4gICAqIFJMUyBiYWNrc3RvcCBmb3IgdGhlIHdpZGVuZWQgcmVhZDsgYSBzaW5nbGUtR1VDIGBhcHAub3JnX2lkYCBjYW4ndCBleHByZXNzXG4gICAqIHRoZSBcIm93biBPUiBwYXJlbnQgT1Igc3lzdGVtXCIgc2V0IHRoZSBwb2xpY3kgd291bGQgbmVlZCwgc28gcmVwbGFjaW5nIHRoZVxuICAgKiBieXBhc3Mgd291bGQgcmVxdWlyZSBhIHRlbmFuY3ktbGF5ZXIgY2hhbmdlIChlLmcuIGEgbXVsdGktb3JnIFJMUyBwb2xpY3kpLlxuICAgKiBEZWZlcnJlZCBkZWxpYmVyYXRlbHkg4oCUIGRvIG5vdCBzd2FwIHRoaXMgZm9yIGEgYmxhbmtldCBieXBhc3Mgd2l0aG91dFxuICAgKiByZS1jaGVja2luZyB0aGUgV0hFUkUgaXMgc3RpbGwgZnVsbHkgc2VydmVyLWJ1aWx0LlxuICAgKi9cbiAgcHJpdmF0ZSBydW5SZWFkPFQ+KHBhcmVudE9yZ0lkOiBzdHJpbmcgfCB1bmRlZmluZWQsIGZuOiAoKSA9PiBQcm9taXNlPFQ+KTogUHJvbWlzZTxUPiB7XG4gICAgcmV0dXJuIHBhcmVudE9yZ0lkID8gcnVuV2l0aFRlbmFudENvbnRleHQoeyBpc1N1cGVyQWRtaW46IHRydWUgfSwgZm4pIDogZm4oKTtcbiAgfVxuXG4gIGFzeW5jIGZpbmQoZmlsdGVyOiBQYXJ0aWFsPFRGaWx0ZXI+LCBvcmdJZD86IHN0cmluZywgcGFyZW50T3JnSWQ/OiBzdHJpbmcpOiBQcm9taXNlPFRFbnRpdHlbXT4ge1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSB0aGlzLmJ1aWxkQ29uZGl0aW9ucyhmaWx0ZXIsIG9yZ0lkLCBwYXJlbnRPcmdJZCk7XG5cbiAgICByZXR1cm4gdGhpcy5ydW5SZWFkKHBhcmVudE9yZ0lkLCAoKSA9PiB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB0eFxuICAgICAgLnNlbGVjdCgpXG4gICAgICAuZnJvbSh0aGlzLnNjaGVtYSlcbiAgICAgIC53aGVyZShhbmQoLi4uY29uZGl0aW9ucykpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSkpKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBGaW5kIGVudGl0aWVzIHdpdGggcGFnaW5hdGlvbiBhbmQgc29ydGluZ1xuICAgKlxuICAgKiBAcGFyYW0gZmlsdGVyIC0gRmlsdGVyIGNyaXRlcmlhXG4gICAqIEBwYXJhbSBvcmdJZCAtIFVzZXIncyBvcmdhbml6YXRpb24gSUQgKG9wdGlvbmFsIOKAlCBvbWl0IGZvciBhbm9ueW1vdXMvc3lzdGVtLXB1YmxpYy1vbmx5IGFjY2VzcylcbiAgICogQHBhcmFtIG9wdGlvbnMgLSBQYWdpbmF0aW9uIGFuZCBzb3J0aW5nIG9wdGlvbnNcbiAgICovXG4gIGFzeW5jIGZpbmRQYWdpbmF0ZWQoXG4gICAgZmlsdGVyOiBQYXJ0aWFsPFRGaWx0ZXI+LFxuICAgIG9yZ0lkPzogc3RyaW5nLFxuICAgIG9wdGlvbnM6IFF1ZXJ5T3B0aW9ucyA9IHt9LFxuICAgIHBhcmVudE9yZ0lkPzogc3RyaW5nLFxuICApOiBQcm9taXNlPFBhZ2luYXRlZFJlc3VsdDxURW50aXR5Pj4ge1xuICAgIGNvbnN0IHsgbGltaXQ6IHJhd0xpbWl0ID0gREVGQVVMVF9QQUdFX0xJTUlULCBvZmZzZXQgPSAwLCBzb3J0QnksIHNvcnRPcmRlciA9ICdhc2MnLCBpbmNsdWRlVG90YWwgPSBmYWxzZSwgY3Vyc29yLCBmaWVsZHMgfSA9IG9wdGlvbnM7XG4gICAgY29uc3QgbGltaXQgPSBNYXRoLm1pbihNYXRoLm1heCgxLCByYXdMaW1pdCksIE1BWF9QQUdFX0xJTUlUKTtcblxuICAgIC8vIEN1cnNvciBhbmQgb2Zmc2V0IGFyZSBtdXR1YWxseSBleGNsdXNpdmUg4oCUIGN1cnNvciB0YWtlcyBwcmVjZWRlbmNlXG4gICAgY29uc3QgdXNlQ3Vyc29yID0gISEoY3Vyc29yICYmIHNvcnRCeSk7XG5cbiAgICBjb25zdCBjb25kaXRpb25zID0gdGhpcy5idWlsZENvbmRpdGlvbnMoZmlsdGVyLCBvcmdJZCwgcGFyZW50T3JnSWQpO1xuXG4gICAgLy8gQ3Vyc29yLWJhc2VkIHBhZ2luYXRpb246IGFkZCBXSEVSRSBjbGF1c2UgZm9yIGtleXNldCBwYWdpbmF0aW9uXG4gICAgaWYgKHVzZUN1cnNvcikge1xuICAgICAgY29uc3Qgc29ydENvbHVtbiA9IHRoaXMuZ2V0U29ydENvbHVtbihzb3J0QnkpO1xuICAgICAgaWYgKHNvcnRDb2x1bW4pIHtcbiAgICAgICAgY29uc3Qgb3AgPSBzb3J0T3JkZXIgPT09ICdkZXNjJ1xuICAgICAgICAgID8gc3FsYCR7c29ydENvbHVtbn0gPCAke2N1cnNvcn1gXG4gICAgICAgICAgOiBzcWxgJHtzb3J0Q29sdW1ufSA+ICR7Y3Vyc29yfWA7XG4gICAgICAgIGNvbmRpdGlvbnMucHVzaChvcCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gV3JhcCB0aGUgd2hvbGUgcGFnaW5hdGVkIHJlYWQgKFNFTEVDVCArIG9wdGlvbmFsIENPVU5UKSBpbiBvbmVcbiAgICAvLyB0ZW5hbnQgdHguIEJvdGggcXVlcmllcyBhcmUgdmlzaWJpbGl0eS1zY29wZWQgYnkgdGhlIHNhbWUgUkxTIHBvbGljeSxcbiAgICAvLyBhbmQgcGlubmluZyB0aGVtIHRvIGEgc2luZ2xlIHR4IGtlZXBzIHRoZSBgYXBwLm9yZ19pZGAgR1VDIHN0YWJsZVxuICAgIC8vIGJldHdlZW4gdGhlbS4gV2hlbiB3aWRlbmluZyB0byBhIHBhcmVudCBvcmcsIHRoZSB3aG9sZSByZWFkIHJ1bnMgdW5kZXJcbiAgICAvLyBzeXNhZG1pbiBjb250ZXh0IChzZWUgcnVuUmVhZCkgc28gdGhlIGFjY2Vzcy1jb250cm9sIFdIRVJFIGlzIHRoZSBnYXRlLlxuICAgIHJldHVybiB0aGlzLnJ1blJlYWQocGFyZW50T3JnSWQsICgpID0+IHdpdGhUZW5hbnRUeChhc3luYyAodHgpID0+IHtcbiAgICAgIC8vIEJ1aWxkIFNFTEVDVCDigJQgc3BhcnNlIGZpZWxkc2V0IHdoZW4gZmllbGRzIGFyZSBzcGVjaWZpZWRcbiAgICAgIGNvbnN0IHNlbGVjdFNwZWMgPSBmaWVsZHMgPyB0aGlzLmJ1aWxkRmllbGRTZWxlY3QoZmllbGRzKSA6IHVuZGVmaW5lZDtcbiAgICAgIGxldCBxdWVyeSA9IHNlbGVjdFNwZWNcbiAgICAgICAgPyB0eC5zZWxlY3Qoc2VsZWN0U3BlYyBhcyBhbnkpLmZyb20odGhpcy5zY2hlbWEpLndoZXJlKGFuZCguLi5jb25kaXRpb25zKSlcbiAgICAgICAgOiB0eC5zZWxlY3QoKS5mcm9tKHRoaXMuc2NoZW1hKS53aGVyZShhbmQoLi4uY29uZGl0aW9ucykpO1xuXG4gICAgICBpZiAoc29ydEJ5KSB7XG4gICAgICAgIGNvbnN0IHNvcnRDb2x1bW4gPSB0aGlzLmdldFNvcnRDb2x1bW4oc29ydEJ5KTtcbiAgICAgICAgaWYgKHNvcnRDb2x1bW4pIHtcbiAgICAgICAgICBxdWVyeSA9IHF1ZXJ5Lm9yZGVyQnkoc29ydE9yZGVyID09PSAnZGVzYycgPyBkZXNjKHNvcnRDb2x1bW4pIDogYXNjKHNvcnRDb2x1bW4pKSBhcyBhbnk7XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgLy8gRmV0Y2ggbGltaXQrMSB0byBkZXRlY3QgaGFzTW9yZSB3aXRob3V0IENPVU5UKCopXG4gICAgICBjb25zdCBlZmZlY3RpdmVPZmZzZXQgPSB1c2VDdXJzb3IgPyAwIDogb2Zmc2V0O1xuICAgICAgY29uc3Qgcm93cyA9IGF3YWl0IHF1ZXJ5XG4gICAgICAgIC5saW1pdChsaW1pdCArIDEpXG4gICAgICAgIC5vZmZzZXQoZWZmZWN0aXZlT2Zmc2V0KS50aGVuKHIgPT4gZHJpenpsZVJvd3M8VEVudGl0eT4ocikpO1xuXG4gICAgICBjb25zdCBoYXNNb3JlID0gcm93cy5sZW5ndGggPiBsaW1pdDtcbiAgICAgIGNvbnN0IGRhdGEgPSBoYXNNb3JlID8gcm93cy5zbGljZSgwLCBsaW1pdCkgOiByb3dzO1xuXG4gICAgICBjb25zdCByZXN1bHQ6IFBhZ2luYXRlZFJlc3VsdDxURW50aXR5PiA9IHsgZGF0YSwgbGltaXQsIG9mZnNldDogZWZmZWN0aXZlT2Zmc2V0LCBoYXNNb3JlIH07XG5cbiAgICAgIC8vIFByb3ZpZGUgbmV4dCBjdXJzb3IgZnJvbSBsYXN0IGl0ZW0ncyBzb3J0IGNvbHVtbiB2YWx1ZVxuICAgICAgaWYgKGRhdGEubGVuZ3RoID4gMCAmJiBzb3J0QnkpIHtcbiAgICAgICAgY29uc3QgbGFzdEl0ZW0gPSBkYXRhW2RhdGEubGVuZ3RoIC0gMV0gYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG4gICAgICAgIGNvbnN0IGN1cnNvclZhbHVlID0gbGFzdEl0ZW1bc29ydEJ5XTtcbiAgICAgICAgaWYgKGN1cnNvclZhbHVlICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICByZXN1bHQubmV4dEN1cnNvciA9IGN1cnNvclZhbHVlIGluc3RhbmNlb2YgRGF0ZSA/IGN1cnNvclZhbHVlLnRvSVNPU3RyaW5nKCkgOiBTdHJpbmcoY3Vyc29yVmFsdWUpO1xuICAgICAgICB9XG4gICAgICB9XG5cbiAgICAgIC8vIE9ubHkgcnVuIHRoZSBDT1VOVCgqKSBxdWVyeSB3aGVuIHRoZSBjYWxsZXIgZXhwbGljaXRseSBuZWVkcyB0aGUgdG90YWwuXG4gICAgICAvLyBNdXN0IGluY2x1ZGUgcGFyZW50T3JnSWQgc28gYHRvdGFsYCBtYXRjaGVzIHRoZSB3aWRlbmVkIGRhdGEgc2V0LlxuICAgICAgaWYgKGluY2x1ZGVUb3RhbCkge1xuICAgICAgICBjb25zdCBiYXNlQ29uZGl0aW9ucyA9IHRoaXMuYnVpbGRDb25kaXRpb25zKGZpbHRlciwgb3JnSWQsIHBhcmVudE9yZ0lkKTtcbiAgICAgICAgY29uc3QgW2NvdW50UmVzdWx0XSA9IGF3YWl0IHR4XG4gICAgICAgICAgLnNlbGVjdCh7IGNvdW50OiBzcWw8bnVtYmVyPmBjb3VudCgqKTo6aW50YCB9KVxuICAgICAgICAgIC5mcm9tKHRoaXMuc2NoZW1hKVxuICAgICAgICAgIC53aGVyZShhbmQoLi4uYmFzZUNvbmRpdGlvbnMpKS50aGVuKHIgPT4gZHJpenpsZUNvdW50KHIpKTtcbiAgICAgICAgcmVzdWx0LnRvdGFsID0gY291bnRSZXN1bHQ/LmNvdW50IHx8IDA7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiByZXN1bHQ7XG4gICAgfSkpO1xuICB9XG5cbiAgLyoqXG4gICAqIEJ1aWxkIGEgY29sdW1uIHNlbGVjdGlvbiBtYXAgZm9yIHNwYXJzZSBmaWVsZHNldHMuXG4gICAqIEZhbGxzIGJhY2sgdG8gZnVsbCBzZWxlY3QgaWYgbm8gbWF0Y2hpbmcgY29sdW1ucyBmb3VuZC5cbiAgICovXG4gIHByaXZhdGUgYnVpbGRGaWVsZFNlbGVjdChmaWVsZHM6IHN0cmluZ1tdKTogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gfCB1bmRlZmluZWQge1xuICAgIGlmIChmaWVsZHMubGVuZ3RoID09PSAwKSByZXR1cm4gdW5kZWZpbmVkO1xuXG4gICAgY29uc3QgY29sdW1uczogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gPSB7fTtcbiAgICAvLyBBbHdheXMgaW5jbHVkZSBpZCBmb3IgZW50aXR5IGlkZW50aXR5XG4gICAgY29sdW1ucy5pZCA9ICh0aGlzLnNjaGVtYSBhcyBhbnkpLmlkO1xuXG4gICAgZm9yIChjb25zdCBmaWVsZCBvZiBmaWVsZHMpIHtcbiAgICAgIGlmIChmaWVsZCA9PT0gJ2lkJykgY29udGludWU7IC8vIEFscmVhZHkgaW5jbHVkZWRcbiAgICAgIGNvbnN0IGNvbCA9ICh0aGlzLnNjaGVtYSBhcyBhbnkpW2ZpZWxkXTtcbiAgICAgIGlmIChjb2wpIGNvbHVtbnNbZmllbGRdID0gY29sO1xuICAgIH1cblxuICAgIC8vIEF0IG1pbmltdW0gd2UnbGwgaGF2ZSB7IGlkIH0sIHdoaWNoIGlzIHZhbGlkXG4gICAgcmV0dXJuIGNvbHVtbnM7XG4gIH1cblxuICAvKipcbiAgICogQ291bnQgZW50aXRpZXMgbWF0Y2hpbmcgZmlsdGVyIGNyaXRlcmlhXG4gICAqXG4gICAqIEBwYXJhbSBmaWx0ZXIgLSBGaWx0ZXIgY3JpdGVyaWFcbiAgICogQHBhcmFtIG9yZ0lkIC0gVXNlcidzIG9yZ2FuaXphdGlvbiBJRCAob3B0aW9uYWwg4oCUIG9taXQgZm9yIGFub255bW91cy9zeXN0ZW0tcHVibGljLW9ubHkgYWNjZXNzKVxuICAgKiBAcGFyYW0gcGFyZW50T3JnSWQgLSBPcmcg4oaSIHRlYW0gaGllcmFyY2h5OiB3aWRlbiB0aGUgY291bnQgdG8gdGhlIHBhcmVudCBvcmcnc1xuICAgKiAgIHB1YmxpYyByb3dzLiBNVVNUIG1pcnJvciBgZmluZGAvYGZpbmRQYWdpbmF0ZWRgJ3Mgd2lkZW5pbmcgKHNhbWVcbiAgICogICBgYnVpbGRDb25kaXRpb25zYCBhcmdzICsgc3lzYWRtaW4tc2NvcGVkIHJlYWQgdmlhIGBydW5SZWFkYCkgc28gYSBwYWdlZFxuICAgKiAgIGxpc3QncyBgdG90YWxgIG1hdGNoZXMgdGhlIHJvd3MgYSB3aWRlbmVkIGBmaW5kKClgIHJldHVybnMg4oCUIG90aGVyd2lzZSB0aGVcbiAgICogICBjb3VudCBvbWl0cyB0aGUgcGFyZW50J3Mgcm93cyBhbmQgcmVwb3J0cyBhIG5hcnJvd2VyIHRvdGFsIHRoYW4gdGhlIGRhdGEgc2V0LlxuICAgKi9cbiAgYXN5bmMgY291bnQoZmlsdGVyOiBQYXJ0aWFsPFRGaWx0ZXI+LCBvcmdJZD86IHN0cmluZywgcGFyZW50T3JnSWQ/OiBzdHJpbmcpOiBQcm9taXNlPG51bWJlcj4ge1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSB0aGlzLmJ1aWxkQ29uZGl0aW9ucyhmaWx0ZXIsIG9yZ0lkLCBwYXJlbnRPcmdJZCk7XG5cbiAgICBjb25zdCBbcmVzdWx0XSA9IGF3YWl0IHRoaXMucnVuUmVhZChwYXJlbnRPcmdJZCwgKCkgPT4gd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4gdHhcbiAgICAgIC5zZWxlY3QoeyBjb3VudDogc3FsPG51bWJlcj5gY291bnQoKik6OmludGAgfSlcbiAgICAgIC5mcm9tKHRoaXMuc2NoZW1hKVxuICAgICAgLndoZXJlKGFuZCguLi5jb25kaXRpb25zKSkudGhlbihyID0+IGRyaXp6bGVDb3VudChyKSkpKTtcblxuICAgIHJldHVybiByZXN1bHQ/LmNvdW50IHx8IDA7XG4gIH1cblxuICAvKipcbiAgICogRmluZCBhIHNpbmdsZSBlbnRpdHkgYnkgSURcbiAgICpcbiAgICogQHBhcmFtIGlkIC0gRW50aXR5IElEXG4gICAqIEBwYXJhbSBvcmdJZCAtIFVzZXIncyBvcmdhbml6YXRpb24gSUQgKG9wdGlvbmFsIOKAlCBvbWl0IGZvciBhbm9ueW1vdXMvc3lzdGVtLXB1YmxpYy1vbmx5IGFjY2VzcylcbiAgICogQHBhcmFtIHBhcmVudE9yZ0lkIC0gT3JnIOKGkiB0ZWFtIGhpZXJhcmNoeTogd2lkZW4gdmlzaWJpbGl0eSB0byB0aGUgcGFyZW50XG4gICAqICAgb3JnJ3MgcHVibGljIHJvd3MgKHNvIGEgdGVhbSBjYW4gZmV0Y2ggYSBwYXJlbnQncyBwdWJsaWMgZW50aXR5IGJ5IGlkKS5cbiAgICogICBTYW1lIG9wdC1pbiArIHN5c2FkbWluLXNjb3BlZCByZWFkIGFzIGBmaW5kYC9gZmluZFBhZ2luYXRlZGA7IHRoZVxuICAgKiAgIGFjY2Vzcy1jb250cm9sIFdIRVJFIGNsYXVzZSBpcyB0aGUgYXV0aG9yaXRhdGl2ZSB0ZW5hbmN5IGdhdGUuXG4gICAqL1xuICBhc3luYyBmaW5kQnlJZChpZDogc3RyaW5nLCBvcmdJZD86IHN0cmluZywgcGFyZW50T3JnSWQ/OiBzdHJpbmcpOiBQcm9taXNlPFRFbnRpdHkgfCBudWxsPiB7XG4gICAgY29uc3QgY29uZGl0aW9ucyA9IHRoaXMuaWRDb25kaXRpb25zKGlkLCBvcmdJZCwgcGFyZW50T3JnSWQpO1xuXG4gICAgY29uc3QgcmVzdWx0cyA9IGF3YWl0IHRoaXMucnVuUmVhZChwYXJlbnRPcmdJZCwgKCkgPT4gd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4gdHhcbiAgICAgIC5zZWxlY3QoKVxuICAgICAgLmZyb20odGhpcy5zY2hlbWEpXG4gICAgICAud2hlcmUoYW5kKC4uLmNvbmRpdGlvbnMpKVxuICAgICAgLmxpbWl0KDEpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSkpKTtcblxuICAgIHJldHVybiByZXN1bHRzWzBdIHx8IG51bGw7XG4gIH1cblxuICAvLyBNdXRhdGlvbiBvcGVyYXRpb25zXG5cbiAgLyoqXG4gICAqIERlZmVuc2UtaW4tZGVwdGggdGVuYW50IHN0YW1wLiBSTFMgaXMgaW4gb3duZXItYnlwYXNzIG1vZGUsIHNvIHRoZSBhcHAgbGF5ZXJcbiAgICogaXMgdGhlIG9ubHkgdGVuYW50IGdhdGUgb24gd3JpdGVzLiBBIE5PTi1zeXNhZG1pbiBjYWxsZXIgbWF5IG9ubHkgd3JpdGUgaW50b1xuICAgKiBpdHMgT1dOIG9yZywgc28gb3ZlcndyaXRlIGFueSBjYWxsZXItc3VwcGxpZWQgYG9yZ0lkYCB3aXRoIHRoZSB0cnVzdGVkXG4gICAqIHRlbmFudC1jb250ZXh0IG9yZyDigJQgYSByb3V0ZSB0aGF0IGZvcndhcmRzIGEgZm9yZ2VkIGBkYXRhLm9yZ0lkYCB0aGVuIGNhbid0XG4gICAqIGNyb3NzIHRlbmFudHMuIFN5c2FkbWluIChhbmQgb3V0LW9mLWNvbnRleHQgd29ya2VyL3N5c3RlbSBwYXRocykga2VlcCB0aGVcbiAgICogc3VwcGxpZWQgb3JnLCBtYXRjaGluZyB0aGUgUkxTIHBvbGljeSBgY3VycmVudF9pc19zeXNhZG1pbigpIE9SIG9yZ19pZCA9IGN1cnJlbnRfb3JnX2lkKClgLlxuICAgKi9cbiAgcHJvdGVjdGVkIGVuZm9yY2VPcmdJZChkYXRhOiBUSW5zZXJ0KTogVEluc2VydCB7XG4gICAgY29uc3QgY3R4ID0gZ2V0VGVuYW50Q29udGV4dCgpO1xuICAgIGNvbnN0IGQgPSBkYXRhIGFzIFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuICAgIGlmIChjdHggJiYgIWN0eC5pc1N1cGVyQWRtaW4gJiYgY3R4Lm9yZ0lkICYmICdvcmdJZCcgaW4gZCAmJiBkLm9yZ0lkICE9PSBjdHgub3JnSWQpIHtcbiAgICAgIHRoaXMuX2xvZ2dlci53YXJuKCdDcnVkU2VydmljZTogb3ZlcnJpZGluZyBjYWxsZXIgb3JnSWQgd2l0aCB0ZW5hbnQtY29udGV4dCBvcmcnLCB7XG4gICAgICAgIHN1cHBsaWVkOiBkLm9yZ0lkLCBlbmZvcmNlZDogY3R4Lm9yZ0lkLFxuICAgICAgfSk7XG4gICAgICByZXR1cm4geyAuLi5kLCBvcmdJZDogY3R4Lm9yZ0lkIH0gYXMgVEluc2VydDtcbiAgICB9XG4gICAgcmV0dXJuIGRhdGE7XG4gIH1cblxuICAvKipcbiAgICogQ3JlYXRlIGEgbmV3IGVudGl0eVxuICAgKi9cbiAgYXN5bmMgY3JlYXRlKGRhdGE6IFRJbnNlcnQsIHVzZXJJZDogc3RyaW5nKTogUHJvbWlzZTxURW50aXR5PiB7XG4gICAgY29uc3Qgc2FmZURhdGEgPSB0aGlzLmVuZm9yY2VPcmdJZChkYXRhKTtcbiAgICBjb25zdCBbY3JlYXRlZF0gPSBhd2FpdCB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB0eFxuICAgICAgLmluc2VydCh0aGlzLnNjaGVtYSlcbiAgICAgIC52YWx1ZXMoe1xuICAgICAgICAuLi5zYWZlRGF0YSxcbiAgICAgICAgY3JlYXRlZEJ5OiB1c2VySWQgfHwgJ3N5c3RlbScsXG4gICAgICAgIHVwZGF0ZWRCeTogdXNlcklkIHx8ICdzeXN0ZW0nLFxuICAgICAgfSBhcyBhbnkpXG4gICAgICAub25Db25mbGljdERvVXBkYXRlKHtcbiAgICAgICAgdGFyZ2V0OiB0aGlzLmNvbmZsaWN0VGFyZ2V0IGFzIGFueSxcbiAgICAgICAgc2V0OiB7XG4gICAgICAgICAgLi4uc2FmZURhdGEsXG4gICAgICAgICAgdXBkYXRlZEF0OiBuZXcgRGF0ZSgpLFxuICAgICAgICAgIHVwZGF0ZWRCeTogdXNlcklkIHx8ICdzeXN0ZW0nLFxuICAgICAgICB9IGFzIGFueSxcbiAgICAgIH0pXG4gICAgICAucmV0dXJuaW5nKCkudGhlbihyID0+IGRyaXp6bGVSb3dzPFRFbnRpdHk+KHIpKSk7XG5cbiAgICAvLyBBd2FpdGVkIGludGVudGlvbmFsbHk6IGNhY2hlIGludmFsaWRhdGlvbiBoYXBwZW5zIGluIHRoZSBob29rLCBhbmQgYVxuICAgIC8vIGZpcmUtYW5kLWZvcmdldCBwYXR0ZXJuIGxldHMgYSBzdWJzZXF1ZW50IHJlYWQgaW5zaWRlIHRoZSBzYW1lIHJlcXVlc3RcbiAgICAvLyByZXR1cm4gdGhlIHN0YWxlIHByZS13cml0ZSBlbnRyeS4gVGhlIGhvb2sgaXMgZXhwZWN0ZWQgdG8gYmUgZmFzdFxuICAgIC8vIChzaW5nbGUgUmVkaXMgb3ApOyBzbG93IGhvb2tzIHNob3VsZCBydW4gdGhlaXIgb3duIGJhY2tncm91bmQgd29yay5cbiAgICB0cnkge1xuICAgICAgYXdhaXQgdGhpcy5vbkFmdGVyQ3JlYXRlKGNyZWF0ZWQsIHVzZXJJZCk7XG4gICAgfSBjYXRjaCAoZXJyKSB7XG4gICAgICB0aGlzLl9sb2dnZXIud2FybignTGlmZWN5Y2xlIGhvb2sgZmFpbGVkJywgeyBlcnJvcjogU3RyaW5nKGVycikgfSk7XG4gICAgfVxuXG4gICAgcmV0dXJuIGNyZWF0ZWQ7XG4gIH1cblxuICAvKipcbiAgICogVXBkYXRlIGFuIGV4aXN0aW5nIGVudGl0eVxuICAgKi9cbiAgYXN5bmMgdXBkYXRlKFxuICAgIGlkOiBzdHJpbmcsXG4gICAgZGF0YTogUGFydGlhbDxUVXBkYXRlPixcbiAgICBvcmdJZDogc3RyaW5nLFxuICAgIHVzZXJJZDogc3RyaW5nLFxuICApOiBQcm9taXNlPFRFbnRpdHkgfCBudWxsPiB7XG4gICAgY29uc3QgY29uZGl0aW9ucyA9IHRoaXMud3JpdGVDb25kaXRpb25zKGlkLCBvcmdJZCk7XG5cbiAgICBjb25zdCBbdXBkYXRlZF0gPSBhd2FpdCB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB0eFxuICAgICAgLnVwZGF0ZSh0aGlzLnNjaGVtYSlcbiAgICAgIC5zZXQoe1xuICAgICAgICAuLi5kYXRhLFxuICAgICAgICB1cGRhdGVkQXQ6IG5ldyBEYXRlKCksXG4gICAgICAgIHVwZGF0ZWRCeTogdXNlcklkIHx8ICdzeXN0ZW0nLFxuICAgICAgfSBhcyBhbnkpXG4gICAgICAud2hlcmUoYW5kKC4uLmNvbmRpdGlvbnMpKVxuICAgICAgLnJldHVybmluZygpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSkpO1xuXG4gICAgaWYgKHVwZGF0ZWQpIHtcbiAgICAgIHRyeSB7XG4gICAgICAgIGF3YWl0IHRoaXMub25BZnRlclVwZGF0ZShpZCwgdXBkYXRlZCwgdXNlcklkKTtcbiAgICAgIH0gY2F0Y2ggKGVycikge1xuICAgICAgICB0aGlzLl9sb2dnZXIud2FybignTGlmZWN5Y2xlIGhvb2sgZmFpbGVkJywgeyBlcnJvcjogU3RyaW5nKGVycikgfSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIHVwZGF0ZWQgfHwgbnVsbDtcbiAgfVxuXG4gIC8qKlxuICAgKiBEZWxldGUgYW4gZW50aXR5IChzb2Z0IGRlbGV0ZSBieSBzZXR0aW5nIGlzQWN0aXZlID0gZmFsc2UpXG4gICAqL1xuICBhc3luYyBkZWxldGUoaWQ6IHN0cmluZywgb3JnSWQ6IHN0cmluZywgdXNlcklkOiBzdHJpbmcpOiBQcm9taXNlPFRFbnRpdHkgfCBudWxsPiB7XG4gICAgY29uc3QgY29uZGl0aW9ucyA9IHRoaXMud3JpdGVDb25kaXRpb25zKGlkLCBvcmdJZCk7XG5cbiAgICBjb25zdCBbZGVsZXRlZF0gPSBhd2FpdCB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB0eFxuICAgICAgLnVwZGF0ZSh0aGlzLnNjaGVtYSlcbiAgICAgIC5zZXQoe1xuICAgICAgICBpc0FjdGl2ZTogZmFsc2UsXG4gICAgICAgIHVwZGF0ZWRBdDogbmV3IERhdGUoKSxcbiAgICAgICAgdXBkYXRlZEJ5OiB1c2VySWQgfHwgJ3N5c3RlbScsXG4gICAgICAgIGRlbGV0ZWRBdDogbmV3IERhdGUoKSxcbiAgICAgICAgZGVsZXRlZEJ5OiB1c2VySWQgfHwgJ3N5c3RlbScsXG4gICAgICB9IGFzIGFueSlcbiAgICAgIC53aGVyZShhbmQoLi4uY29uZGl0aW9ucykpXG4gICAgICAucmV0dXJuaW5nKCkudGhlbihyID0+IGRyaXp6bGVSb3dzPFRFbnRpdHk+KHIpKSk7XG5cbiAgICBpZiAoZGVsZXRlZCkge1xuICAgICAgdHJ5IHtcbiAgICAgICAgYXdhaXQgdGhpcy5vbkFmdGVyRGVsZXRlKGlkLCBkZWxldGVkLCB1c2VySWQpO1xuICAgICAgfSBjYXRjaCAoZXJyKSB7XG4gICAgICAgIHRoaXMuX2xvZ2dlci53YXJuKCdMaWZlY3ljbGUgaG9vayBmYWlsZWQnLCB7IGVycm9yOiBTdHJpbmcoZXJyKSB9KTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gZGVsZXRlZCB8fCBudWxsO1xuICB9XG5cbiAgLyoqXG4gICAqIFNldCBhbiBlbnRpdHkgYXMgdGhlIGRlZmF1bHQgZm9yIGEgcHJvamVjdC9vcmdhbml6YXRpb24gc2NvcGUuXG4gICAqIE1hcmtzIGFsbCBvdGhlciBlbnRpdGllcyBhcyBub24tZGVmYXVsdCwgdGhlbiBzZXRzIHRoZSBzcGVjaWZpZWQgZW50aXR5LlxuICAgKiBVc2VzIGEgdHJhbnNhY3Rpb24gdG8gZW5zdXJlIGF0b21pY2l0eS5cbiAgICovXG4gIGFzeW5jIHNldERlZmF1bHQoXG4gICAgcHJvamVjdDogc3RyaW5nLFxuICAgIG9yZzogc3RyaW5nLFxuICAgIGlkOiBzdHJpbmcsXG4gICAgdXNlcklkOiBzdHJpbmcsXG4gICk6IFByb21pc2U8VEVudGl0eT4ge1xuICAgIC8vIEEgbm9uLXN5c2FkbWluIG1heSBvbmx5IGZsaXAgZGVmYXVsdHMgd2l0aGluIGl0cyBPV04gb3JnIOKAlCBwaW4gdGhlIHNjb3BlIHRvXG4gICAgLy8gdGhlIHRydXN0ZWQgdGVuYW50IGNvbnRleHQgc28gYSBmb3J3YXJkZWQgYG9yZ2AgYXJnIGNhbid0IHRvdWNoIGFub3RoZXJcbiAgICAvLyB0ZW5hbnQncyBkZWZhdWx0cyAoUkxTIGlzIGluIG93bmVyLWJ5cGFzcyBtb2RlOyB0aGlzIGlzIHRoZSBnYXRlKS5cbiAgICBjb25zdCBjdHggPSBnZXRUZW5hbnRDb250ZXh0KCk7XG4gICAgaWYgKGN0eCAmJiAhY3R4LmlzU3VwZXJBZG1pbiAmJiBjdHgub3JnSWQpIG9yZyA9IGN0eC5vcmdJZDtcbiAgICByZXR1cm4gd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4ge1xuICAgICAgY29uc3Qgb3JnQ29sdW1uID0gdGhpcy5nZXRPcmdDb2x1bW4oKTtcbiAgICAgIGNvbnN0IHByb2plY3RDb2x1bW4gPSB0aGlzLmdldFByb2plY3RDb2x1bW4oKTtcblxuICAgICAgLy8gQnVpbGQgc2NvcGluZyBjb25kaXRpb25zIGZvciBjbGVhcmluZyBkZWZhdWx0c1xuICAgICAgY29uc3Qgc2NvcGVDb25kaXRpb25zID0gW1xuICAgICAgICBlcShvcmdDb2x1bW4sIG9yZyksXG4gICAgICAgIGVxKCh0aGlzLnNjaGVtYSBhcyBhbnkpLmlzRGVmYXVsdCwgdHJ1ZSksXG4gICAgICBdO1xuICAgICAgaWYgKHByb2plY3RDb2x1bW4pIHtcbiAgICAgICAgc2NvcGVDb25kaXRpb25zLnB1c2goZXEocHJvamVjdENvbHVtbiwgcHJvamVjdCkpO1xuICAgICAgfVxuXG4gICAgICAvLyBMb2NrIGV4aXN0aW5nIGRlZmF1bHRzIHdpdGggRk9SIFVQREFURSB0byBwcmV2ZW50IGNvbmN1cnJlbnQgc2V0RGVmYXVsdCByYWNlc1xuICAgICAgYXdhaXQgdHguZXhlY3V0ZShcbiAgICAgICAgc3FsYFNFTEVDVCBpZCBGUk9NICR7dGhpcy5zY2hlbWF9XG4gICAgICAgICAgICBXSEVSRSAke29yZ0NvbHVtbn0gPSAke29yZ31cbiAgICAgICAgICAgICAgQU5EICR7KHRoaXMuc2NoZW1hIGFzIGFueSkuaXNEZWZhdWx0fSA9IHRydWVcbiAgICAgICAgICAgICR7cHJvamVjdENvbHVtbiA/IHNxbGBBTkQgJHtwcm9qZWN0Q29sdW1ufSA9ICR7cHJvamVjdH1gIDogc3FsYGB9XG4gICAgICAgICAgICBGT1IgVVBEQVRFYCxcbiAgICAgICk7XG5cbiAgICAgIC8vIE1hcmsgYWxsIGVudGl0aWVzIGluIHNjb3BlIGFzIG5vbi1kZWZhdWx0XG4gICAgICBhd2FpdCB0eFxuICAgICAgICAudXBkYXRlKHRoaXMuc2NoZW1hKVxuICAgICAgICAuc2V0KHtcbiAgICAgICAgICBpc0RlZmF1bHQ6IGZhbHNlLFxuICAgICAgICAgIHVwZGF0ZWRBdDogbmV3IERhdGUoKSxcbiAgICAgICAgICB1cGRhdGVkQnk6IHVzZXJJZCB8fCAnc3lzdGVtJyxcbiAgICAgICAgfSBhcyBhbnkpXG4gICAgICAgIC53aGVyZShhbmQoLi4uc2NvcGVDb25kaXRpb25zKSk7XG5cbiAgICAgIC8vIFNldCB0aGUgc3BlY2lmaWVkIGVudGl0eSBhcyBkZWZhdWx0XG4gICAgICBjb25zdCBbdXBkYXRlZF0gPSBhd2FpdCB0eFxuICAgICAgICAudXBkYXRlKHRoaXMuc2NoZW1hKVxuICAgICAgICAuc2V0KHtcbiAgICAgICAgICBpc0RlZmF1bHQ6IHRydWUsXG4gICAgICAgICAgdXBkYXRlZEF0OiBuZXcgRGF0ZSgpLFxuICAgICAgICAgIHVwZGF0ZWRCeTogdXNlcklkIHx8ICdzeXN0ZW0nLFxuICAgICAgICB9IGFzIGFueSlcbiAgICAgICAgLndoZXJlKFxuICAgICAgICAgIGFuZChcbiAgICAgICAgICAgIGVxKCh0aGlzLnNjaGVtYSBhcyBhbnkpLmlkLCBpZCksXG4gICAgICAgICAgICBlcShvcmdDb2x1bW4sIG9yZyksXG4gICAgICAgICAgKSxcbiAgICAgICAgKVxuICAgICAgICAucmV0dXJuaW5nKCkudGhlbihyID0+IGRyaXp6bGVSb3dzPFRFbnRpdHk+KHIpKTtcblxuICAgICAgaWYgKCF1cGRhdGVkKSB7XG4gICAgICAgIHRocm93IG5ldyBOb3RGb3VuZEVycm9yKGBFbnRpdHkgd2l0aCBpZCAke2lkfSBub3QgZm91bmRgKTtcbiAgICAgIH1cblxuICAgICAgcmV0dXJuIHVwZGF0ZWQ7XG4gICAgfSk7XG4gIH1cblxuICAvKipcbiAgICogVXBkYXRlIG11bHRpcGxlIGVudGl0aWVzIG1hdGNoaW5nIGZpbHRlclxuICAgKi9cbiAgYXN5bmMgdXBkYXRlTWFueShcbiAgICBmaWx0ZXI6IFBhcnRpYWw8VEZpbHRlcj4sXG4gICAgZGF0YTogUGFydGlhbDxUVXBkYXRlPixcbiAgICBvcmdJZDogc3RyaW5nLFxuICAgIHVzZXJJZDogc3RyaW5nLFxuICApOiBQcm9taXNlPFRFbnRpdHlbXT4ge1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSB0aGlzLmJ1aWxkQ29uZGl0aW9ucyhmaWx0ZXIsIG9yZ0lkKTtcblxuICAgIHJldHVybiB3aXRoVGVuYW50VHgoYXN5bmMgKHR4KSA9PiB0eFxuICAgICAgLnVwZGF0ZSh0aGlzLnNjaGVtYSlcbiAgICAgIC5zZXQoe1xuICAgICAgICAuLi5kYXRhLFxuICAgICAgICB1cGRhdGVkQXQ6IG5ldyBEYXRlKCksXG4gICAgICAgIHVwZGF0ZWRCeTogdXNlcklkIHx8ICdzeXN0ZW0nLFxuICAgICAgfSBhcyBhbnkpXG4gICAgICAud2hlcmUoYW5kKC4uLmNvbmRpdGlvbnMpKVxuICAgICAgLnJldHVybmluZygpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSkpO1xuICB9XG5cbiAgLyoqXG4gICAqIENyZWF0ZSBtdWx0aXBsZSBlbnRpdGllcyBpbiBhIHNpbmdsZSBiYXRjaCBpbnNlcnQuXG4gICAqIFVzZXMgdXBzZXJ0IChvbkNvbmZsaWN0RG9VcGRhdGUpIOKAlCBhbGwgcm93cyBhcmUgaW5zZXJ0ZWQgaW4gb25lIHF1ZXJ5IHBlciBjaHVuay5cbiAgICogQ2h1bmtzIG9mIDEwMCB0byBzdGF5IHdpdGhpbiBQb3N0Z3JlU1FMIHBhcmFtZXRlciBsaW1pdHMuXG4gICAqL1xuICAvKipcbiAgICogQnVpbGQgdGhlIGBvbkNvbmZsaWN0RG9VcGRhdGVgIFNFVCBmb3IgYSBidWxrIHVwc2VydC4gVW5saWtlIGEgc2luZ2xlLXJvd1xuICAgKiBjcmVhdGUgKHdoaWNoIGNhbiBzcHJlYWQgdGhlIG9uZSByb3cncyBkYXRhKSwgYSBiYXRjaGVkIGluc2VydCBoYXMgbWFueSByb3dzLFxuICAgKiBzbyBlYWNoIHVwZGF0YWJsZSBjb2x1bW4gaXMgd3JpdHRlbiBmcm9tIGBleGNsdWRlZC4qYCAodGhlIHdvdWxkLWJlLWluc2VydGVkXG4gICAqIHZhbHVlKSDigJQgb3RoZXJ3aXNlIGFuIGV4aXN0aW5nIHJvdydzIGZpZWxkcyBhcmUgc2lsZW50bHkgZGlzY2FyZGVkIGFuZCBvbmx5XG4gICAqIHRpbWVzdGFtcHMgYnVtcC4gU2tpcHMgaWRlbnRpdHkvaW1tdXRhYmxlIChgaWRgLCBgY3JlYXRlZEF0YCwgYGNyZWF0ZWRCeWApXG4gICAqIGFuZCB0aGUgY29uZmxpY3QtdGFyZ2V0IGNvbHVtbnM7IGB1cGRhdGVkQXRgL2B1cGRhdGVkQnlgIGdldCB0aGUgZnJlc2ggdmFsdWVzLlxuICAgKi9cbiAgcHJpdmF0ZSBidWlsZEJ1bGtVcHNlcnRTZXQobm93OiBEYXRlLCB1c2VyOiBzdHJpbmcpOiBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPiB7XG4gICAgY29uc3QgY29uZmxpY3ROYW1lcyA9IG5ldyBTZXQodGhpcy5jb25mbGljdFRhcmdldC5tYXAoKGMpID0+IChjIGFzIHVua25vd24gYXMgeyBuYW1lOiBzdHJpbmcgfSkubmFtZSkpO1xuICAgIGNvbnN0IHNldDogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gPSB7fTtcbiAgICBmb3IgKGNvbnN0IFtrZXksIGNvbF0gb2YgT2JqZWN0LmVudHJpZXMoZ2V0VGFibGVDb2x1bW5zKHRoaXMuc2NoZW1hKSkpIHtcbiAgICAgIGNvbnN0IG5hbWUgPSAoY29sIGFzIHVua25vd24gYXMgeyBuYW1lOiBzdHJpbmcgfSkubmFtZTtcbiAgICAgIGlmIChrZXkgPT09ICdpZCcgfHwga2V5ID09PSAnY3JlYXRlZEF0JyB8fCBrZXkgPT09ICdjcmVhdGVkQnknIHx8IGNvbmZsaWN0TmFtZXMuaGFzKG5hbWUpKSBjb250aW51ZTtcbiAgICAgIGlmIChrZXkgPT09ICd1cGRhdGVkQXQnKSB7IHNldFtrZXldID0gbm93OyBjb250aW51ZTsgfVxuICAgICAgaWYgKGtleSA9PT0gJ3VwZGF0ZWRCeScpIHsgc2V0W2tleV0gPSB1c2VyOyBjb250aW51ZTsgfVxuICAgICAgc2V0W2tleV0gPSBzcWxgZXhjbHVkZWQuJHtzcWwuaWRlbnRpZmllcihuYW1lKX1gO1xuICAgIH1cbiAgICByZXR1cm4gc2V0O1xuICB9XG5cbiAgYXN5bmMgYnVsa0NyZWF0ZShpdGVtczogVEluc2VydFtdLCB1c2VySWQ6IHN0cmluZyk6IFByb21pc2U8VEVudGl0eVtdPiB7XG4gICAgaWYgKGl0ZW1zLmxlbmd0aCA9PT0gMCkgcmV0dXJuIFtdO1xuXG4gICAgY29uc3QgQ0hVTktfU0laRSA9IDEwMDtcbiAgICBjb25zdCBub3cgPSBuZXcgRGF0ZSgpO1xuICAgIGNvbnN0IHVzZXIgPSB1c2VySWQgfHwgJ3N5c3RlbSc7XG4gICAgY29uc3QgY29uZmxpY3RTZXQgPSB0aGlzLmJ1aWxkQnVsa1Vwc2VydFNldChub3csIHVzZXIpO1xuXG4gICAgY29uc3QgcmVzdWx0cyA9IGF3YWl0IHdpdGhUZW5hbnRUeChhc3luYyAodHgpID0+IHtcbiAgICAgIGNvbnN0IGFsbENyZWF0ZWQ6IFRFbnRpdHlbXSA9IFtdO1xuXG4gICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGl0ZW1zLmxlbmd0aDsgaSArPSBDSFVOS19TSVpFKSB7XG4gICAgICAgIGNvbnN0IGNodW5rID0gaXRlbXMuc2xpY2UoaSwgaSArIENIVU5LX1NJWkUpO1xuICAgICAgICBjb25zdCB2YWx1ZXMgPSBjaHVuay5tYXAoZGF0YSA9PiAoe1xuICAgICAgICAgIC4uLnRoaXMuZW5mb3JjZU9yZ0lkKGRhdGEpLFxuICAgICAgICAgIGNyZWF0ZWRCeTogdXNlcixcbiAgICAgICAgICB1cGRhdGVkQnk6IHVzZXIsXG4gICAgICAgIH0gYXMgYW55KSk7XG5cbiAgICAgICAgY29uc3QgY3JlYXRlZCA9IGF3YWl0IHR4XG4gICAgICAgICAgLmluc2VydCh0aGlzLnNjaGVtYSlcbiAgICAgICAgICAudmFsdWVzKHZhbHVlcylcbiAgICAgICAgICAub25Db25mbGljdERvVXBkYXRlKHtcbiAgICAgICAgICAgIHRhcmdldDogdGhpcy5jb25mbGljdFRhcmdldCBhcyBhbnksXG4gICAgICAgICAgICBzZXQ6IGNvbmZsaWN0U2V0IGFzIGFueSxcbiAgICAgICAgICB9KVxuICAgICAgICAgIC5yZXR1cm5pbmcoKS50aGVuKHIgPT4gZHJpenpsZVJvd3M8VEVudGl0eT4ocikpO1xuXG4gICAgICAgIGFsbENyZWF0ZWQucHVzaCguLi5jcmVhdGVkKTtcbiAgICAgIH1cblxuICAgICAgcmV0dXJuIGFsbENyZWF0ZWQ7XG4gICAgfSk7XG5cbiAgICAvLyBSdW4gaG9va3MgaW4gcGFyYWxsZWwgYnV0IGF3YWl0IGFsbCBiZWZvcmUgcmV0dXJuaW5nIHNvIGEgc3Vic2VxdWVudFxuICAgIC8vIHJlYWQgaW4gdGhlIHNhbWUgcmVxdWVzdCBzZWVzIGEgY29oZXJlbnQgcG9zdC13cml0ZSB2aWV3LlxuICAgIGF3YWl0IFByb21pc2UuYWxsKFxuICAgICAgcmVzdWx0cy5tYXAoZW50aXR5ID0+XG4gICAgICAgIHRoaXMub25BZnRlckNyZWF0ZShlbnRpdHksIHVzZXJJZCkuY2F0Y2goZXJyID0+XG4gICAgICAgICAgdGhpcy5fbG9nZ2VyLndhcm4oJ0xpZmVjeWNsZSBob29rIGZhaWxlZCcsIHsgZXJyb3I6IFN0cmluZyhlcnIpIH0pLFxuICAgICAgICApLFxuICAgICAgKSxcbiAgICApO1xuXG4gICAgcmV0dXJuIHJlc3VsdHM7XG4gIH1cblxuICAvKipcbiAgICogU29mdC1kZWxldGUgbXVsdGlwbGUgZW50aXRpZXMgYnkgSURzIGluIGEgc2luZ2xlIGJhdGNoIG9wZXJhdGlvbi5cbiAgICovXG4gIGFzeW5jIGJ1bGtEZWxldGUoXG4gICAgaWRzOiBzdHJpbmdbXSxcbiAgICBvcmdJZDogc3RyaW5nLFxuICAgIHVzZXJJZDogc3RyaW5nLFxuICAgIC8qKiBXaGVuIHRydWUsIG9ubHkgUFJJVkFURSByZWNvcmRzIGFyZSBkZWxldGVkIOKAlCBtaXJyb3JzIHRoZSBzaW5nbGUtZGVsZXRlXG4gICAgICogIGByZXF1aXJlUHVibGljQWNjZXNzYCBnYXRlIHNvIGEgbm9uLXN5c2FkbWluIGNhbid0IGJ1bGstZGVsZXRlIHB1YmxpY1xuICAgICAqICAoc2hhcmVkL3N5c2FkbWluLW1hbmFnZWQpIHJlY29yZHMuIE5vLW9wIGZvciBlbnRpdGllcyB3aXRob3V0IGFuXG4gICAgICogIGBhY2Nlc3NNb2RpZmllcmAgY29sdW1uLiBDYWxsZXJzIHBhc3MgYCFpc1N5c3RlbUFkbWluKHJlcSlgLiAqL1xuICAgIHJlc3RyaWN0VG9Qcml2YXRlID0gZmFsc2UsXG4gICk6IFByb21pc2U8VEVudGl0eVtdPiB7XG4gICAgaWYgKGlkcy5sZW5ndGggPT09IDApIHJldHVybiBbXTtcblxuICAgIGNvbnN0IG5vdyA9IG5ldyBEYXRlKCk7XG4gICAgY29uc3QgdXNlciA9IHVzZXJJZCB8fCAnc3lzdGVtJztcbiAgICAvLyBPd25lci1zY29wZSB0aGUgYnVsayBzb2Z0LWRlbGV0ZTogYnVpbGRDb25kaXRpb25zIGFsc28gbWF0Y2hlcyBzeXN0ZW0vb3RoZXJcbiAgICAvLyAtb3JnIFBVQkxJQyByb3dzLCBzbyB3aXRob3V0IHRoZSBzdHJpY3Qgb3JnSWQgcGluIGEgdGVuYW50IGNvdWxkIGRlbGV0ZVxuICAgIC8vIHNoYXJlZCByZWNvcmRzIGJ5IGlkLiAoU2VlIHdyaXRlQ29uZGl0aW9ucy4pXG4gICAgY29uc3QgYWNjZXNzQ29sID0gKHRoaXMuc2NoZW1hIGFzIGFueSkuYWNjZXNzTW9kaWZpZXIgYXMgQW55Q29sdW1uIHwgdW5kZWZpbmVkO1xuICAgIGNvbnN0IGNvbmRpdGlvbnMgPSBbXG4gICAgICBpbkFycmF5KCh0aGlzLnNjaGVtYSBhcyBhbnkpLmlkLCBpZHMpLFxuICAgICAgLi4udGhpcy5idWlsZENvbmRpdGlvbnMoe30gYXMgUGFydGlhbDxURmlsdGVyPiwgb3JnSWQpLFxuICAgICAgLy8gVGVuYW50IGNvbHVtbiAoZ2V0T3JnQ29sdW1uLCBhc3NlcnRlZCBub24tbnVsbCkg4oCUIGNvbnNpc3RlbnQgd2l0aFxuICAgICAgLy8gd3JpdGVDb25kaXRpb25zOyBubyBzaWxlbnQgZmFpbC1vcGVuIHdoZW4gdGhlIHByb3BlcnR5IGlzIGFic2VudC5cbiAgICAgIC4uLihvcmdJZCA/IFtlcSh0aGlzLmdldE9yZ0NvbHVtbigpLCBvcmdJZCldIDogW10pLFxuICAgICAgLi4uKHJlc3RyaWN0VG9Qcml2YXRlICYmIGFjY2Vzc0NvbCA/IFtlcShhY2Nlc3NDb2wsICdwcml2YXRlJyldIDogW10pLFxuICAgIF07XG5cbiAgICBjb25zdCBkZWxldGVkID0gYXdhaXQgd2l0aFRlbmFudFR4KGFzeW5jICh0eCkgPT4gdHhcbiAgICAgIC51cGRhdGUodGhpcy5zY2hlbWEpXG4gICAgICAuc2V0KHtcbiAgICAgICAgaXNBY3RpdmU6IGZhbHNlLFxuICAgICAgICB1cGRhdGVkQXQ6IG5vdyxcbiAgICAgICAgdXBkYXRlZEJ5OiB1c2VyLFxuICAgICAgICBkZWxldGVkQXQ6IG5vdyxcbiAgICAgICAgZGVsZXRlZEJ5OiB1c2VyLFxuICAgICAgfSBhcyBhbnkpXG4gICAgICAud2hlcmUoYW5kKC4uLmNvbmRpdGlvbnMpKVxuICAgICAgLnJldHVybmluZygpLnRoZW4ociA9PiBkcml6emxlUm93czxURW50aXR5PihyKSkpO1xuXG4gICAgYXdhaXQgUHJvbWlzZS5hbGwoXG4gICAgICBkZWxldGVkLm1hcChlbnRpdHkgPT5cbiAgICAgICAgdGhpcy5vbkFmdGVyRGVsZXRlKGVudGl0eS5pZCwgZW50aXR5LCB1c2VySWQpLmNhdGNoKGVyciA9PlxuICAgICAgICAgIHRoaXMuX2xvZ2dlci53YXJuKCdMaWZlY3ljbGUgaG9vayBmYWlsZWQnLCB7IGVycm9yOiBTdHJpbmcoZXJyKSB9KSxcbiAgICAgICAgKSxcbiAgICAgICksXG4gICAgKTtcblxuICAgIHJldHVybiBkZWxldGVkO1xuICB9XG59XG4iXX0=
|