angular-odata 0.121.0 → 0.123.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/esm2022/lib/client.mjs +253 -0
- package/esm2022/lib/models/collection.mjs +862 -0
- package/esm2022/lib/models/model.mjs +519 -0
- package/esm2022/lib/models/options.mjs +1110 -0
- package/esm2022/lib/module.mjs +43 -0
- package/esm2022/lib/resources/query/builder.mjs +619 -0
- package/{esm2020 → esm2022}/lib/resources/query/expressions/base.mjs +1 -1
- package/{esm2020 → esm2022}/lib/resources/query/expressions/compute.mjs +1 -1
- package/{esm2020 → esm2022}/lib/resources/query/expressions/count.mjs +1 -1
- package/esm2022/lib/resources/query/expressions/expand.mjs +119 -0
- package/esm2022/lib/resources/query/expressions/filter.mjs +161 -0
- package/{esm2020 → esm2022}/lib/resources/query/expressions/orderby.mjs +1 -1
- package/{esm2020 → esm2022}/lib/resources/query/expressions/search.mjs +1 -1
- package/{esm2020 → esm2022}/lib/resources/query/expressions/select.mjs +1 -1
- package/esm2022/lib/resources/query/expressions/syntax.mjs +409 -0
- package/{esm2020 → esm2022}/lib/resources/query/handlers.mjs +1 -1
- package/esm2022/lib/resources/query/options.mjs +115 -0
- package/esm2022/lib/resources/responses/metadata.mjs +548 -0
- package/esm2022/lib/schema/parsers/edm.mjs +99 -0
- package/{esm2020 → esm2022}/lib/schema/parsers/enum-type.mjs +2 -2
- package/esm2022/lib/services/factory.mjs +34 -0
- package/esm2022/lib/utils/enums.mjs +61 -0
- package/{fesm2020 → fesm2022}/angular-odata.mjs +643 -614
- package/fesm2022/angular-odata.mjs.map +1 -0
- package/lib/helper.d.ts +1 -1
- package/lib/models/model.d.ts +7 -16
- package/lib/models/options.d.ts +51 -33
- package/lib/resources/path/segments.d.ts +1 -1
- package/lib/resources/query/builder.d.ts +21 -20
- package/lib/resources/query/expressions/base.d.ts +3 -3
- package/lib/resources/query/expressions/compute.d.ts +2 -2
- package/lib/resources/query/expressions/count.d.ts +3 -3
- package/lib/resources/query/expressions/expand.d.ts +13 -12
- package/lib/resources/query/expressions/filter.d.ts +15 -15
- package/lib/resources/query/expressions/orderby.d.ts +3 -3
- package/lib/resources/query/expressions/search.d.ts +3 -3
- package/lib/resources/query/expressions/select.d.ts +2 -2
- package/lib/resources/query/expressions/syntax.d.ts +59 -58
- package/lib/resources/query/handlers.d.ts +2 -2
- package/lib/resources/query/options.d.ts +1 -1
- package/lib/resources/resource.d.ts +1 -1
- package/lib/resources/responses/types.d.ts +3 -3
- package/lib/resources/types/options.d.ts +7 -7
- package/lib/schema/parsers/structured-type.d.ts +5 -5
- package/lib/types.d.ts +15 -15
- package/lib/utils/durations.d.ts +1 -1
- package/lib/utils/enums.d.ts +3 -0
- package/package.json +9 -15
- package/esm2020/lib/client.mjs +0 -252
- package/esm2020/lib/models/collection.mjs +0 -857
- package/esm2020/lib/models/model.mjs +0 -518
- package/esm2020/lib/models/options.mjs +0 -1130
- package/esm2020/lib/module.mjs +0 -42
- package/esm2020/lib/resources/query/builder.mjs +0 -588
- package/esm2020/lib/resources/query/expressions/expand.mjs +0 -115
- package/esm2020/lib/resources/query/expressions/filter.mjs +0 -161
- package/esm2020/lib/resources/query/expressions/syntax.mjs +0 -409
- package/esm2020/lib/resources/query/options.mjs +0 -115
- package/esm2020/lib/resources/responses/metadata.mjs +0 -547
- package/esm2020/lib/schema/parsers/edm.mjs +0 -104
- package/esm2020/lib/services/factory.mjs +0 -33
- package/esm2020/lib/utils/enums.mjs +0 -45
- package/fesm2015/angular-odata.mjs +0 -11841
- package/fesm2015/angular-odata.mjs.map +0 -1
- package/fesm2020/angular-odata.mjs.map +0 -1
- /package/{esm2020 → esm2022}/angular-odata.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/api.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/cache/cache.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/cache/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/cache/memory.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/cache/storage.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/constants.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/helper.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/loaders.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/models/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/options.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/path/handlers.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/path/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/path/segments.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/query/expressions/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/query/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/request.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/resource.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/annotations.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-annotation.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-entity-container.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-entity-set.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-enum-type.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-function-action.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-navigation-property-binding.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-reference.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-schema.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-singleton.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-structural-property.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-structured-type.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/csdl/csdl-type-definition.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/options.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/response.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/responses/types.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/action.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/batch.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/count.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/entity-set.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/entity.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/function.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/media.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/metadata.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/navigation-property.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/options.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/property.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/reference.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/singleton.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/resources/types/value.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/annotation.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/callable.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/element.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/entity-container.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/entity-set.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/enum-type.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/parsers/callable.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/parsers/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/parsers/structured-type.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/schema.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/schema/structured-type.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/services/base.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/services/entity-set.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/services/entity.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/services/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/services/singleton.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/settings.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/types.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/arraybuffers.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/arrays.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/dates.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/durations.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/http.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/index.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/objects.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/odata.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/strings.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/types.mjs +0 -0
- /package/{esm2020 → esm2022}/lib/utils/urls.mjs +0 -0
- /package/{esm2020 → esm2022}/public-api.mjs +0 -0
|
@@ -0,0 +1,519 @@
|
|
|
1
|
+
import { EventEmitter } from '@angular/core';
|
|
2
|
+
import { forkJoin, NEVER, of, throwError } from 'rxjs';
|
|
3
|
+
import { map, tap } from 'rxjs/operators';
|
|
4
|
+
import { DEFAULT_VERSION } from '../constants';
|
|
5
|
+
import { ODataHelper } from '../helper';
|
|
6
|
+
import { ODataEntityAnnotations, ODataEntityResource, ODataNavigationPropertyResource, } from '../resources';
|
|
7
|
+
import { Objects, Strings, Types } from '../utils';
|
|
8
|
+
import { ODataCollection } from './collection';
|
|
9
|
+
import { INCLUDE_DEEP, INCLUDE_SHALLOW, ODataModelEvent, ODataModelOptions, ODataModelEventType, } from './options';
|
|
10
|
+
// @dynamic
|
|
11
|
+
export class ODataModel {
|
|
12
|
+
static buildMeta({ options, schema, }) {
|
|
13
|
+
if (options === undefined) {
|
|
14
|
+
let fields = schema
|
|
15
|
+
.fields({ include_navigation: true, include_parents: true })
|
|
16
|
+
.reduce((acc, field) => {
|
|
17
|
+
let name = field.name;
|
|
18
|
+
// Prevent collision with reserved keywords
|
|
19
|
+
while (RESERVED_FIELD_NAMES.includes(name)) {
|
|
20
|
+
name = name + '_';
|
|
21
|
+
}
|
|
22
|
+
return Object.assign(acc, {
|
|
23
|
+
[name]: {
|
|
24
|
+
field: field.name,
|
|
25
|
+
default: field.default,
|
|
26
|
+
required: !field.nullable,
|
|
27
|
+
},
|
|
28
|
+
});
|
|
29
|
+
}, {});
|
|
30
|
+
options = { fields };
|
|
31
|
+
}
|
|
32
|
+
this.meta = new ODataModelOptions({ options, schema });
|
|
33
|
+
}
|
|
34
|
+
constructor(data = {}, { parent, resource, annots, reset = false, } = {}) {
|
|
35
|
+
// Parent
|
|
36
|
+
this._parent = null;
|
|
37
|
+
this._resource = null;
|
|
38
|
+
this._resources = [];
|
|
39
|
+
this._attributes = new Map();
|
|
40
|
+
this._annotations = null;
|
|
41
|
+
this._reset = false;
|
|
42
|
+
this._reparent = false;
|
|
43
|
+
this._silent = false;
|
|
44
|
+
// Events
|
|
45
|
+
this.events$ = new EventEmitter();
|
|
46
|
+
const Klass = this.constructor;
|
|
47
|
+
if (Klass.meta === undefined)
|
|
48
|
+
throw new Error(`ODataModel: Can't create model without metadata`);
|
|
49
|
+
this._meta = Klass.meta;
|
|
50
|
+
this._meta.bind(this, { parent, resource, annots });
|
|
51
|
+
// Client Id
|
|
52
|
+
this[this._meta.cid] =
|
|
53
|
+
data[this._meta.cid] ||
|
|
54
|
+
Strings.uniqueId({ prefix: `${Klass.meta.schema.name.toLowerCase()}-` });
|
|
55
|
+
let attrs = this.annots().attributes(data, 'full');
|
|
56
|
+
let defaults = this.defaults();
|
|
57
|
+
this.assign(Objects.merge(defaults, attrs), {
|
|
58
|
+
reset,
|
|
59
|
+
});
|
|
60
|
+
}
|
|
61
|
+
//#region Resources
|
|
62
|
+
resource() {
|
|
63
|
+
return ODataModelOptions.resource(this);
|
|
64
|
+
}
|
|
65
|
+
pushResource(resource) {
|
|
66
|
+
// Push current parent and resource
|
|
67
|
+
this._resources.push({ parent: this._parent, resource: this._resource });
|
|
68
|
+
// Replace parent and resource
|
|
69
|
+
this._parent = null;
|
|
70
|
+
this._resource = resource;
|
|
71
|
+
}
|
|
72
|
+
popResource() {
|
|
73
|
+
// Pop parent and resource
|
|
74
|
+
const pop = this._resources.pop();
|
|
75
|
+
if (pop !== undefined) {
|
|
76
|
+
const current = { parent: this._parent, resource: this._resource };
|
|
77
|
+
this._parent = pop.parent;
|
|
78
|
+
this._resource = pop.resource;
|
|
79
|
+
return current;
|
|
80
|
+
}
|
|
81
|
+
return undefined;
|
|
82
|
+
}
|
|
83
|
+
navigationProperty(name) {
|
|
84
|
+
const field = this._meta.field(name);
|
|
85
|
+
if (field === undefined || !field.navigation)
|
|
86
|
+
throw Error(`navigationProperty: Can't find navigation property ${name}`);
|
|
87
|
+
const resource = this.resource();
|
|
88
|
+
if (!(resource instanceof ODataEntityResource) || !resource.hasKey())
|
|
89
|
+
throw Error("navigationProperty: Can't get navigation without ODataEntityResource with key");
|
|
90
|
+
return field.resourceFactory(resource);
|
|
91
|
+
}
|
|
92
|
+
property(name) {
|
|
93
|
+
const field = this._meta.field(name);
|
|
94
|
+
if (field === undefined || field.navigation)
|
|
95
|
+
throw Error(`property: Can't find property ${name}`);
|
|
96
|
+
const resource = this.resource();
|
|
97
|
+
if (!(resource instanceof ODataEntityResource) || !resource.hasKey())
|
|
98
|
+
throw Error("property: Can't get property without ODataEntityResource with key");
|
|
99
|
+
return field.resourceFactory(resource);
|
|
100
|
+
}
|
|
101
|
+
attach(resource) {
|
|
102
|
+
return this._meta.attach(this, resource);
|
|
103
|
+
}
|
|
104
|
+
//#endregion
|
|
105
|
+
schema() {
|
|
106
|
+
return this._meta.schema;
|
|
107
|
+
}
|
|
108
|
+
annots() {
|
|
109
|
+
return (this._annotations ??
|
|
110
|
+
new ODataEntityAnnotations(ODataHelper[DEFAULT_VERSION]));
|
|
111
|
+
}
|
|
112
|
+
key({ field_mapping = false, resolve = true, } = {}) {
|
|
113
|
+
return this._meta.resolveKey(this, { field_mapping, resolve });
|
|
114
|
+
}
|
|
115
|
+
isOpenModel() {
|
|
116
|
+
return this._meta.isOpenType();
|
|
117
|
+
}
|
|
118
|
+
isParentOf(child) {
|
|
119
|
+
return (child !== this &&
|
|
120
|
+
ODataModelOptions.chain(child).some((p) => p[0] === this));
|
|
121
|
+
}
|
|
122
|
+
referential(attr, { field_mapping = false, resolve = true, } = {}) {
|
|
123
|
+
return this._meta.resolveReferential(this, attr, {
|
|
124
|
+
field_mapping,
|
|
125
|
+
resolve,
|
|
126
|
+
});
|
|
127
|
+
}
|
|
128
|
+
referenced(attr, { field_mapping = false, resolve = true, } = {}) {
|
|
129
|
+
return this._meta.resolveReferenced(this, attr, {
|
|
130
|
+
field_mapping,
|
|
131
|
+
resolve,
|
|
132
|
+
});
|
|
133
|
+
}
|
|
134
|
+
validate({ method, navigation = false, } = {}) {
|
|
135
|
+
return this._meta.validate(this, { method, navigation });
|
|
136
|
+
}
|
|
137
|
+
isValid({ method, navigation = false, } = {}) {
|
|
138
|
+
this._errors = this.validate({ method, navigation });
|
|
139
|
+
if (this._errors !== undefined)
|
|
140
|
+
this.events$.emit(new ODataModelEvent(ODataModelEventType.Invalid, {
|
|
141
|
+
model: this,
|
|
142
|
+
value: this._errors,
|
|
143
|
+
options: { method },
|
|
144
|
+
}));
|
|
145
|
+
return this._errors === undefined;
|
|
146
|
+
}
|
|
147
|
+
defaults() {
|
|
148
|
+
return this._meta.defaults() || {};
|
|
149
|
+
}
|
|
150
|
+
toEntity({ client_id = false, include_navigation = false, include_concurrency = false, include_computed = false, include_key = true, include_non_field = false, changes_only = false, field_mapping = false, chain = [], } = {}) {
|
|
151
|
+
return this._meta.toEntity(this, {
|
|
152
|
+
client_id,
|
|
153
|
+
include_navigation,
|
|
154
|
+
include_concurrency,
|
|
155
|
+
include_computed,
|
|
156
|
+
include_key,
|
|
157
|
+
include_non_field,
|
|
158
|
+
changes_only,
|
|
159
|
+
field_mapping,
|
|
160
|
+
chain,
|
|
161
|
+
});
|
|
162
|
+
}
|
|
163
|
+
toJSON() {
|
|
164
|
+
return this.toEntity();
|
|
165
|
+
}
|
|
166
|
+
set(path, value, { type } = {}) {
|
|
167
|
+
const pathArray = (Types.isArray(path) ? path : path.match(/([^[.\]])+/g));
|
|
168
|
+
if (pathArray.length === 0)
|
|
169
|
+
return undefined;
|
|
170
|
+
if (pathArray.length > 1) {
|
|
171
|
+
const model = this[pathArray[0]];
|
|
172
|
+
return model.set(pathArray.slice(1), value, {});
|
|
173
|
+
}
|
|
174
|
+
if (pathArray.length === 1) {
|
|
175
|
+
return this._meta.set(this, pathArray[0], value, { type });
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
get(path) {
|
|
179
|
+
const pathArray = (Types.isArray(path) ? path : path.match(/([^[.\]])+/g));
|
|
180
|
+
if (pathArray.length === 0)
|
|
181
|
+
return undefined;
|
|
182
|
+
const value = this._meta.get(this, pathArray[0]);
|
|
183
|
+
if (pathArray.length > 1 &&
|
|
184
|
+
(value instanceof ODataModel || value instanceof ODataCollection)) {
|
|
185
|
+
return value.get(pathArray.slice(1));
|
|
186
|
+
}
|
|
187
|
+
return value;
|
|
188
|
+
}
|
|
189
|
+
has(path) {
|
|
190
|
+
const pathArray = (Types.isArray(path) ? path : path.match(/([^[.\]])+/g));
|
|
191
|
+
if (pathArray.length === 0)
|
|
192
|
+
return false;
|
|
193
|
+
const value = this._meta.get(this, pathArray[0]);
|
|
194
|
+
if (pathArray.length > 1 &&
|
|
195
|
+
(value instanceof ODataModel || value instanceof ODataCollection)) {
|
|
196
|
+
return value.has(pathArray.slice(1));
|
|
197
|
+
}
|
|
198
|
+
return value !== undefined;
|
|
199
|
+
}
|
|
200
|
+
reset({ path, silent = false, } = {}) {
|
|
201
|
+
const pathArray = (path === undefined
|
|
202
|
+
? []
|
|
203
|
+
: Types.isArray(path)
|
|
204
|
+
? path
|
|
205
|
+
: path.match(/([^[.\]])+/g));
|
|
206
|
+
const name = pathArray[0];
|
|
207
|
+
const value = name !== undefined ? this[name] : undefined;
|
|
208
|
+
if (ODataModelOptions.isModel(value) ||
|
|
209
|
+
ODataModelOptions.isCollection(value)) {
|
|
210
|
+
value.reset({ path: pathArray.slice(1), silent });
|
|
211
|
+
}
|
|
212
|
+
else {
|
|
213
|
+
this._meta.reset(this, { name: pathArray[0], silent });
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
clear({ silent = false } = {}) {
|
|
217
|
+
this._attributes.clear();
|
|
218
|
+
//this._changes.clear();
|
|
219
|
+
//this._relations.clear();
|
|
220
|
+
if (!silent) {
|
|
221
|
+
this.events$.emit(new ODataModelEvent(ODataModelEventType.Update, {
|
|
222
|
+
model: this,
|
|
223
|
+
}));
|
|
224
|
+
}
|
|
225
|
+
}
|
|
226
|
+
assign(entity, { reset = false, reparent = false, silent = false, } = {}) {
|
|
227
|
+
return this._meta.assign(this, entity, { reset, silent, reparent });
|
|
228
|
+
}
|
|
229
|
+
clone() {
|
|
230
|
+
let Ctor = this.constructor;
|
|
231
|
+
return new Ctor(this.toEntity(INCLUDE_SHALLOW), {
|
|
232
|
+
resource: this.resource(),
|
|
233
|
+
annots: this.annots(),
|
|
234
|
+
});
|
|
235
|
+
}
|
|
236
|
+
_request(obs$) {
|
|
237
|
+
this.events$.emit(new ODataModelEvent(ODataModelEventType.Request, {
|
|
238
|
+
model: this,
|
|
239
|
+
options: { observable: obs$ },
|
|
240
|
+
}));
|
|
241
|
+
return obs$.pipe(map(({ entity, annots }) => {
|
|
242
|
+
this._annotations = annots;
|
|
243
|
+
this.assign(annots.attributes(entity || {}, 'full'), {
|
|
244
|
+
reset: true,
|
|
245
|
+
});
|
|
246
|
+
this.events$.emit(new ODataModelEvent(ODataModelEventType.Sync, {
|
|
247
|
+
model: this,
|
|
248
|
+
options: { entity, annots },
|
|
249
|
+
}));
|
|
250
|
+
return this;
|
|
251
|
+
}));
|
|
252
|
+
}
|
|
253
|
+
fetch({ ...options } = {}) {
|
|
254
|
+
let resource = this.resource();
|
|
255
|
+
if (resource === undefined)
|
|
256
|
+
return throwError(() => new Error('fetch: Resource is undefined'));
|
|
257
|
+
let obs$;
|
|
258
|
+
if (resource instanceof ODataEntityResource) {
|
|
259
|
+
obs$ = resource.fetch(options);
|
|
260
|
+
}
|
|
261
|
+
else if (resource instanceof ODataNavigationPropertyResource) {
|
|
262
|
+
obs$ = resource.fetch({ responseType: 'entity', ...options });
|
|
263
|
+
}
|
|
264
|
+
else {
|
|
265
|
+
obs$ = resource.fetch({
|
|
266
|
+
responseType: 'entity',
|
|
267
|
+
...options,
|
|
268
|
+
});
|
|
269
|
+
}
|
|
270
|
+
return this._request(obs$);
|
|
271
|
+
}
|
|
272
|
+
save({ method, navigation = false, validate = true, ...options } = {}) {
|
|
273
|
+
let resource = this.resource();
|
|
274
|
+
if (resource === undefined)
|
|
275
|
+
return throwError(() => new Error('save: Resource is undefined'));
|
|
276
|
+
if (!(resource instanceof ODataEntityResource ||
|
|
277
|
+
resource instanceof ODataNavigationPropertyResource))
|
|
278
|
+
return throwError(() => new Error('save: Resource type ODataEntityResource/ODataNavigationPropertyResource needed'));
|
|
279
|
+
// Resolve method and resource key
|
|
280
|
+
if (method === undefined && this.schema().isCompoundKey())
|
|
281
|
+
return throwError(() => new Error('save: Composite key require a specific method, use create/update/modify'));
|
|
282
|
+
method = method || (!resource.hasKey() ? 'create' : 'update');
|
|
283
|
+
if (resource instanceof ODataEntityResource &&
|
|
284
|
+
(method === 'update' || method === 'modify') &&
|
|
285
|
+
!resource.hasKey())
|
|
286
|
+
return throwError(() => new Error('save: Update/Patch require entity key'));
|
|
287
|
+
if (resource instanceof ODataNavigationPropertyResource ||
|
|
288
|
+
method === 'create')
|
|
289
|
+
resource.clearKey();
|
|
290
|
+
if (validate && !this.isValid({ method, navigation })) {
|
|
291
|
+
return throwError(() => new Error('save: Validation errors'));
|
|
292
|
+
}
|
|
293
|
+
const _entity = this.toEntity({
|
|
294
|
+
changes_only: method === 'modify',
|
|
295
|
+
field_mapping: true,
|
|
296
|
+
include_concurrency: true,
|
|
297
|
+
include_navigation: navigation,
|
|
298
|
+
});
|
|
299
|
+
return this._request((method === 'create'
|
|
300
|
+
? resource.create(_entity, options)
|
|
301
|
+
: method === 'modify'
|
|
302
|
+
? resource.modify(_entity, { etag: this.annots().etag, ...options })
|
|
303
|
+
: resource.update(_entity, { etag: this.annots().etag, ...options })).pipe(map(({ entity, annots }) => ({ entity: entity || _entity, annots }))));
|
|
304
|
+
}
|
|
305
|
+
destroy({ ...options } = {}) {
|
|
306
|
+
let resource = this.resource();
|
|
307
|
+
if (resource === undefined)
|
|
308
|
+
return throwError(() => new Error('destroy: Resource is undefined'));
|
|
309
|
+
if (!(resource instanceof ODataEntityResource ||
|
|
310
|
+
resource instanceof ODataNavigationPropertyResource))
|
|
311
|
+
return throwError(() => new Error('destroy: Resource type ODataEntityResource/ODataNavigationPropertyResource needed'));
|
|
312
|
+
if (!resource.hasKey())
|
|
313
|
+
return throwError(() => new Error("destroy: Can't destroy model without key"));
|
|
314
|
+
const _entity = this.toEntity({ field_mapping: true });
|
|
315
|
+
const obs$ = resource
|
|
316
|
+
.destroy({ etag: this.annots().etag, ...options })
|
|
317
|
+
.pipe(map(({ entity, annots }) => ({ entity: entity || _entity, annots })));
|
|
318
|
+
return this._request(obs$).pipe(tap(() => this.events$.emit(new ODataModelEvent(ODataModelEventType.Destroy, { model: this }))));
|
|
319
|
+
}
|
|
320
|
+
/**
|
|
321
|
+
* Create an execution context for change the internal query of a resource
|
|
322
|
+
* @param ctx Function to execute
|
|
323
|
+
*/
|
|
324
|
+
query(ctx) {
|
|
325
|
+
return this._meta.query(this, this.resource(), ctx);
|
|
326
|
+
}
|
|
327
|
+
/**
|
|
328
|
+
* Perform a check on the internal state of the model and return true if the model is changed.
|
|
329
|
+
* @param include_navigation Check in navigation properties
|
|
330
|
+
* @returns true if the model has changed, false otherwise
|
|
331
|
+
*/
|
|
332
|
+
hasChanged({ include_navigation = false, } = {}) {
|
|
333
|
+
return this._meta.hasChanged(this, { include_navigation });
|
|
334
|
+
}
|
|
335
|
+
encode(name, options) {
|
|
336
|
+
let value = this[name];
|
|
337
|
+
if (value === undefined)
|
|
338
|
+
return undefined;
|
|
339
|
+
let field = this._meta.field(name);
|
|
340
|
+
return field !== undefined ? field.encode(value, options) : value;
|
|
341
|
+
}
|
|
342
|
+
isNew() {
|
|
343
|
+
return !this._meta.hasKey(this);
|
|
344
|
+
}
|
|
345
|
+
withResource(resource, ctx) {
|
|
346
|
+
return this._meta.withResource(this, resource, ctx);
|
|
347
|
+
}
|
|
348
|
+
/**
|
|
349
|
+
* Create an execution context for a given function, where the model is bound to its entity endpoint
|
|
350
|
+
* @param ctx Context function
|
|
351
|
+
* @returns The result of the context
|
|
352
|
+
*/
|
|
353
|
+
asEntity(ctx) {
|
|
354
|
+
return this._meta.asEntity(this, ctx);
|
|
355
|
+
}
|
|
356
|
+
//#region Callables
|
|
357
|
+
callFunction(name, params, responseType, { ...options } = {}) {
|
|
358
|
+
const resource = this.resource();
|
|
359
|
+
if (!(resource instanceof ODataEntityResource) || !resource.hasKey())
|
|
360
|
+
return throwError(() => new Error("callFunction: Can't call function without ODataEntityResource with key"));
|
|
361
|
+
const func = resource.function(name).query((q) => q.apply(options));
|
|
362
|
+
switch (responseType) {
|
|
363
|
+
case 'property':
|
|
364
|
+
return func.callProperty(params, options);
|
|
365
|
+
case 'model':
|
|
366
|
+
return func.callModel(params, options);
|
|
367
|
+
case 'collection':
|
|
368
|
+
return func.callCollection(params, options);
|
|
369
|
+
case 'blob':
|
|
370
|
+
return func.callBlob(params, options);
|
|
371
|
+
case 'arraybuffer':
|
|
372
|
+
return func.callArraybuffer(params, options);
|
|
373
|
+
default:
|
|
374
|
+
return func.call(params, { responseType, ...options });
|
|
375
|
+
}
|
|
376
|
+
}
|
|
377
|
+
callAction(name, params, responseType, { ...options } = {}) {
|
|
378
|
+
const resource = this.resource();
|
|
379
|
+
if (!(resource instanceof ODataEntityResource) || !resource.hasKey())
|
|
380
|
+
return throwError(() => new Error("callAction: Can't call action without ODataEntityResource with key"));
|
|
381
|
+
const action = resource.action(name).query((q) => q.apply(options));
|
|
382
|
+
switch (responseType) {
|
|
383
|
+
case 'property':
|
|
384
|
+
return action.callProperty(params, options);
|
|
385
|
+
case 'model':
|
|
386
|
+
return action.callModel(params, options);
|
|
387
|
+
case 'collection':
|
|
388
|
+
return action.callCollection(params, options);
|
|
389
|
+
case 'blob':
|
|
390
|
+
return action.callBlob(params, options);
|
|
391
|
+
case 'arraybuffer':
|
|
392
|
+
return action.callArraybuffer(params, options);
|
|
393
|
+
default:
|
|
394
|
+
return action.call(params, { responseType, ...options });
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
//#endregion
|
|
398
|
+
// Cast
|
|
399
|
+
cast(type) {
|
|
400
|
+
//: ODataModel<S> {
|
|
401
|
+
const resource = this.resource();
|
|
402
|
+
if (!(resource instanceof ODataEntityResource))
|
|
403
|
+
throw new Error(`cast: Can't cast to derived model without ODataEntityResource`);
|
|
404
|
+
return resource
|
|
405
|
+
.cast(type)
|
|
406
|
+
.asModel(this.toEntity(INCLUDE_DEEP), {
|
|
407
|
+
annots: this.annots(),
|
|
408
|
+
});
|
|
409
|
+
}
|
|
410
|
+
fetchNavigationProperty(name, responseType, { ...options } = {}) {
|
|
411
|
+
const nav = this.navigationProperty(name);
|
|
412
|
+
nav.query((q) => q.apply(options));
|
|
413
|
+
switch (responseType) {
|
|
414
|
+
case 'model':
|
|
415
|
+
return nav.fetchModel(options);
|
|
416
|
+
case 'collection':
|
|
417
|
+
return nav.fetchCollection(options);
|
|
418
|
+
}
|
|
419
|
+
}
|
|
420
|
+
// Get Value
|
|
421
|
+
getValue(name, options) {
|
|
422
|
+
const field = this._meta.field(name);
|
|
423
|
+
if (field === undefined || field.navigation)
|
|
424
|
+
throw Error(`getValue: Can't find property ${name}`);
|
|
425
|
+
let value = this[name];
|
|
426
|
+
if (value === undefined) {
|
|
427
|
+
const prop = field.resourceFactory(this.resource());
|
|
428
|
+
return field.collection
|
|
429
|
+
? prop
|
|
430
|
+
.fetchCollection(options)
|
|
431
|
+
.pipe(tap((c) => this.assign({ [name]: c }, { silent: true })))
|
|
432
|
+
: field.isStructuredType()
|
|
433
|
+
? prop
|
|
434
|
+
.fetchModel(options)
|
|
435
|
+
.pipe(tap((c) => this.assign({ [name]: c }, { silent: true })))
|
|
436
|
+
: prop
|
|
437
|
+
.fetchProperty(options)
|
|
438
|
+
.pipe(tap((c) => this.assign({ [name]: c }, { silent: true })));
|
|
439
|
+
}
|
|
440
|
+
return of(value);
|
|
441
|
+
}
|
|
442
|
+
//#region References
|
|
443
|
+
setReference(name, model, options) {
|
|
444
|
+
const reference = this.navigationProperty(name).reference();
|
|
445
|
+
const etag = this.annots().etag;
|
|
446
|
+
let obs$ = NEVER;
|
|
447
|
+
if (model instanceof ODataModel) {
|
|
448
|
+
obs$ = reference.set(model._meta.entityResource(model), { etag, ...options });
|
|
449
|
+
}
|
|
450
|
+
else if (model instanceof ODataCollection) {
|
|
451
|
+
obs$ = forkJoin(model
|
|
452
|
+
.models()
|
|
453
|
+
.map((m) => reference.add(m._meta.entityResource(m), options)));
|
|
454
|
+
}
|
|
455
|
+
else if (model === null) {
|
|
456
|
+
obs$ = reference.unset({ etag, ...options });
|
|
457
|
+
}
|
|
458
|
+
this.events$.emit(new ODataModelEvent(ODataModelEventType.Request, {
|
|
459
|
+
model: this,
|
|
460
|
+
options: { observable: obs$ },
|
|
461
|
+
}));
|
|
462
|
+
return obs$.pipe(map((model) => {
|
|
463
|
+
this.assign({ [name]: model });
|
|
464
|
+
this.events$.emit(new ODataModelEvent(ODataModelEventType.Sync, { model: this }));
|
|
465
|
+
return this;
|
|
466
|
+
}));
|
|
467
|
+
}
|
|
468
|
+
getReference(name) {
|
|
469
|
+
const field = this._meta.field(name);
|
|
470
|
+
if (field === undefined || !field.navigation)
|
|
471
|
+
throw Error(`getReference: Can't find navigation property ${name}`);
|
|
472
|
+
let model = this[name];
|
|
473
|
+
if (model === null)
|
|
474
|
+
return null;
|
|
475
|
+
if (model === undefined) {
|
|
476
|
+
if (field.collection) {
|
|
477
|
+
model = field.collectionFactory({ parent: this });
|
|
478
|
+
}
|
|
479
|
+
else {
|
|
480
|
+
const value = this.referenced(field);
|
|
481
|
+
model =
|
|
482
|
+
value === null ? null : field.modelFactory({ parent: this, value });
|
|
483
|
+
}
|
|
484
|
+
this[name] = model;
|
|
485
|
+
}
|
|
486
|
+
return model;
|
|
487
|
+
}
|
|
488
|
+
//#endregion
|
|
489
|
+
//#region Model Identity
|
|
490
|
+
get [Symbol.toStringTag]() {
|
|
491
|
+
return 'Model';
|
|
492
|
+
}
|
|
493
|
+
equals(other) {
|
|
494
|
+
const thisKey = this.key();
|
|
495
|
+
const otherKey = other.key();
|
|
496
|
+
return (this === other ||
|
|
497
|
+
(typeof this === typeof other &&
|
|
498
|
+
(this[this._meta.cid] === other[this._meta.cid] ||
|
|
499
|
+
(thisKey !== undefined &&
|
|
500
|
+
otherKey !== undefined &&
|
|
501
|
+
Types.isEqual(thisKey, otherKey)))));
|
|
502
|
+
}
|
|
503
|
+
//#endregion
|
|
504
|
+
//#region Collection Tools
|
|
505
|
+
collection() {
|
|
506
|
+
return this._parent !== null &&
|
|
507
|
+
ODataModelOptions.isCollection(this._parent[0])
|
|
508
|
+
? this._parent[0]
|
|
509
|
+
: undefined;
|
|
510
|
+
}
|
|
511
|
+
next() {
|
|
512
|
+
return this.collection()?.next(this);
|
|
513
|
+
}
|
|
514
|
+
prev() {
|
|
515
|
+
return this.collection()?.prev(this);
|
|
516
|
+
}
|
|
517
|
+
}
|
|
518
|
+
export const RESERVED_FIELD_NAMES = Object.getOwnPropertyNames(ODataModel.prototype);
|
|
519
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibW9kZWwuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi9wcm9qZWN0cy9hbmd1bGFyLW9kYXRhL3NyYy9saWIvbW9kZWxzL21vZGVsLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFDN0MsT0FBTyxFQUFFLFFBQVEsRUFBRSxLQUFLLEVBQWMsRUFBRSxFQUFFLFVBQVUsRUFBRSxNQUFNLE1BQU0sQ0FBQztBQUNuRSxPQUFPLEVBQUUsR0FBRyxFQUFFLEdBQUcsRUFBRSxNQUFNLGdCQUFnQixDQUFDO0FBQzFDLE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSxjQUFjLENBQUM7QUFDL0MsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLFdBQVcsQ0FBQztBQUN4QyxPQUFPLEVBSUwsc0JBQXNCLEVBQ3RCLG1CQUFtQixFQUVuQiwrQkFBK0IsR0FPaEMsTUFBTSxjQUFjLENBQUM7QUFFdEIsT0FBTyxFQUFFLE9BQU8sRUFBRSxPQUFPLEVBQUUsS0FBSyxFQUFFLE1BQU0sVUFBVSxDQUFDO0FBQ25ELE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSxjQUFjLENBQUM7QUFDL0MsT0FBTyxFQUNMLFlBQVksRUFDWixlQUFlLEVBRWYsZUFBZSxFQUVmLGlCQUFpQixFQUVqQixtQkFBbUIsR0FDcEIsTUFBTSxXQUFXLENBQUM7QUFHbkIsV0FBVztBQUNYLE1BQU0sT0FBTyxVQUFVO0lBSXJCLE1BQU0sQ0FBQyxTQUFTLENBQUksRUFDbEIsT0FBTyxFQUNQLE1BQU0sR0FJUDtRQUNDLElBQUksT0FBTyxLQUFLLFNBQVMsRUFBRTtZQUN6QixJQUFJLE1BQU0sR0FBRyxNQUFNO2lCQUNoQixNQUFNLENBQUMsRUFBRSxrQkFBa0IsRUFBRSxJQUFJLEVBQUUsZUFBZSxFQUFFLElBQUksRUFBRSxDQUFDO2lCQUMzRCxNQUFNLENBQUMsQ0FBQyxHQUFHLEVBQUUsS0FBSyxFQUFF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QUFDLE9BQU8sRUFBRSxRQUFRLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FDMUMsQ0FBQztJQUNKLENBQUM7SUFDRCxZQUFZO0lBRVosMEJBQTBCO0lBQzFCLFVBQVU7UUFDUixPQUFPLElBQUksQ0FBQyxPQUFPLEtBQUssSUFBSTtZQUMxQixpQkFBaUIsQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUMvQyxDQUFDLENBQUUsSUFBSSxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQXVDO1lBQ3hELENBQUMsQ0FBQyxTQUFTLENBQUM7SUFDaEIsQ0FBQztJQUVELElBQUk7UUFDRixPQUFPLElBQUksQ0FBQyxVQUFVLEVBQUUsRUFBRSxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUM7SUFDdkMsQ0FBQztJQUVELElBQUk7UUFDRixPQUFPLElBQUksQ0FBQyxVQUFVLEVBQUUsRUFBRSxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUM7SUFDdkMsQ0FBQztDQUVGO0FBRUQsTUFBTSxDQUFDLE1BQU0sb0JBQW9CLEdBQUcsTUFBTSxDQUFDLG1CQUFtQixDQUM1RCxVQUFVLENBQUMsU0FBUyxDQUNyQixDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgRXZlbnRFbWl0dGVyIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBmb3JrSm9pbiwgTkVWRVIsIE9ic2VydmFibGUsIG9mLCB0aHJvd0Vycm9yIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBtYXAsIHRhcCB9IGZyb20gJ3J4anMvb3BlcmF0b3JzJztcbmltcG9ydCB7IERFRkFVTFRfVkVSU0lPTiB9IGZyb20gJy4uL2NvbnN0YW50cyc7XG5pbXBvcnQgeyBPRGF0YUhlbHBlciB9IGZyb20gJy4uL2hlbHBlcic7XG5pbXBvcnQge1xuICBFbnRpdHlLZXksXG4gIE9EYXRhQWN0aW9uT3B0aW9ucyxcbiAgT0RhdGFFbnRpdHksXG4gIE9EYXRhRW50aXR5QW5ub3RhdGlvbnMsXG4gIE9EYXRhRW50aXR5UmVzb3VyY2UsXG4gIE9EYXRhRnVuY3Rpb25PcHRpb25zLFxuICBPRGF0YU5hdmlnYXRpb25Qcm9wZXJ0eVJlc291cmNlLFxuICBPRGF0YU9wdGlvbnMsXG4gIE9EYXRhUHJvcGVydHlSZXNvdXJjZSxcbiAgT0RhdGFRdWVyeUFyZ3VtZW50c09wdGlvbnMsXG4gIE9EYXRhUXVlcnlPcHRpb25zSGFuZGxlcixcbiAgT0RhdGFSZXNvdXJjZSxcbiAgT0RhdGFTaW5nbGV0b25SZXNvdXJjZSxcbn0gZnJvbSAnLi4vcmVzb3VyY2VzJztcbmltcG9ydCB7IE9EYXRhU3RydWN0dXJlZFR5cGUgfSBmcm9tICcuLi9zY2hlbWEnO1xuaW1wb3J0IHsgT2JqZWN0cywgU3RyaW5ncywgVHlwZXMgfSBmcm9tICcuLi91dGlscyc7XG5pbXBvcnQgeyBPRGF0YUNvbGxlY3Rpb24gfSBmcm9tICcuL2NvbGxlY3Rpb24nO1xuaW1wb3J0IHtcbiAgSU5DTFVERV9ERUVQLFxuICBJTkNMVURFX1NIQUxMT1csXG4gIE1vZGVsT3B0aW9ucyxcbiAgT0RhdGFNb2RlbEV2ZW50LFxuICBPRGF0YU1vZGVsRmllbGQsXG4gIE9EYXRhTW9kZWxPcHRpb25zLFxuICBPRGF0YU1vZGVsQXR0cmlidXRlLFxuICBPRGF0YU1vZGVsRXZlbnRUeXBlLFxufSBmcm9tICcuL29wdGlvbnMnO1xuaW1wb3J0IHsgUGFyc2VyT3B0aW9ucyB9IGZyb20gJy4uL3R5cGVzJztcblxuLy8gQGR5bmFtaWNcbmV4cG9ydCBjbGFzcyBPRGF0YU1vZGVsPFQ+IHtcbiAgLy8gUHJvcGVydGllc1xuICBzdGF0aWMgb3B0aW9uczogTW9kZWxPcHRpb25zO1xuICBzdGF0aWMgbWV0YTogT0RhdGFNb2RlbE9wdGlvbnM8YW55PjtcbiAgc3RhdGljIGJ1aWxkTWV0YTxUPih7XG4gICAgb3B0aW9ucyxcbiAgICBzY2hlbWEsXG4gIH06IHtcbiAgICBvcHRpb25zPzogTW9kZWxPcHRpb25zO1xuICAgIHNjaGVtYTogT0RhdGFTdHJ1Y3R1cmVkVHlwZTxUPjtcbiAgfSkge1xuICAgIGlmIChvcHRpb25zID09PSB1bmRlZmluZWQpIHtcbiAgICAgIGxldCBmaWVsZHMgPSBzY2hlbWFcbiAgICAgICAgLmZpZWxkcyh7IGluY2x1ZGVfbmF2aWdhdGlvbjogdHJ1ZSwgaW5jbHVkZV9wYXJlbnRzOiB0cnVlIH0pXG4gICAgICAgIC5yZWR1Y2UoKGFjYywgZmllbGQpID0+IHtcbiAgICAgICAgICBsZXQgbmFtZSA9IGZpZWxkLm5hbWU7XG4gICAgICAgICAgLy8gUHJldmVudCBjb2xsaXNpb24gd2l0aCByZXNlcnZlZCBrZXl3b3Jkc1xuICAgICAgICAgIHdoaWxlIChSRVNFUlZFRF9GSUVMRF9OQU1FUy5pbmNsdWRlcyhuYW1lKSkge1xuICAgICAgICAgICAgbmFtZSA9IG5hbWUgKyAnXyc7XG4gICAgICAgICAgfVxuICAgICAgICAgIHJldHVybiBPYmplY3QuYXNzaWduKGFjYywge1xuICAgICAgICAgICAgW25hbWVdOiB7XG4gICAgICAgICAgICAgIGZpZWxkOiBmaWVsZC5uYW1lLFxuICAgICAgICAgICAgICBkZWZhdWx0OiBmaWVsZC5kZWZhdWx0LFxuICAgICAgICAgICAgICByZXF1aXJlZDogIWZpZWxkLm51bGxhYmxlLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICB9KTtcbiAgICAgICAgfSwge30pO1xuICAgICAgb3B0aW9ucyA9IHsgZmllbGRzIH07XG4gICAgfVxuICAgIHRoaXMubWV0YSA9IG5ldyBPRGF0YU1vZGVsT3B0aW9uczxUPih7IG9wdGlvbnMsIHNjaGVtYSB9KTtcbiAgfVxuICAvLyBQYXJlbnRcbiAgX3BhcmVudDpcbiAgICB8IFtcbiAgICAgICAgT0RhdGFNb2RlbDxhbnk+IHwgT0RhdGFDb2xsZWN0aW9uPGFueSwgT0RhdGFNb2RlbDxhbnk+PixcbiAgICAgICAgT0RhdGFNb2RlbEZpZWxkPGFueT4gfCBudWxsXG4gICAgICBdXG4gICAgfCBudWxsID0gbnVsbDtcbiAgX3Jlc291cmNlOiBPRGF0YVJlc291cmNlPFQ+IHwgbnVsbCA9IG51bGw7XG4gIF9yZXNvdXJjZXM6IHtcbiAgICBwYXJlbnQ6XG4gICAgICB8IFtcbiAgICAgICAgICBPRGF0YU1vZGVsPGFueT4gfCBPRGF0YUNvbGxlY3Rpb248YW55LCBPRGF0YU1vZGVsPGFueT4+LFxuICAgICAgICAgIE9EYXRhTW9kZWxGaWVsZDxhbnk+IHwgbnVsbFxuICAgICAgICBdXG4gICAgICB8IG51bGw7XG4gICAgcmVzb3VyY2U6IE9EYXRhUmVzb3VyY2U8VD4gfCBudWxsO1xuICB9W10gPSBbXTtcbiAgX2F0dHJpYnV0ZXM6IE1hcDxzdHJpbmcsIE9EYXRhTW9kZWxBdHRyaWJ1dGU8YW55Pj4gPSBuZXcgTWFwPFxuICAgIHN0cmluZyxcbiAgICBPRGF0YU1vZGVsQXR0cmlidXRlPGFueT5cbiAgPigpO1xuICBfYW5ub3RhdGlvbnM6IE9EYXRhRW50aXR5QW5ub3RhdGlvbnM8VD4gfCBudWxsID0gbnVsbDtcbiAgX3Jlc2V0OiBib29sZWFuID0gZmFsc2U7XG4gIF9yZXBhcmVudDogYm9vbGVhbiA9IGZhbHNlO1xuICBfc2lsZW50OiBib29sZWFuID0gZmFsc2U7XG4gIF9tZXRhOiBPRGF0YU1vZGVsT3B0aW9uczxhbnk+O1xuICAvLyBFdmVudHNcbiAgZXZlbnRzJCA9IG5ldyBFdmVudEVtaXR0ZXI8T0RhdGFNb2RlbEV2ZW50PFQ+PigpO1xuXG4gIGNvbnN0cnVjdG9yKFxuICAgIGRhdGE6IFBhcnRpYWw8VD4gfCB7IFtuYW1lOiBzdHJpbmddOiBhbnkgfSA9IHt9LFxuICAgIHtcbiAgICAgIHBhcmVudCxcbiAgICAgIHJlc291cmNlLFxuICAgICAgYW5ub3RzLFxuICAgICAgcmVzZXQgPSBmYWxzZSxcbiAgICB9OiB7XG4gICAgICBwYXJlbnQ/OiBbXG4gICAgICAgIE9EYXRhTW9kZWw8YW55PiB8IE9EYXRhQ29sbGVjdGlvbjxhbnksIE9EYXRhTW9kZWw8YW55Pj4sXG4gICAgICAgIE9EYXRhTW9kZWxGaWVsZDxhbnk+IHwgbnVsbFxuICAgICAgXTtcbiAgICAgIHJlc291cmNlPzogT0RhdGFSZXNvdXJjZTxUPjtcbiAgICAgIGFubm90cz86IE9EYXRhRW50aXR5QW5ub3RhdGlvbnM8VD47XG4gICAgICByZXNldD86IGJvb2xlYW47XG4gICAgfSA9IHt9XG4gICkge1xuICAgIGNvbnN0IEtsYXNzID0gdGhpcy5jb25zdHJ1Y3RvciBhcyB0eXBlb2YgT0RhdGFNb2RlbDtcbiAgICBpZiAoS2xhc3MubWV0YSA9PT0gdW5kZWZpbmVkKVxuICAgICAgdGhyb3cgbmV3IEVycm9yKGBPRGF0YU1vZGVsOiBDYW4ndCBjcmVhdGUgbW9kZWwgd2l0aG91dCBtZXRhZGF0YWApO1xuICAgIHRoaXMuX21ldGEgPSBLbGFzcy5tZXRhO1xuICAgIHRoaXMuX21ldGEuYmluZCh0aGlzLCB7IHBhcmVudCwgcmVzb3VyY2UsIGFubm90cyB9KTtcblxuICAgIC8vIENsaWVudCBJZFxuICAgICg8YW55PnRoaXMpW3RoaXMuX21ldGEuY2lkXSA9XG4gICAgICAoPGFueT5kYXRhKVt0aGlzLl9tZXRhLmNpZF0gfHxcbiAgICAgIFN0cmluZ3MudW5pcXVlSWQoeyBwcmVmaXg6IGAke0tsYXNzLm1ldGEuc2NoZW1hLm5hbWUudG9Mb3dlckNhc2UoKX0tYCB9KTtcblxuICAgIGxldCBhdHRycyA9IHRoaXMuYW5ub3RzKCkuYXR0cmlidXRlcyhkYXRhLCAnZnVsbCcpO1xuICAgIGxldCBkZWZhdWx0cyA9IHRoaXMuZGVmYXVsdHMoKTtcblxuICAgIHRoaXMuYXNzaWduKE9iamVjdHMubWVyZ2UoZGVmYXVsdHMsIGF0dHJzIGFzIHsgW25hbWU6IHN0cmluZ106IGFueSB9KSwge1xuICAgICAgcmVzZXQsXG4gICAgfSk7XG4gIH1cblxuICAvLyNyZWdpb24gUmVzb3VyY2VzXG4gIHJlc291cmNlKCk6XG4gICAgfCBPRGF0YUVudGl0eVJlc291cmNlPFQ+XG4gICAgfCBPRGF0YU5hdmlnYXRpb25Qcm9wZXJ0eVJlc291cmNlPFQ+XG4gICAgfCBPRGF0YVByb3BlcnR5UmVzb3VyY2U8VD5cbiAgICB8IE9EYXRhU2luZ2xldG9uUmVzb3VyY2U8VD4ge1xuICAgIHJldHVybiBPRGF0YU1vZGVsT3B0aW9ucy5yZXNvdXJjZTxUPih0aGlzKSBhc1xuICAgICAgfCBPRGF0YUVudGl0eVJlc291cmNlPFQ+XG4gICAgICB8IE9EYXRhTmF2aWdhdGlvblByb3BlcnR5UmVzb3VyY2U8VD5cbiAgICAgIHwgT0RhdGFQcm9wZXJ0eVJlc291cmNlPFQ+XG4gICAgICB8IE9EYXRhU2luZ2xldG9uUmVzb3VyY2U8VD47XG4gIH1cblxuICBwdXNoUmVzb3VyY2UoXG4gICAgcmVzb3VyY2U6XG4gICAgICB8IE9EYXRhRW50aXR5UmVzb3VyY2U8VD5cbiAgICAgIHwgT0RhdGFOYXZpZ2F0aW9uUHJvcGVydHlSZXNvdXJjZTxUPlxuICAgICAgfCBPRGF0YVByb3BlcnR5UmVzb3VyY2U8VD5cbiAgICAgIHwgT0RhdGFTaW5nbGV0b25SZXNvdXJjZTxUPlxuICApIHtcbiAgICAvLyBQdXNoIGN1cnJlbnQgcGFyZW50IGFuZCByZXNvdXJjZVxuICAgIHRoaXMuX3Jlc291cmNlcy5wdXNoKHsgcGFyZW50OiB0aGlzLl9wYXJlbnQsIHJlc291cmNlOiB0aGlzLl9yZXNvdXJjZSB9KTtcbiAgICAvLyBSZXBsYWNlIHBhcmVudCBhbmQgcmVzb3VyY2VcbiAgICB0aGlzLl9wYXJlbnQgPSBudWxsO1xuICAgIHRoaXMuX3Jlc291cmNlID0gcmVzb3VyY2U7XG4gIH1cblxuICBwb3BSZXNvdXJjZSgpIHtcbiAgICAvLyBQb3AgcGFyZW50IGFuZCByZXNvdXJjZVxuICAgIGNvbnN0IHBvcCA9IHRoaXMuX3Jlc291cmNlcy5wb3AoKTtcbiAgICBpZiAocG9wICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGNvbnN0IGN1cnJlbnQgPSB7IHBhcmVudDogdGhpcy5fcGFyZW50LCByZXNvdXJjZTogdGhpcy5fcmVzb3VyY2UgfTtcbiAgICAgIHRoaXMuX3BhcmVudCA9IHBvcC5wYXJlbnQ7XG4gICAgICB0aGlzLl9yZXNvdXJjZSA9IHBvcC5yZXNvdXJjZTtcbiAgICAgIHJldHVybiBjdXJyZW50O1xuICAgIH1cbiAgICByZXR1cm4gdW5kZWZpbmVkO1xuICB9XG5cbiAgbmF2aWdhdGlvblByb3BlcnR5PE4+KFxuICAgIG5hbWU6IGtleW9mIFQgfCBzdHJpbmdcbiAgKTogT0RhdGFOYXZpZ2F0aW9uUHJvcGVydHlSZXNvdXJjZTxOPiB7XG4gICAgY29uc3QgZmllbGQgPSB0aGlzLl9tZXRhLmZpZWxkKG5hbWUpO1xuICAgIGlmIChmaWVsZCA9PT0gdW5kZWZpbmVkIHx8ICFmaWVsZC5uYXZpZ2F0aW9uKVxuICAgICAgdGhyb3cgRXJyb3IoXG4gICAgICAgIGBuYXZpZ2F0aW9uUHJvcGVydHk6IENhbid0IGZpbmQgbmF2aWdhdGlvbiBwcm9wZXJ0eSAke25hbWUgYXMgc3RyaW5nfWBcbiAgICAgICk7XG5cbiAgICBjb25zdCByZXNvdXJjZSA9IHRoaXMucmVzb3VyY2UoKTtcbiAgICBpZiAoIShyZXNvdXJjZSBpbnN0YW5jZW9mIE9EYXRhRW50aXR5UmVzb3VyY2UpIHx8ICFyZXNvdXJjZS5oYXNLZXkoKSlcbiAgICAgIHRocm93IEVycm9yKFxuICAgICAgICBcIm5hdmlnYXRpb25Qcm9wZXJ0eTogQ2FuJ3QgZ2V0IG5hdmlnYXRpb24gd2l0aG91dCBPRGF0YUVudGl0eVJlc291cmNlIHdpdGgga2V5XCJcbiAgICAgICk7XG5cbiAgICByZXR1cm4gZmllbGQucmVzb3VyY2VGYWN0b3J5PFQsIE4+KFxuICAgICAgcmVzb3VyY2VcbiAgICApIGFzIE9EYXRhTmF2aWdhdGlvblByb3BlcnR5UmVzb3VyY2U8Tj47XG4gIH1cblxuICBwcm9wZXJ0eTxOPihuYW1lOiBzdHJpbmcpOiBPRGF0YVByb3BlcnR5UmVzb3VyY2U8Tj4ge1xuICAgIGNvbnN0IGZpZWxkID0gdGhpcy5fbWV0YS5maWVsZChuYW1lKTtcbiAgICBpZiAoZmllbGQgPT09IHVuZGVmaW5lZCB8fCBmaWVsZC5uYXZpZ2F0aW9uKVxuICAgICAgdGhyb3cgRXJyb3IoYHByb3BlcnR5OiBDYW4ndCBmaW5kIHByb3BlcnR5ICR7bmFtZX1gKTtcblxuICAgIGNvbnN0IHJlc291cmNlID0gdGhpcy5yZXNvdXJjZSgpO1xuICAgIGlmICghKHJlc291cmNlIGluc3RhbmNlb2YgT0RhdGFFbnRpdHlSZXNvdXJjZSkgfHwgIXJlc291cmNlLmhhc0tleSgpKVxuICAgICAgdGhyb3cgRXJyb3IoXG4gICAgICAgIFwicHJvcGVydHk6IENhbid0IGdldCBwcm9wZXJ0eSB3aXRob3V0IE9EYXRhRW50aXR5UmVzb3VyY2Ugd2l0aCBrZXlcIlxuICAgICAgKTtcblxuICAgIHJldHVybiBmaWVsZC5yZXNvdXJjZUZhY3Rvcnk8VCwgTj4ocmVzb3VyY2UpIGFzIE9EYXRhUHJvcGVydHlSZXNvdXJjZTxOPjtcbiAgfVxuXG4gIGF0dGFjaChcbiAgICByZXNvdXJjZTpcbiAgICAgIHwgT0RhdGFFbnRpdHlSZXNvdXJjZTxUPlxuICAgICAgfCBPRGF0YU5hdmlnYXRpb25Qcm9wZXJ0eVJlc291cmNlPFQ+XG4gICAgICB8IE9EYXRhUHJvcGVydHlSZXNvdXJjZTxUPlxuICAgICAgfCBPRGF0YVNpbmdsZXRvblJlc291cmNlPFQ+XG4gICkge1xuICAgIHJldHVybiB0aGlzLl9tZXRhLmF0dGFjaCh0aGlzLCByZXNvdXJjZSk7XG4gIH1cbiAgLy8jZW5kcmVnaW9uXG5cbiAgc2NoZW1hKCkge1xuICAgIHJldHVybiB0aGlzLl9tZXRhLnNjaGVtYTtcbiAgfVxuXG4gIGFubm90cygpIHtcbiAgICByZXR1cm4gKFxuICAgICAgdGhpcy5fYW5ub3RhdGlvbnMgPz9cbiAgICAgIG5ldyBPRGF0YUVudGl0eUFubm90YXRpb25zPFQ+KE9EYXRhSGVscGVyW0RFRkFVTFRfVkVSU0lPTl0pXG4gICAgKTtcbiAgfVxuXG4gIGtleSh7XG4gICAgZmllbGRfbWFwcGluZyA9IGZhbHNlLFxuICAgIHJlc29sdmUgPSB0cnVlLFxuICB9OiB7IGZpZWxkX21hcHBpbmc/OiBib29sZWFuOyByZXNvbHZlPzogYm9vbGVhbiB9ID0ge30pOlxuICAgIHwgRW50aXR5S2V5PFQ+XG4gICAgfCB7IFtuYW1lOiBzdHJpbmddOiBhbnkgfVxuICAgIHwgdW5kZWZpbmVkIHtcbiAgICByZXR1cm4gdGhpcy5fbWV0YS5yZXNvbHZlS2V5KHRoaXMsIHsgZmllbGRfbWFwcGluZywgcmVzb2x2ZSB9KTtcbiAgfVxuXG4gIGlzT3Blbk1vZGVsKCkge1xuICAgIHJldHVybiB0aGlzLl9tZXRhLmlzT3BlblR5cGUoKTtcbiAgfVxuXG4gIGlzUGFyZW50T2YoXG4gICAgY2hpbGQ6IE9EYXRhTW9kZWw8YW55PiB8IE9EYXRhQ29sbGVjdGlvbjxhbnksIE9EYXRhTW9kZWw8YW55Pj5cbiAgKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIChcbiAgICAgIGNoaWxkICE9PSB0aGlzICYmXG4gICAgICBPRGF0YU1vZGVsT3B0aW9ucy5jaGFpbihjaGlsZCkuc29tZSgocCkgPT4gcFswXSA9PT0gdGhpcylcbiAgICApO1xuICB9XG5cbiAgcmVmZXJlbnRpYWwoXG4gICAgYXR0cjogT0RhdGFNb2RlbEF0dHJpYnV0ZTxhbnk+IHwgT0RhdGFNb2RlbEZpZWxkPGFueT4sXG4gICAge1xuICAgICAgZmllbGRfbWFwcGluZyA9IGZhbHNlLFxuICAgICAgcmVzb2x2ZSA9IHRydWUsXG4gICAgfTogeyBmaWVsZF9tYXBwaW5nPzogYm9vbGVhbjsgcmVzb2x2ZT86IGJvb2xlYW4gfSA9IHt9XG4gICk6IHsgW25hbWU6IHN0cmluZ106IGFueSB9IHwgbnVsbCB8IHVuZGVmaW5lZCB7XG4gICAgcmV0dXJuIHRoaXMuX21ldGEucmVzb2x2ZVJlZmVyZW50aWFsKHRoaXMsIGF0dHIsIHtcbiAgICAgIGZpZWxkX21hcHBpbmcsXG4gICAgICByZXNvbHZlLFxuICAgIH0pO1xuICB9XG5cbiAgcmVmZXJlbmNlZChcbiAgICBhdHRyOiBPRGF0YU1vZGVsQXR0cmlidXRlPGFueT4gfCBPRGF0YU1vZGVsRmllbGQ8YW55PixcbiAgICB7XG4gICAgICBmaWVsZF9tYXBwaW5nID0gZmFsc2UsXG4gICAgICByZXNvbHZlID0gdHJ1ZSxcbiAgICB9OiB7IGZpZWxkX21hcHBpbmc/OiBib29sZWFuOyByZXNvbHZlPzogYm9vbGVhbiB9ID0ge31cbiAgKTogeyBbbmFtZTogc3RyaW5nXTogYW55IH0gfCBudWxsIHwgdW5kZWZpbmVkIHtcbiAgICByZXR1cm4gdGhpcy5fbWV0YS5yZXNvbHZlUmVmZXJlbmNlZCh0aGlzLCBhdHRyLCB7XG4gICAgICBmaWVsZF9tYXBwaW5nLFxuICAgICAgcmVzb2x2ZSxcbiAgICB9KTtcbiAgfVxuXG4gIC8vIFZhbGlkYXRpb25cbiAgX2Vycm9ycz86IHsgW2tleTogc3RyaW5nXTogYW55IH07XG4gIHZhbGlkYXRlKHtcbiAgICBtZXRob2QsXG4gICAgbmF2aWdhdGlvbiA9IGZhbHNlLFxuICB9OiB7XG4gICAgbWV0aG9kPzogJ2NyZWF0ZScgfCAndXBkYXRlJyB8ICdtb2RpZnknO1xuICAgIG5hdmlnYXRpb24/OiBib29sZWFuO1xuICB9ID0ge30pIHtcbiAgICByZXR1cm4gdGhpcy5fbWV0YS52YWxpZGF0ZSh0aGlzLCB7IG1ldGhvZCwgbmF2aWdhdGlvbiB9KTtcbiAgfVxuXG4gIGlzVmFsaWQoe1xuICAgIG1ldGhvZCxcbiAgICBuYXZpZ2F0aW9uID0gZmFsc2UsXG4gIH06IHtcbiAgICBtZXRob2Q/OiAnY3JlYXRlJyB8ICd1cGRhdGUnIHwgJ21vZGlmeSc7XG4gICAgbmF2aWdhdGlvbj86IGJvb2xlYW47XG4gIH0gPSB7fSk6IGJvb2xlYW4ge1xuICAgIHRoaXMuX2Vycm9ycyA9IHRoaXMudmFsaWRhdGUoeyBtZXRob2QsIG5hdmlnYXRpb24gfSk7XG4gICAgaWYgKHRoaXMuX2Vycm9ycyAhPT0gdW5kZWZpbmVkKVxuICAgICAgdGhpcy5ldmVudHMkLmVtaXQoXG4gICAgICAgIG5ldyBPRGF0YU1vZGVsRXZlbnQoT0RhdGFNb2RlbEV2ZW50VHlwZS5JbnZhbGlkLCB7XG4gICAgICAgICAgbW9kZWw6IHRoaXMsXG4gICAgICAgICAgdmFsdWU6IHRoaXMuX2Vycm9ycyxcbiAgICAgICAgICBvcHRpb25zOiB7IG1ldGhvZCB9LFxuICAgICAgICB9KVxuICAgICAgKTtcbiAgICByZXR1cm4gdGhpcy5fZXJyb3JzID09PSB1bmRlZmluZWQ7XG4gIH1cblxuICBkZWZhdWx0cygpIHtcbiAgICByZXR1cm4gdGhpcy5fbWV0YS5kZWZhdWx0cygpIHx8IHt9O1xuICB9XG5cbiAgdG9FbnRpdHkoe1xuICAgIGNsaWVudF9pZCA9IGZhbHNlLFxuICAgIGluY2x1ZGVfbmF2aWdhdGlvbiA9IGZhbHNlLFxuICAgIGluY2x1ZGVfY29uY3VycmVuY3kgPSBmYWxzZSxcbiAgICBpbmNsdWRlX2NvbXB1dGVkID0gZmFsc2UsXG4gICAgaW5jbHVkZV9rZXkgPSB0cnVlLFxuICAgIGluY2x1ZGVfbm9uX2ZpZWxkID0gZmFsc2UsXG4gICAgY2hhbmdlc19vbmx5ID0gZmFsc2UsXG4gICAgZmllbGRfbWFwcGluZyA9IGZhbHNlLFxuICAgIGNoYWluID0gW10sXG4gIH06IHtcbiAgICBjbGllbnRfaWQ/OiBib29sZWFuO1xuICAgIGluY2x1ZGVfbmF2aWdhdGlvbj86IGJvb2xlYW47XG4gICAgaW5jbHVkZV9jb25jdXJyZW5jeT86IGJvb2xlYW47XG4gICAgaW5jbHVkZV9jb21wdXRlZD86IGJvb2xlYW47XG4gICAgaW5jbHVkZV9rZXk/OiBib29sZWFuO1xuICAgIGluY2x1ZGVfbm9uX2ZpZWxkPzogYm9vbGVhbjtcbiAgICBjaGFuZ2VzX29ubHk/OiBib29sZWFuO1xuICAgIGZpZWxkX21hcHBpbmc/OiBib29sZWFuO1xuICAgIGNoYWluPzogKE9EYXRhTW9kZWw8YW55PiB8IE9EYXRhQ29sbGVjdGlvbjxhbnksIE9EYXRhTW9kZWw8YW55Pj4pW107XG4gIH0gPSB7fSk6IFQgfCB7IFtuYW1lOiBzdHJpbmddOiBhbnkgfSB7XG4gICAgcmV0dXJuIHRoaXMuX21ldGEudG9FbnRpdHkodGhpcywge1xuICAgICAgY2xpZW50X2lkLFxuICAgICAgaW5jbHVkZV9uYXZpZ2F0aW9uLFxuICAgICAgaW5jbHVkZV9jb25jdXJyZW5jeSxcbiAgICAgIGluY2x1ZGVfY29tcHV0ZWQsXG4gICAgICBpbmNsdWRlX2tleSxcbiAgICAgIGluY2x1ZGVfbm9uX2ZpZWxkLFxuICAgICAgY2hhbmdlc19vbmx5LFxuICAgICAgZmllbGRfbWFwcGluZyxcbiAgICAgIGNoYWluLFxuICAgIH0pO1xuICB9XG5cbiAgdG9KU09OKCkge1xuICAgIHJldHVybiB0aGlzLnRvRW50aXR5KCk7XG4gIH1cblxuICBzZXQocGF0aDogc3RyaW5nIHwgc3RyaW5nW10sIHZhbHVlOiBhbnksIHsgdHlwZSB9OiB7IHR5cGU/OiBzdHJpbmcgfSA9IHt9KSB7XG4gICAgY29uc3QgcGF0aEFycmF5ID0gKFxuICAgICAgVHlwZXMuaXNBcnJheShwYXRoKSA/IHBhdGggOiAocGF0aCBhcyBzdHJpbmcpLm1hdGNoKC8oW15bLlxcXV0pKy9nKVxuICAgICkgYXMgYW55W107XG4gICAgaWYgKHBhdGhBcnJheS5sZW5ndGggPT09IDApIHJldHVybiB1bmRlZmluZWQ7XG4gICAgaWYgKHBhdGhBcnJheS5sZW5ndGggPiAxKSB7XG4gICAgICBjb25zdCBtb2RlbCA9ICg8YW55PnRoaXMpW3BhdGhBcnJheVswXV07XG4gICAgICByZXR1cm4gbW9kZWwuc2V0KHBhdGhBcnJheS5zbGljZSgxKSwgdmFsdWUsIHt9KTtcbiAgICB9XG4gICAgaWYgKHBhdGhBcnJheS5sZW5ndGggPT09IDEpIHtcbiAgICAgIHJldHVybiB0aGlzLl9tZXRhLnNldCh0aGlzLCBwYXRoQXJyYXlbMF0sIHZhbHVlLCB7IHR5cGUgfSk7XG4gICAgfVxuICB9XG5cbiAgZ2V0KHBhdGg6IHN0cmluZyB8IHN0cmluZ1tdKTogYW55IHtcbiAgICBjb25zdCBwYXRoQXJyYXkgPSAoXG4gICAgICBUeXBlcy5pc0FycmF5KHBhdGgpID8gcGF0aCA6IChwYXRoIGFzIHN0cmluZykubWF0Y2goLyhbXlsuXFxdXSkrL2cpXG4gICAgKSBhcyBhbnlbXTtcbiAgICBpZiAocGF0aEFycmF5Lmxlbmd0aCA9PT0gMCkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICBjb25zdCB2YWx1ZSA9IHRoaXMuX21ldGEuZ2V0PGFueT4odGhpcywgcGF0aEFycmF5WzBdKTtcbiAgICBpZiAoXG4gICAgICBwYXRoQXJyYXkubGVuZ3RoID4gMSAmJlxuICAgICAgKHZhbHVlIGluc3RhbmNlb2YgT0RhdGFNb2RlbCB8fCB2YWx1ZSBpbnN0YW5jZW9mIE9EYXRhQ29sbGVjdGlvbilcbiAgICApIHtcbiAgICAgIHJldHVybiB2YWx1ZS5nZXQocGF0aEFycmF5LnNsaWNlKDEpKTtcbiAgICB9XG4gICAgcmV0dXJuIHZhbHVlO1xuICB9XG5cbiAgaGFzKHBhdGg6IHN0cmluZyB8IHN0cmluZ1tdKTogYm9vbGVhbiB7XG4gICAgY29uc3QgcGF0aEFycmF5ID0gKFxuICAgICAgVHlwZXMuaXNBcnJheShwYXRoKSA/IHBhdGggOiAocGF0aCBhcyBzdHJpbmcpLm1hdGNoKC8oW15bLlxcXV0pKy9nKVxuICAgICkgYXMgYW55W107XG4gICAgaWYgKHBhdGhBcnJheS5sZW5ndGggPT09IDApIHJldHVybiBmYWxzZTtcbiAgICBjb25zdCB2YWx1ZSA9IHRoaXMuX21ldGEuZ2V0PGFueT4odGhpcywgcGF0aEFycmF5WzBdKTtcbiAgICBpZiAoXG4gICAgICBwYXRoQXJyYXkubGVuZ3RoID4gMSAmJlxuICAgICAgKHZhbHVlIGluc3RhbmNlb2YgT0RhdGFNb2RlbCB8fCB2YWx1ZSBpbnN0YW5jZW9mIE9EYXRhQ29sbGVjdGlvbilcbiAgICApIHtcbiAgICAgIHJldHVybiB2YWx1ZS5oYXMocGF0aEFycmF5LnNsaWNlKDEpKTtcbiAgICB9XG4gICAgcmV0dXJuIHZhbHVlICE9PSB1bmRlZmluZWQ7XG4gIH1cblxuICByZXNldCh7XG4gICAgcGF0aCxcbiAgICBzaWxlbnQgPSBmYWxzZSxcbiAgfTogeyBwYXRoPzogc3RyaW5nIHwgc3RyaW5nW107IHNpbGVudD86IGJvb2xlYW4gfSA9IHt9KSB7XG4gICAgY29uc3QgcGF0aEFycmF5OiBzdHJpbmdbXSA9IChcbiAgICAgIHBhdGggPT09IHVuZGVmaW5lZFxuICAgICAgICA/IFtdXG4gICAgICAgIDogVHlwZXMuaXNBcnJheShwYXRoKVxuICAgICAgICA/IHBhdGhcbiAgICAgICAgOiAocGF0aCBhcyBzdHJpbmcpLm1hdGNoKC8oW15bLlxcXV0pKy9nKVxuICAgICkgYXMgYW55W107XG4gICAgY29uc3QgbmFtZSA9IHBhdGhBcnJheVswXTtcbiAgICBjb25zdCB2YWx1ZSA9IG5hbWUgIT09IHVuZGVmaW5lZCA/ICg8YW55PnRoaXMpW25hbWVdIDogdW5kZWZpbmVkO1xuICAgIGlmIChcbiAgICAgIE9EYXRhTW9kZWxPcHRpb25zLmlzTW9kZWwodmFsdWUpIHx8XG4gICAgICBPRGF0YU1vZGVsT3B0aW9ucy5pc0NvbGxlY3Rpb24odmFsdWUpXG4gICAgKSB7XG4gICAgICB2YWx1ZS5yZXNldCh7IHBhdGg6IHBhdGhBcnJheS5zbGljZSgxKSwgc2lsZW50IH0pO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLl9tZXRhLnJlc2V0KHRoaXMsIHsgbmFtZTogcGF0aEFycmF5WzBdLCBzaWxlbnQgfSk7XG4gICAgfVxuICB9XG5cbiAgY2xlYXIoeyBzaWxlbnQgPSBmYWxzZSB9OiB7IHNpbGVudD86IGJvb2xlYW4gfSA9IHt9KSB7XG4gICAgdGhpcy5fYXR0cmlidXRlcy5jbGVhcigpO1xuICAgIC8vdGhpcy5fY2hhbmdlcy5jbGVhcigpO1xuICAgIC8vdGhpcy5fcmVsYXRpb25zLmNsZWFyKCk7XG4gICAgaWYgKCFzaWxlbnQpIHtcbiAgICAgIHRoaXMuZXZlbnRzJC5lbWl0KFxuICAgICAgICBuZXcgT0RhdGFNb2RlbEV2ZW50KE9EYXRhTW9kZWxFdmVudFR5cGUuVXBkYXRlLCB7XG4gICAgICAgICAgbW9kZWw6IHRoaXMsXG4gICAgICAgIH0pXG4gICAgICApO1xuICAgIH1cbiAgfVxuXG4gIGFzc2lnbihcbiAgICBlbnRpdHk6IFBhcnRpYWw8VD4gfCB7IFtuYW1lOiBzdHJpbmddOiBhbnkgfSxcbiAgICB7XG4gICAgICByZXNldCA9IGZhbHNlLFxuICAgICAgcmVwYXJlbnQgPSBmYWxzZSxcbiAgICAgIHNpbGVudCA9IGZhbHNlLFxuICAgIH06IHtcbiAgICAgIHJlc2V0PzogYm9vbGVhbjtcbiAgICAgIHJlcGFyZW50PzogYm9vbGVhbjtcbiAgICAgIHNpbGVudD86IGJvb2xlYW47XG4gICAgfSA9IHt9XG4gICkge1xuICAgIHJldHVybiB0aGlzLl9tZXRhLmFzc2lnbih0aGlzLCBlbnRpdHksIHsgcmVzZXQsIHNpbGVudCwgcmVwYXJlbnQgfSk7XG4gIH1cblxuICBjbG9uZTxNIGV4dGVuZHMgT0RhdGFNb2RlbDxUPj4oKSB7XG4gICAgbGV0IEN0b3IgPSA8dHlwZW9mIE9EYXRhTW9kZWw+dGhpcy5jb25zdHJ1Y3RvcjtcbiAgICByZXR1cm4gbmV3IEN0b3IodGhpcy50b0VudGl0eShJTkNMVURFX1NIQUxMT1cpLCB7XG4gICAgICByZXNvdXJjZTogdGhpcy5yZXNvdXJjZSgpIGFzIE9EYXRhUmVzb3VyY2U8VD4sXG4gICAgICBhbm5vdHM6IHRoaXMuYW5ub3RzKCksXG4gICAgfSkgYXMgTTtcbiAgfVxuXG4gIHByaXZhdGUgX3JlcXVlc3Qob2JzJDogT2JzZXJ2YWJsZTxPRGF0YUVudGl0eTxhbnk+Pik6IE9ic2VydmFibGU8dGhpcz4ge1xuICAgIHRoaXMuZXZlbnRzJC5lbWl0KFxuICAgICAgbmV3IE9EYXRhTW9kZWxFdmVudChPRGF0YU1vZGVsRXZlbnRUeXBlLlJlcXVlc3QsIHtcbiAgICAgICAgbW9kZWw6IHRoaXMsXG4gICAgICAgIG9wdGlvbnM6IHsgb2JzZXJ2YWJsZTogb2JzJCB9LFxuICAgICAgfSlcbiAgICApO1xuICAgIHJldHVybiBvYnMkLnBpcGUoXG4gICAgICBtYXAoKHsgZW50aXR5LCBhbm5vdHMgfSkgPT4ge1xuICAgICAgICB0aGlzLl9hbm5vdGF0aW9ucyA9IGFubm90cztcbiAgICAgICAgdGhpcy5hc3NpZ24oYW5ub3RzLmF0dHJpYnV0ZXMoZW50aXR5IHx8IHt9LCAnZnVsbCcpLCB7XG4gICAgICAgICAgcmVzZXQ6IHRydWUsXG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLmV2ZW50cyQuZW1pdChcbiAgICAgICAgICBuZXcgT0RhdGFNb2RlbEV2ZW50KE9EYXRhTW9kZWxFdmVudFR5cGUuU3luYywge1xuICAgICAgICAgICAgbW9kZWw6IHRoaXMsXG4gICAgICAgICAgICBvcHRpb25zOiB7IGVudGl0eSwgYW5ub3RzIH0sXG4gICAgICAgICAgfSlcbiAgICAgICAgKTtcbiAgICAgICAgcmV0dXJuIHRoaXM7XG4gICAgICB9KVxuICAgICk7XG4gIH1cblxuICBmZXRjaCh7XG4gICAgLi4ub3B0aW9uc1xuICB9OiBPRGF0YU9wdGlvbnMgJiB7XG4gICAgb3B0aW9ucz86IE9EYXRhT3B0aW9ucztcbiAgfSA9IHt9KTogT2JzZXJ2YWJsZTx0aGlzPiB7XG4gICAgbGV0IHJlc291cmNlID0gdGhpcy5yZXNvdXJjZSgpO1xuICAgIGlmIChyZXNvdXJjZSA9PT0gdW5kZWZpbmVkKVxuICAgICAgcmV0dXJuIHRocm93RXJyb3IoKCkgPT4gbmV3IEVycm9yKCdmZXRjaDogUmVzb3VyY2UgaXMgdW5kZWZpbmVkJykpO1xuXG4gICAgbGV0IG9icyQ6IE9ic2VydmFibGU8T0RhdGFFbnRpdHk8VD4+O1xuICAgIGlmIChyZXNvdXJjZSBpbnN0YW5jZW9mIE9EYXRhRW50aXR5UmVzb3VyY2UpIHtcbiAgICAgIG9icyQgPSByZXNvdXJjZS5mZXRjaChvcHRpb25zKTtcbiAgICB9IGVsc2UgaWYgKHJlc291cmNlIGluc3RhbmNlb2YgT0RhdGFOYXZpZ2F0aW9uUHJvcGVydHlSZXNvdXJjZSkge1xuICAgICAgb2JzJCA9IHJlc291cmNlLmZldGNoKHsgcmVzcG9uc2VUeXBlOiAnZW50aXR5JywgLi4ub3B0aW9ucyB9KTtcbiAgICB9IGVsc2Uge1xuICAgICAgb2JzJCA9IChyZXNvdXJjZSBhcyBPRGF0YVByb3BlcnR5UmVzb3VyY2U8VD4pLmZldGNoKHtcbiAgICAgICAgcmVzcG9uc2VUeXBlOiAnZW50aXR5JyxcbiAgICAgICAgLi4ub3B0aW9ucyxcbiAgICAgIH0pO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcy5fcmVxdWVzdChvYnMkKTtcbiAgfVxuXG4gIHNhdmUoe1xuICAgIG1ldGhvZCxcbiAgICBuYXZpZ2F0aW9uID0gZmFsc2UsXG4gICAgdmFsaWRhdGUgPSB0cnVlLFxuICAgIC4uLm9wdGlvbnNcbiAgfTogT0RhdGFPcHRpb25zICYge1xuICAgIG1ldGhvZD86ICdjcmVhdGUnIHwgJ3VwZGF0ZScgfCAnbW9kaWZ5JztcbiAgICBuYXZpZ2F0aW9uPzogYm9vbGVhbjtcbiAgICB2YWxpZGF0ZT86IGJvb2xlYW47XG4gICAgb3B0aW9ucz86IE9EYXRhT3B0aW9ucztcbiAgfSA9IHt9KTogT2JzZXJ2YWJsZTx0aGlzPiB7XG4gICAgbGV0IHJlc291cmNlID0gdGhpcy5yZXNvdXJjZSgpO1xuICAgIGlmIChyZXNvdXJjZSA9PT0gdW5kZWZpbmVkKVxuICAgICAgcmV0dXJuIHRocm93RXJyb3IoKCkgPT4gbmV3IEVycm9yKCdzYXZlOiBSZXNvdXJjZSBpcyB1bmRlZmluZWQnKSk7XG4gICAgaWYgKFxuICAgICAgIShcbiAgICAgICAgcmVzb3VyY2UgaW5zdGFuY2VvZiBPRGF0YUVudGl0eVJlc291cmNlIHx8XG4gICAgICAgIHJlc291cmNlIGluc3RhbmNlb2YgT0RhdGFOYXZpZ2F0aW9uUHJvcGVydHlSZXNvdXJjZVxuICAgICAgKVxuICAgIClcbiAgICAgIHJldHVybiB0aHJvd0Vycm9yKFxuICAgICAgICAoKSA9PlxuICAgICAgICAgIG5ldyBFcnJvcihcbiAgICAgICAgICAgICdzYXZlOiBSZXNvdXJjZSB0eXBlIE9EYXRhRW50aXR5UmVzb3VyY2UvT0RhdGFOYXZpZ2F0aW9uUHJvcGVydHlSZXNvdXJjZSBuZWVkZWQnXG4gICAgICAgICAgKVxuICAgICAgKTtcblxuICAgIC8vIFJlc29sdmUgbWV0aG9kIGFuZCByZXNvdXJjZSBrZXlcbiAgICBpZiAobWV0aG9kID09PSB1bmRlZmluZWQgJiYgdGhpcy5zY2hlbWEoKS5pc0NvbXBvdW5kS2V5KCkpXG4gICAgICByZXR1cm4gdGhyb3dFcnJvcihcbiAgICAgICAgKCkgPT5cbiAgICAgICAgICBuZXcgRXJyb3IoXG4gICAgICAgICAgICAnc2F2ZTogQ29tcG9zaXRlIGtleSByZXF1aXJlIGEgc3BlY2lmaWMgbWV0aG9kLCB1c2UgY3JlYXRlL3VwZGF0ZS9tb2RpZnknXG4gICAgICAgICAgKVxuICAgICAgKTtcbiAgICBtZXRob2QgPSBtZXRob2QgfHwgKCFyZXNvdXJjZS5oYXNLZXkoKSA/ICdjcmVhdGUnIDogJ3VwZGF0ZScpO1xuICAgIGlmIChcbiAgICAgIHJlc291cmNlIGluc3RhbmNlb2YgT0RhdGFFbnRpdHlSZXNvdXJjZSAmJlxuICAgICAgKG1ldGhvZCA9PT0gJ3VwZGF0ZScgfHwgbWV0aG9kID09PSAnbW9kaWZ5JykgJiZcbiAgICAgICFyZXNvdXJjZS5oYXNLZXkoKVxuICAgIClcbiAgICAgIHJldHVybiB0aHJvd0Vycm9yKFxuICAgICAgICAoKSA9PiBuZXcgRXJyb3IoJ3NhdmU6IFVwZGF0ZS9QYXRjaCByZXF1aXJlIGVudGl0eSBrZXknKVxuICAgICAgKTtcbiAgICBpZiAoXG4gICAgICByZXNvdXJjZSBpbnN0YW5jZW9mIE9EYXRhTmF2aWdhdGlvblByb3BlcnR5UmVzb3VyY2UgfHxcbiAgICAgIG1ldGhvZCA9PT0gJ2NyZWF0ZSdcbiAgICApXG4gICAgICByZXNvdXJjZS5jbGVhcktleSgpO1xuXG4gICAgaWYgKHZhbGlkYXRlICYmICF0aGlzLmlzVmFsaWQoeyBtZXRob2QsIG5hdmlnYXRpb24gfSkpIHtcbiAgICAgIHJldHVybiB0aHJvd0Vycm9yKCgpID0+IG5ldyBFcnJvcignc2F2ZTogVmFsaWRhdGlvbiBlcnJvcnMnKSk7XG4gICAgfVxuICAgIGNvbnN0IF9lbnRpdHkgPSB0aGlzLnRvRW50aXR5KHtcbiAgICAgIGNoYW5nZXNfb25seTogbWV0aG9kID09PSAnbW9kaWZ5JyxcbiAgICAgIGZpZWxkX21hcHBpbmc6IHRydWUsXG4gICAgICBpbmNsdWRlX2NvbmN1cnJlbmN5OiB0cnVlLFxuICAgICAgaW5jbHVkZV9uYXZpZ2F0aW9uOiBuYXZpZ2F0aW9uLFxuICAgIH0pIGFzIFQ7XG4gICAgcmV0dXJuIHRoaXMuX3JlcXVlc3QoXG4gICAgICAobWV0aG9kID09PSAnY3JlYXRlJ1xuICAgICAgICA/IHJlc291cmNlLmNyZWF0ZShfZW50aXR5LCBvcHRpb25zKVxuICAgICAgICA6IG1ldGhvZCA9PT0gJ21vZGlmeSdcbiAgICAgICAgPyByZXNvdXJjZS5tb2RpZnkoX2VudGl0eSwgeyBldGFnOiB0aGlzLmFubm90cygpLmV0YWcsIC4uLm9wdGlvbnMgfSlcbiAgICAgICAgOiByZXNvdXJjZS51cGRhdGUoX2VudGl0eSwgeyBldGFnOiB0aGlzLmFubm90cygpLmV0YWcsIC4uLm9wdGlvbnMgfSlcbiAgICAgICkucGlwZShcbiAgICAgICAgbWFwKCh7IGVudGl0eSwgYW5ub3RzIH0pID0+ICh7IGVudGl0eTogZW50aXR5IHx8IF9lbnRpdHksIGFubm90cyB9KSlcbiAgICAgIClcbiAgICApO1xuICB9XG5cbiAgZGVzdHJveSh7XG4gICAgLi4ub3B0aW9uc1xuICB9OiBPRGF0YU9wdGlvbnMgJiB7XG4gICAgb3B0aW9ucz86IE9EYXRhT3B0aW9ucztcbiAgfSA9IHt9KTogT2JzZXJ2YWJsZTx0aGlzPiB7XG4gICAgbGV0IHJlc291cmNlID0gdGhpcy5yZXNvdXJjZSgpO1xuICAgIGlmIChyZXNvdXJjZSA9PT0gdW5kZWZpbmVkKVxuICAgICAgcmV0dXJuIHRocm93RXJyb3IoKCkgPT4gbmV3IEVycm9yKCdkZXN0cm95OiBSZXNvdXJjZSBpcyB1bmRlZmluZWQnKSk7XG4gICAgaWYgKFxuICAgICAgIShcbiAgICAgICAgcmVzb3VyY2UgaW5zdGFuY2VvZiBPRGF0YUVudGl0eVJlc291cmNlIHx8XG4gICAgICAgIHJlc291cmNlIGluc3RhbmNlb2YgT0RhdGFOYXZpZ2F0aW9uUHJvcGVydHlSZXNvdXJjZVxuICAgICAgKVxuICAgIClcbiAgICAgIHJldHVybiB0aHJvd0Vycm9yKFxuICAgICAgICAoKSA9PlxuICAgICAgICAgIG5ldyBFcnJvcihcbiAgICAgICAgICAgICdkZXN0cm95OiBSZXNvdXJjZSB0eXBlIE9EYXRhRW50aXR5UmVzb3VyY2UvT0RhdGFOYXZpZ2F0aW9uUHJvcGVydHlSZXNvdXJjZSBuZWVkZWQnXG4gICAgICAgICAgKVxuICAgICAgKTtcbiAgICBpZiAoIXJlc291cmNlLmhhc0tleSgpKVxuICAgICAgcmV0dXJuIHRocm93RXJyb3IoXG4gICAgICAgICgpID0+IG5ldyBFcnJvcihcImRlc3Ryb3k6IENhbid0IGRlc3Ryb3kgbW9kZWwgd2l0aG91dCBrZXlcIilcbiAgICAgICk7XG5cbiAgICBjb25zdCBfZW50aXR5ID0gdGhpcy50b0VudGl0eSh7IGZpZWxkX21hcHBpbmc6IHRydWUgfSkgYXMgVDtcbiAgICBjb25zdCBvYnMkID0gcmVzb3VyY2VcbiAgICAgIC5kZXN0cm95KHsgZXRhZzogdGhpcy5hbm5vdHMoKS5ldGFnLCAuLi5vcHRpb25zIH0pXG4gICAgICAucGlwZShcbiAgICAgICAgbWFwKCh7IGVudGl0eSwgYW5ub3RzIH0pID0+ICh7IGVudGl0eTogZW50aXR5IHx8IF9lbnRpdHksIGFubm90cyB9KSlcbiAgICAgICk7XG4gICAgcmV0dXJuIHRoaXMuX3JlcXVlc3Qob2JzJCkucGlwZShcbiAgICAgIHRhcCgoKSA9PlxuICAgICAgICB0aGlzLmV2ZW50cyQuZW1pdChcbiAgICAgICAgICBuZXcgT0RhdGFNb2RlbEV2ZW50KE9EYXRhTW9kZWxFdmVudFR5cGUuRGVzdHJveSwgeyBtb2RlbDogdGhpcyB9KVxuICAgICAgICApXG4gICAgICApXG4gICAgKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDcmVhdGUgYW4gZXhlY3V0aW9uIGNvbnRleHQgZm9yIGNoYW5nZSB0aGUgaW50ZXJuYWwgcXVlcnkgb2YgYSByZXNvdXJjZVxuICAgKiBAcGFyYW0gY3R4IEZ1bmN0aW9uIHRvIGV4ZWN1dGVcbiAgICovXG4gIHF1ZXJ5KFxuICAgIGN0eDogKHE6IE9EYXRhUXVlcnlPcHRpb25zSGFuZGxlcjxUPiwgcz86IE9EYXRhU3RydWN0dXJlZFR5cGU8VD4pID0+IHZvaWRcbiAgKSB7XG4gICAgcmV0dXJuIHRoaXMuX21ldGEucXVlcnkodGhpcywgdGhpcy5yZXNvdXJjZSgpLCBjdHgpIGFzIHRoaXM7XG4gIH1cblxuICAvKipcbiAgICogUGVyZm9ybSBhIGNoZWNrIG9uIHRoZSBpbnRlcm5hbCBzdGF0ZSBvZiB0aGUgbW9kZWwgYW5kIHJldHVybiB0cnVlIGlmIHRoZSBtb2RlbCBpcyBjaGFuZ2VkLlxuICAgKiBAcGFyYW0gaW5jbHVkZV9uYXZpZ2F0aW9uIENoZWNrIGluIG5hdmlnYXRpb24gcHJvcGVydGllc1xuICAgKiBAcmV0dXJucyB0cnVlIGlmIHRoZSBtb2RlbCBoYXMgY2hhbmdlZCwgZmFsc2Ugb3RoZXJ3aXNlXG4gICAqL1xuICBoYXNDaGFuZ2VkKHtcbiAgICBpbmNsdWRlX25hdmlnYXRpb24gPSBmYWxzZSxcbiAgfTogeyBpbmNsdWRlX25hdmlnYXRpb24/OiBib29sZWFuIH0gPSB7fSkge1xuICAgIHJldHVybiB0aGlzLl9tZXRhLmhhc0NoYW5nZWQodGhpcywgeyBpbmNsdWRlX25hdmlnYXRpb24gfSk7XG4gIH1cblxuICBlbmNvZGU8RT4obmFtZToga2V5b2YgVCwgb3B0aW9ucz86IFBhcnNlck9wdGlvbnMpIHtcbiAgICBsZXQgdmFsdWUgPSAoPGFueT50aGlzKVtuYW1lXTtcbiAgICBpZiAodmFsdWUgPT09IHVuZGVmaW5lZCkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICBsZXQgZmllbGQgPSB0aGlzLl9tZXRhLmZpZWxkPEU+KG5hbWUpO1xuICAgIHJldHVybiBmaWVsZCAhPT0gdW5kZWZpbmVkID8gZmllbGQuZW5jb2RlKHZhbHVlLCBvcHRpb25zKSA6IHZhbHVlO1xuICB9XG5cbiAgaXNOZXcoKSB7XG4gICAgcmV0dXJuICF0aGlzLl9tZXRhLmhhc0tleSh0aGlzKTtcbiAgfVxuXG4gIHdpdGhSZXNvdXJjZTxSPihyZXNvdXJjZTogYW55LCBjdHg6IChtb2RlbDogdGhpcykgPT4gUik6IFIge1xuICAgIHJldHVybiB0aGlzLl9tZXRhLndpdGhSZXNvdXJjZSh0aGlzLCByZXNvdXJjZSwgY3R4KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDcmVhdGUgYW4gZXhlY3V0aW9uIGNvbnRleHQgZm9yIGEgZ2l2ZW4gZnVuY3Rpb24sIHdoZXJlIHRoZSBtb2RlbCBpcyBib3VuZCB0byBpdHMgZW50aXR5IGVuZHBvaW50XG4gICAqIEBwYXJhbSBjdHggQ29udGV4dCBmdW5jdGlvblxuICAgKiBAcmV0dXJucyBUaGUgcmVzdWx0IG9mIHRoZSBjb250ZXh0XG4gICAqL1xuICBhc0VudGl0eTxSPihjdHg6IChtb2RlbDogdGhpcykgPT4gUik6IFIge1xuICAgIHJldHVybiB0aGlzLl9tZXRhLmFzRW50aXR5KHRoaXMsIGN0eCk7XG4gIH1cblxuICAvLyNyZWdpb24gQ2FsbGFibGVzXG4gIGNhbGxGdW5jdGlvbjxQLCBSPihcbiAgICBuYW1lOiBzdHJpbmcsXG4gICAgcGFyYW1zOiBQIHwgbnVsbCxcbiAgICByZXNwb25zZVR5cGU6XG4gICAgICB8ICdwcm9wZXJ0eSdcbiAgICAgIHwgJ21vZGVsJ1xuICAgICAgfCAnY29sbGVjdGlvbidcbiAgICAgIHwgJ25vbmUnXG4gICAgICB8ICdibG9iJ1xuICAgICAgfCAnYXJyYXlidWZmZXInLFxuICAgIHsgLi4ub3B0aW9ucyB9OiB7fSAmIE9EYXRhRnVuY3Rpb25PcHRpb25zPFI+ID0ge31cbiAgKTogT2JzZXJ2YWJsZTxcbiAgICB8IFJcbiAgICB8IE9EYXRhTW9kZWw8Uj5cbiAgICB8IE9EYXRhQ29sbGVjdGlvbjxSLCBPRGF0YU1vZGVsPFI+PlxuICAgIHwgbnVsbFxuICAgIHwgQmxvYlxuICAgIHwgQXJyYXlCdWZmZXJcbiAgPiB7XG4gICAgY29uc3QgcmVzb3VyY2UgPSB0aGlzLnJlc291cmNlKCk7XG4gICAgaWYgKCEocmVzb3VyY2UgaW5zdGFuY2VvZiBPRGF0YUVudGl0eVJlc291cmNlKSB8fCAhcmVzb3VyY2UuaGFzS2V5KCkpXG4gICAgICByZXR1cm4gdGhyb3dFcnJvcihcbiAgICAgICAgKCkgPT5cbiAgICAgICAgICBuZXcgRXJyb3IoXG4gICAgICAgICAgICBcImNhbGxGdW5jdGlvbjogQ2FuJ3QgY2FsbCBmdW5jdGlvbiB3aXRob3V0IE9EYXRhRW50aXR5UmVzb3VyY2Ugd2l0aCBrZXlcIlxuICAgICAgICAgIClcbiAgICAgICk7XG5cbiAgICBjb25zdCBmdW5jID0gcmVzb3VyY2UuZnVuY3Rpb248UCwgUj4obmFtZSkucXVlcnkoKHEpID0+IHEuYXBwbHkob3B0aW9ucykpO1xuICAgIHN3aXRjaCAocmVzcG9uc2VUeXBlKSB7XG4gICAgICBjYXNlICdwcm9wZXJ0eSc6XG4gICAgICAgIHJldHVybiBmdW5jLmNhbGxQcm9wZXJ0eShwYXJhbXMsIG9wdGlvbnMpO1xuICAgICAgY2FzZSAnbW9kZWwnOlxuICAgICAgICByZXR1cm4gZnVuYy5jYWxsTW9kZWwocGFyYW1zLCBvcHRpb25zKTtcbiAgICAgIGNhc2UgJ2NvbGxlY3Rpb24nOlxuICAgICAgICByZXR1cm4gZnVuYy5jYWxsQ29sbGVjdGlvbihwYXJhbXMsIG9wdGlvbnMpO1xuICAgICAgY2FzZSAnYmxvYic6XG4gICAgICAgIHJldHVybiBmdW5jLmNhbGxCbG9iKHBhcmFtcywgb3B0aW9ucyk7XG4gICAgICBjYXNlICdhcnJheWJ1ZmZlcic6XG4gICAgICAgIHJldHVybiBmdW5jLmNhbGxBcnJheWJ1ZmZlcihwYXJhbXMsIG9wdGlvbnMpO1xuICAgICAgZGVmYXVsdDpcbiAgICAgICAgcmV0dXJuIGZ1bmMuY2FsbChwYXJhbXMsIHsgcmVzcG9uc2VUeXBlLCAuLi5vcHRpb25zIH0pO1xuICAgIH1cbiAgfVxuXG4gIGNhbGxBY3Rpb248UCwgUj4oXG4gICAgbmFtZTogc3RyaW5nLFxuICAgIHBhcmFtczogUCB8IG51bGwsXG4gICAgcmVzcG9uc2VUeXBlPzpcbiAgICAgIHwgJ3Byb3BlcnR5J1xuICAgICAgfCAnbW9kZWwnXG4gICAgICB8ICdjb2xsZWN0aW9uJ1xuICAgICAgfCAnbm9uZSdcbiAgICAgIHwgJ2Jsb2InXG4gICAgICB8ICdhcnJheWJ1ZmZlcicsXG4gICAgeyAuLi5vcHRpb25zIH06IHt9ICYgT0RhdGFBY3Rpb25PcHRpb25zPFI+ID0ge31cbiAgKTogT2JzZXJ2YWJsZTxcbiAgICB8IFJcbiAgICB8IE9EYXRhTW9kZWw8Uj5cbiAgICB8IE9EYXRhQ29sbGVjdGlvbjxSLCBPRGF0YU1vZGVsPFI+PlxuICAgIHwgbnVsbFxuICAgIHwgQmxvYlxuICAgIHwgQXJyYXlCdWZmZXJcbiAgPiB7XG4gICAgY29uc3QgcmVzb3VyY2UgPSB0aGlzLnJlc291cmNlKCk7XG4gICAgaWYgKCEocmVzb3VyY2UgaW5zdGFuY2VvZiBPRGF0YUVudGl0eVJlc291cmNlKSB8fCAhcmVzb3VyY2UuaGFzS2V5KCkpXG4gICAgICByZXR1cm4gdGhyb3dFcnJvcihcbiAgICAgICAgKCkgPT5cbiAgICAgICAgICBuZXcgRXJyb3IoXG4gICAgICAgICAgICBcImNhbGxBY3Rpb246IENhbid0IGNhbGwgYWN0aW9uIHdpdGhvdXQgT0RhdGFFbnRpdHlSZXNvdXJjZSB3aXRoIGtleVwiXG4gICAgICAgICAgKVxuICAgICAgKTtcblxuICAgIGNvbnN0IGFjdGlvbiA9IHJlc291cmNlLmFjdGlvbjxQLCBSPihuYW1lKS5xdWVyeSgocSkgPT4gcS5hcHBseShvcHRpb25zKSk7XG4gICAgc3dpdGNoIChyZXNwb25zZVR5cGUpIHtcbiAgICAgIGNhc2UgJ3Byb3BlcnR5JzpcbiAgICAgICAgcmV0dXJuIGFjdGlvbi5jYWxsUHJvcGVydHkocGFyYW1zLCBvcHRpb25zKTtcbiAgICAgIGNhc2UgJ21vZGVsJzpcbiAgICAgICAgcmV0dXJuIGFjdGlvbi5jYWxsTW9kZWwocGFyYW1zLCBvcHRpb25zKTtcbiAgICAgIGNhc2UgJ2NvbGxlY3Rpb24nOlxuICAgICAgICByZXR1cm4gYWN0aW9uLmNhbGxDb2xsZWN0aW9uKHBhcmFtcywgb3B0aW9ucyk7XG4gICAgICBjYXNlICdibG9iJzpcbiAgICAgICAgcmV0dXJuIGFjdGlvbi5jYWxsQmxvYihwYXJhbXMsIG9wdGlvbnMpO1xuICAgICAgY2FzZSAnYXJyYXlidWZmZXInOlxuICAgICAgICByZXR1cm4gYWN0aW9uLmNhbGxBcnJheWJ1ZmZlcihwYXJhbXMsIG9wdGlvbnMpO1xuICAgICAgZGVmYXVsdDpcbiAgICAgICAgcmV0dXJuIGFjdGlvbi5jYWxsKHBhcmFtcywgeyByZXNwb25zZVR5cGUsIC4uLm9wdGlvbnMgfSk7XG4gICAgfVxuICB9XG4gIC8vI2VuZHJlZ2lvblxuXG4gIC8vIENhc3RcbiAgY2FzdDxTPih0eXBlOiBzdHJpbmcpIHtcbiAgICAvLzogT0RhdGFNb2RlbDxTPiB7XG4gICAgY29uc3QgcmVzb3VyY2UgPSB0aGlzLnJlc291cmNlKCk7XG4gICAgaWYgKCEocmVzb3VyY2UgaW5zdGFuY2VvZiBPRGF0YUVudGl0eVJlc291cmNlKSlcbiAgICAgIHRocm93IG5ldyBFcnJvcihcbiAgICAgICAgYGNhc3Q6IENhbid0IGNhc3QgdG8gZGVyaXZlZCBtb2RlbCB3aXRob3V0IE9EYXRhRW50aXR5UmVzb3VyY2VgXG4gICAgICApO1xuXG4gICAgcmV0dXJuIHJlc291cmNlXG4gICAgICAuY2FzdDxTPih0eXBlKVxuICAgICAgLmFzTW9kZWwodGhpcy50b0VudGl0eShJTkNMVURFX0RFRVApIGFzIHsgW25hbWU6IHN0cmluZ106IGFueSB9LCB7XG4gICAgICAgIGFubm90czogdGhpcy5hbm5vdHMoKSBhcyBhbnksXG4gICAgICB9KTtcbiAgfVxuXG4gIGZldGNoTmF2aWdhdGlvblByb3BlcnR5PFM+KFxuICAgIG5hbWU6IGtleW9mIFQgfCBzdHJpbmcsXG4gICAgcmVzcG9uc2VUeXBlOiAnbW9kZWwnIHwgJ2NvbGxlY3Rpb24nLFxuICAgIHsgLi4ub3B0aW9ucyB9OiB7fSAmIE9EYXRhUXVlcnlBcmd1bWVudHNPcHRpb25zPFM+ID0ge31cbiAgKTogT2JzZXJ2YWJsZTxPRGF0YU1vZGVsPFM+IHwgT0RhdGFDb2xsZWN0aW9uPFMsIE9EYXRhTW9kZWw8Uz4+IHwgbnVsbD4ge1xuICAgIGNvbnN0IG5hdiA9IHRoaXMubmF2aWdhdGlvblByb3BlcnR5PFM+KFxuICAgICAgbmFtZVxuICAgICkgYXMgT0RhdGFOYXZpZ2F0aW9uUHJvcGVydHlSZXNvdXJjZTxTPjtcbiAgICBuYXYucXVlcnkoKHEpID0+IHEuYXBwbHkob3B0aW9ucykpO1xuICAgIHN3aXRjaCAocmVzcG9uc2VUeXBlKSB7XG4gICAgICBjYXNlICdtb2RlbCc6XG4gICAgICAgIHJldHVybiBuYXYuZmV0Y2hNb2RlbChvcHRpb25zKTtcbiAgICAgIGNhc2UgJ2NvbGxlY3Rpb24nOlxuICAgICAgICByZXR1cm4gbmF2LmZldGNoQ29sbGVjdGlvbihvcHRpb25zKTtcbiAgICB9XG4gIH1cblxuICAvLyBHZXQgVmFsdWVcbiAgZ2V0VmFsdWU8UD4oXG4gICAgbmFtZToga2V5b2YgVCB8IHN0cmluZyxcbiAgICBvcHRpb25zPzogT0RhdGFPcHRpb25zXG4gICk6IE9ic2VydmFibGU8UCB8IE9EYXRhTW9kZWw8UD4gfCBPRGF0YUNvbGxlY3Rpb248UCwgT0RhdGFNb2RlbDxQPj4gfCBudWxsPiB7XG4gICAgY29uc3QgZmllbGQgPSB0aGlzLl9tZXRhLmZpZWxkKG5hbWUpO1xuICAgIGlmIChmaWVsZCA9PT0gdW5kZWZpbmVkIHx8IGZpZWxkLm5hdmlnYXRpb24pXG4gICAgICB0aHJvdyBFcnJvcihgZ2V0VmFsdWU6IENhbid0IGZpbmQgcHJvcGVydHkgJHtuYW1lIGFzIHN0cmluZ31gKTtcblxuICAgIGxldCB2YWx1ZSA9ICh0aGlzIGFzIGFueSlbbmFtZV0gYXNcbiAgICAgIHwgUFxuICAgICAgfCBPRGF0YU1vZGVsPFA+XG4gICAgICB8IE9EYXRhQ29sbGVjdGlvbjxQLCBPRGF0YU1vZGVsPFA+PjtcbiAgICBpZiAodmFsdWUgPT09IHVuZGVmaW5lZCkge1xuICAgICAgY29uc3QgcHJvcCA9IGZpZWxkLnJlc291cmNlRmFjdG9yeShcbiAgICAgICAgdGhpcy5yZXNvdXJjZSgpXG4gICAgICApIGFzIE9EYXRhUHJvcGVydHlSZXNvdXJjZTxQPjtcbiAgICAgIHJldHVybiBmaWVsZC5jb2xsZWN0aW9uXG4gICAgICAgID8gcHJvcFxuICAgICAgICAgICAgLmZldGNoQ29sbGVjdGlvbihvcHRpb25zKVxuICAgICAgICAgICAgLnBpcGUodGFwKChjKSA9PiB0aGlzLmFzc2lnbih7IFtuYW1lXTogYyB9LCB7IHNpbGVudDogdHJ1ZSB9KSkpXG4gICAgICAgIDogZmllbGQuaXNTdHJ1Y3R1cmVkVHlwZSgpXG4gICAgICAgID8gcHJvcFxuICAgICAgICAgICAgLmZldGNoTW9kZWwob3B0aW9ucylcbiAgICAgICAgICAgIC5waXBlKHRhcCgoYykgPT4gdGhpcy5hc3NpZ24oeyBbbmFtZV06IGMgfSwgeyBzaWxlbnQ6IHRydWUgfSkpKVxuICAgICAgICA6IHByb3BcbiAgICAgICAgICAgIC5mZXRjaFByb3BlcnR5KG9wdGlvbnMpXG4gICAgICAgICAgICAucGlwZSh0YXAoKGMpID0+IHRoaXMuYXNzaWduKHsgW25hbWVdOiBjIH0sIHsgc2lsZW50OiB0cnVlIH0pKSk7XG4gICAgfVxuICAgIHJldHVybiBvZih2YWx1ZSBhcyBQKTtcbiAgfVxuXG4gIC8vI3JlZ2lvbiBSZWZlcmVuY2VzXG4gIHNldFJlZmVyZW5jZTxOPihcbiAgICBuYW1lOiBrZXlvZiBUIHwgc3RyaW5nLFxuICAgIG1vZGVsOiBPRGF0YU1vZGVsPE4+IHwgT0RhdGFDb2xsZWN0aW9uPE4sIE9EYXRhTW9kZWw8Tj4+IHwgbnVsbCxcbiAgICBvcHRpb25zPzogT0RhdGFPcHRpb25zXG4gICk6IE9ic2VydmFibGU8dGhpcz4ge1xuICAgIGNvbnN0IHJlZmVyZW5jZSA9IChcbiAgICAgIHRoaXMubmF2aWdhdGlvblByb3BlcnR5PE4+KG5hbWUpIGFzIE9EYXRhTmF2aWdhdGlvblByb3BlcnR5UmVzb3VyY2U8Tj5cbiAgICApLnJlZmVyZW5jZSgpO1xuXG4gICAgY29uc3QgZXRhZyA9IHRoaXMuYW5ub3RzKCkuZXRhZztcbiAgICBsZXQgb2JzJCA9IE5FVkVSIGFzIE9ic2VydmFibGU8YW55PjtcbiAgICBpZiAobW9kZWwgaW5zdGFuY2VvZiBPRGF0YU1vZGVsKSB7XG4gICAgICBvYnMkID0gcmVmZXJlbmNlLnNldChcbiAgICAgICAgbW9kZWwuX21ldGEuZW50aXR5UmVzb3VyY2UobW9kZWwpIGFzIE9EYXRhRW50aXR5UmVzb3VyY2U8Tj4sXG4gICAgICAgIHsgZXRhZywgLi4ub3B0aW9ucyB9XG4gICAgICApO1xuICAgIH0gZWxzZSBpZiAobW9kZWwgaW5zdGFuY2VvZiBPRGF0YUNvbGxlY3Rpb24pIHtcbiAgICAgIG9icyQgPSBmb3JrSm9pbihcbiAgICAgICAgbW9kZWxcbiAgICAgICAgICAubW9kZWxzKClcbiAgICAgICAgICAubWFwKChtKSA9PlxuICAgICAgICAgICAgcmVmZXJlbmNlLmFkZChcbiAgICAgICAgICAgICAgbS5fbWV0YS5lbnRpdHlSZXNvdXJjZShtKSBhcyBPRGF0YUVudGl0eVJlc291cmNlPE4+LFxuICAgICAgICAgICAgICBvcHRpb25zXG4gICAgICAgICAgICApXG4gICAgICAgICAgKVxuICAgICAgKTtcbiAgICB9IGVsc2UgaWYgKG1vZGVsID09PSBudWxsKSB7XG4gICAgICBvYnMkID0gcmVmZXJlbmNlLnVuc2V0KHsgZXRhZywgLi4ub3B0aW9ucyB9KTtcbiAgICB9XG4gICAgdGhpcy5ldmVudHMkLmVtaXQoXG4gICAgICBuZXcgT0RhdGFNb2RlbEV2ZW50KE9EYXRhTW9kZWxFdmVudFR5cGUuUmVxdWVzdCwge1xuICAgICAgICBtb2RlbDogdGhpcyxcbiAgICAgICAgb3B0aW9uczogeyBvYnNlcnZhYmxlOiBvYnMkIH0sXG4gICAgICB9KVxuICAgICk7XG4gICAgcmV0dXJuIG9icyQucGlwZShcbiAgICAgIG1hcCgobW9kZWwpID0+IHtcbiAgICAgICAgdGhpcy5hc3NpZ24oeyBbbmFtZV06IG1vZGVsIH0pO1xuICAgICAgICB0aGlzLmV2ZW50cyQuZW1pdChcbiAgICAgICAgICBuZXcgT0RhdGFNb2RlbEV2ZW50KE9EYXRhTW9kZWxFdmVudFR5cGUuU3luYywgeyBtb2RlbDogdGhpcyB9KVxuICAgICAgICApO1xuICAgICAgICByZXR1cm4gdGhpcztcbiAgICAgIH0pXG4gICAgKTtcbiAgfVxuXG4gIGdldFJlZmVyZW5jZTxQPihcbiAgICBuYW1lOiBrZXlvZiBUIHwgc3RyaW5nXG4gICk6IE9EYXRhTW9kZWw8UD4gfCBPRGF0YUNvbGxlY3Rpb248UCwgT0RhdGFNb2RlbDxQPj4gfCBudWxsIHtcbiAgICBjb25zdCBmaWVsZCA9IHRoaXMuX21ldGEuZmllbGQ8UD4obmFtZSk7XG4gICAgaWYgKGZpZWxkID09PSB1bmRlZmluZWQgfHwgIWZpZWxkLm5hdmlnYXRpb24pXG4gICAgICB0aHJvdyBFcnJvcihcbiAgICAgICAgYGdldFJlZmVyZW5jZTogQ2FuJ3QgZmluZCBuYXZpZ2F0aW9uIHByb3BlcnR5ICR7bmFtZSBhcyBzdHJpbmd9YFxuICAgICAgKTtcblxuICAgIGxldCBtb2RlbCA9ICh0aGlzIGFzIGFueSlbbmFtZV0gYXNcbiAgICAgIHwgT0RhdGFNb2RlbDxQPlxuICAgICAgfCBPRGF0YUNvbGxlY3Rpb248UCwgT0RhdGFNb2RlbDxQPj5cbiAgICAgIHwgbnVsbDtcbiAgICBpZiAobW9kZWwgPT09IG51bGwpIHJldHVybiBudWxsO1xuICAgIGlmIChtb2RlbCA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICBpZiAoZmllbGQuY29sbGVjdGlvbikge1xuICAgICAgICBtb2RlbCA9IGZpZWxkLmNvbGxlY3Rpb25GYWN0b3J5KHsgcGFyZW50OiB0aGlzIH0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSB0aGlzLnJlZmVyZW5jZWQoZmllbGQpIGFzIFA7XG4gICAgICAgIG1vZGVsID1cbiAgICAgICAgICB2YWx1ZSA9PT0gbnVsbCA/IG51bGwgOiBmaWVsZC5tb2RlbEZhY3RvcnkoeyBwYXJlbnQ6IHRoaXMsIHZhbHVlIH0pO1xuICAgICAgfVxuICAgICAgKHRoaXMgYXMgYW55KVtuYW1lXSA9IG1vZGVsO1xuICAgIH1cbiAgICByZXR1cm4gbW9kZWw7XG4gIH1cbiAgLy8jZW5kcmVnaW9uXG5cbiAgLy8jcmVnaW9uIE1vZGVsIElkZW50aXR5XG4gIGdldCBbU3ltYm9sLnRvU3RyaW5nVGFnXSgpIHtcbiAgICByZXR1cm4gJ01vZGVsJztcbiAgfVxuICBlcXVhbHMob3RoZXI6IE9EYXRhTW9kZWw8VD4pOiBib29sZWFuIHtcbiAgICBjb25zdCB0aGlzS2V5ID0gdGhpcy5rZXkoKTtcbiAgICBjb25zdCBvdGhlcktleSA9IG90aGVyLmtleSgpO1xuICAgIHJldHVybiAoXG4gICAgICB0aGlzID09PSBvdGhlciB8fFxuICAgICAgKHR5cGVvZiB0aGlzID09PSB0eXBlb2Ygb3RoZXIgJiZcbiAgICAgICAgKCg8YW55PnRoaXMpW3RoaXMuX21ldGEuY2lkXSA9PT0gKDxhbnk+b3RoZXIpW3RoaXMuX21ldGEuY2lkXSB8fFxuICAgICAgICAgICh0aGlzS2V5ICE9PSB1bmRlZmluZWQgJiZcbiAgICAgICAgICAgIG90aGVyS2V5ICE9PSB1bmRlZmluZWQgJiZcbiAgICAgICAgICAgIFR5cGVzLmlzRXF1YWwodGhpc0tleSwgb3RoZXJLZXkpKSkpXG4gICAgKTtcbiAgfVxuICAvLyNlbmRyZWdpb25cblxuICAvLyNyZWdpb24gQ29sbGVjdGlvbiBUb29sc1xuICBjb2xsZWN0aW9uKCkge1xuICAgIHJldHVybiB0aGlzLl9wYXJlbnQgIT09IG51bGwgJiZcbiAgICAgIE9EYXRhTW9kZWxPcHRpb25zLmlzQ29sbGVjdGlvbih0aGlzLl9wYXJlbnRbMF0pXG4gICAgICA/ICh0aGlzLl9wYXJlbnRbMF0gYXMgT0RhdGFDb2xsZWN0aW9uPFQsIE9EYXRhTW9kZWw8VD4+KVxuICAgICAgOiB1bmRlZmluZWQ7XG4gIH1cblxuICBuZXh0KCk6IE9EYXRhTW9kZWw8VD4gfCB1bmRlZmluZWQge1xuICAgIHJldHVybiB0aGlzLmNvbGxlY3Rpb24oKT8ubmV4dCh0aGlzKTtcbiAgfVxuXG4gIHByZXYoKTogT0RhdGFNb2RlbDxUPiB8IHVuZGVmaW5lZCB7XG4gICAgcmV0dXJuIHRoaXMuY29sbGVjdGlvbigpPy5wcmV2KHRoaXMpO1xuICB9XG4gIC8vI2VuZHJlZ2lvblxufVxuXG5leHBvcnQgY29uc3QgUkVTRVJWRURfRklFTERfTkFNRVMgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhcbiAgT0RhdGFNb2RlbC5wcm90b3R5cGVcbik7XG4iXX0=
|