@edugis-org/webmapx 0.1.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.
Files changed (84) hide show
  1. package/README.md +149 -0
  2. package/dist-lib/WMTS-DCN4zX0-.js +1169 -0
  3. package/dist-lib/alert-GeHlqlN8.js +310 -0
  4. package/dist-lib/assets/epsg-lookup.worker-J7TVnHDq.js +1 -0
  5. package/dist-lib/assets/shapefile.worker-kQfZj6G2.js +4 -0
  6. package/dist-lib/attribution-format-B4f05_u0.js +62 -0
  7. package/dist-lib/button-DFdGkRPQ.js +741 -0
  8. package/dist-lib/cesium-adapter-BHXNytkU.js +1488 -0
  9. package/dist-lib/checkbox-QoR4S8tV.js +284 -0
  10. package/dist-lib/chunk-HEgqtunE.js +20 -0
  11. package/dist-lib/chunk.36O46B5H-B6ZL7Sm1.js +77 -0
  12. package/dist-lib/chunk.3RPBFEDE-BFO1fHVm.js +138 -0
  13. package/dist-lib/chunk.5JY5FUCG-DTXsslmx.js +1090 -0
  14. package/dist-lib/chunk.6CTB5ZDJ-DjZrBd6Y.js +99 -0
  15. package/dist-lib/chunk.AJ3ENQ5C-Ci7Gm2b6.js +175 -0
  16. package/dist-lib/chunk.LD4M4QGE-CiCfhE8r.js +8 -0
  17. package/dist-lib/chunk.NYIIDP5N-BikXIStD.js +99 -0
  18. package/dist-lib/chunk.RWUUFNUL-DFztA4uV.js +43 -0
  19. package/dist-lib/chunk.SI4ACBFK-CLb9VfMG.js +61 -0
  20. package/dist-lib/chunk.YHLNUJ7P-D-kanrCf.js +503 -0
  21. package/dist-lib/core-CMAlSR68.js +22 -0
  22. package/dist-lib/decorate-CWgUV1hU.js +1139 -0
  23. package/dist-lib/decorators-B35AgiCU.js +351 -0
  24. package/dist-lib/deferred-query-service-BJDcngw6.js +386 -0
  25. package/dist-lib/dist-Dm6b7XCs.js +12318 -0
  26. package/dist-lib/dist-Ha9LQCut.js +244 -0
  27. package/dist-lib/dist-c1PlDAd1.js +2359 -0
  28. package/dist-lib/dist-kKlmcBXq.js +50 -0
  29. package/dist-lib/divider-CPm675yY.js +41 -0
  30. package/dist-lib/dropped-config-C_GyVa8o.js +17 -0
  31. package/dist-lib/dropped-layer-builder-DAaYgUPk.js +396 -0
  32. package/dist-lib/epsg-definitions-BZLZWa8Q.js +668 -0
  33. package/dist-lib/esm-CTuscnN5.js +46 -0
  34. package/dist-lib/file-sniff-Dhxj3KTF.js +251 -0
  35. package/dist-lib/geo-calculations-DbFJAUoI.js +30 -0
  36. package/dist-lib/icon-CEOgWlro.js +9 -0
  37. package/dist-lib/icon-button-Da_nBTy3.js +408 -0
  38. package/dist-lib/input-CeGntPlT.js +590 -0
  39. package/dist-lib/layer-discovery-afWzu5hY.js +2825 -0
  40. package/dist-lib/leaflet-adapter-D9djjrKv.js +1227 -0
  41. package/dist-lib/lib-CdHVicAE.js +4074 -0
  42. package/dist-lib/map-layer-registry-2cmkiRDK.js +62 -0
  43. package/dist-lib/maplibre-adapter-TFc3e0G9.js +1190 -0
  44. package/dist-lib/maplibre-expression-evaluator-DCWUcpwf.js +7233 -0
  45. package/dist-lib/marker-utils-DztWXeop.js +12 -0
  46. package/dist-lib/ol-tilegrid-9VtyxaLG.js +64 -0
  47. package/dist-lib/openlayers-adapter-DVW1KCRv.js +13307 -0
  48. package/dist-lib/option-CBxl1mZP.js +1106 -0
  49. package/dist-lib/papaparse.min-B7v3c0D7.js +501 -0
  50. package/dist-lib/rbush-C8k41T4z.js +254 -0
  51. package/dist-lib/shapefile-SawVY6xg.js +207 -0
  52. package/dist-lib/spinner-DysxdNG9.js +6 -0
  53. package/dist-lib/src-CL94RDe3.js +111 -0
  54. package/dist-lib/throttle-BeneRNYK.js +16 -0
  55. package/dist-lib/toast-Cm28o9U6.js +15 -0
  56. package/dist-lib/togeojson.es-DAgiTBvg.js +579 -0
  57. package/dist-lib/tooltip-Cucn1SiD.js +197 -0
  58. package/dist-lib/webmapx-3d-tool-D4CTD2gB.js +176 -0
  59. package/dist-lib/webmapx-base-tool-Dm9NAWLD.js +75 -0
  60. package/dist-lib/webmapx-config-edit-tool-DCTyxqTk.js +389 -0
  61. package/dist-lib/webmapx-coordinates-tool-jeWohup9.js +648 -0
  62. package/dist-lib/webmapx-core-bundle-BDImi1RE.js +8203 -0
  63. package/dist-lib/webmapx-draw-tool-DooAV8cF.js +4336 -0
  64. package/dist-lib/webmapx-geolocation-tool-Rw3-Iad1.js +788 -0
  65. package/dist-lib/webmapx-import-layer-tool-DRYviHd5.js +250 -0
  66. package/dist-lib/webmapx-info-tool-BJA157cy.js +412 -0
  67. package/dist-lib/webmapx-language-osmvector-M5y_lwOg.js +489 -0
  68. package/dist-lib/webmapx-measure-tool-BXhMJFC6.js +590 -0
  69. package/dist-lib/webmapx-modal-tool-eF6Naluv.js +84 -0
  70. package/dist-lib/webmapx-plugin-tool-D2Hghf9n.js +45 -0
  71. package/dist-lib/webmapx-print-tool-ob1bOsR5.js +348 -0
  72. package/dist-lib/webmapx-search-tool-Cv8BrYvY.js +437 -0
  73. package/dist-lib/webmapx-settings-DDEJ8aoV.js +479 -0
  74. package/dist-lib/webmapx-truearea-tool-CMB4Orm-.js +615 -0
  75. package/dist-lib/webmapx-view-mode-tool-CUpLNjOj.js +106 -0
  76. package/dist-lib/webmapx.css +2 -0
  77. package/dist-lib/webmapx.js +1321 -0
  78. package/dist-lib/wms-feature-info-C0RVMEQC.js +145 -0
  79. package/dist-lib/wms-url-builder-DIJLQ1v2.js +54 -0
  80. package/dist-lib/zip.js-DVhmtjxZ.js +3615 -0
  81. package/package.json +107 -0
  82. package/public/data/country-epsg-codes.json +297 -0
  83. package/public/data/world-countries-simplified.topojson +1 -0
  84. package/src/locales/en/core.json +20 -0
@@ -0,0 +1,2825 @@
1
+ import { t as e } from "./chunk-HEgqtunE.js";
2
+ import { n as t } from "./lib-CdHVicAE.js";
3
+ import { t as n } from "./epsg-definitions-BZLZWa8Q.js";
4
+ import { t as r } from "./wms-url-builder-DIJLQ1v2.js";
5
+ //#region node_modules/@camptocamp/ogc-client/dist/worker/index.js
6
+ var i = 0;
7
+ function a() {
8
+ return i++;
9
+ }
10
+ var o = Object.defineProperty, s = Object.getOwnPropertyDescriptor, c = Object.getOwnPropertyNames, l = Object.prototype.hasOwnProperty, u = (e, t) => {
11
+ for (var n in t) o(e, n, {
12
+ get: t[n],
13
+ enumerable: !0
14
+ });
15
+ }, d = (e, t, n, r) => {
16
+ if (t && typeof t == "object" || typeof t == "function") for (let i of c(t)) !l.call(e, i) && i !== n && o(e, i, {
17
+ get: () => t[i],
18
+ enumerable: !(r = s(t, i)) || r.enumerable
19
+ });
20
+ return e;
21
+ }, f = (e) => d(o({}, "__esModule", { value: !0 }), e), p = {};
22
+ u(p, {
23
+ XmlCdata: () => ee,
24
+ XmlComment: () => te,
25
+ XmlDeclaration: () => j,
26
+ XmlDocument: () => ne,
27
+ XmlDocumentType: () => N,
28
+ XmlElement: () => M,
29
+ XmlError: () => re,
30
+ XmlNode: () => k,
31
+ XmlProcessingInstruction: () => ie,
32
+ XmlText: () => A,
33
+ parseXml: () => se
34
+ }), f(p);
35
+ var m = "", h = /[\uD800-\uDBFF][\uDC00-\uDFFF]/g, g = class {
36
+ constructor(e) {
37
+ if (this.k = this.q(e, !0), this.d = 0, this.length = e.length, this.n = this.k !== this.length, this.m = e, this.n) {
38
+ let t = [];
39
+ for (let n = 0, r = 0; r < this.k; ++r) t[r] = n, n += e.codePointAt(n) > 65535 ? 2 : 1;
40
+ this.y = t;
41
+ }
42
+ }
43
+ get z() {
44
+ return this.d >= this.k;
45
+ }
46
+ q(e, t = this.n) {
47
+ return t ? e.replace(h, "_").length : e.length;
48
+ }
49
+ g(e = 1) {
50
+ this.d = Math.min(this.k, this.d + e);
51
+ }
52
+ i(e = this.d) {
53
+ return this.n ? this.y[e] ?? Infinity : e;
54
+ }
55
+ F(e = 1) {
56
+ let t = this.h(e);
57
+ return this.g(e), t;
58
+ }
59
+ G(e) {
60
+ if (!e.sticky) throw Error("`regex` must have a sticky flag (\"y\")");
61
+ e.lastIndex = this.i();
62
+ let t = e.exec(this.m);
63
+ if (t === null || t.length === 0) return m;
64
+ let n = t[0];
65
+ return this.g(this.q(n)), n;
66
+ }
67
+ v(e) {
68
+ let t, n = m;
69
+ for (; (t = this.h()) && e(t);) n += t, this.g();
70
+ return n;
71
+ }
72
+ Q(e) {
73
+ if (this.b(e)) return e;
74
+ if (this.n) {
75
+ let { length: t } = e, n = this.q(e);
76
+ if (n !== t && e === this.h(n)) return this.g(n), e;
77
+ }
78
+ return m;
79
+ }
80
+ b(e) {
81
+ let { length: t } = e;
82
+ return this.h(t) === e ? (this.g(t), e) : m;
83
+ }
84
+ A(e) {
85
+ let t = this.m.slice(this.i()), n = t.search(e);
86
+ if (n <= 0) return m;
87
+ let r = t.slice(0, n);
88
+ return this.g(this.q(r)), r;
89
+ }
90
+ t(e) {
91
+ let { m: t } = this, n = this.i(), r = t.indexOf(e, n);
92
+ if (r <= 0) return m;
93
+ let i = t.slice(n, r);
94
+ return this.g(this.q(i)), i;
95
+ }
96
+ h(e = 1) {
97
+ let { d: t, n, m: r } = this;
98
+ return n ? t >= this.k ? m : r.slice(this.i(t), this.i(t + e)) : r.slice(t, t + e);
99
+ }
100
+ o(e = 0) {
101
+ this.d = e >= 0 ? Math.min(this.k, e) : Math.max(0, this.d + e);
102
+ }
103
+ }, _ = /[^"&<]+/y, v = /[^'&<]+/y, y = /\r\n|[\n\r\t]/g, b = /<|&|]]>/, x = Object.freeze(Object.assign(/* @__PURE__ */ Object.create(null), {
104
+ amp: "&",
105
+ apos: "'",
106
+ gt: ">",
107
+ lt: "<",
108
+ quot: "\""
109
+ }));
110
+ function S(e) {
111
+ let t = D(e);
112
+ return t >= 97 && t <= 122 || t >= 65 && t <= 90 || t >= 48 && t <= 57 || t === 45 || t === 46 || t === 183 || t >= 768 && t <= 879 || t >= 8255 && t <= 8256 || C(e, t);
113
+ }
114
+ function C(e, t = D(e)) {
115
+ return t >= 97 && t <= 122 || t >= 65 && t <= 90 || t === 58 || t === 95 || t >= 192 && t <= 214 || t >= 216 && t <= 246 || t >= 248 && t <= 767 || t >= 880 && t <= 893 || t >= 895 && t <= 8191 || t >= 8204 && t <= 8205 || t >= 8304 && t <= 8591 || t >= 11264 && t <= 12271 || t >= 12289 && t <= 55295 || t >= 63744 && t <= 64975 || t >= 65008 && t <= 65533 || t >= 65536 && t <= 983039;
116
+ }
117
+ function w(e) {
118
+ return e === "#" || S(e);
119
+ }
120
+ function T(e) {
121
+ let t = D(e);
122
+ return t === 32 || t === 9 || t === 10 || t === 13;
123
+ }
124
+ function E(e) {
125
+ return e === 9 || e === 10 || e === 13 || e >= 32 && e <= 55295 || e >= 57344 && e <= 65533 || e >= 65536 && e <= 1114111;
126
+ }
127
+ function D(e) {
128
+ return e.codePointAt(0) || -1;
129
+ }
130
+ var O = class {
131
+ constructor() {
132
+ this.parent = null, this.start = -1, this.end = -1;
133
+ }
134
+ get document() {
135
+ return this.parent?.document ?? null;
136
+ }
137
+ get isRootNode() {
138
+ return this.parent !== null && this.parent === this.document && this.type === O.TYPE_ELEMENT;
139
+ }
140
+ get preserveWhitespace() {
141
+ return !!this.parent?.preserveWhitespace;
142
+ }
143
+ get type() {
144
+ return "";
145
+ }
146
+ toJSON() {
147
+ let e = { type: this.type };
148
+ return this.isRootNode && (e.isRootNode = !0), this.preserveWhitespace && (e.preserveWhitespace = !0), this.start !== -1 && (e.start = this.start, e.end = this.end), e;
149
+ }
150
+ }, k = O;
151
+ k.TYPE_CDATA = "cdata", k.TYPE_COMMENT = "comment", k.TYPE_DOCUMENT = "document", k.TYPE_DOCUMENT_TYPE = "doctype", k.TYPE_ELEMENT = "element", k.TYPE_PROCESSING_INSTRUCTION = "pi", k.TYPE_TEXT = "text", k.TYPE_XML_DECLARATION = "xmldecl";
152
+ var A = class extends k {
153
+ constructor(e = "") {
154
+ super(), this.text = e;
155
+ }
156
+ get type() {
157
+ return k.TYPE_TEXT;
158
+ }
159
+ toJSON() {
160
+ return Object.assign(k.prototype.toJSON.call(this), { text: this.text });
161
+ }
162
+ }, ee = class extends A {
163
+ get type() {
164
+ return k.TYPE_CDATA;
165
+ }
166
+ }, te = class extends k {
167
+ constructor(e = "") {
168
+ super(), this.content = e;
169
+ }
170
+ get type() {
171
+ return k.TYPE_COMMENT;
172
+ }
173
+ toJSON() {
174
+ return Object.assign(k.prototype.toJSON.call(this), { content: this.content });
175
+ }
176
+ }, j = class extends k {
177
+ constructor(e, t, n) {
178
+ super(), this.version = e, this.encoding = t ?? null, this.standalone = n ?? null;
179
+ }
180
+ get type() {
181
+ return k.TYPE_XML_DECLARATION;
182
+ }
183
+ toJSON() {
184
+ let e = k.prototype.toJSON.call(this);
185
+ e.version = this.version;
186
+ for (let t of ["encoding", "standalone"]) this[t] !== null && (e[t] = this[t]);
187
+ return e;
188
+ }
189
+ }, M = class extends k {
190
+ constructor(e, t = /* @__PURE__ */ Object.create(null), n = []) {
191
+ super(), this.name = e, this.attributes = t, this.children = n;
192
+ }
193
+ get isEmpty() {
194
+ return this.children.length === 0;
195
+ }
196
+ get preserveWhitespace() {
197
+ let e = this;
198
+ for (; e instanceof M;) {
199
+ if ("xml:space" in e.attributes) return e.attributes["xml:space"] === "preserve";
200
+ e = e.parent;
201
+ }
202
+ return !1;
203
+ }
204
+ get text() {
205
+ return this.children.map((e) => "text" in e ? e.text : "").join("");
206
+ }
207
+ get type() {
208
+ return k.TYPE_ELEMENT;
209
+ }
210
+ toJSON() {
211
+ return Object.assign(k.prototype.toJSON.call(this), {
212
+ name: this.name,
213
+ attributes: this.attributes,
214
+ children: this.children.map((e) => e.toJSON())
215
+ });
216
+ }
217
+ }, ne = class extends k {
218
+ constructor(e = []) {
219
+ super(), this.children = e;
220
+ }
221
+ get document() {
222
+ return this;
223
+ }
224
+ get root() {
225
+ for (let e of this.children) if (e instanceof M) return e;
226
+ return null;
227
+ }
228
+ get text() {
229
+ return this.children.map((e) => "text" in e ? e.text : "").join("");
230
+ }
231
+ get type() {
232
+ return k.TYPE_DOCUMENT;
233
+ }
234
+ toJSON() {
235
+ return Object.assign(k.prototype.toJSON.call(this), { children: this.children.map((e) => e.toJSON()) });
236
+ }
237
+ }, N = class extends k {
238
+ constructor(e, t, n, r) {
239
+ super(), this.name = e, this.publicId = t ?? null, this.systemId = n ?? null, this.internalSubset = r ?? null;
240
+ }
241
+ get type() {
242
+ return k.TYPE_DOCUMENT_TYPE;
243
+ }
244
+ toJSON() {
245
+ let e = k.prototype.toJSON.call(this);
246
+ e.name = this.name;
247
+ for (let t of [
248
+ "publicId",
249
+ "systemId",
250
+ "internalSubset"
251
+ ]) this[t] !== null && (e[t] = this[t]);
252
+ return e;
253
+ }
254
+ }, re = class extends Error {
255
+ constructor(e, t, n) {
256
+ let r = 1, i = "", a = 1;
257
+ for (let e = 0; e < t; ++e) {
258
+ let t = n[e];
259
+ t === "\n" ? (r = 1, i = "", a += 1) : (r += 1, i += t);
260
+ }
261
+ let o = n.indexOf("\n", t);
262
+ i += o === -1 ? n.slice(t) : n.slice(t, o);
263
+ let s = 0;
264
+ i.length > 50 && (r < 40 ? i = i.slice(0, 50) : (s = r - 20, i = i.slice(s, r + 30))), super(`${e} (line ${a}, column ${r})
265
+ ${i}
266
+ ` + " ".repeat(r - s + 1) + "^\n"), this.column = r, this.excerpt = i, this.line = a, this.name = "XmlError", this.pos = t;
267
+ }
268
+ }, ie = class extends k {
269
+ constructor(e, t = "") {
270
+ super(), this.name = e, this.content = t;
271
+ }
272
+ get type() {
273
+ return k.TYPE_PROCESSING_INSTRUCTION;
274
+ }
275
+ toJSON() {
276
+ return Object.assign(k.prototype.toJSON.call(this), {
277
+ name: this.name,
278
+ content: this.content
279
+ });
280
+ }
281
+ }, ae = "", oe = class {
282
+ constructor(e, t = {}) {
283
+ let n = this.document = new ne(), r = this.c = new g(e);
284
+ if (this.l = n, this.f = t, this.f.includeOffsets && (n.start = 0, n.end = e.length), r.b(""), this.H(), !this.B()) throw this.a("Root element is missing or invalid");
285
+ for (; this.w(););
286
+ if (!r.z) throw this.a("Extra content at the end of the document");
287
+ }
288
+ j(e, t) {
289
+ return e.parent = this.l, this.f.includeOffsets && (e.start = this.c.i(t), e.end = this.c.i()), this.l.children.push(e), !0;
290
+ }
291
+ x(e, t) {
292
+ let { children: n } = this.l, { length: r } = n;
293
+ if (e = P(e), r > 0) {
294
+ let t = n[r - 1];
295
+ if (t?.type === k.TYPE_TEXT) {
296
+ let n = t;
297
+ return n.text += e, this.f.includeOffsets && (n.end = this.c.i()), !0;
298
+ }
299
+ }
300
+ return this.j(new A(e), t);
301
+ }
302
+ I() {
303
+ let e = /* @__PURE__ */ Object.create(null);
304
+ for (; this.e();) {
305
+ let t = this.r();
306
+ if (!t) break;
307
+ let n = this.u() && this.J();
308
+ if (n === !1) throw this.a("Attribute value expected");
309
+ if (t in e) throw this.a(`Duplicate attribute: ${t}`);
310
+ if (t === "xml:space" && n !== "default" && n !== "preserve") throw this.a("Value of the `xml:space` attribute must be \"default\" or \"preserve\"");
311
+ e[t] = n;
312
+ }
313
+ if (this.f.sortAttributes) {
314
+ let t = Object.keys(e).sort(), n = /* @__PURE__ */ Object.create(null);
315
+ for (let r = 0; r < t.length; ++r) {
316
+ let i = t[r];
317
+ n[i] = e[i];
318
+ }
319
+ e = n;
320
+ }
321
+ return e;
322
+ }
323
+ J() {
324
+ let { c: e } = this, t = e.h();
325
+ if (t !== "\"" && t !== "'") return !1;
326
+ e.g();
327
+ let n, r = !1, i = ae, a = t === "\"" ? _ : v;
328
+ matchLoop: for (; !e.z;) switch (n = e.G(a), n && (this.p(n), i += n.replace(y, " ")), e.h()) {
329
+ case t:
330
+ r = !0;
331
+ break matchLoop;
332
+ case "&":
333
+ i += this.C();
334
+ continue;
335
+ case "<": throw this.a("Unescaped `<` is not allowed in an attribute value");
336
+ case ae: break matchLoop;
337
+ }
338
+ if (!r) throw this.a("Unclosed attribute");
339
+ return e.g(), i;
340
+ }
341
+ K() {
342
+ let { c: e } = this, t = e.d;
343
+ if (!e.b("<![CDATA[")) return !1;
344
+ let n = e.t("]]>");
345
+ if (this.p(n), !e.b("]]>")) throw this.a("Unclosed CDATA section");
346
+ return this.f.preserveCdata ? this.j(new ee(P(n)), t) : this.x(n, t);
347
+ }
348
+ L() {
349
+ let { c: e } = this, t = e.d, n = e.A(b);
350
+ if (!n) return !1;
351
+ if (this.p(n), e.h(3) === "]]>") throw this.a("Element content may not contain the CDATA section close delimiter `]]>`");
352
+ return this.x(n, t);
353
+ }
354
+ D() {
355
+ let { c: e } = this, t = e.d;
356
+ if (!e.b("<!--")) return !1;
357
+ let n = e.t("--");
358
+ if (this.p(n), !e.b("-->")) throw e.h(2) === "--" ? this.a("The string `--` isn't allowed inside a comment") : this.a("Unclosed comment");
359
+ return this.f.preserveComments ? this.j(new te(P(n)), t) : !0;
360
+ }
361
+ M() {
362
+ let e = this.c.d, t = this.C();
363
+ return t ? this.x(t, e) : !1;
364
+ }
365
+ N() {
366
+ let { c: e } = this, t = e.d;
367
+ if (!e.b("<!DOCTYPE")) return !1;
368
+ let n = this.e() && this.r();
369
+ if (!n) throw this.a("Expected a name");
370
+ let r, i;
371
+ if (this.e()) {
372
+ if (e.b("PUBLIC")) {
373
+ if (r = this.e() && this.O(), r === !1) throw this.a("Expected a public identifier");
374
+ this.e();
375
+ }
376
+ if (r !== void 0 || e.b("SYSTEM")) {
377
+ if (this.e(), i = this.s(), i === !1) throw this.a("Expected a system identifier");
378
+ this.e();
379
+ }
380
+ }
381
+ let a;
382
+ if (e.b("[")) {
383
+ if (a = e.A(/\][\x20\t\r\n]*>/), !e.b("]")) throw this.a("Unclosed internal subset");
384
+ this.e();
385
+ }
386
+ if (!e.b(">")) throw this.a("Unclosed doctype declaration");
387
+ return this.f.preserveDocumentType ? this.j(new N(n, r, i, a), t) : !0;
388
+ }
389
+ B() {
390
+ let { c: e } = this, t = e.d;
391
+ if (!e.b("<")) return !1;
392
+ let n = this.r();
393
+ if (!n) return e.o(t), !1;
394
+ let r = this.I(), i = !!e.b("/>"), a = new M(n, r);
395
+ if (a.parent = this.l, !i) {
396
+ if (!e.b(">")) throw this.a(`Unclosed start tag for element \`${n}\``);
397
+ this.l = a;
398
+ do
399
+ this.L();
400
+ while (this.B() || this.M() || this.K() || this.E() || this.D());
401
+ let t = e.d, r;
402
+ if (!e.b("</") || !(r = this.r()) || r !== n) throw e.o(t), this.a(`Missing end tag for element ${n}`);
403
+ if (this.e(), !e.b(">")) throw this.a(`Unclosed end tag for element ${n}`);
404
+ this.l = a.parent;
405
+ }
406
+ return this.j(a, t);
407
+ }
408
+ u() {
409
+ return this.e(), this.c.b("=") ? (this.e(), !0) : !1;
410
+ }
411
+ w() {
412
+ return this.D() || this.E() || this.e();
413
+ }
414
+ r() {
415
+ return C(this.c.h()) ? this.c.v(S) : ae;
416
+ }
417
+ E() {
418
+ let { c: e } = this, t = e.d;
419
+ if (!e.b("<?")) return !1;
420
+ let n = this.r();
421
+ if (n) {
422
+ if (n.toLowerCase() === "xml") throw e.o(t), this.a("XML declaration isn't allowed here");
423
+ } else throw this.a("Invalid processing instruction");
424
+ if (!this.e()) {
425
+ if (e.b("?>")) return this.j(new ie(n), t);
426
+ throw this.a("Whitespace is required after a processing instruction name");
427
+ }
428
+ let r = e.t("?>");
429
+ if (this.p(r), !e.b("?>")) throw this.a("Unterminated processing instruction");
430
+ return this.j(new ie(n, P(r)), t);
431
+ }
432
+ H() {
433
+ let { c: e } = this, t = e.d;
434
+ for (this.P(); this.w(););
435
+ if (this.N()) for (; this.w(););
436
+ return t < e.d;
437
+ }
438
+ O() {
439
+ let e = this.c.d, t = this.s();
440
+ if (t !== !1 && !/^[-\x20\r\na-zA-Z0-9'()+,./:=?;!*#@$_%]*$/.test(t)) throw this.c.o(e), this.a("Invalid character in public identifier");
441
+ return t;
442
+ }
443
+ C() {
444
+ let { c: e } = this;
445
+ if (!e.b("&")) return !1;
446
+ let t = e.v(w);
447
+ if (e.F() !== ";") throw this.a("Unterminated reference (a reference must end with `;`)");
448
+ let n;
449
+ if (t[0] === "#") {
450
+ let e = t[1] === "x" ? parseInt(t.slice(2), 16) : parseInt(t.slice(1), 10);
451
+ if (isNaN(e)) throw this.a("Invalid character reference");
452
+ if (!E(e)) throw this.a("Character reference resolves to an invalid character");
453
+ n = String.fromCodePoint(e);
454
+ } else if (n = x[t], n === void 0) {
455
+ let { ignoreUndefinedEntities: n, resolveUndefinedEntity: r } = this.f, i = `&${t};`;
456
+ if (r) {
457
+ let e = r(i);
458
+ if (e != null) {
459
+ let t = typeof e;
460
+ if (t !== "string") throw TypeError(`\`resolveUndefinedEntity()\` must return a string, \`null\`, or \`undefined\`, but returned a value of type ${t}`);
461
+ return e;
462
+ }
463
+ }
464
+ if (n) return i;
465
+ throw e.o(-i.length), this.a(`Named entity isn't defined: ${i}`);
466
+ }
467
+ return n;
468
+ }
469
+ s() {
470
+ let { c: e } = this, t = e.b("\"") || e.b("'");
471
+ if (!t) return !1;
472
+ let n = e.t(t);
473
+ if (this.p(n), !e.b(t)) throw this.a("Missing end quote");
474
+ return n;
475
+ }
476
+ e() {
477
+ return !!this.c.v(T);
478
+ }
479
+ P() {
480
+ let { c: e } = this, t = e.d;
481
+ if (!e.b("<?xml")) return !1;
482
+ if (!this.e()) throw this.a("Invalid XML declaration");
483
+ let n = !!e.b("version") && this.u() && this.s();
484
+ if (n === !1) throw this.a("XML version is missing or invalid");
485
+ if (!/^1\.[0-9]+$/.test(n)) throw this.a("Invalid character in version number");
486
+ let r, i;
487
+ if (this.e() && (r = !!e.b("encoding") && this.u() && this.s(), r && this.e(), i = !!e.b("standalone") && this.u() && this.s(), i)) {
488
+ if (i !== "yes" && i !== "no") throw this.a("Only \"yes\" and \"no\" are permitted as values of `standalone`");
489
+ this.e();
490
+ }
491
+ if (!e.b("?>")) throw this.a("Invalid or unclosed XML declaration");
492
+ return this.f.preserveXmlDeclaration ? this.j(new j(n, r || void 0, i || void 0), t) : !0;
493
+ }
494
+ a(e) {
495
+ let { c: t } = this;
496
+ return new re(e, t.d, t.m);
497
+ }
498
+ p(e) {
499
+ let { length: t } = e;
500
+ for (let n = 0; n < t; ++n) {
501
+ let t = e.codePointAt(n);
502
+ if (!E(t)) throw this.c.o(-([...e].length - n)), this.a("Invalid character");
503
+ t > 65535 && (n += 1);
504
+ }
505
+ }
506
+ };
507
+ function P(e) {
508
+ let t = 0;
509
+ for (; (t = e.indexOf("\r", t)) !== -1;) e = e[t + 1] === "\n" ? e.slice(0, t) + e.slice(t + 1) : e.slice(0, t) + "\n" + e.slice(t + 1);
510
+ return e;
511
+ }
512
+ function se(e, t) {
513
+ return new oe(e, t).document;
514
+ }
515
+ var ce = class extends Error {
516
+ constructor(e, t, n) {
517
+ super(e), this.httpStatus = t, this.isCrossOriginRelated = n, this.name = "EndpointError";
518
+ }
519
+ }, le = class extends Error {
520
+ constructor(e, t, n, r, i) {
521
+ super(e), this.requestUrl = t, this.code = n, this.locator = r, this.response = i, this.name = "ServiceExceptionError";
522
+ }
523
+ };
524
+ function ue(e) {
525
+ if (e.name === "ServiceExceptionError") {
526
+ let t = new le(e.message, e.requestUrl, e.code, e.locator, e.response);
527
+ return t.stack = e.stack, t;
528
+ }
529
+ if (e.name === "EndpointError") {
530
+ let t = new ce(e.message, e.httpStatus, e.isCrossOriginRelated);
531
+ return t.stack = e.stack, t;
532
+ }
533
+ let t = Error(e.message);
534
+ return t.stack = e.stack, t;
535
+ }
536
+ var de = new EventTarget();
537
+ function fe(e, t, n) {
538
+ return new Promise((r, i) => {
539
+ let o = a(), s = {
540
+ requestId: o,
541
+ taskName: e,
542
+ params: n
543
+ };
544
+ t === null ? de.dispatchEvent(new CustomEvent("ogc-client.request", { detail: s })) : t.postMessage(s);
545
+ let c = (e) => {
546
+ e.requestId === o && (t === null ? de.removeEventListener("ogc-client.response", l) : t.removeEventListener("message", u), "error" in e ? i(ue(e.error)) : r(e.response));
547
+ }, l = (e) => c(e.detail), u = (e) => c(e.data);
548
+ t === null ? de.addEventListener("ogc-client.response", l) : t.addEventListener("message", u);
549
+ });
550
+ }
551
+ var pe = typeof window < "u" && window.Blob && new Blob([atob("KGZ1bmN0aW9uKCkgewogICJ1c2Ugc3RyaWN0IjsKICAvKiEgQHJncm92ZS9wYXJzZS14bWwgdjQuMS4wIHwgSVNDIExpY2Vuc2UgfCBDb3B5cmlnaHQgUnlhbiBHcm92ZSAqLwogIHZhciBfX2RlZlByb3AgPSBPYmplY3QuZGVmaW5lUHJvcGVydHk7CiAgdmFyIF9fZ2V0T3duUHJvcERlc2MgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yOwogIHZhciBfX2dldE93blByb3BOYW1lcyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzOwogIHZhciBfX2hhc093blByb3AgPSBPYmplY3QucHJvdG90eXBlLmhhc093blByb3BlcnR5OwogIHZhciBfX2V4cG9ydCA9ICh0YXJnZXQsIGFsbCkgPT4gewogICAgZm9yICh2YXIgbmFtZSBpbiBhbGwpCiAgICAgIF9fZGVmUHJvcCh0YXJnZXQsIG5hbWUsIHsgZ2V0OiBhbGxbbmFtZV0sIGVudW1lcmFibGU6IHRydWUgfSk7CiAgfTsKICB2YXIgX19jb3B5UHJvcHMgPSAodG8sIGZyb20sIGV4Y2VwdCwgZGVzYykgPT4gewogICAgaWYgKGZyb20gJiYgdHlwZW9mIGZyb20gPT09ICJvYmplY3QiIHx8IHR5cGVvZiBmcm9tID09PSAiZnVuY3Rpb24iKSB7CiAgICAgIGZvciAobGV0IGtleSBvZiBfX2dldE93blByb3BOYW1lcyhmcm9tKSkKICAgICAgICBpZiAoIV9faGFzT3duUHJvcC5jYWxsKHRvLCBrZXkpICYmIGtleSAhPT0gZXhjZXB0KQogICAgICAgICAgX19kZWZQcm9wKHRvLCBrZXksIHsgZ2V0OiAoKSA9PiBmcm9tW2tleV0sIGVudW1lcmFibGU6ICEoZGVzYyA9IF9fZ2V0T3duUHJvcERlc2MoZnJvbSwga2V5KSkgfHwgZGVzYy5lbnVtZXJhYmxlIH0pOwogICAgfQogICAgcmV0dXJuIHRvOwogIH07CiAgdmFyIF9fdG9Db21tb25KUyA9IChtb2QpID0+IF9fY29weVByb3BzKF9fZGVmUHJvcCh7fSwgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pLCBtb2QpOwogIHZhciBzcmNfZXhwb3J0cyA9IHt9OwogIF9fZXhwb3J0KHNyY19leHBvcnRzLCB7CiAgICBYbWxDZGF0YTogKCkgPT4gWG1sQ2RhdGEsCiAgICBYbWxDb21tZW50OiAoKSA9PiBYbWxDb21tZW50LAogICAgWG1sRGVjbGFyYXRpb246ICgpID0+IFhtbERlY2xhcmF0aW9uLAogICAgWG1sRG9jdW1lbnQ6ICgpID0+IFhtbERvY3VtZW50LAogICAgWG1sRG9jdW1lbnRUeXBlOiAoKSA9PiBYbWxEb2N1bWVudFR5cGUsCiAgICBYbWxFbGVtZW50OiAoKSA9PiBYbWxFbGVtZW50LAogICAgWG1sRXJyb3I6ICgpID0+IFhtbEVycm9yLAogICAgWG1sTm9kZTogKCkgPT4gWG1sTm9kZSwKICAgIFhtbFByb2Nlc3NpbmdJbnN0cnVjdGlvbjogKCkgPT4gWG1sUHJvY2Vzc2luZ0luc3RydWN0aW9uLAogICAgWG1sVGV4dDogKCkgPT4gWG1sVGV4dCwKICAgIHBhcnNlWG1sOiAoKSA9PiBwYXJzZVhtbAogIH0pOwogIHZhciBicm93c2VyID0gX190b0NvbW1vbkpTKHNyY19leHBvcnRzKTsKICB2YXIgZW1wdHlTdHJpbmcgPSAiIjsKICB2YXIgc3Vycm9nYXRlUGFpciA9IC9bXHVEODAwLVx1REJGRl1bXHVEQzAwLVx1REZGRl0vZzsKICB2YXIgU3RyaW5nU2Nhbm5lciA9IGNsYXNzIHsKICAgIGNvbnN0cnVjdG9yKHN0cmluZykgewogICAgICB0aGlzLmsgPSB0aGlzLnEoc3RyaW5nLCB0cnVlKTsKICAgICAgdGhpcy5kID0gMDsKICAgICAgdGhpcy5sZW5ndGggPSBzdHJpbmcubGVuZ3RoOwogICAgICB0aGlzLm4gPSB0aGlzLmsgIT09IHRoaXMubGVuZ3RoOwogICAgICB0aGlzLm0gPSBzdHJpbmc7CiAgICAgIGlmICh0aGlzLm4pIHsKICAgICAgICBsZXQgY2hhcnNUb0J5dGVzID0gW107CiAgICAgICAgZm9yIChsZXQgYnl0ZUluZGV4ID0gMCwgY2hhckluZGV4ID0gMDsgY2hhckluZGV4IDwgdGhpcy5rOyArK2NoYXJJbmRleCkgewogICAgICAgICAgY2hhcnNUb0J5dGVzW2NoYXJJbmRleF0gPSBieXRlSW5kZXg7CiAgICAgICAgICBieXRlSW5kZXggKz0gc3RyaW5nLmNvZGVQb2ludEF0KGJ5dGVJbmRleCkgPiA2NTUzNSA/IDIgOiAxOwogICAgICAgIH0KICAgICAgICB0aGlzLnkgPSBjaGFyc1RvQnl0ZXM7CiAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogV2hldGhlciB0aGUgY3VycmVudCBjaGFyYWN0ZXIgaW5kZXggaXMgYXQgdGhlIGVuZCBvZiB0aGUgaW5wdXQgc3RyaW5nLgogICAgICovCiAgICBnZXQgeigpIHsKICAgICAgcmV0dXJuIHRoaXMuZCA+PSB0aGlzLms7CiAgICB9CiAgICAvLyAtLSBQcm90ZWN0ZWQgTWV0aG9kcyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgbnVtYmVyIG9mIGNoYXJhY3RlcnMgaW4gdGhlIGdpdmVuIHN0cmluZywgd2hpY2ggbWF5IGRpZmZlciBmcm9tCiAgICAgKiB0aGUgYnl0ZSBsZW5ndGggaWYgdGhlIHN0cmluZyBjb250YWlucyBtdWx0aWJ5dGUgY2hhcmFjdGVycy4KICAgICAqLwogICAgcShzdHJpbmcsIG11bHRpQnl0ZVNhZmUgPSB0aGlzLm4pIHsKICAgICAgcmV0dXJuIG11bHRpQnl0ZVNhZmUgPyBzdHJpbmcucmVwbGFjZShzdXJyb2dhdGVQYWlyLCAiXyIpLmxlbmd0aCA6IHN0cmluZy5sZW5ndGg7CiAgICB9CiAgICAvLyAtLSBQdWJsaWMgTWV0aG9kcyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgIC8qKgogICAgICogQWR2YW5jZXMgdGhlIHNjYW5uZXIgYnkgdGhlIGdpdmVuIG51bWJlciBvZiBjaGFyYWN0ZXJzLCBzdG9wcGluZyBpZiB0aGUgZW5kCiAgICAgKiBvZiB0aGUgc3RyaW5nIGlzIHJlYWNoZWQuCiAgICAgKi8KICAgIGcoY291bnQgPSAxKSB7CiAgICAgIHRoaXMuZCA9IE1hdGgubWluKHRoaXMuaywgdGhpcy5kICsgY291bnQpOwogICAgfQogICAgLyoqCiAgICAgKiBSZXR1cm5zIHRoZSBieXRlIGluZGV4IG9mIHRoZSBnaXZlbiBjaGFyYWN0ZXIgaW5kZXggaW4gdGhlIHN0cmluZy4gVGhlIHR3bwogICAgICogbWF5IGRpZmZlciBpbiBzdHJpbmdzIHRoYXQgY29udGFpbiBtdWx0aWJ5dGUgY2hhcmFjdGVycy4KICAgICAqLwogICAgaShjaGFySW5kZXggPSB0aGlzLmQpIHsKICAgICAgdmFyIF9hOwogICAgICByZXR1cm4gdGhpcy5uID8gKF9hID0gdGhpcy55W2NoYXJJbmRleF0pICE9IG51bGwgPyBfYSA6IEluZmluaXR5IDogY2hhckluZGV4OwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhbmQgcmV0dXJucyB0aGUgZ2l2ZW4gbnVtYmVyIG9mIGNoYXJhY3RlcnMgaWYgcG9zc2libGUsIGFkdmFuY2luZwogICAgICogdGhlIHNjYW5uZXIgYW5kIHN0b3BwaW5nIGlmIHRoZSBlbmQgb2YgdGhlIHN0cmluZyBpcyByZWFjaGVkLgogICAgICoKICAgICAqIElmIG5vIGNoYXJhY3RlcnMgY291bGQgYmUgY29uc3VtZWQsIGFuIGVtcHR5IHN0cmluZyB3aWxsIGJlIHJldHVybmVkLgogICAgICovCiAgICBGKGNvdW50ID0gMSkgewogICAgICBsZXQgY2hhcnMgPSB0aGlzLmgoY291bnQpOwogICAgICB0aGlzLmcoY291bnQpOwogICAgICByZXR1cm4gY2hhcnM7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgbWF0Y2ggZm9yIHRoZSBnaXZlbiBzdGlja3kgcmVnZXgsIGFkdmFuY2VzIHRoZSBzY2FubmVyLCB1cGRhdGVzCiAgICAgKiB0aGUgYGxhc3RJbmRleGAgcHJvcGVydHkgb2YgdGhlIHJlZ2V4LCBhbmQgcmV0dXJucyB0aGUgbWF0Y2hpbmcgc3RyaW5nLgogICAgICoKICAgICAqIFRoZSByZWdleCBtdXN0IGhhdmUgYSBzdGlja3kgZmxhZyAoInkiKSBzbyB0aGF0IGl0cyBgbGFzdEluZGV4YCBwcm9wIGNhbiBiZQogICAgICogdXNlZCB0byBhbmNob3IgdGhlIG1hdGNoIGF0IHRoZSBjdXJyZW50IHNjYW5uZXIgcG9zaXRpb24uCiAgICAgKgogICAgICogUmV0dXJucyB0aGUgY29uc3VtZWQgc3RyaW5nLCBvciBhbiBlbXB0eSBzdHJpbmcgaWYgbm90aGluZyB3YXMgY29uc3VtZWQuCiAgICAgKi8KICAgIEcocmVnZXgpIHsKICAgICAgaWYgKCFyZWdleC5zdGlja3kpIHsKICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ2ByZWdleGAgbXVzdCBoYXZlIGEgc3RpY2t5IGZsYWcgKCJ5IiknKTsKICAgICAgfQogICAgICByZWdleC5sYXN0SW5kZXggPSB0aGlzLmkoKTsKICAgICAgbGV0IHJlc3VsdCA9IHJlZ2V4LmV4ZWModGhpcy5tKTsKICAgICAgaWYgKHJlc3VsdCA9PT0gbnVsbCB8fCByZXN1bHQubGVuZ3RoID09PSAwKSB7CiAgICAgICAgcmV0dXJuIGVtcHR5U3RyaW5nOwogICAgICB9CiAgICAgIGxldCBtYXRjaCA9IHJlc3VsdFswXTsKICAgICAgdGhpcy5nKHRoaXMucShtYXRjaCkpOwogICAgICByZXR1cm4gbWF0Y2g7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGFuZCByZXR1cm5zIGFsbCBjaGFyYWN0ZXJzIGZvciB3aGljaCB0aGUgZ2l2ZW4gZnVuY3Rpb24gcmV0dXJucyBhCiAgICAgKiB0cnV0aHkgdmFsdWUsIHN0b3BwaW5nIG9uIHRoZSBmaXJzdCBmYWxzeSByZXR1cm4gdmFsdWUgb3IgaWYgdGhlIGVuZCBvZiB0aGUKICAgICAqIGlucHV0IGlzIHJlYWNoZWQuCiAgICAgKi8KICAgIHYoZm4pIHsKICAgICAgbGV0IGNoYXI7CiAgICAgIGxldCBtYXRjaCA9IGVtcHR5U3RyaW5nOwogICAgICB3aGlsZSAoKGNoYXIgPSB0aGlzLmgoKSkgJiYgZm4oY2hhcikpIHsKICAgICAgICBtYXRjaCArPSBjaGFyOwogICAgICAgIHRoaXMuZygpOwogICAgICB9CiAgICAgIHJldHVybiBtYXRjaDsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgdGhlIGdpdmVuIHN0cmluZyBpZiBpdCBleGlzdHMgYXQgdGhlIGN1cnJlbnQgY2hhcmFjdGVyIGluZGV4LCBhbmQKICAgICAqIGFkdmFuY2VzIHRoZSBzY2FubmVyLgogICAgICoKICAgICAqIElmIHRoZSBnaXZlbiBzdHJpbmcgZG9lc24ndCBleGlzdCBhdCB0aGUgY3VycmVudCBjaGFyYWN0ZXIgaW5kZXgsIGFuIGVtcHR5CiAgICAgKiBzdHJpbmcgd2lsbCBiZSByZXR1cm5lZCBhbmQgdGhlIHNjYW5uZXIgd2lsbCBub3QgYmUgYWR2YW5jZWQuCiAgICAgKi8KICAgIFEoc3RyaW5nVG9Db25zdW1lKSB7CiAgICAgIGlmICh0aGlzLmIoc3RyaW5nVG9Db25zdW1lKSkgewogICAgICAgIHJldHVybiBzdHJpbmdUb0NvbnN1bWU7CiAgICAgIH0KICAgICAgaWYgKHRoaXMubikgewogICAgICAgIGxldCB7IGxlbmd0aCB9ID0gc3RyaW5nVG9Db25zdW1lOwogICAgICAgIGxldCBjaGFyTGVuZ3RoVG9NYXRjaCA9IHRoaXMucShzdHJpbmdUb0NvbnN1bWUpOwogICAgICAgIGlmIChjaGFyTGVuZ3RoVG9NYXRjaCAhPT0gbGVuZ3RoICYmIHN0cmluZ1RvQ29uc3VtZSA9PT0gdGhpcy5oKGNoYXJMZW5ndGhUb01hdGNoKSkgewogICAgICAgICAgdGhpcy5nKGNoYXJMZW5ndGhUb01hdGNoKTsKICAgICAgICAgIHJldHVybiBzdHJpbmdUb0NvbnN1bWU7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiBlbXB0eVN0cmluZzsKICAgIH0KICAgIC8qKgogICAgICogRG9lcyB0aGUgc2FtZSB0aGluZyBhcyBgY29uc3VtZVN0cmluZygpYCwgYnV0IGRvZXNuJ3Qgc3VwcG9ydCBjb25zdW1pbmcKICAgICAqIG11bHRpYnl0ZSBjaGFyYWN0ZXJzLiBUaGlzIGNhbiBiZSBmYXN0ZXIgaWYgeW91IG9ubHkgbmVlZCB0byBtYXRjaCBzaW5nbGUKICAgICAqIGJ5dGUgY2hhcmFjdGVycy4KICAgICAqLwogICAgYihzdHJpbmdUb0NvbnN1bWUpIHsKICAgICAgbGV0IHsgbGVuZ3RoIH0gPSBzdHJpbmdUb0NvbnN1bWU7CiAgICAgIGlmICh0aGlzLmgobGVuZ3RoKSA9PT0gc3RyaW5nVG9Db25zdW1lKSB7CiAgICAgICAgdGhpcy5nKGxlbmd0aCk7CiAgICAgICAgcmV0dXJuIHN0cmluZ1RvQ29uc3VtZTsKICAgICAgfQogICAgICByZXR1cm4gZW1wdHlTdHJpbmc7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGNoYXJhY3RlcnMgdW50aWwgdGhlIGdpdmVuIGdsb2JhbCByZWdleCBpcyBtYXRjaGVkLCBhZHZhbmNpbmcgdGhlCiAgICAgKiBzY2FubmVyIHVwIHRvIChidXQgbm90IGJleW9uZCkgdGhlIGJlZ2lubmluZyBvZiB0aGUgbWF0Y2guIElmIHRoZSByZWdleAogICAgICogZG9lc24ndCBtYXRjaCwgbm90aGluZyB3aWxsIGJlIGNvbnN1bWVkLgogICAgICoKICAgICAqIFJldHVybnMgdGhlIGNvbnN1bWVkIHN0cmluZywgb3IgYW4gZW1wdHkgc3RyaW5nIGlmIG5vdGhpbmcgd2FzIGNvbnN1bWVkLgogICAgICovCiAgICBBKHJlZ2V4KSB7CiAgICAgIGxldCByZXN0T2ZTdHJpbmcgPSB0aGlzLm0uc2xpY2UodGhpcy5pKCkpOwogICAgICBsZXQgbWF0Y2hCeXRlSW5kZXggPSByZXN0T2ZTdHJpbmcuc2VhcmNoKHJlZ2V4KTsKICAgICAgaWYgKG1hdGNoQnl0ZUluZGV4IDw9IDApIHsKICAgICAgICByZXR1cm4gZW1wdHlTdHJpbmc7CiAgICAgIH0KICAgICAgbGV0IHJlc3VsdCA9IHJlc3RPZlN0cmluZy5zbGljZSgwLCBtYXRjaEJ5dGVJbmRleCk7CiAgICAgIHRoaXMuZyh0aGlzLnEocmVzdWx0KSk7CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGNoYXJhY3RlcnMgdW50aWwgdGhlIGdpdmVuIHN0cmluZyBpcyBmb3VuZCwgYWR2YW5jaW5nIHRoZSBzY2FubmVyCiAgICAgKiB1cCB0byAoYnV0IG5vdCBiZXlvbmQpIHRoYXQgcG9pbnQuIElmIHRoZSBzdHJpbmcgaXMgbmV2ZXIgZm91bmQsIG5vdGhpbmcKICAgICAqIHdpbGwgYmUgY29uc3VtZWQuCiAgICAgKgogICAgICogUmV0dXJucyB0aGUgY29uc3VtZWQgc3RyaW5nLCBvciBhbiBlbXB0eSBzdHJpbmcgaWYgbm90aGluZyB3YXMgY29uc3VtZWQuCiAgICAgKi8KICAgIHQoc2VhcmNoU3RyaW5nKSB7CiAgICAgIGxldCB7IG06IHN0cmluZyB9ID0gdGhpczsKICAgICAgbGV0IGJ5dGVJbmRleCA9IHRoaXMuaSgpOwogICAgICBsZXQgbWF0Y2hCeXRlSW5kZXggPSBzdHJpbmcuaW5kZXhPZihzZWFyY2hTdHJpbmcsIGJ5dGVJbmRleCk7CiAgICAgIGlmIChtYXRjaEJ5dGVJbmRleCA8PSAwKSB7CiAgICAgICAgcmV0dXJuIGVtcHR5U3RyaW5nOwogICAgICB9CiAgICAgIGxldCByZXN1bHQgPSBzdHJpbmcuc2xpY2UoYnl0ZUluZGV4LCBtYXRjaEJ5dGVJbmRleCk7CiAgICAgIHRoaXMuZyh0aGlzLnEocmVzdWx0KSk7CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGdpdmVuIG51bWJlciBvZiBjaGFyYWN0ZXJzIHN0YXJ0aW5nIGF0IHRoZSBjdXJyZW50IGNoYXJhY3RlcgogICAgICogaW5kZXgsIHdpdGhvdXQgYWR2YW5jaW5nIHRoZSBzY2FubmVyIGFuZCB3aXRob3V0IGV4Y2VlZGluZyB0aGUgZW5kIG9mIHRoZQogICAgICogaW5wdXQgc3RyaW5nLgogICAgICovCiAgICBoKGNvdW50ID0gMSkgewogICAgICBsZXQgeyBkOiBjaGFySW5kZXgsIG46IG11bHRpQnl0ZU1vZGUsIG06IHN0cmluZyB9ID0gdGhpczsKICAgICAgaWYgKG11bHRpQnl0ZU1vZGUpIHsKICAgICAgICBpZiAoY2hhckluZGV4ID49IHRoaXMuaykgewogICAgICAgICAgcmV0dXJuIGVtcHR5U3RyaW5nOwogICAgICAgIH0KICAgICAgICByZXR1cm4gc3RyaW5nLnNsaWNlKAogICAgICAgICAgdGhpcy5pKGNoYXJJbmRleCksCiAgICAgICAgICB0aGlzLmkoY2hhckluZGV4ICsgY291bnQpCiAgICAgICAgKTsKICAgICAgfQogICAgICByZXR1cm4gc3RyaW5nLnNsaWNlKGNoYXJJbmRleCwgY2hhckluZGV4ICsgY291bnQpOwogICAgfQogICAgLyoqCiAgICAgKiBSZXNldHMgdGhlIHNjYW5uZXIgcG9zaXRpb24gdG8gdGhlIGdpdmVuIGNoYXJhY3RlciBfaW5kZXhfLCBvciB0byB0aGUgc3RhcnQKICAgICAqIG9mIHRoZSBpbnB1dCBzdHJpbmcgaWYgbm8gaW5kZXggaXMgZ2l2ZW4uCiAgICAgKgogICAgICogSWYgX2luZGV4XyBpcyBuZWdhdGl2ZSwgdGhlIHNjYW5uZXIgcG9zaXRpb24gd2lsbCBiZSBtb3ZlZCBiYWNrd2FyZCBieSB0aGF0CiAgICAgKiBtYW55IGNoYXJhY3RlcnMsIHN0b3BwaW5nIGlmIHRoZSBiZWdpbm5pbmcgb2YgdGhlIHN0cmluZyBpcyByZWFjaGVkLgogICAgICovCiAgICBvKGluZGV4ID0gMCkgewogICAgICB0aGlzLmQgPSBpbmRleCA+PSAwID8gTWF0aC5taW4odGhpcy5rLCBpbmRleCkgOiBNYXRoLm1heCgwLCB0aGlzLmQgKyBpbmRleCk7CiAgICB9CiAgfTsKICB2YXIgYXR0VmFsdWVDaGFyRG91YmxlUXVvdGUgPSAvW14iJjxdKy95OwogIHZhciBhdHRWYWx1ZUNoYXJTaW5nbGVRdW90ZSA9IC9bXicmPF0rL3k7CiAgdmFyIGF0dFZhbHVlTm9ybWFsaXplZFdoaXRlc3BhY2UgPSAvXHJcbnxbXG5cclx0XS9nOwogIHZhciBlbmRDaGFyRGF0YSA9IC88fCZ8XV0+LzsKICB2YXIgcHJlZGVmaW5lZEVudGl0aWVzID0gT2JqZWN0LmZyZWV6ZShPYmplY3QuYXNzaWduKC8qIEBfX1BVUkVfXyAqLyBPYmplY3QuY3JlYXRlKG51bGwpLCB7CiAgICBhbXA6ICImIiwKICAgIGFwb3M6ICInIiwKICAgIGd0OiAiPiIsCiAgICBsdDogIjwiLAogICAgcXVvdDogJyInCiAgfSkpOwogIGZ1bmN0aW9uIGlzTmFtZUNoYXIoY2hhcikgewogICAgbGV0IGNwID0gZ2V0Q29kZVBvaW50KGNoYXIpOwogICAgcmV0dXJuIGNwID49IDk3ICYmIGNwIDw9IDEyMiB8fCBjcCA+PSA2NSAmJiBjcCA8PSA5MCB8fCBjcCA+PSA0OCAmJiBjcCA8PSA1NyB8fCBjcCA9PT0gNDUgfHwgY3AgPT09IDQ2IHx8IGNwID09PSAxODMgfHwgY3AgPj0gNzY4ICYmIGNwIDw9IDg3OSB8fCBjcCA+PSA4MjU1ICYmIGNwIDw9IDgyNTYgfHwgaXNOYW1lU3RhcnRDaGFyKGNoYXIsIGNwKTsKICB9CiAgZnVuY3Rpb24gaXNOYW1lU3RhcnRDaGFyKGNoYXIsIGNwID0gZ2V0Q29kZVBvaW50KGNoYXIpKSB7CiAgICByZXR1cm4gY3AgPj0gOTcgJiYgY3AgPD0gMTIyIHx8IGNwID49IDY1ICYmIGNwIDw9IDkwIHx8IGNwID09PSA1OCB8fCBjcCA9PT0gOTUgfHwgY3AgPj0gMTkyICYmIGNwIDw9IDIxNCB8fCBjcCA+PSAyMTYgJiYgY3AgPD0gMjQ2IHx8IGNwID49IDI0OCAmJiBjcCA8PSA3NjcgfHwgY3AgPj0gODgwICYmIGNwIDw9IDg5MyB8fCBjcCA+PSA4OTUgJiYgY3AgPD0gODE5MSB8fCBjcCA+PSA4MjA0ICYmIGNwIDw9IDgyMDUgfHwgY3AgPj0gODMwNCAmJiBjcCA8PSA4NTkxIHx8IGNwID49IDExMjY0ICYmIGNwIDw9IDEyMjcxIHx8IGNwID49IDEyMjg5ICYmIGNwIDw9IDU1Mjk1IHx8IGNwID49IDYzNzQ0ICYmIGNwIDw9IDY0OTc1IHx8IGNwID49IDY1MDA4ICYmIGNwIDw9IDY1NTMzIHx8IGNwID49IDY1NTM2ICYmIGNwIDw9IDk4MzAzOTsKICB9CiAgZnVuY3Rpb24gaXNSZWZlcmVuY2VDaGFyKGNoYXIpIHsKICAgIHJldHVybiBjaGFyID09PSAiIyIgfHwgaXNOYW1lQ2hhcihjaGFyKTsKICB9CiAgZnVuY3Rpb24gaXNXaGl0ZXNwYWNlKGNoYXIpIHsKICAgIGxldCBjcCA9IGdldENvZGVQb2ludChjaGFyKTsKICAgIHJldHVybiBjcCA9PT0gMzIgfHwgY3AgPT09IDkgfHwgY3AgPT09IDEwIHx8IGNwID09PSAxMzsKICB9CiAgZnVuY3Rpb24gaXNYbWxDb2RlUG9pbnQoY3ApIHsKICAgIHJldHVybiBjcCA9PT0gOSB8fCBjcCA9PT0gMTAgfHwgY3AgPT09IDEzIHx8IGNwID49IDMyICYmIGNwIDw9IDU1Mjk1IHx8IGNwID49IDU3MzQ0ICYmIGNwIDw9IDY1NTMzIHx8IGNwID49IDY1NTM2ICYmIGNwIDw9IDExMTQxMTE7CiAgfQogIGZ1bmN0aW9uIGdldENvZGVQb2ludChjaGFyKSB7CiAgICByZXR1cm4gY2hhci5jb2RlUG9pbnRBdCgwKSB8fCAtMTsKICB9CiAgdmFyIF9YbWxOb2RlID0gY2xhc3MgewogICAgY29uc3RydWN0b3IoKSB7CiAgICAgIHRoaXMucGFyZW50ID0gbnVsbDsKICAgICAgdGhpcy5zdGFydCA9IC0xOwogICAgICB0aGlzLmVuZCA9IC0xOwogICAgfQogICAgLyoqCiAgICAgKiBEb2N1bWVudCB0aGF0IGNvbnRhaW5zIHRoaXMgbm9kZSwgb3IgYG51bGxgIGlmIHRoaXMgbm9kZSBpcyBub3QgYXNzb2NpYXRlZAogICAgICogd2l0aCBhIGRvY3VtZW50LgogICAgICovCiAgICBnZXQgZG9jdW1lbnQoKSB7CiAgICAgIHZhciBfYSwgX2I7CiAgICAgIHJldHVybiAoX2IgPSAoX2EgPSB0aGlzLnBhcmVudCkgPT0gbnVsbCA/IHZvaWQgMCA6IF9hLmRvY3VtZW50KSAhPSBudWxsID8gX2IgOiBudWxsOwogICAgfQogICAgLyoqCiAgICAgKiBXaGV0aGVyIHRoaXMgbm9kZSBpcyB0aGUgcm9vdCBub2RlIG9mIHRoZSBkb2N1bWVudCAoYWxzbyBrbm93biBhcyB0aGUKICAgICAqIGRvY3VtZW50IGVsZW1lbnQpLgogICAgICovCiAgICBnZXQgaXNSb290Tm9kZSgpIHsKICAgICAgcmV0dXJuIHRoaXMucGFyZW50ICE9PSBudWxsICYmIHRoaXMucGFyZW50ID09PSB0aGlzLmRvY3VtZW50ICYmIHRoaXMudHlwZSA9PT0gX1htbE5vZGUuVFlQRV9FTEVNRU5UOwogICAgfQogICAgLyoqCiAgICAgKiBXaGV0aGVyIHdoaXRlc3BhY2Ugc2hvdWxkIGJlIHByZXNlcnZlZCBpbiB0aGUgY29udGVudCBvZiB0aGlzIGVsZW1lbnQgYW5kCiAgICAgKiBpdHMgY2hpbGRyZW4uCiAgICAgKgogICAgICogVGhpcyBpcyBpbmZsdWVuY2VkIGJ5IHRoZSB2YWx1ZSBvZiB0aGUgc3BlY2lhbCBgeG1sOnNwYWNlYCBhdHRyaWJ1dGUsIGFuZAogICAgICogd2lsbCBiZSBgdHJ1ZWAgZm9yIGFueSBub2RlIHdob3NlIGB4bWw6c3BhY2VgIGF0dHJpYnV0ZSBpcyBzZXQgdG8KICAgICAqICJwcmVzZXJ2ZSIuIElmIGEgbm9kZSBoYXMgbm8gc3VjaCBhdHRyaWJ1dGUsIGl0IHdpbGwgaW5oZXJpdCB0aGUgdmFsdWUgb2YKICAgICAqIHRoZSBuZWFyZXN0IGFuY2VzdG9yIHRoYXQgZG9lcyAoaWYgYW55KS4KICAgICAqCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI3NlYy13aGl0ZS1zcGFjZQogICAgICovCiAgICBnZXQgcHJlc2VydmVXaGl0ZXNwYWNlKCkgewogICAgICB2YXIgX2E7CiAgICAgIHJldHVybiAhISgoX2EgPSB0aGlzLnBhcmVudCkgPT0gbnVsbCA/IHZvaWQgMCA6IF9hLnByZXNlcnZlV2hpdGVzcGFjZSk7CiAgICB9CiAgICAvKioKICAgICAqIFR5cGUgb2YgdGhpcyBub2RlLgogICAgICoKICAgICAqIFRoZSB2YWx1ZSBvZiB0aGlzIHByb3BlcnR5IGlzIGEgc3RyaW5nIHRoYXQgbWF0Y2hlcyBvbmUgb2YgdGhlIHN0YXRpYwogICAgICogYFRZUEVfKmAgcHJvcGVydGllcyBvbiB0aGUgYFhtbE5vZGVgIGNsYXNzIChlLmcuIGBUWVBFX0VMRU1FTlRgLAogICAgICogYFRZUEVfVEVYVGAsIGV0Yy4pLgogICAgICoKICAgICAqIFRoZSBgWG1sTm9kZWAgY2xhc3MgaXRzZWxmIGlzIGEgYmFzZSBjbGFzcyBhbmQgZG9lc24ndCBoYXZlIGl0cyBvd24gdHlwZQogICAgICogbmFtZS4KICAgICAqLwogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiAiIjsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyBhIEpTT04tc2VyaWFsaXphYmxlIG9iamVjdCByZXByZXNlbnRpbmcgdGhpcyBub2RlLCBtaW51cyBwcm9wZXJ0aWVzCiAgICAgKiB0aGF0IGNvdWxkIHJlc3VsdCBpbiBjaXJjdWxhciByZWZlcmVuY2VzLgogICAgICovCiAgICB0b0pTT04oKSB7CiAgICAgIGxldCBqc29uID0gewogICAgICAgIHR5cGU6IHRoaXMudHlwZQogICAgICB9OwogICAgICBpZiAodGhpcy5pc1Jvb3ROb2RlKSB7CiAgICAgICAganNvbi5pc1Jvb3ROb2RlID0gdHJ1ZTsKICAgICAgfQogICAgICBpZiAodGhpcy5wcmVzZXJ2ZVdoaXRlc3BhY2UpIHsKICAgICAgICBqc29uLnByZXNlcnZlV2hpdGVzcGFjZSA9IHRydWU7CiAgICAgIH0KICAgICAgaWYgKHRoaXMuc3RhcnQgIT09IC0xKSB7CiAgICAgICAganNvbi5zdGFydCA9IHRoaXMuc3RhcnQ7CiAgICAgICAganNvbi5lbmQgPSB0aGlzLmVuZDsKICAgICAgfQogICAgICByZXR1cm4ganNvbjsKICAgIH0KICB9OwogIHZhciBYbWxOb2RlID0gX1htbE5vZGU7CiAgWG1sTm9kZS5UWVBFX0NEQVRBID0gImNkYXRhIjsKICBYbWxOb2RlLlRZUEVfQ09NTUVOVCA9ICJjb21tZW50IjsKICBYbWxOb2RlLlRZUEVfRE9DVU1FTlQgPSAiZG9jdW1lbnQiOwogIFhtbE5vZGUuVFlQRV9ET0NVTUVOVF9UWVBFID0gImRvY3R5cGUiOwogIFhtbE5vZGUuVFlQRV9FTEVNRU5UID0gImVsZW1lbnQiOwogIFhtbE5vZGUuVFlQRV9QUk9DRVNTSU5HX0lOU1RSVUNUSU9OID0gInBpIjsKICBYbWxOb2RlLlRZUEVfVEVYVCA9ICJ0ZXh0IjsKICBYbWxOb2RlLlRZUEVfWE1MX0RFQ0xBUkFUSU9OID0gInhtbGRlY2wiOwogIHZhciBYbWxUZXh0ID0gY2xhc3MgZXh0ZW5kcyBYbWxOb2RlIHsKICAgIGNvbnN0cnVjdG9yKHRleHQgPSAiIikgewogICAgICBzdXBlcigpOwogICAgICB0aGlzLnRleHQgPSB0ZXh0OwogICAgfQogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiBYbWxOb2RlLlRZUEVfVEVYVDsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24oWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyksIHsKICAgICAgICB0ZXh0OiB0aGlzLnRleHQKICAgICAgfSk7CiAgICB9CiAgfTsKICB2YXIgWG1sQ2RhdGEgPSBjbGFzcyBleHRlbmRzIFhtbFRleHQgewogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiBYbWxOb2RlLlRZUEVfQ0RBVEE7CiAgICB9CiAgfTsKICB2YXIgWG1sQ29tbWVudCA9IGNsYXNzIGV4dGVuZHMgWG1sTm9kZSB7CiAgICBjb25zdHJ1Y3Rvcihjb250ZW50ID0gIiIpIHsKICAgICAgc3VwZXIoKTsKICAgICAgdGhpcy5jb250ZW50ID0gY29udGVudDsKICAgIH0KICAgIGdldCB0eXBlKCkgewogICAgICByZXR1cm4gWG1sTm9kZS5UWVBFX0NPTU1FTlQ7CiAgICB9CiAgICB0b0pTT04oKSB7CiAgICAgIHJldHVybiBPYmplY3QuYXNzaWduKFhtbE5vZGUucHJvdG90eXBlLnRvSlNPTi5jYWxsKHRoaXMpLCB7CiAgICAgICAgY29udGVudDogdGhpcy5jb250ZW50CiAgICAgIH0pOwogICAgfQogIH07CiAgdmFyIFhtbERlY2xhcmF0aW9uID0gY2xhc3MgZXh0ZW5kcyBYbWxOb2RlIHsKICAgIGNvbnN0cnVjdG9yKHZlcnNpb24sIGVuY29kaW5nLCBzdGFuZGFsb25lKSB7CiAgICAgIHN1cGVyKCk7CiAgICAgIHRoaXMudmVyc2lvbiA9IHZlcnNpb247CiAgICAgIHRoaXMuZW5jb2RpbmcgPSBlbmNvZGluZyAhPSBudWxsID8gZW5jb2RpbmcgOiBudWxsOwogICAgICB0aGlzLnN0YW5kYWxvbmUgPSBzdGFuZGFsb25lICE9IG51bGwgPyBzdGFuZGFsb25lIDogbnVsbDsKICAgIH0KICAgIGdldCB0eXBlKCkgewogICAgICByZXR1cm4gWG1sTm9kZS5UWVBFX1hNTF9ERUNMQVJBVElPTjsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgbGV0IGpzb24gPSBYbWxOb2RlLnByb3RvdHlwZS50b0pTT04uY2FsbCh0aGlzKTsKICAgICAganNvbi52ZXJzaW9uID0gdGhpcy52ZXJzaW9uOwogICAgICBmb3IgKGxldCBrZXkgb2YgWyJlbmNvZGluZyIsICJzdGFuZGFsb25lIl0pIHsKICAgICAgICBpZiAodGhpc1trZXldICE9PSBudWxsKSB7CiAgICAgICAgICBqc29uW2tleV0gPSB0aGlzW2tleV07CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiBqc29uOwogICAgfQogIH07CiAgdmFyIFhtbEVsZW1lbnQgPSBjbGFzcyBleHRlbmRzIFhtbE5vZGUgewogICAgY29uc3RydWN0b3IobmFtZSwgYXR0cmlidXRlcyA9IC8qIEBfX1BVUkVfXyAqLyBPYmplY3QuY3JlYXRlKG51bGwpLCBjaGlsZHJlbiA9IFtdKSB7CiAgICAgIHN1cGVyKCk7CiAgICAgIHRoaXMubmFtZSA9IG5hbWU7CiAgICAgIHRoaXMuYXR0cmlidXRlcyA9IGF0dHJpYnV0ZXM7CiAgICAgIHRoaXMuY2hpbGRyZW4gPSBjaGlsZHJlbjsKICAgIH0KICAgIC8qKgogICAgICogV2hldGhlciB0aGlzIGVsZW1lbnQgaXMgZW1wdHkgKG1lYW5pbmcgaXQgaGFzIG5vIGNoaWxkcmVuKS4KICAgICAqLwogICAgZ2V0IGlzRW1wdHkoKSB7CiAgICAgIHJldHVybiB0aGlzLmNoaWxkcmVuLmxlbmd0aCA9PT0gMDsKICAgIH0KICAgIGdldCBwcmVzZXJ2ZVdoaXRlc3BhY2UoKSB7CiAgICAgIGxldCBub2RlID0gdGhpczsKICAgICAgd2hpbGUgKG5vZGUgaW5zdGFuY2VvZiBYbWxFbGVtZW50KSB7CiAgICAgICAgaWYgKCJ4bWw6c3BhY2UiIGluIG5vZGUuYXR0cmlidXRlcykgewogICAgICAgICAgcmV0dXJuIG5vZGUuYXR0cmlidXRlc1sieG1sOnNwYWNlIl0gPT09ICJwcmVzZXJ2ZSI7CiAgICAgICAgfQogICAgICAgIG5vZGUgPSBub2RlLnBhcmVudDsKICAgICAgfQogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgICAvKioKICAgICAqIFRleHQgY29udGVudCBvZiB0aGlzIGVsZW1lbnQgYW5kIGFsbCBpdHMgZGVzY2VuZGFudHMuCiAgICAgKi8KICAgIGdldCB0ZXh0KCkgewogICAgICByZXR1cm4gdGhpcy5jaGlsZHJlbi5tYXAoKGNoaWxkKSA9PiAidGV4dCIgaW4gY2hpbGQgPyBjaGlsZC50ZXh0IDogIiIpLmpvaW4oIiIpOwogICAgfQogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiBYbWxOb2RlLlRZUEVfRUxFTUVOVDsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24oWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyksIHsKICAgICAgICBuYW1lOiB0aGlzLm5hbWUsCiAgICAgICAgYXR0cmlidXRlczogdGhpcy5hdHRyaWJ1dGVzLAogICAgICAgIGNoaWxkcmVuOiB0aGlzLmNoaWxkcmVuLm1hcCgoY2hpbGQpID0+IGNoaWxkLnRvSlNPTigpKQogICAgICB9KTsKICAgIH0KICB9OwogIHZhciBYbWxEb2N1bWVudCA9IGNsYXNzIGV4dGVuZHMgWG1sTm9kZSB7CiAgICBjb25zdHJ1Y3RvcihjaGlsZHJlbiA9IFtdKSB7CiAgICAgIHN1cGVyKCk7CiAgICAgIHRoaXMuY2hpbGRyZW4gPSBjaGlsZHJlbjsKICAgIH0KICAgIGdldCBkb2N1bWVudCgpIHsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CiAgICAvKioKICAgICAqIFJvb3QgZWxlbWVudCBvZiB0aGlzIGRvY3VtZW50LCBvciBgbnVsbGAgaWYgdGhpcyBkb2N1bWVudCBpcyBlbXB0eS4KICAgICAqLwogICAgZ2V0IHJvb3QoKSB7CiAgICAgIGZvciAobGV0IGNoaWxkIG9mIHRoaXMuY2hpbGRyZW4pIHsKICAgICAgICBpZiAoY2hpbGQgaW5zdGFuY2VvZiBYbWxFbGVtZW50KSB7CiAgICAgICAgICByZXR1cm4gY2hpbGQ7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiBudWxsOwogICAgfQogICAgLyoqCiAgICAgKiBUZXh0IGNvbnRlbnQgb2YgdGhpcyBkb2N1bWVudCBhbmQgYWxsIGl0cyBkZXNjZW5kYW50cy4KICAgICAqLwogICAgZ2V0IHRleHQoKSB7CiAgICAgIHJldHVybiB0aGlzLmNoaWxkcmVuLm1hcCgoY2hpbGQpID0+ICJ0ZXh0IiBpbiBjaGlsZCA/IGNoaWxkLnRleHQgOiAiIikuam9pbigiIik7CiAgICB9CiAgICBnZXQgdHlwZSgpIHsKICAgICAgcmV0dXJuIFhtbE5vZGUuVFlQRV9ET0NVTUVOVDsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24oWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyksIHsKICAgICAgICBjaGlsZHJlbjogdGhpcy5jaGlsZHJlbi5tYXAoKGNoaWxkKSA9PiBjaGlsZC50b0pTT04oKSkKICAgICAgfSk7CiAgICB9CiAgfTsKICB2YXIgWG1sRG9jdW1lbnRUeXBlID0gY2xhc3MgZXh0ZW5kcyBYbWxOb2RlIHsKICAgIGNvbnN0cnVjdG9yKG5hbWUsIHB1YmxpY0lkLCBzeXN0ZW1JZCwgaW50ZXJuYWxTdWJzZXQpIHsKICAgICAgc3VwZXIoKTsKICAgICAgdGhpcy5uYW1lID0gbmFtZTsKICAgICAgdGhpcy5wdWJsaWNJZCA9IHB1YmxpY0lkICE9IG51bGwgPyBwdWJsaWNJZCA6IG51bGw7CiAgICAgIHRoaXMuc3lzdGVtSWQgPSBzeXN0ZW1JZCAhPSBudWxsID8gc3lzdGVtSWQgOiBudWxsOwogICAgICB0aGlzLmludGVybmFsU3Vic2V0ID0gaW50ZXJuYWxTdWJzZXQgIT0gbnVsbCA/IGludGVybmFsU3Vic2V0IDogbnVsbDsKICAgIH0KICAgIGdldCB0eXBlKCkgewogICAgICByZXR1cm4gWG1sTm9kZS5UWVBFX0RPQ1VNRU5UX1RZUEU7CiAgICB9CiAgICB0b0pTT04oKSB7CiAgICAgIGxldCBqc29uID0gWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyk7CiAgICAgIGpzb24ubmFtZSA9IHRoaXMubmFtZTsKICAgICAgZm9yIChsZXQga2V5IG9mIFsicHVibGljSWQiLCAic3lzdGVtSWQiLCAiaW50ZXJuYWxTdWJzZXQiXSkgewogICAgICAgIGlmICh0aGlzW2tleV0gIT09IG51bGwpIHsKICAgICAgICAgIGpzb25ba2V5XSA9IHRoaXNba2V5XTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGpzb247CiAgICB9CiAgfTsKICB2YXIgWG1sRXJyb3IgPSBjbGFzcyBleHRlbmRzIEVycm9yIHsKICAgIGNvbnN0cnVjdG9yKG1lc3NhZ2UsIGNoYXJJbmRleCwgeG1sKSB7CiAgICAgIGxldCBjb2x1bW4gPSAxOwogICAgICBsZXQgZXhjZXJwdCA9ICIiOwogICAgICBsZXQgbGluZSA9IDE7CiAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgY2hhckluZGV4OyArK2kpIHsKICAgICAgICBsZXQgY2hhciA9IHhtbFtpXTsKICAgICAgICBpZiAoY2hhciA9PT0gIlxuIikgewogICAgICAgICAgY29sdW1uID0gMTsKICAgICAgICAgIGV4Y2VycHQgPSAiIjsKICAgICAgICAgIGxpbmUgKz0gMTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgY29sdW1uICs9IDE7CiAgICAgICAgICBleGNlcnB0ICs9IGNoYXI7CiAgICAgICAgfQogICAgICB9CiAgICAgIGxldCBlb2wgPSB4bWwuaW5kZXhPZigiXG4iLCBjaGFySW5kZXgpOwogICAgICBleGNlcnB0ICs9IGVvbCA9PT0gLTEgPyB4bWwuc2xpY2UoY2hhckluZGV4KSA6IHhtbC5zbGljZShjaGFySW5kZXgsIGVvbCk7CiAgICAgIGxldCBleGNlcnB0U3RhcnQgPSAwOwogICAgICBpZiAoZXhjZXJwdC5sZW5ndGggPiA1MCkgewogICAgICAgIGlmIChjb2x1bW4gPCA0MCkgewogICAgICAgICAgZXhjZXJwdCA9IGV4Y2VycHQuc2xpY2UoMCwgNTApOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBleGNlcnB0U3RhcnQgPSBjb2x1bW4gLSAyMDsKICAgICAgICAgIGV4Y2VycHQgPSBleGNlcnB0LnNsaWNlKGV4Y2VycHRTdGFydCwgY29sdW1uICsgMzApOwogICAgICAgIH0KICAgICAgfQogICAgICBzdXBlcigKICAgICAgICBgJHttZXNzYWdlfSAobGluZSAke2xpbmV9LCBjb2x1bW4gJHtjb2x1bW59KQogICR7ZXhjZXJwdH0KYCArICIgIi5yZXBlYXQoY29sdW1uIC0gZXhjZXJwdFN0YXJ0ICsgMSkgKyAiXlxuIgogICAgICApOwogICAgICB0aGlzLmNvbHVtbiA9IGNvbHVtbjsKICAgICAgdGhpcy5leGNlcnB0ID0gZXhjZXJwdDsKICAgICAgdGhpcy5saW5lID0gbGluZTsKICAgICAgdGhpcy5uYW1lID0gIlhtbEVycm9yIjsKICAgICAgdGhpcy5wb3MgPSBjaGFySW5kZXg7CiAgICB9CiAgfTsKICB2YXIgWG1sUHJvY2Vzc2luZ0luc3RydWN0aW9uID0gY2xhc3MgZXh0ZW5kcyBYbWxOb2RlIHsKICAgIGNvbnN0cnVjdG9yKG5hbWUsIGNvbnRlbnQgPSAiIikgewogICAgICBzdXBlcigpOwogICAgICB0aGlzLm5hbWUgPSBuYW1lOwogICAgICB0aGlzLmNvbnRlbnQgPSBjb250ZW50OwogICAgfQogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiBYbWxOb2RlLlRZUEVfUFJPQ0VTU0lOR19JTlNUUlVDVElPTjsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24oWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyksIHsKICAgICAgICBuYW1lOiB0aGlzLm5hbWUsCiAgICAgICAgY29udGVudDogdGhpcy5jb250ZW50CiAgICAgIH0pOwogICAgfQogIH07CiAgdmFyIGVtcHR5U3RyaW5nMiA9ICIiOwogIHZhciBQYXJzZXIgPSBjbGFzcyB7CiAgICAvKioKICAgICAqIEBwYXJhbSB4bWwgWE1MIHN0cmluZyB0byBwYXJzZS4KICAgICAqIEBwYXJhbSBvcHRpb25zIFBhcnNlciBvcHRpb25zLgogICAgICovCiAgICBjb25zdHJ1Y3Rvcih4bWwsIG9wdGlvbnMgPSB7fSkgewogICAgICBsZXQgZG9jID0gdGhpcy5kb2N1bWVudCA9IG5ldyBYbWxEb2N1bWVudCgpOwogICAgICBsZXQgc2Nhbm5lciA9IHRoaXMuYyA9IG5ldyBTdHJpbmdTY2FubmVyKHhtbCk7CiAgICAgIHRoaXMubCA9IGRvYzsKICAgICAgdGhpcy5mID0gb3B0aW9uczsKICAgICAgaWYgKHRoaXMuZi5pbmNsdWRlT2Zmc2V0cykgewogICAgICAgIGRvYy5zdGFydCA9IDA7CiAgICAgICAgZG9jLmVuZCA9IHhtbC5sZW5ndGg7CiAgICAgIH0KICAgICAgc2Nhbm5lci5iKCJcdUZFRkYiKTsKICAgICAgdGhpcy5IKCk7CiAgICAgIGlmICghdGhpcy5CKCkpIHsKICAgICAgICB0aHJvdyB0aGlzLmEoIlJvb3QgZWxlbWVudCBpcyBtaXNzaW5nIG9yIGludmFsaWQiKTsKICAgICAgfQogICAgICB3aGlsZSAodGhpcy53KCkpIHsKICAgICAgfQogICAgICBpZiAoIXNjYW5uZXIueikgewogICAgICAgIHRocm93IHRoaXMuYSgiRXh0cmEgY29udGVudCBhdCB0aGUgZW5kIG9mIHRoZSBkb2N1bWVudCIpOwogICAgICB9CiAgICB9CiAgICAvKioKICAgICAqIEFkZHMgdGhlIGdpdmVuIGBYbWxOb2RlYCBhcyBhIGNoaWxkIG9mIGB0aGlzLmN1cnJlbnROb2RlYC4KICAgICAqLwogICAgaihub2RlLCBjaGFySW5kZXgpIHsKICAgICAgbm9kZS5wYXJlbnQgPSB0aGlzLmw7CiAgICAgIGlmICh0aGlzLmYuaW5jbHVkZU9mZnNldHMpIHsKICAgICAgICBub2RlLnN0YXJ0ID0gdGhpcy5jLmkoY2hhckluZGV4KTsKICAgICAgICBub2RlLmVuZCA9IHRoaXMuYy5pKCk7CiAgICAgIH0KICAgICAgdGhpcy5sLmNoaWxkcmVuLnB1c2gobm9kZSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgLyoqCiAgICAgKiBBZGRzIHRoZSBnaXZlbiBfdGV4dF8gdG8gdGhlIGRvY3VtZW50LCBlaXRoZXIgYnkgYXBwZW5kaW5nIGl0IHRvIGEKICAgICAqIHByZWNlZGluZyBgWG1sVGV4dGAgbm9kZSAoaWYgcG9zc2libGUpIG9yIGJ5IGNyZWF0aW5nIGEgbmV3IGBYbWxUZXh0YCBub2RlLgogICAgICovCiAgICB4KHRleHQsIGNoYXJJbmRleCkgewogICAgICBsZXQgeyBjaGlsZHJlbiB9ID0gdGhpcy5sOwogICAgICBsZXQgeyBsZW5ndGggfSA9IGNoaWxkcmVuOwogICAgICB0ZXh0ID0gbm9ybWFsaXplTGluZUJyZWFrcyh0ZXh0KTsKICAgICAgaWYgKGxlbmd0aCA+IDApIHsKICAgICAgICBsZXQgcHJldk5vZGUgPSBjaGlsZHJlbltsZW5ndGggLSAxXTsKICAgICAgICBpZiAoKHByZXZOb2RlID09IG51bGwgPyB2b2lkIDAgOiBwcmV2Tm9kZS50eXBlKSA9PT0gWG1sTm9kZS5UWVBFX1RFWFQpIHsKICAgICAgICAgIGxldCB0ZXh0Tm9kZSA9IHByZXZOb2RlOwogICAgICAgICAgdGV4dE5vZGUudGV4dCArPSB0ZXh0OwogICAgICAgICAgaWYgKHRoaXMuZi5pbmNsdWRlT2Zmc2V0cykgewogICAgICAgICAgICB0ZXh0Tm9kZS5lbmQgPSB0aGlzLmMuaSgpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmoobmV3IFhtbFRleHQodGV4dCksIGNoYXJJbmRleCk7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGVsZW1lbnQgYXR0cmlidXRlcy4KICAgICAqCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI3NlYy1zdGFydHRhZ3MKICAgICAqLwogICAgSSgpIHsKICAgICAgbGV0IGF0dHJpYnV0ZXMgPSAvKiBAX19QVVJFX18gKi8gT2JqZWN0LmNyZWF0ZShudWxsKTsKICAgICAgd2hpbGUgKHRoaXMuZSgpKSB7CiAgICAgICAgbGV0IGF0dHJOYW1lID0gdGhpcy5yKCk7CiAgICAgICAgaWYgKCFhdHRyTmFtZSkgewogICAgICAgICAgYnJlYWs7CiAgICAgICAgfQogICAgICAgIGxldCBhdHRyVmFsdWUgPSB0aGlzLnUoKSAmJiB0aGlzLkooKTsKICAgICAgICBpZiAoYXR0clZhbHVlID09PSBmYWxzZSkgewogICAgICAgICAgdGhyb3cgdGhpcy5hKCJBdHRyaWJ1dGUgdmFsdWUgZXhwZWN0ZWQiKTsKICAgICAgICB9CiAgICAgICAgaWYgKGF0dHJOYW1lIGluIGF0dHJpYnV0ZXMpIHsKICAgICAgICAgIHRocm93IHRoaXMuYShgRHVwbGljYXRlIGF0dHJpYnV0ZTogJHthdHRyTmFtZX1gKTsKICAgICAgICB9CiAgICAgICAgaWYgKGF0dHJOYW1lID09PSAieG1sOnNwYWNlIiAmJiBhdHRyVmFsdWUgIT09ICJkZWZhdWx0IiAmJiBhdHRyVmFsdWUgIT09ICJwcmVzZXJ2ZSIpIHsKICAgICAgICAgIHRocm93IHRoaXMuYSgnVmFsdWUgb2YgdGhlIGB4bWw6c3BhY2VgIGF0dHJpYnV0ZSBtdXN0IGJlICJkZWZhdWx0IiBvciAicHJlc2VydmUiJyk7CiAgICAgICAgfQogICAgICAgIGF0dHJpYnV0ZXNbYXR0ck5hbWVdID0gYXR0clZhbHVlOwogICAgICB9CiAgICAgIGlmICh0aGlzLmYuc29ydEF0dHJpYnV0ZXMpIHsKICAgICAgICBsZXQgYXR0ck5hbWVzID0gT2JqZWN0LmtleXMoYXR0cmlidXRlcykuc29ydCgpOwogICAgICAgIGxldCBzb3J0ZWRBdHRyaWJ1dGVzID0gLyogQF9fUFVSRV9fICovIE9iamVjdC5jcmVhdGUobnVsbCk7CiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBhdHRyTmFtZXMubGVuZ3RoOyArK2kpIHsKICAgICAgICAgIGxldCBhdHRyTmFtZSA9IGF0dHJOYW1lc1tpXTsKICAgICAgICAgIHNvcnRlZEF0dHJpYnV0ZXNbYXR0ck5hbWVdID0gYXR0cmlidXRlc1thdHRyTmFtZV07CiAgICAgICAgfQogICAgICAgIGF0dHJpYnV0ZXMgPSBzb3J0ZWRBdHRyaWJ1dGVzOwogICAgICB9CiAgICAgIHJldHVybiBhdHRyaWJ1dGVzOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhbiBgQXR0VmFsdWVgIChhdHRyaWJ1dGUgdmFsdWUpIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEByZXR1cm5zCiAgICAgKiAgIENvbnRlbnRzIG9mIHRoZSBgQXR0VmFsdWVgIG1pbnVzIHF1b3Rlcywgb3IgYGZhbHNlYCBpZiBub3RoaW5nIHdhcwogICAgICogICBjb25zdW1lZC4gQW4gZW1wdHkgc3RyaW5nIGluZGljYXRlcyB0aGF0IGFuIGBBdHRWYWx1ZWAgd2FzIGNvbnN1bWVkIGJ1dAogICAgICogICB3YXMgZW1wdHkuCiAgICAgKgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1BdHRWYWx1ZQogICAgICovCiAgICBKKCkgewogICAgICBsZXQgeyBjOiBzY2FubmVyIH0gPSB0aGlzOwogICAgICBsZXQgcXVvdGUgPSBzY2FubmVyLmgoKTsKICAgICAgaWYgKHF1b3RlICE9PSAnIicgJiYgcXVvdGUgIT09ICInIikgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICBzY2FubmVyLmcoKTsKICAgICAgbGV0IGNoYXJzOwogICAgICBsZXQgaXNDbG9zZWQgPSBmYWxzZTsKICAgICAgbGV0IHZhbHVlID0gZW1wdHlTdHJpbmcyOwogICAgICBsZXQgcmVnZXggPSBxdW90ZSA9PT0gJyInID8gYXR0VmFsdWVDaGFyRG91YmxlUXVvdGUgOiBhdHRWYWx1ZUNoYXJTaW5nbGVRdW90ZTsKICAgICAgbWF0Y2hMb29wOgogICAgICAgIHdoaWxlICghc2Nhbm5lci56KSB7CiAgICAgICAgICBjaGFycyA9IHNjYW5uZXIuRyhyZWdleCk7CiAgICAgICAgICBpZiAoY2hhcnMpIHsKICAgICAgICAgICAgdGhpcy5wKGNoYXJzKTsKICAgICAgICAgICAgdmFsdWUgKz0gY2hhcnMucmVwbGFjZShhdHRWYWx1ZU5vcm1hbGl6ZWRXaGl0ZXNwYWNlLCAiICIpOwogICAgICAgICAgfQogICAgICAgICAgc3dpdGNoIChzY2FubmVyLmgoKSkgewogICAgICAgICAgICBjYXNlIHF1b3RlOgogICAgICAgICAgICAgIGlzQ2xvc2VkID0gdHJ1ZTsKICAgICAgICAgICAgICBicmVhayBtYXRjaExvb3A7CiAgICAgICAgICAgIGNhc2UgIiYiOgogICAgICAgICAgICAgIHZhbHVlICs9IHRoaXMuQygpOwogICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICBjYXNlICI8IjoKICAgICAgICAgICAgICB0aHJvdyB0aGlzLmEoIlVuZXNjYXBlZCBgPGAgaXMgbm90IGFsbG93ZWQgaW4gYW4gYXR0cmlidXRlIHZhbHVlIik7CiAgICAgICAgICAgIGNhc2UgZW1wdHlTdHJpbmcyOgogICAgICAgICAgICAgIGJyZWFrIG1hdGNoTG9vcDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIGlmICghaXNDbG9zZWQpIHsKICAgICAgICB0aHJvdyB0aGlzLmEoIlVuY2xvc2VkIGF0dHJpYnV0ZSIpOwogICAgICB9CiAgICAgIHNjYW5uZXIuZygpOwogICAgICByZXR1cm4gdmFsdWU7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgQ0RBVEEgc2VjdGlvbiBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGEgQ0RBVEEgc2VjdGlvbiB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI3NlYy1jZGF0YS1zZWN0CiAgICAgKi8KICAgIEsoKSB7CiAgICAgIGxldCB7IGM6IHNjYW5uZXIgfSA9IHRoaXM7CiAgICAgIGxldCBzdGFydEluZGV4ID0gc2Nhbm5lci5kOwogICAgICBpZiAoIXNjYW5uZXIuYigiPCFbQ0RBVEFbIikpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IHRleHQgPSBzY2FubmVyLnQoIl1dPiIpOwogICAgICB0aGlzLnAodGV4dCk7CiAgICAgIGlmICghc2Nhbm5lci5iKCJdXT4iKSkgewogICAgICAgIHRocm93IHRoaXMuYSgiVW5jbG9zZWQgQ0RBVEEgc2VjdGlvbiIpOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmYucHJlc2VydmVDZGF0YSA/IHRoaXMuaihuZXcgWG1sQ2RhdGEobm9ybWFsaXplTGluZUJyZWFrcyh0ZXh0KSksIHN0YXJ0SW5kZXgpIDogdGhpcy54KHRleHQsIHN0YXJ0SW5kZXgpOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBjaGFyYWN0ZXIgZGF0YSBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGNoYXJhY3RlciBkYXRhIHdhcyBjb25zdW1lZC4KICAgICAqIEBzZWUgaHR0cHM6Ly93d3cudzMub3JnL1RSLzIwMDgvUkVDLXhtbC0yMDA4MTEyNi8jZHQtY2hhcmRhdGEKICAgICAqLwogICAgTCgpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgbGV0IHN0YXJ0SW5kZXggPSBzY2FubmVyLmQ7CiAgICAgIGxldCBjaGFyRGF0YSA9IHNjYW5uZXIuQShlbmRDaGFyRGF0YSk7CiAgICAgIGlmICghY2hhckRhdGEpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgdGhpcy5wKGNoYXJEYXRhKTsKICAgICAgaWYgKHNjYW5uZXIuaCgzKSA9PT0gIl1dPiIpIHsKICAgICAgICB0aHJvdyB0aGlzLmEoIkVsZW1lbnQgY29udGVudCBtYXkgbm90IGNvbnRhaW4gdGhlIENEQVRBIHNlY3Rpb24gY2xvc2UgZGVsaW1pdGVyIGBdXT5gIik7CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXMueChjaGFyRGF0YSwgc3RhcnRJbmRleCk7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgY29tbWVudCBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGEgY29tbWVudCB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI05ULUNvbW1lbnQKICAgICAqLwogICAgRCgpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgbGV0IHN0YXJ0SW5kZXggPSBzY2FubmVyLmQ7CiAgICAgIGlmICghc2Nhbm5lci5iKCI8IS0tIikpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IGNvbnRlbnQgPSBzY2FubmVyLnQoIi0tIik7CiAgICAgIHRoaXMucChjb250ZW50KTsKICAgICAgaWYgKCFzY2FubmVyLmIoIi0tPiIpKSB7CiAgICAgICAgaWYgKHNjYW5uZXIuaCgyKSA9PT0gIi0tIikgewogICAgICAgICAgdGhyb3cgdGhpcy5hKCJUaGUgc3RyaW5nIGAtLWAgaXNuJ3QgYWxsb3dlZCBpbnNpZGUgYSBjb21tZW50Iik7CiAgICAgICAgfQogICAgICAgIHRocm93IHRoaXMuYSgiVW5jbG9zZWQgY29tbWVudCIpOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmYucHJlc2VydmVDb21tZW50cyA/IHRoaXMuaihuZXcgWG1sQ29tbWVudChub3JtYWxpemVMaW5lQnJlYWtzKGNvbnRlbnQpKSwgc3RhcnRJbmRleCkgOiB0cnVlOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhIHJlZmVyZW5jZSBpbiBhIGNvbnRlbnQgY29udGV4dCBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBUaGlzIGRpZmZlcnMgZnJvbSBgY29uc3VtZVJlZmVyZW5jZSgpYCBpbiB0aGF0IGEgY29uc3VtZWQgcmVmZXJlbmNlIHdpbGwgYmUKICAgICAqIGFkZGVkIHRvIHRoZSBkb2N1bWVudCBhcyBhIHRleHQgbm9kZSBpbnN0ZWFkIG9mIHJldHVybmVkLgogICAgICoKICAgICAqIEByZXR1cm5zIFdoZXRoZXIgYSByZWZlcmVuY2Ugd2FzIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNlbnRwcm9jCiAgICAgKi8KICAgIE0oKSB7CiAgICAgIGxldCBzdGFydEluZGV4ID0gdGhpcy5jLmQ7CiAgICAgIGxldCByZWYgPSB0aGlzLkMoKTsKICAgICAgcmV0dXJuIHJlZiA/IHRoaXMueChyZWYsIHN0YXJ0SW5kZXgpIDogZmFsc2U7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgZG9jdHlwZSBkZWNsYXJhdGlvbiBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBUaGlzIGlzIGEgbG9vc2UgaW1wbGVtZW50YXRpb24gc2luY2UgZG9jdHlwZSBkZWNsYXJhdGlvbnMgYXJlIGN1cnJlbnRseQogICAgICogZGlzY2FyZGVkIHdpdGhvdXQgZnVydGhlciBwYXJzaW5nLgogICAgICoKICAgICAqIEByZXR1cm5zIFdoZXRoZXIgYSBkb2N0eXBlIGRlY2xhcmF0aW9uIHdhcyBjb25zdW1lZC4KICAgICAqIEBzZWUgaHR0cHM6Ly93d3cudzMub3JnL1RSLzIwMDgvUkVDLXhtbC0yMDA4MTEyNi8jZHRkCiAgICAgKi8KICAgIE4oKSB7CiAgICAgIGxldCB7IGM6IHNjYW5uZXIgfSA9IHRoaXM7CiAgICAgIGxldCBzdGFydEluZGV4ID0gc2Nhbm5lci5kOwogICAgICBpZiAoIXNjYW5uZXIuYigiPCFET0NUWVBFIikpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IG5hbWUgPSB0aGlzLmUoKSAmJiB0aGlzLnIoKTsKICAgICAgaWYgKCFuYW1lKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJFeHBlY3RlZCBhIG5hbWUiKTsKICAgICAgfQogICAgICBsZXQgcHVibGljSWQ7CiAgICAgIGxldCBzeXN0ZW1JZDsKICAgICAgaWYgKHRoaXMuZSgpKSB7CiAgICAgICAgaWYgKHNjYW5uZXIuYigiUFVCTElDIikpIHsKICAgICAgICAgIHB1YmxpY0lkID0gdGhpcy5lKCkgJiYgdGhpcy5PKCk7CiAgICAgICAgICBpZiAocHVibGljSWQgPT09IGZhbHNlKSB7CiAgICAgICAgICAgIHRocm93IHRoaXMuYSgiRXhwZWN0ZWQgYSBwdWJsaWMgaWRlbnRpZmllciIpOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5lKCk7CiAgICAgICAgfQogICAgICAgIGlmIChwdWJsaWNJZCAhPT0gdm9pZCAwIHx8IHNjYW5uZXIuYigiU1lTVEVNIikpIHsKICAgICAgICAgIHRoaXMuZSgpOwogICAgICAgICAgc3lzdGVtSWQgPSB0aGlzLnMoKTsKICAgICAgICAgIGlmIChzeXN0ZW1JZCA9PT0gZmFsc2UpIHsKICAgICAgICAgICAgdGhyb3cgdGhpcy5hKCJFeHBlY3RlZCBhIHN5c3RlbSBpZGVudGlmaWVyIik7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLmUoKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgbGV0IGludGVybmFsU3Vic2V0OwogICAgICBpZiAoc2Nhbm5lci5iKCJbIikpIHsKICAgICAgICBpbnRlcm5hbFN1YnNldCA9IHNjYW5uZXIuQSgvXF1bXHgyMFx0XHJcbl0qPi8pOwogICAgICAgIGlmICghc2Nhbm5lci5iKCJdIikpIHsKICAgICAgICAgIHRocm93IHRoaXMuYSgiVW5jbG9zZWQgaW50ZXJuYWwgc3Vic2V0Iik7CiAgICAgICAgfQogICAgICAgIHRoaXMuZSgpOwogICAgICB9CiAgICAgIGlmICghc2Nhbm5lci5iKCI+IikpIHsKICAgICAgICB0aHJvdyB0aGlzLmEoIlVuY2xvc2VkIGRvY3R5cGUgZGVjbGFyYXRpb24iKTsKICAgICAgfQogICAgICByZXR1cm4gdGhpcy5mLnByZXNlcnZlRG9jdW1lbnRUeXBlID8gdGhpcy5qKG5ldyBYbWxEb2N1bWVudFR5cGUobmFtZSwgcHVibGljSWQsIHN5c3RlbUlkLCBpbnRlcm5hbFN1YnNldCksIHN0YXJ0SW5kZXgpIDogdHJ1ZTsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgYW4gZWxlbWVudCBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGFuIGVsZW1lbnQgd2FzIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1lbGVtZW50CiAgICAgKi8KICAgIEIoKSB7CiAgICAgIGxldCB7IGM6IHNjYW5uZXIgfSA9IHRoaXM7CiAgICAgIGxldCBzdGFydEluZGV4ID0gc2Nhbm5lci5kOwogICAgICBpZiAoIXNjYW5uZXIuYigiPCIpKSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CiAgICAgIGxldCBuYW1lID0gdGhpcy5yKCk7CiAgICAgIGlmICghbmFtZSkgewogICAgICAgIHNjYW5uZXIubyhzdGFydEluZGV4KTsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IGF0dHJpYnV0ZXMgPSB0aGlzLkkoKTsKICAgICAgbGV0IGlzRW1wdHkgPSAhIXNjYW5uZXIuYigiLz4iKTsKICAgICAgbGV0IGVsZW1lbnQgPSBuZXcgWG1sRWxlbWVudChuYW1lLCBhdHRyaWJ1dGVzKTsKICAgICAgZWxlbWVudC5wYXJlbnQgPSB0aGlzLmw7CiAgICAgIGlmICghaXNFbXB0eSkgewogICAgICAgIGlmICghc2Nhbm5lci5iKCI+IikpIHsKICAgICAgICAgIHRocm93IHRoaXMuYShgVW5jbG9zZWQgc3RhcnQgdGFnIGZvciBlbGVtZW50IFxgJHtuYW1lfVxgYCk7CiAgICAgICAgfQogICAgICAgIHRoaXMubCA9IGVsZW1lbnQ7CiAgICAgICAgZG8gewogICAgICAgICAgdGhpcy5MKCk7CiAgICAgICAgfSB3aGlsZSAodGhpcy5CKCkgfHwgdGhpcy5NKCkgfHwgdGhpcy5LKCkgfHwgdGhpcy5FKCkgfHwgdGhpcy5EKCkpOwogICAgICAgIGxldCBlbmRUYWdNYXJrID0gc2Nhbm5lci5kOwogICAgICAgIGxldCBlbmRUYWdOYW1lOwogICAgICAgIGlmICghc2Nhbm5lci5iKCI8LyIpIHx8ICEoZW5kVGFnTmFtZSA9IHRoaXMucigpKSB8fCBlbmRUYWdOYW1lICE9PSBuYW1lKSB7CiAgICAgICAgICBzY2FubmVyLm8oZW5kVGFnTWFyayk7CiAgICAgICAgICB0aHJvdyB0aGlzLmEoYE1pc3NpbmcgZW5kIHRhZyBmb3IgZWxlbWVudCAke25hbWV9YCk7CiAgICAgICAgfQogICAgICAgIHRoaXMuZSgpOwogICAgICAgIGlmICghc2Nhbm5lci5iKCI+IikpIHsKICAgICAgICAgIHRocm93IHRoaXMuYShgVW5jbG9zZWQgZW5kIHRhZyBmb3IgZWxlbWVudCAke25hbWV9YCk7CiAgICAgICAgfQogICAgICAgIHRoaXMubCA9IGVsZW1lbnQucGFyZW50OwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmooZWxlbWVudCwgc3RhcnRJbmRleCk7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGFuIGBFcWAgcHJvZHVjdGlvbiBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGFuIGBFcWAgcHJvZHVjdGlvbiB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI05ULUVxCiAgICAgKi8KICAgIHUoKSB7CiAgICAgIHRoaXMuZSgpOwogICAgICBpZiAodGhpcy5jLmIoIj0iKSkgewogICAgICAgIHRoaXMuZSgpOwogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgYE1pc2NgIGNvbnRlbnQgaWYgcG9zc2libGUuCiAgICAgKgogICAgICogQHJldHVybnMgV2hldGhlciBhbnl0aGluZyB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI05ULU1pc2MKICAgICAqLwogICAgdygpIHsKICAgICAgcmV0dXJuIHRoaXMuRCgpIHx8IHRoaXMuRSgpIHx8IHRoaXMuZSgpOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBvbmUgb3IgbW9yZSBgTmFtZWAgY2hhcmFjdGVycyBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBgTmFtZWAgY2hhcmFjdGVycywgb3IgYW4gZW1wdHkgc3RyaW5nIGlmIG5vbmUgd2VyZSBjb25zdW1lZC4KICAgICAqIEBzZWUgaHR0cHM6Ly93d3cudzMub3JnL1RSLzIwMDgvUkVDLXhtbC0yMDA4MTEyNi8jTlQtTmFtZQogICAgICovCiAgICByKCkgewogICAgICByZXR1cm4gaXNOYW1lU3RhcnRDaGFyKHRoaXMuYy5oKCkpID8gdGhpcy5jLnYoaXNOYW1lQ2hhcikgOiBlbXB0eVN0cmluZzI7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGEgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI3NlYy1waQogICAgICovCiAgICBFKCkgewogICAgICBsZXQgeyBjOiBzY2FubmVyIH0gPSB0aGlzOwogICAgICBsZXQgc3RhcnRJbmRleCA9IHNjYW5uZXIuZDsKICAgICAgaWYgKCFzY2FubmVyLmIoIjw/IikpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IG5hbWUgPSB0aGlzLnIoKTsKICAgICAgaWYgKG5hbWUpIHsKICAgICAgICBpZiAobmFtZS50b0xvd2VyQ2FzZSgpID09PSAieG1sIikgewogICAgICAgICAgc2Nhbm5lci5vKHN0YXJ0SW5kZXgpOwogICAgICAgICAgdGhyb3cgdGhpcy5hKCJYTUwgZGVjbGFyYXRpb24gaXNuJ3QgYWxsb3dlZCBoZXJlIik7CiAgICAgICAgfQogICAgICB9IGVsc2UgewogICAgICAgIHRocm93IHRoaXMuYSgiSW52YWxpZCBwcm9jZXNzaW5nIGluc3RydWN0aW9uIik7CiAgICAgIH0KICAgICAgaWYgKCF0aGlzLmUoKSkgewogICAgICAgIGlmIChzY2FubmVyLmIoIj8+IikpIHsKICAgICAgICAgIHJldHVybiB0aGlzLmoobmV3IFhtbFByb2Nlc3NpbmdJbnN0cnVjdGlvbihuYW1lKSwgc3RhcnRJbmRleCk7CiAgICAgICAgfQogICAgICAgIHRocm93IHRoaXMuYSgiV2hpdGVzcGFjZSBpcyByZXF1aXJlZCBhZnRlciBhIHByb2Nlc3NpbmcgaW5zdHJ1Y3Rpb24gbmFtZSIpOwogICAgICB9CiAgICAgIGxldCBjb250ZW50ID0gc2Nhbm5lci50KCI/PiIpOwogICAgICB0aGlzLnAoY29udGVudCk7CiAgICAgIGlmICghc2Nhbm5lci5iKCI/PiIpKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJVbnRlcm1pbmF0ZWQgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiIpOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmoobmV3IFhtbFByb2Nlc3NpbmdJbnN0cnVjdGlvbihuYW1lLCBub3JtYWxpemVMaW5lQnJlYWtzKGNvbnRlbnQpKSwgc3RhcnRJbmRleCk7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgcHJvbG9nIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEByZXR1cm5zIFdoZXRoZXIgYSBwcm9sb2cgd2FzIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNzZWMtcHJvbG9nLWR0ZAogICAgICovCiAgICBIKCkgewogICAgICBsZXQgeyBjOiBzY2FubmVyIH0gPSB0aGlzOwogICAgICBsZXQgc3RhcnRJbmRleCA9IHNjYW5uZXIuZDsKICAgICAgdGhpcy5QKCk7CiAgICAgIHdoaWxlICh0aGlzLncoKSkgewogICAgICB9CiAgICAgIGlmICh0aGlzLk4oKSkgewogICAgICAgIHdoaWxlICh0aGlzLncoKSkgewogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gc3RhcnRJbmRleCA8IHNjYW5uZXIuZDsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgYSBwdWJsaWMgaWRlbnRpZmllciBsaXRlcmFsIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEByZXR1cm5zCiAgICAgKiAgIFZhbHVlIG9mIHRoZSBwdWJsaWMgaWRlbnRpZmllciBsaXRlcmFsIG1pbnVzIHF1b3Rlcywgb3IgYGZhbHNlYCBpZgogICAgICogICBub3RoaW5nIHdhcyBjb25zdW1lZC4gQW4gZW1wdHkgc3RyaW5nIGluZGljYXRlcyB0aGF0IGEgcHVibGljIGlkIGxpdGVyYWwKICAgICAqICAgd2FzIGNvbnN1bWVkIGJ1dCB3YXMgZW1wdHkuCiAgICAgKgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1QdWJpZExpdGVyYWwKICAgICAqLwogICAgTygpIHsKICAgICAgbGV0IHN0YXJ0SW5kZXggPSB0aGlzLmMuZDsKICAgICAgbGV0IHZhbHVlID0gdGhpcy5zKCk7CiAgICAgIGlmICh2YWx1ZSAhPT0gZmFsc2UgJiYgIS9eWy1ceDIwXHJcbmEtekEtWjAtOScoKSssLi86PT87ISojQCRfJV0qJC8udGVzdCh2YWx1ZSkpIHsKICAgICAgICB0aGlzLmMubyhzdGFydEluZGV4KTsKICAgICAgICB0aHJvdyB0aGlzLmEoIkludmFsaWQgY2hhcmFjdGVyIGluIHB1YmxpYyBpZGVudGlmaWVyIik7CiAgICAgIH0KICAgICAgcmV0dXJuIHZhbHVlOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhIHJlZmVyZW5jZSBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBUaGlzIGRpZmZlcnMgZnJvbSBgY29uc3VtZUNvbnRlbnRSZWZlcmVuY2UoKWAgaW4gdGhhdCBhIGNvbnN1bWVkIHJlZmVyZW5jZQogICAgICogd2lsbCBiZSByZXR1cm5lZCByYXRoZXIgdGhhbiBhZGRlZCB0byB0aGUgZG9jdW1lbnQuCiAgICAgKgogICAgICogQHJldHVybnMKICAgICAqICAgUGFyc2VkIHJlZmVyZW5jZSB2YWx1ZSwgb3IgYGZhbHNlYCBpZiBub3RoaW5nIHdhcyBjb25zdW1lZCAodG8KICAgICAqICAgZGlzdGluZ3Vpc2ggZnJvbSBhIHJlZmVyZW5jZSB0aGF0IHJlc29sdmVzIHRvIGFuIGVtcHR5IHN0cmluZykuCiAgICAgKgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1SZWZlcmVuY2UKICAgICAqLwogICAgQygpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgaWYgKCFzY2FubmVyLmIoIiYiKSkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICBsZXQgcmVmID0gc2Nhbm5lci52KGlzUmVmZXJlbmNlQ2hhcik7CiAgICAgIGlmIChzY2FubmVyLkYoKSAhPT0gIjsiKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJVbnRlcm1pbmF0ZWQgcmVmZXJlbmNlIChhIHJlZmVyZW5jZSBtdXN0IGVuZCB3aXRoIGA7YCkiKTsKICAgICAgfQogICAgICBsZXQgcGFyc2VkVmFsdWU7CiAgICAgIGlmIChyZWZbMF0gPT09ICIjIikgewogICAgICAgIGxldCBjb2RlUG9pbnQgPSByZWZbMV0gPT09ICJ4IiA/IHBhcnNlSW50KHJlZi5zbGljZSgyKSwgMTYpIDogcGFyc2VJbnQocmVmLnNsaWNlKDEpLCAxMCk7CiAgICAgICAgaWYgKGlzTmFOKGNvZGVQb2ludCkpIHsKICAgICAgICAgIHRocm93IHRoaXMuYSgiSW52YWxpZCBjaGFyYWN0ZXIgcmVmZXJlbmNlIik7CiAgICAgICAgfQogICAgICAgIGlmICghaXNYbWxDb2RlUG9pbnQoY29kZVBvaW50KSkgewogICAgICAgICAgdGhyb3cgdGhpcy5hKCJDaGFyYWN0ZXIgcmVmZXJlbmNlIHJlc29sdmVzIHRvIGFuIGludmFsaWQgY2hhcmFjdGVyIik7CiAgICAgICAgfQogICAgICAgIHBhcnNlZFZhbHVlID0gU3RyaW5nLmZyb21Db2RlUG9pbnQoY29kZVBvaW50KTsKICAgICAgfSBlbHNlIHsKICAgICAgICBwYXJzZWRWYWx1ZSA9IHByZWRlZmluZWRFbnRpdGllc1tyZWZdOwogICAgICAgIGlmIChwYXJzZWRWYWx1ZSA9PT0gdm9pZCAwKSB7CiAgICAgICAgICBsZXQgewogICAgICAgICAgICBpZ25vcmVVbmRlZmluZWRFbnRpdGllcywKICAgICAgICAgICAgcmVzb2x2ZVVuZGVmaW5lZEVudGl0eQogICAgICAgICAgfSA9IHRoaXMuZjsKICAgICAgICAgIGxldCB3cmFwcGVkUmVmID0gYCYke3JlZn07YDsKICAgICAgICAgIGlmIChyZXNvbHZlVW5kZWZpbmVkRW50aXR5KSB7CiAgICAgICAgICAgIGxldCByZXNvbHZlZFZhbHVlID0gcmVzb2x2ZVVuZGVmaW5lZEVudGl0eSh3cmFwcGVkUmVmKTsKICAgICAgICAgICAgaWYgKHJlc29sdmVkVmFsdWUgIT09IG51bGwgJiYgcmVzb2x2ZWRWYWx1ZSAhPT0gdm9pZCAwKSB7CiAgICAgICAgICAgICAgbGV0IHR5cGUgPSB0eXBlb2YgcmVzb2x2ZWRWYWx1ZTsKICAgICAgICAgICAgICBpZiAodHlwZSAhPT0gInN0cmluZyIpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoYFxgcmVzb2x2ZVVuZGVmaW5lZEVudGl0eSgpXGAgbXVzdCByZXR1cm4gYSBzdHJpbmcsIFxgbnVsbFxgLCBvciBcYHVuZGVmaW5lZFxgLCBidXQgcmV0dXJuZWQgYSB2YWx1ZSBvZiB0eXBlICR7dHlwZX1gKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgcmV0dXJuIHJlc29sdmVkVmFsdWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIGlmIChpZ25vcmVVbmRlZmluZWRFbnRpdGllcykgewogICAgICAgICAgICByZXR1cm4gd3JhcHBlZFJlZjsKICAgICAgICAgIH0KICAgICAgICAgIHNjYW5uZXIubygtd3JhcHBlZFJlZi5sZW5ndGgpOwogICAgICAgICAgdGhyb3cgdGhpcy5hKGBOYW1lZCBlbnRpdHkgaXNuJ3QgZGVmaW5lZDogJHt3cmFwcGVkUmVmfWApOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gcGFyc2VkVmFsdWU7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgYFN5c3RlbUxpdGVyYWxgIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEEgYFN5c3RlbUxpdGVyYWxgIGlzIHNpbWlsYXIgdG8gYW4gYXR0cmlidXRlIHZhbHVlLCBidXQgYWxsb3dzIHRoZQogICAgICogY2hhcmFjdGVycyBgPGAgYW5kIGAmYCBhbmQgZG9lc24ndCByZXBsYWNlIHJlZmVyZW5jZXMuCiAgICAgKgogICAgICogQHJldHVybnMKICAgICAqICAgVmFsdWUgb2YgdGhlIGBTeXN0ZW1MaXRlcmFsYCBtaW51cyBxdW90ZXMsIG9yIGBmYWxzZWAgaWYgbm90aGluZyB3YXMKICAgICAqICAgY29uc3VtZWQuIEFuIGVtcHR5IHN0cmluZyBpbmRpY2F0ZXMgdGhhdCBhIGBTeXN0ZW1MaXRlcmFsYCB3YXMgY29uc3VtZWQKICAgICAqICAgYnV0IHdhcyBlbXB0eS4KICAgICAqCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI05ULVN5c3RlbUxpdGVyYWwKICAgICAqLwogICAgcygpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgbGV0IHF1b3RlID0gc2Nhbm5lci5iKCciJykgfHwgc2Nhbm5lci5iKCInIik7CiAgICAgIGlmICghcXVvdGUpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IHZhbHVlID0gc2Nhbm5lci50KHF1b3RlKTsKICAgICAgdGhpcy5wKHZhbHVlKTsKICAgICAgaWYgKCFzY2FubmVyLmIocXVvdGUpKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJNaXNzaW5nIGVuZCBxdW90ZSIpOwogICAgICB9CiAgICAgIHJldHVybiB2YWx1ZTsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgb25lIG9yIG1vcmUgd2hpdGVzcGFjZSBjaGFyYWN0ZXJzIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEByZXR1cm5zIFdoZXRoZXIgYW55IHdoaXRlc3BhY2UgY2hhcmFjdGVycyB3ZXJlIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyN3aGl0ZQogICAgICovCiAgICBlKCkgewogICAgICByZXR1cm4gISF0aGlzLmMudihpc1doaXRlc3BhY2UpOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhbiBYTUwgZGVjbGFyYXRpb24gaWYgcG9zc2libGUuCiAgICAgKgogICAgICogQHJldHVybnMgV2hldGhlciBhbiBYTUwgZGVjbGFyYXRpb24gd2FzIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1YTUxEZWNsCiAgICAgKi8KICAgIFAoKSB7CiAgICAgIGxldCB7IGM6IHNjYW5uZXIgfSA9IHRoaXM7CiAgICAgIGxldCBzdGFydEluZGV4ID0gc2Nhbm5lci5kOwogICAgICBpZiAoIXNjYW5uZXIuYigiPD94bWwiKSkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICBpZiAoIXRoaXMuZSgpKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJJbnZhbGlkIFhNTCBkZWNsYXJhdGlvbiIpOwogICAgICB9CiAgICAgIGxldCB2ZXJzaW9uID0gISFzY2FubmVyLmIoInZlcnNpb24iKSAmJiB0aGlzLnUoKSAmJiB0aGlzLnMoKTsKICAgICAgaWYgKHZlcnNpb24gPT09IGZhbHNlKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJYTUwgdmVyc2lvbiBpcyBtaXNzaW5nIG9yIGludmFsaWQiKTsKICAgICAgfSBlbHNlIGlmICghL14xXC5bMC05XSskLy50ZXN0KHZlcnNpb24pKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJJbnZhbGlkIGNoYXJhY3RlciBpbiB2ZXJzaW9uIG51bWJlciIpOwogICAgICB9CiAgICAgIGxldCBlbmNvZGluZzsKICAgICAgbGV0IHN0YW5kYWxvbmU7CiAgICAgIGlmICh0aGlzLmUoKSkgewogICAgICAgIGVuY29kaW5nID0gISFzY2FubmVyLmIoImVuY29kaW5nIikgJiYgdGhpcy51KCkgJiYgdGhpcy5zKCk7CiAgICAgICAgaWYgKGVuY29kaW5nKSB7CiAgICAgICAgICB0aGlzLmUoKTsKICAgICAgICB9CiAgICAgICAgc3RhbmRhbG9uZSA9ICEhc2Nhbm5lci5iKCJzdGFuZGFsb25lIikgJiYgdGhpcy51KCkgJiYgdGhpcy5zKCk7CiAgICAgICAgaWYgKHN0YW5kYWxvbmUpIHsKICAgICAgICAgIGlmIChzdGFuZGFsb25lICE9PSAieWVzIiAmJiBzdGFuZGFsb25lICE9PSAibm8iKSB7CiAgICAgICAgICAgIHRocm93IHRoaXMuYSgnT25seSAieWVzIiBhbmQgIm5vIiBhcmUgcGVybWl0dGVkIGFzIHZhbHVlcyBvZiBgc3RhbmRhbG9uZWAnKTsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuZSgpOwogICAgICAgIH0KICAgICAgfQogICAgICBpZiAoIXNjYW5uZXIuYigiPz4iKSkgewogICAgICAgIHRocm93IHRoaXMuYSgiSW52YWxpZCBvciB1bmNsb3NlZCBYTUwgZGVjbGFyYXRpb24iKTsKICAgICAgfQogICAgICByZXR1cm4gdGhpcy5mLnByZXNlcnZlWG1sRGVjbGFyYXRpb24gPyB0aGlzLmoobmV3IFhtbERlY2xhcmF0aW9uKAogICAgICAgIHZlcnNpb24sCiAgICAgICAgZW5jb2RpbmcgfHwgdm9pZCAwLAogICAgICAgIHN0YW5kYWxvbmUgfHwgdm9pZCAwCiAgICAgICksIHN0YXJ0SW5kZXgpIDogdHJ1ZTsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyBhbiBgWG1sRXJyb3JgIGZvciB0aGUgY3VycmVudCBzY2FubmVyIHBvc2l0aW9uLgogICAgICovCiAgICBhKG1lc3NhZ2UpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgcmV0dXJuIG5ldyBYbWxFcnJvcihtZXNzYWdlLCBzY2FubmVyLmQsIHNjYW5uZXIubSk7CiAgICB9CiAgICAvKioKICAgICAqIFRocm93cyBhbiBpbnZhbGlkIGNoYXJhY3RlciBlcnJvciBpZiBhbnkgY2hhcmFjdGVyIGluIHRoZSBnaXZlbiBfc3RyaW5nXwogICAgICogaXNuJ3QgYSB2YWxpZCBYTUwgY2hhcmFjdGVyLgogICAgICovCiAgICBwKHN0cmluZykgewogICAgICBsZXQgeyBsZW5ndGggfSA9IHN0cmluZzsKICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBsZW5ndGg7ICsraSkgewogICAgICAgIGxldCBjcCA9IHN0cmluZy5jb2RlUG9pbnRBdChpKTsKICAgICAgICBpZiAoIWlzWG1sQ29kZVBvaW50KGNwKSkgewogICAgICAgICAgdGhpcy5jLm8oLShbLi4uc3RyaW5nXS5sZW5ndGggLSBpKSk7CiAgICAgICAgICB0aHJvdyB0aGlzLmEoIkludmFsaWQgY2hhcmFjdGVyIik7CiAgICAgICAgfQogICAgICAgIGlmIChjcCA+IDY1NTM1KSB7CiAgICAgICAgICBpICs9IDE7CiAgICAgICAgfQogICAgICB9CiAgICB9CiAgfTsKICBmdW5jdGlvbiBub3JtYWxpemVMaW5lQnJlYWtzKHRleHQpIHsKICAgIGxldCBpID0gMDsKICAgIHdoaWxlICgoaSA9IHRleHQuaW5kZXhPZigiXHIiLCBpKSkgIT09IC0xKSB7CiAgICAgIHRleHQgPSB0ZXh0W2kgKyAxXSA9PT0gIlxuIiA/IHRleHQuc2xpY2UoMCwgaSkgKyB0ZXh0LnNsaWNlKGkgKyAxKSA6IHRleHQuc2xpY2UoMCwgaSkgKyAiXG4iICsgdGV4dC5zbGljZShpICsgMSk7CiAgICB9CiAgICByZXR1cm4gdGV4dDsKICB9CiAgZnVuY3Rpb24gcGFyc2VYbWwoeG1sLCBvcHRpb25zKSB7CiAgICByZXR1cm4gbmV3IFBhcnNlcih4bWwsIG9wdGlvbnMpLmRvY3VtZW50OwogIH0KICBjbGFzcyBYbWxQYXJzZUVycm9yIGV4dGVuZHMgRXJyb3IgewogICAgY29uc3RydWN0b3IobWVzc2FnZSkgewogICAgICBzdXBlcihtZXNzYWdlKTsKICAgIH0KICB9CiAgZnVuY3Rpb24gcGFyc2VYbWxTdHJpbmcoeG1sU3RyaW5nKSB7CiAgICBsZXQgZG9jID0gbnVsbDsKICAgIHRyeSB7CiAgICAgIGRvYyA9IGJyb3dzZXIucGFyc2VYbWwoeG1sU3RyaW5nKTsKICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgdGhyb3cgbmV3IFhtbFBhcnNlRXJyb3IoZS5tZXNzYWdlKTsKICAgIH0KICAgIHJldHVybiBkb2M7CiAgfQogIGZ1bmN0aW9uIHN0cmlwTmFtZXNwYWNlKG5hbWUpIHsKICAgIGNvbnN0IGNvbG9uID0gbmFtZS5pbmRleE9mKCI6Iik7CiAgICByZXR1cm4gY29sb24gPiAtMSA/IG5hbWUuc3Vic3RyKGNvbG9uICsgMSkgOiBuYW1lOwogIH0KICBmdW5jdGlvbiBnZXRSb290RWxlbWVudCh4bWxEb2MpIHsKICAgIHJldHVybiB4bWxEb2MuY2hpbGRyZW5bMF07CiAgfQogIGZ1bmN0aW9uIGdldEVsZW1lbnROYW1lKGVsZW1lbnQpIHsKICAgIHJldHVybiBlbGVtZW50Lm5hbWUgfHwgIiI7CiAgfQogIGZ1bmN0aW9uIGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgbmFtZSwgbmVzdGVkID0gZmFsc2UpIHsKICAgIGNvbnN0IHN0cmlwcGVkTmFtZSA9IHN0cmlwTmFtZXNwYWNlKG5hbWUpOwogICAgZnVuY3Rpb24gcmVkdWNlcihwcmV2LCBjdXJyKSB7CiAgICAgIGlmIChzdHJpcE5hbWVzcGFjZShnZXRFbGVtZW50TmFtZShjdXJyKSkgPT09IHN0cmlwcGVkTmFtZSkgewogICAgICAgIHByZXYucHVzaChjdXJyKTsKICAgICAgfQogICAgICBpZiAobmVzdGVkICYmIEFycmF5LmlzQXJyYXkoY3Vyci5jaGlsZHJlbikpIHsKICAgICAgICByZXR1cm4gWy4uLnByZXYsIC4uLmN1cnIuY2hpbGRyZW4ucmVkdWNlKHJlZHVjZXIsIFtdKV07CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIHByZXY7CiAgICAgIH0KICAgIH0KICAgIHJldHVybiBlbGVtZW50ICYmIEFycmF5LmlzQXJyYXkoZWxlbWVudC5jaGlsZHJlbikgPyBlbGVtZW50LmNoaWxkcmVuLnJlZHVjZShyZWR1Y2VyLCBbXSkgOiBbXTsKICB9CiAgZnVuY3Rpb24gZmluZENoaWxkRWxlbWVudChlbGVtZW50LCBuYW1lLCBuZXN0ZWQgPSBmYWxzZSkgewogICAgcmV0dXJuIGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgbmFtZSwgbmVzdGVkKVswXSB8fCBudWxsOwogIH0KICBmdW5jdGlvbiBnZXRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCkgewogICAgcmV0dXJuIGVsZW1lbnQgJiYgQXJyYXkuaXNBcnJheShlbGVtZW50LmNoaWxkcmVuKSA/IFsKICAgICAgLi4uZWxlbWVudC5jaGlsZHJlbi5maWx0ZXIoCiAgICAgICAgKGVsKSA9PiBlbCBpbnN0YW5jZW9mIGJyb3dzZXIuWG1sRWxlbWVudAogICAgICApCiAgICBdIDogW107CiAgfQogIGZ1bmN0aW9uIGdldEVsZW1lbnRUZXh0KGVsZW1lbnQpIHsKICAgIGNvbnN0IHRleHROb2RlID0gZWxlbWVudCAmJiBBcnJheS5pc0FycmF5KGVsZW1lbnQuY2hpbGRyZW4pID8gZWxlbWVudC5jaGlsZHJlbi5maW5kKChub2RlKSA9PiBub2RlLnR5cGUgPT09ICJ0ZXh0IikgOiBudWxsOwogICAgcmV0dXJuIHRleHROb2RlID8gdGV4dE5vZGUudGV4dCA6ICIiOwogIH0KICBmdW5jdGlvbiBnZXRFbGVtZW50QXR0cmlidXRlKGVsZW1lbnQsIGF0dHJOYW1lKSB7CiAgICByZXR1cm4gZWxlbWVudCAmJiBlbGVtZW50LmF0dHJpYnV0ZXNbYXR0ck5hbWVdIHx8ICIiOwogIH0KICBjbGFzcyBFbmRwb2ludEVycm9yIGV4dGVuZHMgRXJyb3IgewogICAgY29uc3RydWN0b3IobWVzc2FnZSwgaHR0cFN0YXR1cywgaXNDcm9zc09yaWdpblJlbGF0ZWQpIHsKICAgICAgc3VwZXIobWVzc2FnZSk7CiAgICAgIHRoaXMuaHR0cFN0YXR1cyA9IGh0dHBTdGF0dXM7CiAgICAgIHRoaXMuaXNDcm9zc09yaWdpblJlbGF0ZWQgPSBpc0Nyb3NzT3JpZ2luUmVsYXRlZDsKICAgICAgdGhpcy5uYW1lID0gIkVuZHBvaW50RXJyb3IiOwogICAgfQogIH0KICBjbGFzcyBTZXJ2aWNlRXhjZXB0aW9uRXJyb3IgZXh0ZW5kcyBFcnJvciB7CiAgICAvKioKICAgICAqIENvbnN0cnVjdG9yCiAgICAgKiBAcGFyYW0gbWVzc2FnZSBFcnJvciBtZXNzYWdlCiAgICAgKiBAcGFyYW0gcmVxdWVzdFVybCBVUkwgd2hpY2ggcmVzdWx0ZWQgaW4gdGhlIFNlcnZpY2VFeGNlcHRpb24KICAgICAqIEBwYXJhbSBjb2RlIE9wdGlvbmFsIFNlcnZpY2VFeGNlcHRpb24gY29kZQogICAgICogQHBhcmFtIGxvY2F0b3IgT3B0aW9uYWwgU2VydmljZUV4Y2VwdGlvbiBsb2NhdG9yCiAgICAgKiBAcGFyYW0gcmVzcG9uc2UgT3B0aW9uYWwgcmVzcG9uc2UgY29udGVudCByZWNlaXZlZAogICAgICovCiAgICBjb25zdHJ1Y3RvcihtZXNzYWdlLCByZXF1ZXN0VXJsLCBjb2RlLCBsb2NhdG9yLCByZXNwb25zZSkgewogICAgICBzdXBlcihtZXNzYWdlKTsKICAgICAgdGhpcy5yZXF1ZXN0VXJsID0gcmVxdWVzdFVybDsKICAgICAgdGhpcy5jb2RlID0gY29kZTsKICAgICAgdGhpcy5sb2NhdG9yID0gbG9jYXRvcjsKICAgICAgdGhpcy5yZXNwb25zZSA9IHJlc3BvbnNlOwogICAgICB0aGlzLm5hbWUgPSAiU2VydmljZUV4Y2VwdGlvbkVycm9yIjsKICAgIH0KICB9CiAgZnVuY3Rpb24gcGFyc2Uoc2VydmljZUV4Y2VwdGlvbiwgdXJsKSB7CiAgICBjb25zdCBlcnJvckNvZGUgPSBnZXRFbGVtZW50QXR0cmlidXRlKHNlcnZpY2VFeGNlcHRpb24sICJjb2RlIikgfHwgZ2V0RWxlbWVudEF0dHJpYnV0ZShzZXJ2aWNlRXhjZXB0aW9uLCAiZXhjZXB0aW9uQ29kZSIpOwogICAgY29uc3QgZXJyb3JMb2NhdG9yID0gZ2V0RWxlbWVudEF0dHJpYnV0ZShzZXJ2aWNlRXhjZXB0aW9uLCAibG9jYXRvciIpOwogICAgY29uc3QgdGV4dEVsZW1lbnQgPSBmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2VFeGNlcHRpb24sICJFeGNlcHRpb25UZXh0IikgfHwgc2VydmljZUV4Y2VwdGlvbjsKICAgIGNvbnN0IGVycm9yTWVzc2FnZSA9IGdldEVsZW1lbnRUZXh0KHRleHRFbGVtZW50KS50cmltKCk7CiAgICByZXR1cm4gbmV3IFNlcnZpY2VFeGNlcHRpb25FcnJvcigKICAgICAgZXJyb3JNZXNzYWdlLAogICAgICB1cmwsCiAgICAgIGVycm9yQ29kZSwKICAgICAgZXJyb3JMb2NhdG9yLAogICAgICBzZXJ2aWNlRXhjZXB0aW9uLmRvY3VtZW50CiAgICApOwogIH0KICBmdW5jdGlvbiBjaGVjayhyZXNwb25zZSwgdXJsKSB7CiAgICBjb25zdCByb290RWwgPSBnZXRSb290RWxlbWVudChyZXNwb25zZSk7CiAgICBjb25zdCByb290RWxOYW1lID0gc3RyaXBOYW1lc3BhY2UoZ2V0RWxlbWVudE5hbWUocm9vdEVsKSk7CiAgICBpZiAocm9vdEVsTmFtZSA9PT0gIlNlcnZpY2VFeGNlcHRpb25SZXBvcnQiKSB7CiAgICAgIGNvbnN0IGVycm9yID0gZmluZENoaWxkRWxlbWVudChyb290RWwsICJTZXJ2aWNlRXhjZXB0aW9uIik7CiAgICAgIGlmIChlcnJvcikgewogICAgICAgIHRocm93IHBhcnNlKGVycm9yLCB1cmwpOwogICAgICB9CiAgICB9CiAgICBpZiAocm9vdEVsTmFtZSA9PT0gIkV4Y2VwdGlvblJlcG9ydCIpIHsKICAgICAgY29uc3QgZXJyb3IgPSBmaW5kQ2hpbGRFbGVtZW50KHJvb3RFbCwgIkV4Y2VwdGlvbiIpOwogICAgICBpZiAoZXJyb3IpIHsKICAgICAgICB0aHJvdyBwYXJzZShlcnJvciwgdXJsKTsKICAgICAgfQogICAgfQogICAgcmV0dXJuIHJlc3BvbnNlOwogIH0KICBmdW5jdGlvbiBlbmNvZGVFcnJvcihlcnJvcikgewogICAgY29uc3QgYmFzZSA9IHsKICAgICAgbWVzc2FnZTogZXJyb3IubWVzc2FnZSwKICAgICAgc3RhY2s6IGVycm9yLnN0YWNrLAogICAgICBuYW1lOiBlcnJvci5uYW1lCiAgICB9OwogICAgaWYgKGVycm9yIGluc3RhbmNlb2YgU2VydmljZUV4Y2VwdGlvbkVycm9yKSB7CiAgICAgIHJldHVybiB7CiAgICAgICAgLi4uYmFzZSwKICAgICAgICBjb2RlOiBlcnJvci5jb2RlLAogICAgICAgIGxvY2F0b3I6IGVycm9yLmxvY2F0b3IsCiAgICAgICAgcmVzcG9uc2U6IGVycm9yLnJlc3BvbnNlLAogICAgICAgIHJlcXVlc3RVcmw6IGVycm9yLnJlcXVlc3RVcmwKICAgICAgfTsKICAgIH0KICAgIGlmIChlcnJvciBpbnN0YW5jZW9mIEVuZHBvaW50RXJyb3IpIHsKICAgICAgcmV0dXJuIHsKICAgICAgICAuLi5iYXNlLAogICAgICAgIGh0dHBTdGF0dXM6IGVycm9yLmh0dHBTdGF0dXMsCiAgICAgICAgaXNDcm9zc09yaWdpblJlbGF0ZWQ6IGVycm9yLmlzQ3Jvc3NPcmlnaW5SZWxhdGVkCiAgICAgIH07CiAgICB9CiAgICByZXR1cm4gYmFzZTsKICB9CiAgY29uc3QgZmFsbGJhY2tFdmVudFRhcmdldCA9IG5ldyBFdmVudFRhcmdldCgpOwogIGZ1bmN0aW9uIGFkZFRhc2tIYW5kbGVyKHRhc2tOYW1lLCBzY29wZSwgaGFuZGxlcikgewogICAgY29uc3QgdXNlV29ya2VyID0gdHlwZW9mIFdvcmtlckdsb2JhbFNjb3BlICE9PSAidW5kZWZpbmVkIjsKICAgIGNvbnN0IGV2ZW50SGFuZGxlciA9IGFzeW5jIChyZXF1ZXN0KSA9PiB7CiAgICAgIGlmIChyZXF1ZXN0LnRhc2tOYW1lID09PSB0YXNrTmFtZSkgewogICAgICAgIGxldCByZXNwb25zZSwgZXJyb3I7CiAgICAgICAgdHJ5IHsKICAgICAgICAgIHJlc3BvbnNlID0gYXdhaXQgaGFuZGxlcihyZXF1ZXN0LnBhcmFtcyk7CiAgICAgICAgfSBjYXRjaCAoZSkgewogICAgICAgICAgZXJyb3IgPSBlbmNvZGVFcnJvcihlKTsKICAgICAgICB9CiAgICAgICAgY29uc3QgbWVzc2FnZSA9ICgKICAgICAgICAgIC8qKiBAdHlwZSB7V29ya2VyUmVzcG9uc2V9ICovCiAgICAgICAgICB7CiAgICAgICAgICAgIHRhc2tOYW1lLAogICAgICAgICAgICByZXF1ZXN0SWQ6IHJlcXVlc3QucmVxdWVzdElkLAogICAgICAgICAgICAuLi5yZXNwb25zZSAmJiB7IHJlc3BvbnNlIH0sCiAgICAgICAgICAgIC4uLmVycm9yICYmIHsgZXJyb3IgfQogICAgICAgICAgfQogICAgICAgICk7CiAgICAgICAgaWYgKHVzZVdvcmtlcikgewogICAgICAgICAgc2NvcGUucG9zdE1lc3NhZ2UobWVzc2FnZSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGZhbGxiYWNrRXZlbnRUYXJnZXQuZGlzcGF0Y2hFdmVudCgKICAgICAgICAgICAgbmV3IEN1c3RvbUV2ZW50KCJvZ2MtY2xpZW50LnJlc3BvbnNlIiwgewogICAgICAgICAgICAgIGRldGFpbDogbWVzc2FnZQogICAgICAgICAgICB9KQogICAgICAgICAgKTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CiAgICBpZiAodXNlV29ya2VyKSB7CiAgICAgIHNjb3BlLmFkZEV2ZW50TGlzdGVuZXIoIm1lc3NhZ2UiLCAoZXZlbnQpID0+IGV2ZW50SGFuZGxlcihldmVudC5kYXRhKSk7CiAgICB9IGVsc2UgewogICAgICBmYWxsYmFja0V2ZW50VGFyZ2V0LmFkZEV2ZW50TGlzdGVuZXIoCiAgICAgICAgIm9nYy1jbGllbnQucmVxdWVzdCIsCiAgICAgICAgKGV2ZW50KSA9PiBldmVudEhhbmRsZXIoZXZlbnQuZGV0YWlsKQogICAgICApOwogICAgfQogIH0KICBjb25zdCBFTkNPRElOR1MgPSBbInV0Zi04IiwgInV0Zi0xNiIsICJpc28tODg1OS0xIl07CiAgY29uc3QgRkFMTEJBQ0tfRU5DT0RJTkcgPSAidXRmLTgiOwogIGZ1bmN0aW9uIGV4dHJhY3RFbmNvZGluZyhjb250ZW50VHlwZSkgewogICAgY29uc3QgbWF0Y2hlcyA9IC9jaGFyc2V0PShbXjtdKykvLmV4ZWMoY29udGVudFR5cGUpOwogICAgcmV0dXJuIG1hdGNoZXMgPyBtYXRjaGVzWzFdIDogbnVsbDsKICB9CiAgZnVuY3Rpb24gZGVjb2RlU3RyaW5nKGJ1ZmZlciwgY29udGVudFR5cGUpIHsKICAgIGNvbnN0IGVuY29kaW5nSGludCA9IGNvbnRlbnRUeXBlID8gZXh0cmFjdEVuY29kaW5nKGNvbnRlbnRUeXBlKSA6IG51bGw7CiAgICBjb25zdCBlbmNvZGluZ0F0dGVtcHRzID0gZW5jb2RpbmdIaW50ID8gW2VuY29kaW5nSGludCwgLi4uRU5DT0RJTkdTXSA6IEVOQ09ESU5HUzsKICAgIGZvciAoY29uc3QgZW5jb2Rpbmcgb2YgZW5jb2RpbmdBdHRlbXB0cykgewogICAgICB0cnkgewogICAgICAgIGNvbnN0IGRlY29kZXIgPSBuZXcgVGV4dERlY29kZXIoZW5jb2RpbmcsIHsgZmF0YWw6IHRydWUgfSk7CiAgICAgICAgcmV0dXJuIGRlY29kZXIuZGVjb2RlKGJ1ZmZlcik7CiAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgfQogICAgfQogICAgY29uc29sZS53YXJuKAogICAgICBgW29nYy1jbGllbnRdIFhNTCBkb2N1bWVudCBlbmNvZGluZyBjb3VsZCBub3QgYmUgZGV0ZXJtaW5lZCwgZmFsbGluZyBiYWNrIHRvICR7RkFMTEJBQ0tfRU5DT0RJTkd9LmAKICAgICk7CiAgICByZXR1cm4gbmV3IFRleHREZWNvZGVyKEZBTExCQUNLX0VOQ09ESU5HKS5kZWNvZGUoYnVmZmVyKTsKICB9CiAgY29uc3QgZmV0Y2hQcm9taXNlcyA9IC8qIEBfX1BVUkVfXyAqLyBuZXcgTWFwKCk7CiAgbGV0IGZldGNoT3B0aW9ucyA9IHt9OwogIGZ1bmN0aW9uIHNldEZldGNoT3B0aW9ucyhvcHRpb25zKSB7CiAgICBmZXRjaE9wdGlvbnMgPSBvcHRpb25zOwogIH0KICBmdW5jdGlvbiBnZXRGZXRjaE9wdGlvbnMoKSB7CiAgICByZXR1cm4gZmV0Y2hPcHRpb25zOwogIH0KICBmdW5jdGlvbiBzaGFyZWRGZXRjaCh1cmwsIG1ldGhvZCA9ICJHRVQiLCBhc0pzb24pIHsKICAgIGxldCBmZXRjaEtleSA9IGAke21ldGhvZH0jJHt1cmx9YDsKICAgIGlmIChhc0pzb24pIHsKICAgICAgZmV0Y2hLZXkgPSBgJHttZXRob2R9I2FzSnNvbiMke3VybH1gOwogICAgfQogICAgaWYgKGZldGNoUHJvbWlzZXMuaGFzKGZldGNoS2V5KSkgewogICAgICByZXR1cm4gZmV0Y2hQcm9taXNlcy5nZXQoZmV0Y2hLZXkpOwogICAgfQogICAgY29uc3Qgb3B0aW9ucyA9IHsgLi4uZ2V0RmV0Y2hPcHRpb25zKCkgfTsKICAgIG9wdGlvbnMubWV0aG9kID0gbWV0aG9kOwogICAgaWYgKGFzSnNvbikgewogICAgICBvcHRpb25zLmhlYWRlcnMgPSAiaGVhZGVycyIgaW4gb3B0aW9ucyA/IG9wdGlvbnMuaGVhZGVycyA6IHt9OwogICAgICBvcHRpb25zLmhlYWRlcnNbIkFjY2VwdCJdID0gImFwcGxpY2F0aW9uL2pzb24sYXBwbGljYXRpb24vc2NoZW1hK2pzb24iOwogICAgfQogICAgY29uc3QgcHJvbWlzZSA9IGZldGNoKHVybCwgb3B0aW9ucykuY2F0Y2goKGUpID0+IGUpLnRoZW4oKHJlc3ApID0+IHsKICAgICAgZmV0Y2hQcm9taXNlcy5kZWxldGUoZmV0Y2hLZXkpOwogICAgICByZXR1cm4gcmVzcDsKICAgIH0pOwogICAgZmV0Y2hQcm9taXNlcy5zZXQoZmV0Y2hLZXksIHByb21pc2UpOwogICAgcmV0dXJuIHByb21pc2UudGhlbigocmVzcCkgPT4gewogICAgICBpZiAocmVzcCBpbnN0YW5jZW9mIEVycm9yKQogICAgICAgIHRocm93IHJlc3A7CiAgICAgIHJldHVybiByZXNwLmNsb25lKCk7CiAgICB9KTsKICB9CiAgZnVuY3Rpb24gcXVlcnlYbWxEb2N1bWVudCh1cmwpIHsKICAgIHJldHVybiBzaGFyZWRGZXRjaCh1cmwpLmNhdGNoKAogICAgICAoKSA9PiAoCiAgICAgICAgLy8gYXR0ZW1wdCBhIEhFQUQgdG8gc2VlIGlmIHRoZSBmYWlsdXJlIGNvbWVzIGZyb20gQ09SUyBvciB0aGUgc2VydmljZSBpcyBnZW5lcmFsbHkgdW5yZWFjaGFibGUKICAgICAgICBmZXRjaCh1cmwsIHsgLi4uZ2V0RmV0Y2hPcHRpb25zKCksIG1ldGhvZDogIkhFQUQiLCBtb2RlOiAibm8tY29ycyIgfSkuY2F0Y2goKGVycm9yKSA9PiB7CiAgICAgICAgICB0aHJvdyBuZXcgRW5kcG9pbnRFcnJvcigKICAgICAgICAgICAgYEZldGNoaW5nIHRoZSBkb2N1bWVudCBmYWlsZWQgZWl0aGVyIGR1ZSB0byBuZXR3b3JrIGVycm9ycyBvciB1bnJlYWNoYWJsZSBob3N0LCBlcnJvciBpczogJHtlcnJvci5tZXNzYWdlfWAsCiAgICAgICAgICAgIDAsCiAgICAgICAgICAgIGZhbHNlCiAgICAgICAgICApOwogICAgICAgIH0pLnRoZW4oKCkgPT4gewogICAgICAgICAgdGhyb3cgbmV3IEVuZHBvaW50RXJyb3IoCiAgICAgICAgICAgIGBUaGUgZG9jdW1lbnQgY291bGQgbm90IGJlIGZldGNoZWQgZHVlIHRvIENPUlMgbGltaXRhdGlvbnNgLAogICAgICAgICAgICAwLAogICAgICAgICAgICB0cnVlCiAgICAgICAgICApOwogICAgICAgIH0pCiAgICAgICkKICAgICkudGhlbihhc3luYyAocmVzcCkgPT4gewogICAgICBpZiAoIXJlc3Aub2spIHsKICAgICAgICBjb25zdCB0ZXh0ID0gYXdhaXQgcmVzcC50ZXh0KCk7CiAgICAgICAgdGhyb3cgbmV3IEVuZHBvaW50RXJyb3IoCiAgICAgICAgICBgUmVjZWl2ZWQgYW4gZXJyb3Igd2l0aCBjb2RlICR7cmVzcC5zdGF0dXN9OiAke3RleHR9YCwKICAgICAgICAgIHJlc3Auc3RhdHVzLAogICAgICAgICAgZmFsc2UKICAgICAgICApOwogICAgICB9CiAgICAgIGNvbnN0IGJ1ZmZlciA9IGF3YWl0IHJlc3AuYXJyYXlCdWZmZXIoKTsKICAgICAgY29uc3QgY29udGVudFR5cGVIZWFkZXIgPSByZXNwLmhlYWRlcnMuZ2V0KCJDb250ZW50LVR5cGUiKTsKICAgICAgcmV0dXJuIGRlY29kZVN0cmluZyhidWZmZXIsIGNvbnRlbnRUeXBlSGVhZGVyKTsKICAgIH0pLnRoZW4oKHhtbCkgPT4gcGFyc2VYbWxTdHJpbmcoeG1sKSk7CiAgfQogIGZ1bmN0aW9uIHNldFF1ZXJ5UGFyYW1zKHVybCwgcGFyYW1zKSB7CiAgICBjb25zdCBlbmNvZGVkVXJsTWF0Y2ggPSB1cmwubWF0Y2goLyhodHRwcz8lM0ElMkYlMkZbXi9dKykkLyk7CiAgICBpZiAoZW5jb2RlZFVybE1hdGNoKSB7CiAgICAgIGNvbnN0IGVuY29kZWRVcmwgPSBlbmNvZGVkVXJsTWF0Y2hbMV07CiAgICAgIGNvbnN0IG1vZGlmaWVkVXJsID0gc2V0UXVlcnlQYXJhbXMoZGVjb2RlVVJJQ29tcG9uZW50KGVuY29kZWRVcmwpLCBwYXJhbXMpOwogICAgICByZXR1cm4gdXJsLnJlcGxhY2UoZW5jb2RlZFVybCwgZW5jb2RlVVJJQ29tcG9uZW50KG1vZGlmaWVkVXJsKSk7CiAgICB9CiAgICBjb25zdCB1cmxPYmogPSBuZXcgVVJMKHVybCk7CiAgICBjb25zdCBrZXlzID0gT2JqZWN0LmtleXMocGFyYW1zKTsKICAgIGNvbnN0IGtleXNMb3dlciA9IGtleXMubWFwKChrZXkpID0+IGtleS50b0xvd2VyQ2FzZSgpKTsKICAgIGNvbnN0IHRvRGVsZXRlID0gW107CiAgICBmb3IgKGNvbnN0IHBhcmFtIG9mIHVybE9iai5zZWFyY2hQYXJhbXMua2V5cygpKSB7CiAgICAgIGlmIChrZXlzTG93ZXIuaW5kZXhPZihwYXJhbS50b0xvd2VyQ2FzZSgpKSA+IC0xKSB7CiAgICAgICAgdG9EZWxldGUucHVzaChwYXJhbSk7CiAgICAgIH0KICAgIH0KICAgIHRvRGVsZXRlLm1hcCgocGFyYW0pID0+IHVybE9iai5zZWFyY2hQYXJhbXMuZGVsZXRlKHBhcmFtKSk7CiAgICBrZXlzLmZvckVhY2goCiAgICAgIChrZXkpID0+IHVybE9iai5zZWFyY2hQYXJhbXMuc2V0KAogICAgICAgIGtleSwKICAgICAgICBwYXJhbXNba2V5XSA9PT0gdHJ1ZSA/ICIiIDogcGFyYW1zW2tleV0KICAgICAgKQogICAgKTsKICAgIHJldHVybiB1cmxPYmoudG9TdHJpbmcoKTsKICB9CiAgY29uc3QgTGF0TG9uQ3JzTGlzdCA9IFsKICAgICJFUFNHOjQwNDYiLAogICAgLy8gUkdSREMgMjAwNQogICAgIkVQU0c6NDA3NSIsCiAgICAvLyBTUkVGOTgKICAgICJFUFNHOjQxMjAiLAogICAgLy8gR3JlZWsKICAgICJFUFNHOjQxMjIiLAogICAgLy8gQVRTNzcKICAgICJFUFNHOjQxMjQiLAogICAgLy8gUlQ5MAogICAgIkVQU0c6NDEyNiIsCiAgICAvLyBMS1M5NCAoRVRSUzg5KQogICAgIkVQU0c6NDE0OSIsCiAgICAvLyBDSDE5MDMKICAgICJFUFNHOjQxNTEiLAogICAgLy8gQ0hUUkY5NQogICAgIkVQU0c6NDE1MyIsCiAgICAvLyBSYXNzYWRpcmFuCiAgICAiRVBTRzo0MTU1IiwKICAgIC8vIERhYm9sYSAxOTgxCiAgICAiRVBTRzo0MTU3IiwKICAgIC8vIE1vdW50IERpbGxvbgogICAgIkVQU0c6NDE1OSIsCiAgICAvLyBFTEQ3OQogICAgIkVQU0c6NDE2MSIsCiAgICAvLyBQYW1wYSBkZWwgQ2FzdGlsbG8KICAgICJFUFNHOjQxNjMiLAogICAgLy8gWWVtZW4gTkdOOTYKICAgICJFUFNHOjQxNjUiLAogICAgLy8gQmlzc2F1CiAgICAiRVBTRzo0MTY3IiwKICAgIC8vIE5aR0QyMDAwCiAgICAiRVBTRzo0MTY5IiwKICAgIC8vIEFtZXJpY2FuIFNhbW9hIDE5NjIKICAgICJFUFNHOjQxNzEiLAogICAgLy8gUkdGOTMKICAgICJFUFNHOjQxNzMiLAogICAgLy8gSVJFTkVUOTUKICAgICJFUFNHOjQxNzUiLAogICAgLy8gU2llcnJhIExlb25lIDE5NjgKICAgICJFUFNHOjQxNzgiLAogICAgLy8gUHVsa292byAxOTQyKDgzKQogICAgIkVQU0c6NDE4MCIsCiAgICAvLyBFU1Q5NwogICAgIkVQU0c6NDE4MiIsCiAgICAvLyBBem9yZXMgT2NjaWRlbnRhbCAxOTM5CiAgICAiRVBTRzo0MTg0IiwKICAgIC8vIEF6b3JlcyBPcmllbnRhbCAxOTQwCiAgICAiRVBTRzo0MTg4IiwKICAgIC8vIE9TTkkgMTk1MgogICAgIkVQU0c6NDE5MCIsCiAgICAvLyBQT1NHQVIgOTgKICAgICJFUFNHOjQxOTEiLAogICAgLy8gQWxiYW5pYW4gMTk4NwogICAgIkVQU0c6NDE5NiIsCiAgICAvLyBBbW1hc3NhbGlrIDE5NTgKICAgICJFUFNHOjQxOTgiLAogICAgLy8gS291c3NlcmkKICAgICJFUFNHOjQyMDIiLAogICAgLy8gQUdENjYKICAgICJFUFNHOjQyMTAiLAogICAgLy8gQXJjIDE5NjAKICAgICJFUFNHOjQyMTEiLAogICAgLy8gQmF0YXZpYQogICAgIkVQU0c6NDIxNCIsCiAgICAvLyBCZWlqaW5nIDE5NTQKICAgICJFUFNHOjQyMjYiLAogICAgLy8gQ290ZSBkJ0l2b2lyZQogICAgIkVQU0c6NDIyOSIsCiAgICAvLyBFZ3lwdCAxOTA3CiAgICAiRVBTRzo0MjMxIiwKICAgIC8vIEVEODcKICAgICJFUFNHOjQyMzMiLAogICAgLy8gR2FuZGFqaWthIDE5NzAKICAgICJFUFNHOjQyMzYiLAogICAgLy8gSHUgVHp1IFNoYW4gMTk1MAogICAgIkVQU0c6NDIzOCIsCiAgICAvLyBJRDc0CiAgICAiRVBTRzo0MjQwIiwKICAgIC8vIEluZGlhbiAxOTc1CiAgICAiRVBTRzo0MjQyIiwKICAgIC8vIEpBRDY5CiAgICAiRVBTRzo0MjQ0IiwKICAgIC8vIEthbmRhd2FsYQogICAgIkVQU0c6NDI0NiIsCiAgICAvLyBLT0MKICAgICJFUFNHOjQyNDgiLAogICAgLy8gUFNBRDU2CiAgICAiRVBTRzo0MjUwIiwKICAgIC8vIExlaWdvbgogICAgIkVQU0c6NDI1MiIsCiAgICAvLyBMb21lCiAgICAiRVBTRzo0MjU1IiwKICAgIC8vIEhlcmF0IE5vcnRoCiAgICAiRVBTRzo0MjU4IiwKICAgIC8vIEVUUlM4OQogICAgIkVQU0c6NDI2MSIsCiAgICAvLyBNZXJjaGljaAogICAgIkVQU0c6NDI2NCIsCiAgICAvLyBNaGFzdAogICAgIkVQU0c6NDI2NyIsCiAgICAvLyBOQUQyNwogICAgIkVQU0c6NDI3MCIsCiAgICAvLyBOYWhyd2FuIDE5NjcKICAgICJFUFNHOjQyNzMiLAogICAgLy8gTkdPIDE5NDgKICAgICJFUFNHOjQyNzYiLAogICAgLy8gTlNXQyA5Wi0yCiAgICAiRVBTRzo0Mjc5IiwKICAgIC8vIE9TKFNOKTgwCiAgICAiRVBTRzo0MjgxIiwKICAgIC8vIFBhbGVzdGluZSAxOTIzCiAgICAiRVBTRzo0Mjg0IiwKICAgIC8vIFB1bGtvdm8gMTk0MgogICAgIkVQU0c6NDI4NiIsCiAgICAvLyBRYXRhciAxOTQ4CiAgICAiRVBTRzo0Mjg4IiwKICAgIC8vIExvbWEgUXVpbnRhbmEKICAgICJFUFNHOjQyOTIiLAogICAgLy8gU2FwcGVyIEhpbGwgMTk0MwogICAgIkVQU0c6NDI5NSIsCiAgICAvLyBTZXJpbmR1bmcKICAgICJFUFNHOjQyOTciLAogICAgLy8gVGFuYW5hcml2ZQogICAgIkVQU0c6NDI5OSIsCiAgICAvLyBUTTY1CiAgICAiRVBTRzo0MzAyIiwKICAgIC8vIFRyaW5pZGFkIDE5MDMKICAgICJFUFNHOjQzMjQiLAogICAgLy8gV0dTIDcyQkUKICAgICJFUFNHOjQzMjYiCiAgICAvLyBXR1MgODQKICBdOwogIGZ1bmN0aW9uIGhhc0ludmVydGVkQ29vcmRpbmF0ZXMoY3JzTmFtZSkgewogICAgcmV0dXJuIExhdExvbkNyc0xpc3QuaW5kZXhPZihzaW1wbGlmeUVwc2dVcm4oY3JzTmFtZSkpID4gLTE7CiAgfQogIGZ1bmN0aW9uIHNpbXBsaWZ5RXBzZ1VybihmdWxsQ3JzTmFtZSkgewogICAgaWYgKC9edXJuOig/OngtKT9vZ2M6ZGVmOmNyczplcHNnOi8udGVzdChmdWxsQ3JzTmFtZS50b0xvd2VyQ2FzZSgpKSkgewogICAgICBjb25zdCBjb2RlID0gLyhbMC05XSspJC8uZXhlYyhmdWxsQ3JzTmFtZSlbMV07CiAgICAgIHJldHVybiBgRVBTRzoke2NvZGV9YDsKICAgIH0KICAgIHJldHVybiBmdWxsQ3JzTmFtZTsKICB9CiAgZnVuY3Rpb24gcmVhZE9wZXJhdGlvblVybHNGcm9tQ2FwYWJpbGl0aWVzJDEoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCB1cmxzID0ge307CiAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgIkNhcGFiaWxpdHkiCiAgICApOwogICAgY29uc3QgcmVxdWVzdCA9IGZpbmRDaGlsZEVsZW1lbnQoY2FwYWJpbGl0eSwgIlJlcXVlc3QiKTsKICAgIGdldENoaWxkcmVuRWxlbWVudChyZXF1ZXN0KS5mb3JFYWNoKChvcGVyYXRpb24pID0+IHsKICAgICAgY29uc3Qgb3BlcmF0aW9uTmFtZSA9IHN0cmlwTmFtZXNwYWNlKGdldEVsZW1lbnROYW1lKG9wZXJhdGlvbikpOwogICAgICB1cmxzW29wZXJhdGlvbk5hbWVdID0gcGFyc2VPcGVyYXRpb24ob3BlcmF0aW9uKTsKICAgIH0pOwogICAgcmV0dXJuIHVybHM7CiAgfQogIGZ1bmN0aW9uIHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYykgewogICAgcmV0dXJuIGdldFJvb3RFbGVtZW50KGNhcGFiaWxpdGllc0RvYykuYXR0cmlidXRlc1sidmVyc2lvbiJdOwogIH0KICBmdW5jdGlvbiByZWFkTGF5ZXJzRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdmVyc2lvbiA9IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYyk7CiAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgIkNhcGFiaWxpdHkiCiAgICApOwogICAgcmV0dXJuIGZpbmRDaGlsZHJlbkVsZW1lbnQoY2FwYWJpbGl0eSwgIkxheWVyIikubWFwKAogICAgICAobGF5ZXJFbCkgPT4gcGFyc2VMYXllcihsYXllckVsLCB2ZXJzaW9uKQogICAgKTsKICB9CiAgZnVuY3Rpb24gcmVhZE91dHB1dEZvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzJDEoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgIkNhcGFiaWxpdHkiCiAgICApOwogICAgY29uc3QgZ2V0TWFwID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZmluZENoaWxkRWxlbWVudChjYXBhYmlsaXR5LCAiUmVxdWVzdCIpLAogICAgICAiR2V0TWFwIgogICAgKTsKICAgIGNvbnN0IG91dHB1dEZvcm1hdHMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGdldE1hcCwgIkZvcm1hdCIpLm1hcCgKICAgICAgZ2V0RWxlbWVudFRleHQKICAgICk7CiAgICByZXR1cm4gb3V0cHV0Rm9ybWF0czsKICB9CiAgZnVuY3Rpb24gcmVhZEluZm9Gb3JtYXRzRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpIHsKICAgIGNvbnN0IGNhcGFiaWxpdHkgPSBmaW5kQ2hpbGRFbGVtZW50KAogICAgICBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLAogICAgICAiQ2FwYWJpbGl0eSIKICAgICk7CiAgICBjb25zdCBnZXRGZWF0dXJlSW5mbyA9IGZpbmRDaGlsZEVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQoY2FwYWJpbGl0eSwgIlJlcXVlc3QiKSwKICAgICAgIkdldEZlYXR1cmVJbmZvIgogICAgKTsKICAgIGNvbnN0IG91dHB1dEZvcm1hdHMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGdldEZlYXR1cmVJbmZvLCAiRm9ybWF0IikubWFwKAogICAgICBnZXRFbGVtZW50VGV4dAogICAgKTsKICAgIHJldHVybiBvdXRwdXRGb3JtYXRzOwogIH0KICBmdW5jdGlvbiByZWFkRXhjZXB0aW9uRm9ybWF0c0Zyb21DYXBhYmlsaXRpZXMoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgIkNhcGFiaWxpdHkiCiAgICApOwogICAgY29uc3QgZXhjZXB0aW9uID0gZmluZENoaWxkRWxlbWVudChjYXBhYmlsaXR5LCAiRXhjZXB0aW9uIik7CiAgICBjb25zdCBleGNlcHRpb25Gb3JtYXRzID0gZmluZENoaWxkcmVuRWxlbWVudChleGNlcHRpb24sICJGb3JtYXQiKS5tYXAoCiAgICAgIGdldEVsZW1lbnRUZXh0CiAgICApOwogICAgcmV0dXJuIGV4Y2VwdGlvbkZvcm1hdHM7CiAgfQogIGZ1bmN0aW9uIHJlYWRJbmZvRnJvbUNhcGFiaWxpdGllcyQyKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3Qgc2VydmljZSA9IGZpbmRDaGlsZEVsZW1lbnQoZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwgIlNlcnZpY2UiKTsKICAgIGNvbnN0IG91dHB1dEZvcm1hdHMgPSByZWFkT3V0cHV0Rm9ybWF0c0Zyb21DYXBhYmlsaXRpZXMkMShjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3QgaW5mb0Zvcm1hdHMgPSByZWFkSW5mb0Zvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYyk7CiAgICBjb25zdCBleGNlcHRpb25Gb3JtYXRzID0gcmVhZEV4Y2VwdGlvbkZvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYyk7CiAgICBjb25zdCBrZXl3b3JkcyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIktleXdvcmRMaXN0IiksCiAgICAgICJLZXl3b3JkIgogICAgKS5tYXAoZ2V0RWxlbWVudFRleHQpLmZpbHRlcigodiwgaSwgYXJyKSA9PiBhcnIuaW5kZXhPZih2KSA9PT0gaSk7CiAgICBjb25zdCBwcm92aWRlciA9IHJlYWRQcm92aWRlckZyb21DYXBhYmlsaXRpZXMkMShjYXBhYmlsaXRpZXNEb2MpOwogICAgcmV0dXJuIHsKICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIlRpdGxlIikpLAogICAgICBuYW1lOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJOYW1lIikpLAogICAgICBhYnN0cmFjdDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiQWJzdHJhY3QiKSksCiAgICAgIG91dHB1dEZvcm1hdHMsCiAgICAgIGluZm9Gb3JtYXRzLAogICAgICBleGNlcHRpb25Gb3JtYXRzLAogICAgICBmZWVzOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJGZWVzIikpLAogICAgICBjb25zdHJhaW50czogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiQWNjZXNzQ29uc3RyYWludHMiKSksCiAgICAgIHByb3ZpZGVyLAogICAgICBrZXl3b3JkcwogICAgfTsKICB9CiAgZnVuY3Rpb24gcGFyc2VPcGVyYXRpb24ob3BlcmF0aW9uKSB7CiAgICBjb25zdCB1cmxzID0ge307CiAgICBjb25zdCBkY3BUeXBlID0gZmluZENoaWxkcmVuRWxlbWVudChvcGVyYXRpb24sICJEQ1BUeXBlIik7CiAgICBjb25zdCBodHRwID0gZGNwVHlwZS5mbGF0TWFwKChkKSA9PiBmaW5kQ2hpbGRFbGVtZW50KGQsICJIVFRQIikpOwogICAgY29uc3QgbWV0aG9kcyA9IGh0dHAuZmxhdE1hcCgoaCkgPT4gZ2V0Q2hpbGRyZW5FbGVtZW50KGgpKTsKICAgIG1ldGhvZHMuZm9yRWFjaCgobWV0aG9kKSA9PiB7CiAgICAgIGNvbnN0IG9ubGluZVJlc291cmNlID0gZmluZENoaWxkRWxlbWVudChtZXRob2QsICJPbmxpbmVSZXNvdXJjZSIpOwogICAgICBjb25zdCBtZXRob2ROYW1lID0gc3RyaXBOYW1lc3BhY2UoZ2V0RWxlbWVudE5hbWUobWV0aG9kKSk7CiAgICAgIHVybHNbbWV0aG9kTmFtZV0gPSBnZXRFbGVtZW50QXR0cmlidXRlKG9ubGluZVJlc291cmNlLCAieGxpbms6aHJlZiIpOwogICAgfSk7CiAgICByZXR1cm4gdXJsczsKICB9CiAgZnVuY3Rpb24gcGFyc2VMYXllcihsYXllckVsLCB2ZXJzaW9uLCBpbmhlcml0ZWRTcnMgPSBbXSwgaW5oZXJpdGVkU3R5bGVzID0gW10sIGluaGVyaXRlZEF0dHJpYnV0aW9uID0gbnVsbCwgaW5oZXJpdGVkQm91bmRpbmdCb3hlcyA9IG51bGwsIGluaGVyaXRlZE1heFNjYWxlRGVub20gPSBudWxsLCBpbmhlcml0ZWRNaW5TY2FsZURlbm9tID0gbnVsbCkgewogICAgY29uc3Qgc3JzVGFnID0gdmVyc2lvbiA9PT0gIjEuMy4wIiA/ICJDUlMiIDogIlNSUyI7CiAgICBjb25zdCBzcnNMaXN0ID0gZmluZENoaWxkcmVuRWxlbWVudChsYXllckVsLCBzcnNUYWcpLm1hcChnZXRFbGVtZW50VGV4dCk7CiAgICBjb25zdCBhdmFpbGFibGVDcnMgPSBzcnNMaXN0Lmxlbmd0aCA+IDAgPyBzcnNMaXN0IDogaW5oZXJpdGVkU3JzOwogICAgY29uc3QgbGF5ZXJTdHlsZXMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGxheWVyRWwsICJTdHlsZSIpLm1hcCgKICAgICAgcGFyc2VMYXllclN0eWxlCiAgICApOwogICAgY29uc3Qgc3R5bGVzID0gbGF5ZXJTdHlsZXMubGVuZ3RoID4gMCA/IGxheWVyU3R5bGVzIDogaW5oZXJpdGVkU3R5bGVzOwogICAgZnVuY3Rpb24gcGFyc2VCQm94MihiYm94RWwpIHsKICAgICAgY29uc3Qgc3JzID0gZ2V0RWxlbWVudEF0dHJpYnV0ZShiYm94RWwsIHNyc1RhZyk7CiAgICAgIGNvbnN0IGF0dHJzID0gaGFzSW52ZXJ0ZWRDb29yZGluYXRlcyhzcnMpICYmIHZlcnNpb24gPT09ICIxLjMuMCIgPyBbIm1pbnkiLCAibWlueCIsICJtYXh5IiwgIm1heHgiXSA6IFsibWlueCIsICJtaW55IiwgIm1heHgiLCAibWF4eSJdOwogICAgICByZXR1cm4gYXR0cnMubWFwKChuYW1lKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGJib3hFbCwgbmFtZSkpOwogICAgfQogICAgZnVuY3Rpb24gcGFyc2VFeEdlb2dyYXBoaWNCb3VuZGluZ0JveChiYm94RWwpIHsKICAgICAgcmV0dXJuIFsKICAgICAgICAid2VzdEJvdW5kTG9uZ2l0dWRlIiwKICAgICAgICAic291dGhCb3VuZExhdGl0dWRlIiwKICAgICAgICAiZWFzdEJvdW5kTG9uZ2l0dWRlIiwKICAgICAgICAibm9ydGhCb3VuZExhdGl0dWRlIgogICAgICBdLm1hcCgobmFtZSkgPT4gZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChiYm94RWwsIG5hbWUpKSk7CiAgICB9CiAgICBmdW5jdGlvbiBwYXJzZUxhdExvbkJvdW5kaW5nQm94KGJib3hFbCkgewogICAgICByZXR1cm4gWyJtaW54IiwgIm1pbnkiLCAibWF4eCIsICJtYXh5Il0ubWFwKAogICAgICAgIChuYW1lKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGJib3hFbCwgbmFtZSkKICAgICAgKTsKICAgIH0KICAgIGZ1bmN0aW9uIHBhcnNlU2NhbGVIaW50VmFsdWUodGV4dFZhbHVlLCBkZWZhdWx0VmFsdWUpIHsKICAgICAgaWYgKHRleHRWYWx1ZSA9PT0gIiIpIHsKICAgICAgICByZXR1cm4gZGVmYXVsdFZhbHVlOwogICAgICB9CiAgICAgIHJldHVybiBNYXRoLnNxcnQoMC41ICogcGFyc2VGbG9hdCh0ZXh0VmFsdWUpICoqIDIpIC8gMjhlLTU7CiAgICB9CiAgICBmdW5jdGlvbiBwYXJzZVNjYWxlSGludCgpIHsKICAgICAgY29uc3Qgc2NhbGVIaW50ID0gZmluZENoaWxkRWxlbWVudChsYXllckVsLCAiU2NhbGVIaW50Iik7CiAgICAgIGlmICghc2NhbGVIaW50KSB7CiAgICAgICAgcmV0dXJuIFtpbmhlcml0ZWRNaW5TY2FsZURlbm9tLCBpbmhlcml0ZWRNYXhTY2FsZURlbm9tXTsKICAgICAgfQogICAgICBjb25zdCBtaW4gPSBnZXRFbGVtZW50QXR0cmlidXRlKHNjYWxlSGludCwgIm1pbiIpOwogICAgICBjb25zdCBtYXggPSBnZXRFbGVtZW50QXR0cmlidXRlKHNjYWxlSGludCwgIm1heCIpOwogICAgICByZXR1cm4gWwogICAgICAgIHBhcnNlU2NhbGVIaW50VmFsdWUobWluLCBpbmhlcml0ZWRNaW5TY2FsZURlbm9tKSwKICAgICAgICBwYXJzZVNjYWxlSGludFZhbHVlKG1heCwgaW5oZXJpdGVkTWF4U2NhbGVEZW5vbSkKICAgICAgXTsKICAgIH0KICAgIGZ1bmN0aW9uIHBhcnNlU2NhbGVEZW5vbWluYXRvcihuYW1lLCBpbmhlcml0ZWRWYWx1ZSkgewogICAgICBjb25zdCB0ZXh0VmFsdWUgPSBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGxheWVyRWwsIG5hbWUpKTsKICAgICAgcmV0dXJuIHRleHRWYWx1ZSA9PT0gIiIgPyBpbmhlcml0ZWRWYWx1ZSA6IHBhcnNlRmxvYXQodGV4dFZhbHVlKTsKICAgIH0KICAgIGNvbnN0IGF0dHJpYnV0aW9uRWwgPSBmaW5kQ2hpbGRFbGVtZW50KGxheWVyRWwsICJBdHRyaWJ1dGlvbiIpOwogICAgY29uc3QgYXR0cmlidXRpb24gPSBhdHRyaWJ1dGlvbkVsICE9PSBudWxsID8gcGFyc2VMYXllckF0dHJpYnV0aW9uKGF0dHJpYnV0aW9uRWwpIDogaW5oZXJpdGVkQXR0cmlidXRpb247CiAgICBjb25zdCBsYXRMb25CYm94RWwgPSB2ZXJzaW9uID09PSAiMS4zLjAiID8gZmluZENoaWxkRWxlbWVudChsYXllckVsLCAiRVhfR2VvZ3JhcGhpY0JvdW5kaW5nQm94IikgOiBmaW5kQ2hpbGRFbGVtZW50KGxheWVyRWwsICJMYXRMb25Cb3VuZGluZ0JveCIpOwogICAgY29uc3QgYmFzZUJvdW5kaW5nQm94ID0ge307CiAgICBpZiAobGF0TG9uQmJveEVsKSB7CiAgICAgIGJhc2VCb3VuZGluZ0JveFsiRVBTRzo0MzI2Il0gPSB2ZXJzaW9uID09PSAiMS4zLjAiID8gcGFyc2VFeEdlb2dyYXBoaWNCb3VuZGluZ0JveChsYXRMb25CYm94RWwpIDogcGFyc2VMYXRMb25Cb3VuZGluZ0JveChsYXRMb25CYm94RWwpOwogICAgfQogICAgbGV0IGJvdW5kaW5nQm94ZXMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGxheWVyRWwsICJCb3VuZGluZ0JveCIpLnJlZHVjZSgKICAgICAgKHByZXYsIGJib3hFbCkgPT4gKHsKICAgICAgICAuLi5wcmV2LAogICAgICAgIFtnZXRFbGVtZW50QXR0cmlidXRlKGJib3hFbCwgc3JzVGFnKV06IHBhcnNlQkJveDIoYmJveEVsKQogICAgICB9KSwKICAgICAgYmFzZUJvdW5kaW5nQm94CiAgICApOwogICAgYm91bmRpbmdCb3hlcyA9IE9iamVjdC5rZXlzKGJvdW5kaW5nQm94ZXMpLmxlbmd0aCA+IDAgfHwgaW5oZXJpdGVkQm91bmRpbmdCb3hlcyA9PT0gbnVsbCA/IGJvdW5kaW5nQm94ZXMgOiBpbmhlcml0ZWRCb3VuZGluZ0JveGVzOwogICAgY29uc3QgcXVlcnlhYmxlID0gbGF5ZXJFbC5hdHRyaWJ1dGVzLnF1ZXJ5YWJsZSA9PT0gIjEiIHx8IGxheWVyRWwuYXR0cmlidXRlcy5xdWVyeWFibGUgPT09ICJ0cnVlIiA/IHRydWUgOiBmYWxzZTsKICAgIGNvbnN0IG9wYXF1ZSA9IGxheWVyRWwuYXR0cmlidXRlcy5vcGFxdWUgPT09ICIxIiB8fCBsYXllckVsLmF0dHJpYnV0ZXMub3BhcXVlID09PSAidHJ1ZSIgPyB0cnVlIDogZmFsc2U7CiAgICBjb25zdCBrZXl3b3JkcyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQobGF5ZXJFbCwgIktleXdvcmRMaXN0IiksCiAgICAgICJLZXl3b3JkIgogICAgKS5tYXAoZ2V0RWxlbWVudFRleHQpLmZpbHRlcigodiwgaSwgYXJyKSA9PiBhcnIuaW5kZXhPZih2KSA9PT0gaSk7CiAgICBsZXQgbWluU2NhbGVEZW5vbWluYXRvciwgbWF4U2NhbGVEZW5vbWluYXRvcjsKICAgIGlmICh2ZXJzaW9uID09PSAiMS4zLjAiKSB7CiAgICAgIG1pblNjYWxlRGVub21pbmF0b3IgPSBwYXJzZVNjYWxlRGVub21pbmF0b3IoCiAgICAgICAgIk1pblNjYWxlRGVub21pbmF0b3IiLAogICAgICAgIGluaGVyaXRlZE1pblNjYWxlRGVub20KICAgICAgKTsKICAgICAgbWF4U2NhbGVEZW5vbWluYXRvciA9IHBhcnNlU2NhbGVEZW5vbWluYXRvcigKICAgICAgICAiTWF4U2NhbGVEZW5vbWluYXRvciIsCiAgICAgICAgaW5oZXJpdGVkTWF4U2NhbGVEZW5vbQogICAgICApOwogICAgfSBlbHNlIHsKICAgICAgW21pblNjYWxlRGVub21pbmF0b3IsIG1heFNjYWxlRGVub21pbmF0b3JdID0gcGFyc2VTY2FsZUhpbnQoKTsKICAgIH0KICAgIGNvbnN0IG1ldGFkYXRhID0gZmluZENoaWxkcmVuRWxlbWVudChsYXllckVsLCAiTWV0YWRhdGFVUkwiKS5tYXAoCiAgICAgIChtZXRhZGF0YVVybEVsKSA9PiAoewogICAgICAgIHR5cGU6IGdldEVsZW1lbnRBdHRyaWJ1dGUobWV0YWRhdGFVcmxFbCwgInR5cGUiKSwKICAgICAgICBmb3JtYXQ6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQobWV0YWRhdGFVcmxFbCwgIkZvcm1hdCIpKSwKICAgICAgICB1cmw6IGdldEVsZW1lbnRBdHRyaWJ1dGUoCiAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KG1ldGFkYXRhVXJsRWwsICJPbmxpbmVSZXNvdXJjZSIpLAogICAgICAgICAgInhsaW5rOmhyZWYiCiAgICAgICAgKQogICAgICB9KQogICAgKTsKICAgIGNvbnN0IGNoaWxkcmVuID0gZmluZENoaWxkcmVuRWxlbWVudChsYXllckVsLCAiTGF5ZXIiKS5tYXAoCiAgICAgIChsYXllcikgPT4gcGFyc2VMYXllcigKICAgICAgICBsYXllciwKICAgICAgICB2ZXJzaW9uLAogICAgICAgIGF2YWlsYWJsZUNycywKICAgICAgICBzdHlsZXMsCiAgICAgICAgYXR0cmlidXRpb24sCiAgICAgICAgYm91bmRpbmdCb3hlcywKICAgICAgICBtYXhTY2FsZURlbm9taW5hdG9yLAogICAgICAgIG1pblNjYWxlRGVub21pbmF0b3IKICAgICAgKQogICAgKTsKICAgIHJldHVybiB7CiAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQobGF5ZXJFbCwgIk5hbWUiKSksCiAgICAgIHRpdGxlOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGxheWVyRWwsICJUaXRsZSIpKSwKICAgICAgYWJzdHJhY3Q6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQobGF5ZXJFbCwgIkFic3RyYWN0IikpLAogICAgICBhdmFpbGFibGVDcnMsCiAgICAgIHN0eWxlcywKICAgICAgYXR0cmlidXRpb24sCiAgICAgIGJvdW5kaW5nQm94ZXMsCiAgICAgIGtleXdvcmRzLAogICAgICBxdWVyeWFibGUsCiAgICAgIG9wYXF1ZSwKICAgICAgLi4ubWluU2NhbGVEZW5vbWluYXRvciAhPT0gbnVsbCA/IHsgbWluU2NhbGVEZW5vbWluYXRvciB9IDoge30sCiAgICAgIC4uLm1heFNjYWxlRGVub21pbmF0b3IgIT09IG51bGwgPyB7IG1heFNjYWxlRGVub21pbmF0b3IgfSA6IHt9LAogICAgICAuLi5tZXRhZGF0YS5sZW5ndGggJiYgeyBtZXRhZGF0YSB9LAogICAgICAuLi5jaGlsZHJlbi5sZW5ndGggJiYgeyBjaGlsZHJlbiB9CiAgICB9OwogIH0KICBmdW5jdGlvbiBwYXJzZUxheWVyU3R5bGUoc3R5bGVFbCkgewogICAgY29uc3QgbGVnZW5kVXJsID0gZ2V0RWxlbWVudEF0dHJpYnV0ZSgKICAgICAgZmluZENoaWxkRWxlbWVudChmaW5kQ2hpbGRFbGVtZW50KHN0eWxlRWwsICJMZWdlbmRVUkwiKSwgIk9ubGluZVJlc291cmNlIiksCiAgICAgICJ4bGluazpocmVmIgogICAgKTsKICAgIGNvbnN0IGFic3RyYWN0ID0gZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzdHlsZUVsLCAiQWJzdHJhY3QiKSk7CiAgICByZXR1cm4gewogICAgICBuYW1lOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHN0eWxlRWwsICJOYW1lIikpLAogICAgICB0aXRsZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzdHlsZUVsLCAiVGl0bGUiKSksCiAgICAgIC4uLmFic3RyYWN0ICYmIHsgYWJzdHJhY3QgfSwKICAgICAgLi4ubGVnZW5kVXJsICYmIHsgbGVnZW5kVXJsIH0KICAgIH07CiAgfQogIGZ1bmN0aW9uIHBhcnNlTGF5ZXJBdHRyaWJ1dGlvbihhdHRyaWJ1dGlvbkVsKSB7CiAgICBjb25zdCBsb2dvVXJsID0gZ2V0RWxlbWVudEF0dHJpYnV0ZSgKICAgICAgZmluZENoaWxkRWxlbWVudCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGF0dHJpYnV0aW9uRWwsICJMb2dvVVJMIiksCiAgICAgICAgIk9ubGluZVJlc291cmNlIgogICAgICApLAogICAgICAieGxpbms6aHJlZiIKICAgICk7CiAgICBjb25zdCB1cmwgPSBnZXRFbGVtZW50QXR0cmlidXRlKAogICAgICBmaW5kQ2hpbGRFbGVtZW50KGF0dHJpYnV0aW9uRWwsICJPbmxpbmVSZXNvdXJjZSIpLAogICAgICAieGxpbms6aHJlZiIKICAgICk7CiAgICBjb25zdCB0aXRsZSA9IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoYXR0cmlidXRpb25FbCwgIlRpdGxlIikpOwogICAgcmV0dXJuIHsKICAgICAgLi4udGl0bGUgJiYgeyB0aXRsZSB9LAogICAgICAuLi51cmwgJiYgeyB1cmwgfSwKICAgICAgLi4ubG9nb1VybCAmJiB7IGxvZ29VcmwgfQogICAgfTsKICB9CiAgZnVuY3Rpb24gcmVhZFByb3ZpZGVyRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3Qgc2VydmljZSA9IGZpbmRDaGlsZEVsZW1lbnQoZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwgIlNlcnZpY2UiKTsKICAgIGNvbnN0IGNvbnRhY3RJbmZvcm1hdGlvbiA9IGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIkNvbnRhY3RJbmZvcm1hdGlvbiIpOwogICAgY29uc3QgY29udGFjdFBlcnNvblByaW1hcnkgPSBmaW5kQ2hpbGRFbGVtZW50KAogICAgICBjb250YWN0SW5mb3JtYXRpb24sCiAgICAgICJDb250YWN0UGVyc29uUHJpbWFyeSIKICAgICk7CiAgICBjb25zdCBhZGRyZXNzID0gZmluZENoaWxkRWxlbWVudChjb250YWN0SW5mb3JtYXRpb24sICJDb250YWN0QWRkcmVzcyIpOwogICAgcmV0dXJuIHsKICAgICAgY29udGFjdDogewogICAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgZmluZENoaWxkRWxlbWVudChjb250YWN0UGVyc29uUHJpbWFyeSwgIkNvbnRhY3RQZXJzb24iKQogICAgICAgICksCiAgICAgICAgb3JnYW5pemF0aW9uOiBnZXRFbGVtZW50VGV4dCgKICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoY29udGFjdFBlcnNvblByaW1hcnksICJDb250YWN0T3JnYW5pemF0aW9uIikKICAgICAgICApLAogICAgICAgIHBvc2l0aW9uOiBnZXRFbGVtZW50VGV4dCgKICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoY29udGFjdEluZm9ybWF0aW9uLCAiQ29udGFjdFBvc2l0aW9uIikKICAgICAgICApLAogICAgICAgIHBob25lOiBnZXRFbGVtZW50VGV4dCgKICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoY29udGFjdEluZm9ybWF0aW9uLCAiQ29udGFjdFZvaWNlVGVsZXBob25lIikKICAgICAgICApLAogICAgICAgIGZheDogZ2V0RWxlbWVudFRleHQoCiAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGNvbnRhY3RJbmZvcm1hdGlvbiwgIkNvbnRhY3RGYWNzaW1pbGVUZWxlcGhvbmUiKQogICAgICAgICksCiAgICAgICAgYWRkcmVzczogewogICAgICAgICAgZGVsaXZlcnlQb2ludDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiQWRkcmVzcyIpKSwKICAgICAgICAgIGNpdHk6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoYWRkcmVzcywgIkNpdHkiKSksCiAgICAgICAgICBhZG1pbmlzdHJhdGl2ZUFyZWE6IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGFkZHJlc3MsICJTdGF0ZU9yUHJvdmluY2UiKQogICAgICAgICAgKSwKICAgICAgICAgIHBvc3RhbENvZGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoYWRkcmVzcywgIlBvc3RDb2RlIikpLAogICAgICAgICAgY291bnRyeTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiQ291bnRyeSIpKQogICAgICAgIH0sCiAgICAgICAgZW1haWw6IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgZmluZENoaWxkRWxlbWVudChjb250YWN0SW5mb3JtYXRpb24sICJDb250YWN0RWxlY3Ryb25pY01haWxBZGRyZXNzIikKICAgICAgICApCiAgICAgIH0KICAgIH07CiAgfQogIGZ1bmN0aW9uIHJlYWRQcm92aWRlckZyb21DYXBhYmlsaXRpZXMoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCBzZXJ2aWNlUHJvdmlkZXIgPSBmaW5kQ2hpbGRFbGVtZW50KAogICAgICBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLAogICAgICAiU2VydmljZVByb3ZpZGVyIgogICAgKTsKICAgIGNvbnN0IHNlcnZpY2VDb250YWN0ID0gZmluZENoaWxkRWxlbWVudChzZXJ2aWNlUHJvdmlkZXIsICJTZXJ2aWNlQ29udGFjdCIpOwogICAgY29uc3QgY29udGFjdEluZm8gPSBmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2VDb250YWN0LCAiQ29udGFjdEluZm8iKTsKICAgIGNvbnN0IHBob25lID0gZmluZENoaWxkRWxlbWVudChjb250YWN0SW5mbywgIlBob25lIik7CiAgICBjb25zdCBhZGRyZXNzID0gZmluZENoaWxkRWxlbWVudChjb250YWN0SW5mbywgIkFkZHJlc3MiKTsKICAgIHJldHVybiB7CiAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZVByb3ZpZGVyLCAiUHJvdmlkZXJOYW1lIikpLAogICAgICBzaXRlOiBnZXRFbGVtZW50QXR0cmlidXRlKAogICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZVByb3ZpZGVyLCAiUHJvdmlkZXJTaXRlIiksCiAgICAgICAgInhsaW5rOmhyZWYiCiAgICAgICksCiAgICAgIGNvbnRhY3Q6IHsKICAgICAgICBuYW1lOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2VDb250YWN0LCAiSW5kaXZpZHVhbE5hbWUiKSksCiAgICAgICAgcG9zaXRpb246IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgZmluZENoaWxkRWxlbWVudChzZXJ2aWNlQ29udGFjdCwgIlBvc2l0aW9uTmFtZSIpCiAgICAgICAgKSwKICAgICAgICBwaG9uZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChwaG9uZSwgIlZvaWNlIikpLAogICAgICAgIGZheDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChwaG9uZSwgIkZhY3NpbWlsZSIpKSwKICAgICAgICBhZGRyZXNzOiB7CiAgICAgICAgICBkZWxpdmVyeVBvaW50OiBnZXRFbGVtZW50VGV4dCgKICAgICAgICAgICAgZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiRGVsaXZlcnlQb2ludCIpCiAgICAgICAgICApLAogICAgICAgICAgY2l0eTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiQ2l0eSIpKSwKICAgICAgICAgIGFkbWluaXN0cmF0aXZlQXJlYTogZ2V0RWxlbWVudFRleHQoCiAgICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoYWRkcmVzcywgIkFkbWluaXN0cmF0aXZlQXJlYSIpCiAgICAgICAgICApLAogICAgICAgICAgcG9zdGFsQ29kZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiUG9zdGFsQ29kZSIpKSwKICAgICAgICAgIGNvdW50cnk6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoYWRkcmVzcywgIkNvdW50cnkiKSkKICAgICAgICB9LAogICAgICAgIGVtYWlsOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGFkZHJlc3MsICJFbGVjdHJvbmljTWFpbEFkZHJlc3MiKSkKICAgICAgfQogICAgfTsKICB9CiAgZnVuY3Rpb24gcmVhZE9wZXJhdGlvblVybHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdXJscyA9IHt9OwogICAgY29uc3QgY2FwYWJpbGl0aWVzID0gZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKTsKICAgIGNvbnN0IG9wZXJhdGlvbnNNZXRhZGF0YSA9IGZpbmRDaGlsZEVsZW1lbnQoCiAgICAgIGNhcGFiaWxpdGllcywKICAgICAgIk9wZXJhdGlvbnNNZXRhZGF0YSIKICAgICk7CiAgICBpZiAob3BlcmF0aW9uc01ldGFkYXRhKSB7CiAgICAgIGZpbmRDaGlsZHJlbkVsZW1lbnQob3BlcmF0aW9uc01ldGFkYXRhLCAiT3BlcmF0aW9uIikuZm9yRWFjaCgKICAgICAgICAob3BlcmF0aW9uKSA9PiB7CiAgICAgICAgICBjb25zdCBuYW1lID0gZ2V0RWxlbWVudEF0dHJpYnV0ZShvcGVyYXRpb24sICJuYW1lIik7CiAgICAgICAgICB1cmxzW25hbWVdID0gcGFyc2VPcGVyYXRpb24xMTAob3BlcmF0aW9uKTsKICAgICAgICB9CiAgICAgICk7CiAgICB9IGVsc2UgewogICAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudChjYXBhYmlsaXRpZXMsICJDYXBhYmlsaXR5Iik7CiAgICAgIGNvbnN0IHJlcXVlc3QgPSBmaW5kQ2hpbGRFbGVtZW50KGNhcGFiaWxpdHksICJSZXF1ZXN0Iik7CiAgICAgIGdldENoaWxkcmVuRWxlbWVudChyZXF1ZXN0KS5mb3JFYWNoKChvcGVyYXRpb24pID0+IHsKICAgICAgICBjb25zdCBuYW1lID0gc3RyaXBOYW1lc3BhY2UoZ2V0RWxlbWVudE5hbWUob3BlcmF0aW9uKSk7CiAgICAgICAgdXJsc1tuYW1lXSA9IHBhcnNlT3BlcmF0aW9uMTAwKG9wZXJhdGlvbik7CiAgICAgIH0pOwogICAgfQogICAgcmV0dXJuIHVybHM7CiAgfQogIGZ1bmN0aW9uIHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpIHsKICAgIHJldHVybiBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLmF0dHJpYnV0ZXNbInZlcnNpb24iXTsKICB9CiAgZnVuY3Rpb24gcmVhZE91dHB1dEZvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdmVyc2lvbiA9IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgbGV0IG91dHB1dEZvcm1hdHM7CiAgICBpZiAodmVyc2lvbi5zdGFydHNXaXRoKCIxLjAiKSkgewogICAgICBjb25zdCBnZXRGZWF0dXJlID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KAogICAgICAgICAgZmluZENoaWxkRWxlbWVudChnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLCAiQ2FwYWJpbGl0eSIpLAogICAgICAgICAgIlJlcXVlc3QiCiAgICAgICAgKSwKICAgICAgICAiR2V0RmVhdHVyZSIKICAgICAgKTsKICAgICAgb3V0cHV0Rm9ybWF0cyA9IGdldENoaWxkcmVuRWxlbWVudCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGdldEZlYXR1cmUsICJSZXN1bHRGb3JtYXQiKQogICAgICApLm1hcChnZXRFbGVtZW50TmFtZSk7CiAgICB9IGVsc2UgewogICAgICBjb25zdCBvcGVyYXRpb25zID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgICBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLAogICAgICAgICJPcGVyYXRpb25zTWV0YWRhdGEiCiAgICAgICk7CiAgICAgIGNvbnN0IGdldEZlYXR1cmUgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KG9wZXJhdGlvbnMsICJPcGVyYXRpb24iKS5maW5kKAogICAgICAgIChlbCkgPT4gZ2V0RWxlbWVudEF0dHJpYnV0ZShlbCwgIm5hbWUiKSA9PT0gIkdldEZlYXR1cmUiCiAgICAgICk7CiAgICAgIGNvbnN0IHBhcmFtZXRlciA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoZ2V0RmVhdHVyZSwgIlBhcmFtZXRlciIpLmZpbmQoCiAgICAgICAgKGVsKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGVsLCAibmFtZSIpID09PSAib3V0cHV0Rm9ybWF0IgogICAgICApOwogICAgICBvdXRwdXRGb3JtYXRzID0gZmluZENoaWxkcmVuRWxlbWVudChwYXJhbWV0ZXIsICJWYWx1ZSIsIHRydWUpLm1hcCgKICAgICAgICBnZXRFbGVtZW50VGV4dAogICAgICApOwogICAgfQogICAgcmV0dXJuIG91dHB1dEZvcm1hdHM7CiAgfQogIGZ1bmN0aW9uIHJlYWRJbmZvRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdmVyc2lvbiA9IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3Qgc2VydmljZVRhZyA9IHZlcnNpb24uc3RhcnRzV2l0aCgiMS4wIikgPyAiU2VydmljZSIgOiAiU2VydmljZUlkZW50aWZpY2F0aW9uIjsKICAgIGNvbnN0IG5hbWVUYWcgPSB2ZXJzaW9uLnN0YXJ0c1dpdGgoIjEuMCIpID8gIk5hbWUiIDogIlNlcnZpY2VUeXBlIjsKICAgIGNvbnN0IHNlcnZpY2UgPSBmaW5kQ2hpbGRFbGVtZW50KGdldFJvb3RFbGVtZW50KGNhcGFiaWxpdGllc0RvYyksIHNlcnZpY2VUYWcpOwogICAgbGV0IGtleXdvcmRzOwogICAgaWYgKHZlcnNpb24uc3RhcnRzV2l0aCgiMS4wIikpIHsKICAgICAga2V5d29yZHMgPSBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJLZXl3b3JkcyIpKS5zcGxpdCgiLCIpLm1hcCgoa2V5d29yZCkgPT4ga2V5d29yZC50cmltKCkpOwogICAgfSBlbHNlIHsKICAgICAga2V5d29yZHMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KAogICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIktleXdvcmRzIiksCiAgICAgICAgIktleXdvcmQiCiAgICAgICkubWFwKGdldEVsZW1lbnRUZXh0KTsKICAgIH0KICAgIGxldCBwcm92aWRlcjsKICAgIGlmICh2ZXJzaW9uICE9PSAiMS4wLjAiKSB7CiAgICAgIHByb3ZpZGVyID0gcmVhZFByb3ZpZGVyRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgfQogICAgcmV0dXJuIHsKICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIlRpdGxlIikpLAogICAgICBuYW1lOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsIG5hbWVUYWcpKSwKICAgICAgYWJzdHJhY3Q6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIkFic3RyYWN0IikpLAogICAgICBmZWVzOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJGZWVzIikpLAogICAgICBjb25zdHJhaW50czogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiQWNjZXNzQ29uc3RyYWludHMiKSksCiAgICAgIGtleXdvcmRzLAogICAgICBwcm92aWRlciwKICAgICAgb3V0cHV0Rm9ybWF0czogcmVhZE91dHB1dEZvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYykKICAgIH07CiAgfQogIGZ1bmN0aW9uIHJlYWRGZWF0dXJlVHlwZXNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdmVyc2lvbiA9IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3Qgb3V0cHV0Rm9ybWF0cyA9IHJlYWRPdXRwdXRGb3JtYXRzRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3QgY2FwYWJpbGl0eSA9IGZpbmRDaGlsZEVsZW1lbnQoCiAgICAgIGdldFJvb3RFbGVtZW50KGNhcGFiaWxpdGllc0RvYyksCiAgICAgICJGZWF0dXJlVHlwZUxpc3QiCiAgICApOwogICAgcmV0dXJuIGZpbmRDaGlsZHJlbkVsZW1lbnQoY2FwYWJpbGl0eSwgIkZlYXR1cmVUeXBlIikubWFwKAogICAgICAoZmVhdHVyZVR5cGVFbCkgPT4gcGFyc2VGZWF0dXJlVHlwZShmZWF0dXJlVHlwZUVsLCB2ZXJzaW9uLCBvdXRwdXRGb3JtYXRzKQogICAgKTsKICB9CiAgZnVuY3Rpb24gcGFyc2VPcGVyYXRpb24xMDAob3BlcmF0aW9uKSB7CiAgICBjb25zdCB1cmxzID0ge307CiAgICBjb25zdCBkY3BUeXBlID0gZmluZENoaWxkcmVuRWxlbWVudChvcGVyYXRpb24sICJEQ1BUeXBlIik7CiAgICBjb25zdCBodHRwID0gZGNwVHlwZS5mbGF0TWFwKChkKSA9PiBmaW5kQ2hpbGRyZW5FbGVtZW50KGQsICJIVFRQIikpOwogICAgY29uc3QgbWV0aG9kcyA9IGh0dHAuZmxhdE1hcCgoaCkgPT4gZ2V0Q2hpbGRyZW5FbGVtZW50KGgpKTsKICAgIG1ldGhvZHMuZm9yRWFjaCgobWV0aG9kKSA9PiB7CiAgICAgIGNvbnN0IG1ldGhvZE5hbWUgPSBzdHJpcE5hbWVzcGFjZShnZXRFbGVtZW50TmFtZShtZXRob2QpKTsKICAgICAgdXJsc1ttZXRob2ROYW1lXSA9IGdldEVsZW1lbnRBdHRyaWJ1dGUobWV0aG9kLCAib25saW5lUmVzb3VyY2UiKTsKICAgIH0pOwogICAgcmV0dXJuIHVybHM7CiAgfQogIGZ1bmN0aW9uIHBhcnNlT3BlcmF0aW9uMTEwKG9wZXJhdGlvbikgewogICAgY29uc3QgdXJscyA9IHt9OwogICAgY29uc3QgZGNwVHlwZSA9IGZpbmRDaGlsZHJlbkVsZW1lbnQob3BlcmF0aW9uLCAiRENQIik7CiAgICBjb25zdCBodHRwID0gZGNwVHlwZS5mbGF0TWFwKChkKSA9PiBmaW5kQ2hpbGRFbGVtZW50KGQsICJIVFRQIikpOwogICAgY29uc3QgbWV0aG9kcyA9IGh0dHAuZmxhdE1hcCgoaCkgPT4gZ2V0Q2hpbGRyZW5FbGVtZW50KGgpKTsKICAgIG1ldGhvZHMuZm9yRWFjaCgobWV0aG9kKSA9PiB7CiAgICAgIGNvbnN0IG1ldGhvZE5hbWUgPSBzdHJpcE5hbWVzcGFjZShnZXRFbGVtZW50TmFtZShtZXRob2QpKTsKICAgICAgdXJsc1ttZXRob2ROYW1lXSA9IGdldEVsZW1lbnRBdHRyaWJ1dGUobWV0aG9kLCAieGxpbms6aHJlZiIpOwogICAgfSk7CiAgICByZXR1cm4gdXJsczsKICB9CiAgZnVuY3Rpb24gcGFyc2VGZWF0dXJlVHlwZShmZWF0dXJlVHlwZUVsLCBzZXJ2aWNlVmVyc2lvbiwgZGVmYXVsdE91dHB1dEZvcm1hdHMpIHsKICAgIGNvbnN0IHNyc1RhZyA9IHNlcnZpY2VWZXJzaW9uLnN0YXJ0c1dpdGgoIjIuIikgPyAiQ1JTIiA6ICJTUlMiOwogICAgY29uc3QgZGVmYXVsdFNyc1RhZyA9IHNlcnZpY2VWZXJzaW9uLnN0YXJ0c1dpdGgoIjEuMCIpID8gIlNSUyIgOiBgRGVmYXVsdCR7c3JzVGFnfWA7CiAgICBmdW5jdGlvbiBwYXJzZUJCb3gxMDAoKSB7CiAgICAgIGNvbnN0IGJib3hFbCA9IGZpbmRDaGlsZEVsZW1lbnQoZmVhdHVyZVR5cGVFbCwgIkxhdExvbmdCb3VuZGluZ0JveCIpOwogICAgICByZXR1cm4gWyJtaW54IiwgIm1pbnkiLCAibWF4eCIsICJtYXh5Il0ubWFwKChuYW1lKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGJib3hFbCwgbmFtZSkpLm1hcChwYXJzZUZsb2F0KTsKICAgIH0KICAgIGZ1bmN0aW9uIHBhcnNlQkJveDIoKSB7CiAgICAgIGNvbnN0IGJib3hFbCA9IGZpbmRDaGlsZEVsZW1lbnQoZmVhdHVyZVR5cGVFbCwgIldHUzg0Qm91bmRpbmdCb3giKTsKICAgICAgcmV0dXJuIFsiTG93ZXJDb3JuZXIiLCAiVXBwZXJDb3JuZXIiXS5tYXAoKGVsTmFtZSkgPT4gZmluZENoaWxkRWxlbWVudChiYm94RWwsIGVsTmFtZSkpLm1hcCgoY29ybmVyRWwpID0+IGdldEVsZW1lbnRUZXh0KGNvcm5lckVsKS5zcGxpdCgiICIpKS5yZWR1Y2UoKHByZXYsIGN1cnIpID0+IFsuLi5wcmV2LCAuLi5jdXJyXSkubWFwKHBhcnNlRmxvYXQpOwogICAgfQogICAgY29uc3Qgb3RoZXJDcnMgPSBzZXJ2aWNlVmVyc2lvbi5zdGFydHNXaXRoKCIxLjAiKSA/IFtdIDogZmluZENoaWxkcmVuRWxlbWVudChmZWF0dXJlVHlwZUVsLCBgT3RoZXIke3Nyc1RhZ31gKS5tYXAoZ2V0RWxlbWVudFRleHQpLm1hcChzaW1wbGlmeUVwc2dVcm4pOwogICAgY29uc3Qgb3V0cHV0Rm9ybWF0cyA9IHNlcnZpY2VWZXJzaW9uLnN0YXJ0c1dpdGgoIjEuMCIpID8gW10gOiBmaW5kQ2hpbGRyZW5FbGVtZW50KAogICAgICBmaW5kQ2hpbGRFbGVtZW50KGZlYXR1cmVUeXBlRWwsICJPdXRwdXRGb3JtYXRzIiksCiAgICAgICJGb3JtYXQiCiAgICApLm1hcChnZXRFbGVtZW50VGV4dCk7CiAgICBjb25zdCBrZXl3b3JkcyA9IHNlcnZpY2VWZXJzaW9uLnN0YXJ0c1dpdGgoIjEuMCIpID8gZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiS2V5d29yZHMiKSkuc3BsaXQoIiwiKS5tYXAoKGtleXdvcmQpID0+IGtleXdvcmQudHJpbSgpKSA6IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQoZmVhdHVyZVR5cGVFbCwgIktleXdvcmRzIiksCiAgICAgICJLZXl3b3JkIgogICAgKS5tYXAoZ2V0RWxlbWVudFRleHQpLmZpbHRlcigodiwgaSwgYXJyKSA9PiBhcnIuaW5kZXhPZih2KSA9PT0gaSk7CiAgICBjb25zdCBtZXRhZGF0YSA9IHNlcnZpY2VWZXJzaW9uID09PSAiMi4wLjAiID8gZmluZENoaWxkcmVuRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiTWV0YWRhdGFVUkwiKS5tYXAoCiAgICAgIChtZXRhZGF0YVVybEVsKSA9PiAoewogICAgICAgIHVybDogZ2V0RWxlbWVudEF0dHJpYnV0ZShtZXRhZGF0YVVybEVsLCAieGxpbms6aHJlZiIpCiAgICAgIH0pCiAgICApIDogZmluZENoaWxkcmVuRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiTWV0YWRhdGFVUkwiKS5tYXAoCiAgICAgIChtZXRhZGF0YVVybEVsKSA9PiAoewogICAgICAgIGZvcm1hdDogZ2V0RWxlbWVudEF0dHJpYnV0ZShtZXRhZGF0YVVybEVsLCAiZm9ybWF0IiksCiAgICAgICAgdHlwZTogZ2V0RWxlbWVudEF0dHJpYnV0ZShtZXRhZGF0YVVybEVsLCAidHlwZSIpLAogICAgICAgIHVybDogZ2V0RWxlbWVudFRleHQobWV0YWRhdGFVcmxFbCkudHJpbSgpCiAgICAgIH0pCiAgICApOwogICAgcmV0dXJuIHsKICAgICAgbmFtZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiTmFtZSIpKSwKICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZmVhdHVyZVR5cGVFbCwgIlRpdGxlIikpLAogICAgICBhYnN0cmFjdDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiQWJzdHJhY3QiKSksCiAgICAgIGRlZmF1bHRDcnM6IHNpbXBsaWZ5RXBzZ1VybigKICAgICAgICBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGZlYXR1cmVUeXBlRWwsIGRlZmF1bHRTcnNUYWcpKQogICAgICApLAogICAgICBvdGhlckNycywKICAgICAgb3V0cHV0Rm9ybWF0czogb3V0cHV0Rm9ybWF0cy5sZW5ndGggPiAwID8gb3V0cHV0Rm9ybWF0cyA6IGRlZmF1bHRPdXRwdXRGb3JtYXRzLAogICAgICBsYXRMb25Cb3VuZGluZ0JveDogc2VydmljZVZlcnNpb24uc3RhcnRzV2l0aCgiMS4wIikgPyBwYXJzZUJCb3gxMDAoKSA6IHBhcnNlQkJveDIoKSwKICAgICAga2V5d29yZHMsCiAgICAgIC4uLm1ldGFkYXRhLmxlbmd0aCAmJiB7IG1ldGFkYXRhIH0KICAgIH07CiAgfQogIGZ1bmN0aW9uIHBhcnNlQkJveCh4bWxFbGVtZW50KSB7CiAgICBjb25zdCByZXN1bHQgPSBbIkxvd2VyQ29ybmVyIiwgIlVwcGVyQ29ybmVyIl0ubWFwKChlbE5hbWUpID0+IGZpbmRDaGlsZEVsZW1lbnQoeG1sRWxlbWVudCwgZWxOYW1lKSkubWFwKChjb3JuZXJFbCkgPT4gZ2V0RWxlbWVudFRleHQoY29ybmVyRWwpLnNwbGl0KCIgIikpLnJlZHVjZSgocHJldiwgY3VycikgPT4gWy4uLnByZXYsIC4uLmN1cnJdKS5tYXAocGFyc2VGbG9hdCk7CiAgICBpZiAocmVzdWx0LnNvbWUoTnVtYmVyLmlzTmFOKSkKICAgICAgcmV0dXJuIG51bGw7CiAgICByZXR1cm4gcmVzdWx0OwogIH0KICBmdW5jdGlvbiByZWFkSW5mb0Zyb21DYXBhYmlsaXRpZXMoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCByb290RWwgPSBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3Qgc2VydmljZSA9IGZpbmRDaGlsZEVsZW1lbnQocm9vdEVsLCAiU2VydmljZUlkZW50aWZpY2F0aW9uIik7CiAgICBjb25zdCBrZXl3b3JkcyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIktleXdvcmRzIiksCiAgICAgICJLZXl3b3JkIgogICAgKS5tYXAoZ2V0RWxlbWVudFRleHQpOwogICAgY29uc3QgbWV0YWRhdGEgPSBmaW5kQ2hpbGRFbGVtZW50KHJvb3RFbCwgIk9wZXJhdGlvbnNNZXRhZGF0YSIpOwogICAgY29uc3QgZ2V0VGlsZU9wZXJhdGlvbiA9IGZpbmRDaGlsZHJlbkVsZW1lbnQobWV0YWRhdGEsICJPcGVyYXRpb24iKS5maW5kKAogICAgICAoZWwpID0+IGdldEVsZW1lbnRBdHRyaWJ1dGUoZWwsICJuYW1lIikgPT0gIkdldFRpbGUiCiAgICApOwogICAgY29uc3QgZ2V0VGlsZVVybHMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGdldFRpbGVPcGVyYXRpb24sICJHZXQiLCB0cnVlKS5yZWR1Y2UoCiAgICAgIChwcmV2LCBjdXJyKSA9PiB7CiAgICAgICAgY29uc3QgZW5jb2RpbmdUeXBlID0gZ2V0RWxlbWVudFRleHQoCiAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGN1cnIsICJWYWx1ZSIsIHRydWUpCiAgICAgICAgKTsKICAgICAgICBjb25zdCB1cmwgPSBnZXRFbGVtZW50QXR0cmlidXRlKGN1cnIsICJ4bGluazpocmVmIik7CiAgICAgICAgaWYgKGVuY29kaW5nVHlwZS50b0xvd2VyQ2FzZSgpID09PSAicmVzdGZ1bCIpCiAgICAgICAgICByZXR1cm4geyAuLi5wcmV2LCByZXN0OiB1cmwgfTsKICAgICAgICByZXR1cm4geyAuLi5wcmV2LCBrdnA6IHVybCB9OwogICAgICB9LAogICAgICB7fQogICAgKTsKICAgIHJldHVybiB7CiAgICAgIHRpdGxlOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJUaXRsZSIpKSwKICAgICAgbmFtZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiU2VydmljZVR5cGUiKSksCiAgICAgIGFic3RyYWN0OiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJBYnN0cmFjdCIpKSwKICAgICAgZmVlczogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiRmVlcyIpKSwKICAgICAgY29uc3RyYWludHM6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIkFjY2Vzc0NvbnN0cmFpbnRzIikpLAogICAgICBrZXl3b3JkcywKICAgICAgcHJvdmlkZXI6IHJlYWRQcm92aWRlckZyb21DYXBhYmlsaXRpZXMoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgZ2V0VGlsZVVybHMKICAgIH07CiAgfQogIGZ1bmN0aW9uIHJlYWRNYXRyaXhTZXRzRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpIHsKICAgIGZ1bmN0aW9uIHBhcnNlTWF0cml4U2V0KGVsZW1lbnQpIHsKICAgICAgY29uc3QgdG9wTGVmdCA9IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIlRvcExlZnRDb3JuZXIiKSkuc3BsaXQoIiAiKS5tYXAocGFyc2VGbG9hdCk7CiAgICAgIHJldHVybiB7CiAgICAgICAgaWRlbnRpZmllcjogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50LCAiSWRlbnRpZmllciIpKSwKICAgICAgICB0aWxlV2lkdGg6IHBhcnNlSW50KAogICAgICAgICAgZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50LCAiVGlsZVdpZHRoIikpCiAgICAgICAgKSwKICAgICAgICB0aWxlSGVpZ2h0OiBwYXJzZUludCgKICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIlRpbGVIZWlnaHQiKSkKICAgICAgICApLAogICAgICAgIG1hdHJpeFdpZHRoOiBwYXJzZUludCgKICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIk1hdHJpeFdpZHRoIikpCiAgICAgICAgKSwKICAgICAgICBtYXRyaXhIZWlnaHQ6IHBhcnNlSW50KAogICAgICAgICAgZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50LCAiTWF0cml4SGVpZ2h0IikpCiAgICAgICAgKSwKICAgICAgICBzY2FsZURlbm9taW5hdG9yOiBwYXJzZUZsb2F0KAogICAgICAgICAgZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50LCAiU2NhbGVEZW5vbWluYXRvciIpKQogICAgICAgICksCiAgICAgICAgdG9wTGVmdAogICAgICB9OwogICAgfQogICAgY29uc3QgY29udGVudHMgPSBmaW5kQ2hpbGRFbGVtZW50KAogICAgICBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLAogICAgICAiQ29udGVudHMiCiAgICApOwogICAgY29uc3QgbWF0cml4U2V0cyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoY29udGVudHMsICJUaWxlTWF0cml4U2V0Iik7CiAgICByZXR1cm4gbWF0cml4U2V0cy5tYXAoKGVsZW1lbnQpID0+IHsKICAgICAgY29uc3Qgd2VsbEtub3duU2NhbGVTZXQgPSBnZXRFbGVtZW50VGV4dCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQsICJXZWxsS25vd25TY2FsZVNldCIpCiAgICAgICk7CiAgICAgIGNvbnN0IGJvdW5kaW5nQm94ID0gcGFyc2VCQm94KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIkJvdW5kaW5nQm94IikpOwogICAgICByZXR1cm4gewogICAgICAgIGlkZW50aWZpZXI6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIklkZW50aWZpZXIiKSksCiAgICAgICAgY3JzOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQsICJTdXBwb3J0ZWRDUlMiKSksCiAgICAgICAgdGlsZU1hdHJpY2VzOiBmaW5kQ2hpbGRyZW5FbGVtZW50KGVsZW1lbnQsICJUaWxlTWF0cml4IikubWFwKAogICAgICAgICAgcGFyc2VNYXRyaXhTZXQKICAgICAgICApLAogICAgICAgIC4uLmJvdW5kaW5nQm94ICYmIHsgYm91bmRpbmdCb3ggfSwKICAgICAgICAuLi53ZWxsS25vd25TY2FsZVNldCAmJiB7IHdlbGxLbm93blNjYWxlU2V0IH0KICAgICAgfTsKICAgIH0pOwogIH0KICBmdW5jdGlvbiByZWFkTGF5ZXJzRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpIHsKICAgIGNvbnN0IHJvb3RFbCA9IGdldFJvb3RFbGVtZW50KGNhcGFiaWxpdGllc0RvYyk7CiAgICBjb25zdCBjb250ZW50c0VsID0gZmluZENoaWxkRWxlbWVudChyb290RWwsICJDb250ZW50cyIpOwogICAgZnVuY3Rpb24gZ2V0TWF0cml4U2V0Q3JzKGNvbnRlbnRzRWwyLCBpZGVudGlmaWVyKSB7CiAgICAgIGNvbnN0IG1hdHJpeFNldCA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoY29udGVudHNFbDIsICJUaWxlTWF0cml4U2V0IikuZmluZCgKICAgICAgICAobWF0cml4U2V0RWwpID0+IHsKICAgICAgICAgIGNvbnN0IGlkZW50aWZpZXJFbCA9IGZpbmRDaGlsZEVsZW1lbnQobWF0cml4U2V0RWwsICJJZGVudGlmaWVyIik7CiAgICAgICAgICByZXR1cm4gZ2V0RWxlbWVudFRleHQoaWRlbnRpZmllckVsKSA9PT0gaWRlbnRpZmllcjsKICAgICAgICB9CiAgICAgICk7CiAgICAgIHJldHVybiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KG1hdHJpeFNldCwgIlN1cHBvcnRlZENSUyIpKTsKICAgIH0KICAgIGZ1bmN0aW9uIHBhcnNlTWF0cml4U2V0TGluayhlbGVtZW50KSB7CiAgICAgIGNvbnN0IGlkZW50aWZpZXIgPSBnZXRFbGVtZW50VGV4dCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQsICJUaWxlTWF0cml4U2V0IikKICAgICAgKTsKICAgICAgY29uc3QgY3JzID0gZ2V0TWF0cml4U2V0Q3JzKGNvbnRlbnRzRWwsIGlkZW50aWZpZXIpOwogICAgICByZXR1cm4gewogICAgICAgIGlkZW50aWZpZXIsCiAgICAgICAgY3JzLAogICAgICAgIGxpbWl0czogZmluZENoaWxkcmVuRWxlbWVudChlbGVtZW50LCAiVGlsZU1hdHJpeExpbWl0cyIsIHRydWUpLm1hcCgKICAgICAgICAgIChlbGVtZW50MikgPT4gKHsKICAgICAgICAgICAgdGlsZU1hdHJpeDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50MiwgIlRpbGVNYXRyaXgiKSksCiAgICAgICAgICAgIG1pblRpbGVSb3c6IHBhcnNlSW50KAogICAgICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJNaW5UaWxlUm93IikpCiAgICAgICAgICAgICksCiAgICAgICAgICAgIG1pblRpbGVDb2w6IHBhcnNlSW50KAogICAgICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJNaW5UaWxlQ29sIikpCiAgICAgICAgICAgICksCiAgICAgICAgICAgIG1heFRpbGVSb3c6IHBhcnNlSW50KAogICAgICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJNYXhUaWxlUm93IikpCiAgICAgICAgICAgICksCiAgICAgICAgICAgIG1heFRpbGVDb2w6IHBhcnNlSW50KAogICAgICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJNYXhUaWxlQ29sIikpCiAgICAgICAgICAgICkKICAgICAgICAgIH0pCiAgICAgICAgKQogICAgICB9OwogICAgfQogICAgY29uc3QgZ2V0VGlsZU9wZXJhdGlvbiA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQocm9vdEVsLCAiT3BlcmF0aW9uc01ldGFkYXRhIiksCiAgICAgICJPcGVyYXRpb24iCiAgICApLmZpbmQoKGVsKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGVsLCAibmFtZSIpID09ICJHZXRUaWxlIik7CiAgICBjb25zdCBnZXRLdnBFbHQgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGdldFRpbGVPcGVyYXRpb24sICJHZXQiLCB0cnVlKS5maWx0ZXIoCiAgICAgIChlbHQpID0+IHsKICAgICAgICBjb25zdCBlbmNvZGluZ1R5cGUgPSBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGVsdCwgIlZhbHVlIiwgdHJ1ZSkpOwogICAgICAgIHJldHVybiBlbmNvZGluZ1R5cGUudG9Mb3dlckNhc2UoKSA9PT0gImt2cCI7CiAgICAgIH0KICAgIClbMF07CiAgICBjb25zdCBnZXRLdnBVcmwgPSBnZXRLdnBFbHQgPyBnZXRFbGVtZW50QXR0cmlidXRlKGdldEt2cEVsdCwgInhsaW5rOmhyZWYiKSA6ICIiOwogICAgY29uc3QgY29udGVudHMgPSBmaW5kQ2hpbGRFbGVtZW50KHJvb3RFbCwgIkNvbnRlbnRzIik7CiAgICBjb25zdCBsYXllcnMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGNvbnRlbnRzLCAiTGF5ZXIiKTsKICAgIHJldHVybiBsYXllcnMubWFwKChlbGVtZW50KSA9PiB7CiAgICAgIGNvbnN0IGxhdExvbkJvdW5kaW5nQm94ID0gcGFyc2VCQm94KAogICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIldHUzg0Qm91bmRpbmdCb3giKQogICAgICApOwogICAgICBsZXQgZGVmYXVsdFN0eWxlID0gIiI7CiAgICAgIGNvbnN0IHN0eWxlcyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgIlN0eWxlIikubWFwKChlbGVtZW50MikgPT4gewogICAgICAgIGNvbnN0IGxlZ2VuZFVybCA9IGdldEVsZW1lbnRBdHRyaWJ1dGUoCiAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQyLCAiTGVnZW5kVVJMIiksCiAgICAgICAgICAieGxpbms6aHJlZiIKICAgICAgICApOwogICAgICAgIGNvbnN0IGFic3RyYWN0ID0gZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50MiwgIkFic3RyYWN0IikpOwogICAgICAgIGNvbnN0IHN0eWxlID0gewogICAgICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJUaXRsZSIpKSwKICAgICAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJJZGVudGlmaWVyIikpLAogICAgICAgICAgLi4uYWJzdHJhY3QgJiYgeyBhYnN0cmFjdCB9LAogICAgICAgICAgLi4ubGVnZW5kVXJsICYmIHsgbGVnZW5kVXJsIH0KICAgICAgICB9OwogICAgICAgIGlmIChnZXRFbGVtZW50QXR0cmlidXRlKGVsZW1lbnQyLCAiaXNEZWZhdWx0IikgPT09ICJ0cnVlIikgewogICAgICAgICAgZGVmYXVsdFN0eWxlID0gc3R5bGUubmFtZTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHN0eWxlOwogICAgICB9KTsKICAgICAgY29uc3Qgb3V0cHV0Rm9ybWF0cyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgIkZvcm1hdCIpLm1hcCgKICAgICAgICBnZXRFbGVtZW50VGV4dAogICAgICApOwogICAgICBjb25zdCByZXNvdXJjZUxpbmtzID0gZmluZENoaWxkcmVuRWxlbWVudCgKICAgICAgICBlbGVtZW50LAogICAgICAgICJSZXNvdXJjZVVSTCIKICAgICAgKS5maWx0ZXIoCiAgICAgICAgKGVsZW1lbnQyKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGVsZW1lbnQyLCAicmVzb3VyY2VUeXBlIikgPT09ICJ0aWxlIgogICAgICApLm1hcCgoZWxlbWVudDIpID0+IHsKICAgICAgICBjb25zdCBmb3JtYXQgPSBnZXRFbGVtZW50QXR0cmlidXRlKGVsZW1lbnQyLCAiZm9ybWF0Iik7CiAgICAgICAgY29uc3QgdXJsID0gZ2V0RWxlbWVudEF0dHJpYnV0ZShlbGVtZW50MiwgInRlbXBsYXRlIik7CiAgICAgICAgcmV0dXJuIHsgZm9ybWF0LCB1cmwsIGVuY29kaW5nOiAiUkVTVCIgfTsKICAgICAgfSk7CiAgICAgIGlmIChnZXRLdnBVcmwpIHsKICAgICAgICByZXNvdXJjZUxpbmtzLnB1c2goCiAgICAgICAgICAuLi5vdXRwdXRGb3JtYXRzLm1hcCgoZm9ybWF0KSA9PiAoewogICAgICAgICAgICBlbmNvZGluZzogIktWUCIsCiAgICAgICAgICAgIHVybDogZ2V0S3ZwVXJsLAogICAgICAgICAgICBmb3JtYXQKICAgICAgICAgIH0pKQogICAgICAgICk7CiAgICAgIH0KICAgICAgY29uc3QgbWF0cml4U2V0cyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgIlRpbGVNYXRyaXhTZXRMaW5rIikubWFwKAogICAgICAgIHBhcnNlTWF0cml4U2V0TGluawogICAgICApOwogICAgICBjb25zdCBkaW1lbnNpb25zID0gZmluZENoaWxkcmVuRWxlbWVudChlbGVtZW50LCAiRGltZW5zaW9uIikubWFwKAogICAgICAgIChlbGVtZW50MikgPT4gewogICAgICAgICAgY29uc3QgaWRlbnRpZmllciA9IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQyLCAiSWRlbnRpZmllciIpCiAgICAgICAgICApOwogICAgICAgICAgY29uc3QgZGVmYXVsdFZhbHVlID0gZ2V0RWxlbWVudFRleHQoCiAgICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJEZWZhdWx0IikKICAgICAgICAgICk7CiAgICAgICAgICBjb25zdCB2YWx1ZXMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGVsZW1lbnQyLCAiVmFsdWVzIikubWFwKAogICAgICAgICAgICBnZXRFbGVtZW50VGV4dAogICAgICAgICAgKTsKICAgICAgICAgIHJldHVybiB7IGlkZW50aWZpZXIsIGRlZmF1bHRWYWx1ZSwgdmFsdWVzIH07CiAgICAgICAgfQogICAgICApOwogICAgICByZXR1cm4gewogICAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIklkZW50aWZpZXIiKSksCiAgICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIlRpdGxlIikpLAogICAgICAgIGFic3RyYWN0OiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQsICJBYnN0cmFjdCIpKSwKICAgICAgICBzdHlsZXMsCiAgICAgICAgcmVzb3VyY2VMaW5rcywKICAgICAgICBtYXRyaXhTZXRzLAogICAgICAgIGRlZmF1bHRTdHlsZSwKICAgICAgICAuLi5sYXRMb25Cb3VuZGluZ0JveCAmJiB7IGxhdExvbkJvdW5kaW5nQm94IH0sCiAgICAgICAgLi4uZGltZW5zaW9ucyAmJiB7IGRpbWVuc2lvbnMgfQogICAgICB9OwogICAgfSk7CiAgfQogIGZ1bmN0aW9uIHBhcnNlRmVhdHVyZVByb3BzKGdldEZlYXR1cmVzRG9jLCBmZWF0dXJlVHlwZUZ1bGwsIHNlcnZpY2VWZXJzaW9uKSB7CiAgICBjb25zdCBjb2xsZWN0aW9uID0gZ2V0Um9vdEVsZW1lbnQoZ2V0RmVhdHVyZXNEb2MpOwogICAgbGV0IG1lbWJlcnM7CiAgICBpZiAoc2VydmljZVZlcnNpb24uc3RhcnRzV2l0aCgiMi4wIikpIHsKICAgICAgbWVtYmVycyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoY29sbGVjdGlvbiwgIm1lbWJlciIpLm1hcCgKICAgICAgICAocGFyZW50KSA9PiBnZXRDaGlsZHJlbkVsZW1lbnQocGFyZW50KVswXQogICAgICApOwogICAgfSBlbHNlIHsKICAgICAgY29uc3QgbWVtYmVyc1Jvb3QgPSBmaW5kQ2hpbGRFbGVtZW50KGNvbGxlY3Rpb24sICJmZWF0dXJlTWVtYmVycyIpOwogICAgICBtZW1iZXJzID0gbWVtYmVyc1Jvb3QgPyBnZXRDaGlsZHJlbkVsZW1lbnQobWVtYmVyc1Jvb3QpIDogZmluZENoaWxkcmVuRWxlbWVudChjb2xsZWN0aW9uLCAiZmVhdHVyZU1lbWJlciIpLm1hcCgKICAgICAgICAocGFyZW50KSA9PiBnZXRDaGlsZHJlbkVsZW1lbnQocGFyZW50KVswXQogICAgICApOwogICAgfQogICAgY29uc3QgaWRBdHRyID0gc2VydmljZVZlcnNpb24gPT09ICIxLjAuMCIgPyAiZmlkIiA6ICJnbWw6aWQiOwogICAgZnVuY3Rpb24gaXNFbGVtZW50UHJvcGVydHkocHJvcE5hbWUpIHsKICAgICAgcmV0dXJuIHByb3BOYW1lIGluIGZlYXR1cmVUeXBlRnVsbC5wcm9wZXJ0aWVzOwogICAgfQogICAgZnVuY3Rpb24gcGFyc2VFbGVtZW50UHJvcGVydHlWYWx1ZShwcm9wTmFtZSwgdmFsdWVBc1N0cmluZykgewogICAgICBjb25zdCB0eXBlID0gZmVhdHVyZVR5cGVGdWxsLnByb3BlcnRpZXNbcHJvcE5hbWVdOwogICAgICBzd2l0Y2ggKHR5cGUpIHsKICAgICAgICBjYXNlICJpbnRlZ2VyIjoKICAgICAgICAgIHJldHVybiBwYXJzZUludCh2YWx1ZUFzU3RyaW5nKTsKICAgICAgICBjYXNlICJmbG9hdCI6CiAgICAgICAgICByZXR1cm4gcGFyc2VGbG9hdCh2YWx1ZUFzU3RyaW5nKTsKICAgICAgICBjYXNlICJib29sZWFuIjoKICAgICAgICAgIHJldHVybiB2YWx1ZUFzU3RyaW5nID09PSAidHJ1ZSI7CiAgICAgICAgZGVmYXVsdDoKICAgICAgICAgIHJldHVybiB2YWx1ZUFzU3RyaW5nOwogICAgICB9CiAgICB9CiAgICBmdW5jdGlvbiBnZXRQcm9wZXJ0aWVzKG1lbWJlckVsKSB7CiAgICAgIHJldHVybiBnZXRDaGlsZHJlbkVsZW1lbnQobWVtYmVyRWwpLmZpbHRlcigoZWwpID0+IGlzRWxlbWVudFByb3BlcnR5KHN0cmlwTmFtZXNwYWNlKGdldEVsZW1lbnROYW1lKGVsKSkpKS5yZWR1Y2UoKHByZXYsIGN1cnIpID0+IHsKICAgICAgICBjb25zdCBwcm9wTmFtZSA9IHN0cmlwTmFtZXNwYWNlKGdldEVsZW1lbnROYW1lKGN1cnIpKTsKICAgICAgICByZXR1cm4gewogICAgICAgICAgLi4ucHJldiwKICAgICAgICAgIFtwcm9wTmFtZV06IHBhcnNlRWxlbWVudFByb3BlcnR5VmFsdWUocHJvcE5hbWUsIGdldEVsZW1lbnRUZXh0KGN1cnIpKQogICAgICAgIH07CiAgICAgIH0sIHt9KTsKICAgIH0KICAgIHJldHVybiBtZW1iZXJzLm1hcCgoZWwpID0+ICh7CiAgICAgIGlkOiBnZXRFbGVtZW50QXR0cmlidXRlKGVsLCBpZEF0dHIpLAogICAgICBwcm9wZXJ0aWVzOiBnZXRQcm9wZXJ0aWVzKGVsKQogICAgfSkpOwogIH0KICBmdW5jdGlvbiBjb21wdXRlRmVhdHVyZVByb3BzRGV0YWlscyhmZWF0dXJlc1dpdGhQcm9wcykgewogICAgcmV0dXJuIGZlYXR1cmVzV2l0aFByb3BzLnJlZHVjZSgocHJldiwgY3VycikgPT4gewogICAgICBmb3IgKGNvbnN0IHByb3BOYW1lIGluIGN1cnIucHJvcGVydGllcykgewogICAgICAgIGNvbnN0IHByb3BWYWx1ZSA9IGN1cnIucHJvcGVydGllc1twcm9wTmFtZV07CiAgICAgICAgaWYgKCEocHJvcE5hbWUgaW4gcHJldikpIHsKICAgICAgICAgIHByZXZbcHJvcE5hbWVdID0geyB1bmlxdWVWYWx1ZXM6IFtdIH07CiAgICAgICAgfQogICAgICAgIGNvbnN0IHVuaXF1ZVZhbHVlID0gcHJldltwcm9wTmFtZV0udW5pcXVlVmFsdWVzLmZpbmQoCiAgICAgICAgICAodikgPT4gdi52YWx1ZSA9PT0gcHJvcFZhbHVlCiAgICAgICAgKTsKICAgICAgICBpZiAodW5pcXVlVmFsdWUpCiAgICAgICAgICB1bmlxdWVWYWx1ZS5jb3VudCsrOwogICAgICAgIGVsc2UKICAgICAgICAgIHByZXZbcHJvcE5hbWVdLnVuaXF1ZVZhbHVlcy5wdXNoKHsgdmFsdWU6IHByb3BWYWx1ZSwgY291bnQ6IDEgfSk7CiAgICAgIH0KICAgICAgcmV0dXJuIHByZXY7CiAgICB9LCB7fSk7CiAgfQogIGZ1bmN0aW9uIGdlbmVyYXRlR2V0RmVhdHVyZVVybChzZXJ2aWNlVXJsLCB2ZXJzaW9uLCBmZWF0dXJlVHlwZSwgb3V0cHV0Rm9ybWF0LCBtYXhGZWF0dXJlcywgYXR0cmlidXRlcywgaGl0c09ubHksIG91dHB1dENycywgZXh0ZW50LCBleHRlbnRDcnMsIHN0YXJ0SW5kZXgsIHNvcnRCeSkgewogICAgY29uc3QgdHlwZVBhcmFtID0gdmVyc2lvbiA9PT0gIjIuMC4wIiA/ICJUWVBFTkFNRVMiIDogIlRZUEVOQU1FIjsKICAgIGNvbnN0IGNvdW50UGFyYW0gPSB2ZXJzaW9uID09PSAiMi4wLjAiID8gIkNPVU5UIiA6ICJNQVhGRUFUVVJFUyI7CiAgICBjb25zdCBuZXdQYXJhbXMgPSB7CiAgICAgIFNFUlZJQ0U6ICJXRlMiLAogICAgICBSRVFVRVNUOiAiR2V0RmVhdHVyZSIsCiAgICAgIFZFUlNJT046IHZlcnNpb24sCiAgICAgIFt0eXBlUGFyYW1dOiBmZWF0dXJlVHlwZQogICAgfTsKICAgIGlmIChvdXRwdXRGb3JtYXQgIT09IHZvaWQgMCkKICAgICAgbmV3UGFyYW1zLk9VVFBVVEZPUk1BVCA9IG91dHB1dEZvcm1hdDsKICAgIGlmIChhdHRyaWJ1dGVzICE9PSB2b2lkIDApCiAgICAgIG5ld1BhcmFtcy5QUk9QRVJUWU5BTUUgPSBhdHRyaWJ1dGVzLmpvaW4oIiwiKTsKICAgIGlmIChoaXRzT25seSkgewogICAgICBuZXdQYXJhbXMuUkVTVUxUVFlQRSA9ICJoaXRzIjsKICAgICAgbmV3UGFyYW1zW2NvdW50UGFyYW1dID0gIjEiOwogICAgfSBlbHNlIGlmIChtYXhGZWF0dXJlcyAhPT0gdm9pZCAwKQogICAgICBuZXdQYXJhbXNbY291bnRQYXJhbV0gPSBtYXhGZWF0dXJlcy50b1N0cmluZygxMCk7CiAgICBpZiAob3V0cHV0Q3JzKSB7CiAgICAgIG5ld1BhcmFtcy5TUlNOQU1FID0gb3V0cHV0Q3JzOwogICAgfQogICAgaWYgKGV4dGVudCkgewogICAgICBjb25zdCBleHRlbnRKb2luZWQgPSBleHRlbnQuam9pbigiLCIpOwogICAgICBuZXdQYXJhbXMuQkJPWCA9IGV4dGVudENycyA/IGAke2V4dGVudEpvaW5lZH0sJHtleHRlbnRDcnN9YCA6IGV4dGVudEpvaW5lZDsKICAgIH0KICAgIGlmIChzdGFydEluZGV4KSB7CiAgICAgIG5ld1BhcmFtcy5TVEFSVElOREVYID0gc3RhcnRJbmRleC50b1N0cmluZygxMCk7CiAgICB9CiAgICBjb25zdCB1cmwgPSBuZXcgVVJMKHNldFF1ZXJ5UGFyYW1zKHNlcnZpY2VVcmwsIG5ld1BhcmFtcykpOwogICAgaWYgKEFycmF5LmlzQXJyYXkoc29ydEJ5KSAmJiBzb3J0QnkubGVuZ3RoID4gMCkgewogICAgICBjb25zdCBzb3J0cyA9IHNvcnRCeS5tYXAoKGZpZWxkU29ydCkgPT4gYCR7ZmllbGRTb3J0WzFdfSAke2ZpZWxkU29ydFswXX1gKS5qb2luKCIsIik7CiAgICAgIHVybC5zZWFyY2hQYXJhbXMuc2V0KCJTT1JUQlkiLCBzb3J0cyk7CiAgICB9CiAgICByZXR1cm4gdXJsLnRvU3RyaW5nKCk7CiAgfQogIGFkZFRhc2tIYW5kbGVyKAogICAgInBhcnNlV21zQ2FwYWJpbGl0aWVzIiwKICAgIGdsb2JhbFRoaXMsCiAgICAoeyB1cmwgfSkgPT4gcXVlcnlYbWxEb2N1bWVudCh1cmwpLnRoZW4oKHhtbERvYykgPT4gY2hlY2soeG1sRG9jLCB1cmwpKS50aGVuKCh4bWxEb2MpID0+ICh7CiAgICAgIGluZm86IHJlYWRJbmZvRnJvbUNhcGFiaWxpdGllcyQyKHhtbERvYyksCiAgICAgIGxheWVyczogcmVhZExheWVyc0Zyb21DYXBhYmlsaXRpZXMkMSh4bWxEb2MpLAogICAgICB1cmw6IHJlYWRPcGVyYXRpb25VcmxzRnJvbUNhcGFiaWxpdGllcyQxKHhtbERvYyksCiAgICAgIHZlcnNpb246IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyQxKHhtbERvYykKICAgIH0pKQogICk7CiAgYWRkVGFza0hhbmRsZXIoCiAgICAicGFyc2VXZnNDYXBhYmlsaXRpZXMiLAogICAgZ2xvYmFsVGhpcywKICAgICh7IHVybCB9KSA9PiBxdWVyeVhtbERvY3VtZW50KHVybCkudGhlbigoeG1sRG9jKSA9PiBjaGVjayh4bWxEb2MsIHVybCkpLnRoZW4oKHhtbERvYykgPT4gKHsKICAgICAgaW5mbzogcmVhZEluZm9Gcm9tQ2FwYWJpbGl0aWVzJDEoeG1sRG9jKSwKICAgICAgZmVhdHVyZVR5cGVzOiByZWFkRmVhdHVyZVR5cGVzRnJvbUNhcGFiaWxpdGllcyh4bWxEb2MpLAogICAgICB1cmw6IHJlYWRPcGVyYXRpb25VcmxzRnJvbUNhcGFiaWxpdGllcyh4bWxEb2MpLAogICAgICB2ZXJzaW9uOiByZWFkVmVyc2lvbkZyb21DYXBhYmlsaXRpZXMoeG1sRG9jKQogICAgfSkpCiAgKTsKICBhZGRUYXNrSGFuZGxlcigKICAgICJxdWVyeVdmc0ZlYXR1cmVUeXBlRGV0YWlscyIsCiAgICBnbG9iYWxUaGlzLAogICAgKHsKICAgICAgdXJsLAogICAgICBzZXJ2aWNlVmVyc2lvbiwKICAgICAgZmVhdHVyZVR5cGVGdWxsCiAgICB9KSA9PiB7CiAgICAgIGNvbnN0IGdldEZlYXR1cmVVcmwgPSBnZW5lcmF0ZUdldEZlYXR1cmVVcmwoCiAgICAgICAgdXJsLAogICAgICAgIHNlcnZpY2VWZXJzaW9uLAogICAgICAgIGZlYXR1cmVUeXBlRnVsbC5uYW1lLAogICAgICAgIHZvaWQgMCwKICAgICAgICB2b2lkIDAsCiAgICAgICAgT2JqZWN0LmtleXMoZmVhdHVyZVR5cGVGdWxsLnByb3BlcnRpZXMpCiAgICAgICk7CiAgICAgIHJldHVybiBxdWVyeVhtbERvY3VtZW50KGdldEZlYXR1cmVVcmwpLnRoZW4oKGdldEZlYXR1cmVEb2MpID0+ICh7CiAgICAgICAgcHJvcHM6IGNvbXB1dGVGZWF0dXJlUHJvcHNEZXRhaWxzKAogICAgICAgICAgcGFyc2VGZWF0dXJlUHJvcHMoZ2V0RmVhdHVyZURvYywgZmVhdHVyZVR5cGVGdWxsLCBzZXJ2aWNlVmVyc2lvbikKICAgICAgICApCiAgICAgIH0pKTsKICAgIH0KICApOwogIGFkZFRhc2tIYW5kbGVyKAogICAgInVwZGF0ZUZldGNoT3B0aW9ucyIsCiAgICBnbG9iYWxUaGlzLAogICAgKHsgb3B0aW9ucyB9KSA9PiB7CiAgICAgIHNldEZldGNoT3B0aW9ucyhvcHRpb25zKTsKICAgICAgcmV0dXJuIFByb21pc2UucmVzb2x2ZSh7fSk7CiAgICB9CiAgKTsKICBhZGRUYXNrSGFuZGxlcigKICAgICJwYXJzZVdtdHNDYXBhYmlsaXRpZXMiLAogICAgZ2xvYmFsVGhpcywKICAgICh7IHVybCB9KSA9PiBxdWVyeVhtbERvY3VtZW50KHVybCkudGhlbigoeG1sRG9jKSA9PiBjaGVjayh4bWxEb2MsIHVybCkpLnRoZW4oKHhtbERvYykgPT4gKHsKICAgICAgaW5mbzogcmVhZEluZm9Gcm9tQ2FwYWJpbGl0aWVzKHhtbERvYyksCiAgICAgIGxheWVyczogcmVhZExheWVyc0Zyb21DYXBhYmlsaXRpZXMoeG1sRG9jKSwKICAgICAgbWF0cml4U2V0czogcmVhZE1hdHJpeFNldHNGcm9tQ2FwYWJpbGl0aWVzKHhtbERvYykKICAgIH0pKQogICk7Cn0pKCk7Ci8vIyBzb3VyY2VNYXBwaW5nVVJMPXdvcmtlci1MRGtNT3gwZC5qcy5tYXAK")], { type: "text/javascript;charset=utf-8" });
552
+ function me(e) {
553
+ let t;
554
+ try {
555
+ if (t = pe && (window.URL || window.webkitURL).createObjectURL(pe), !t) throw "";
556
+ let n = new Worker(t, { name: e?.name });
557
+ return n.addEventListener("error", () => {
558
+ (window.URL || window.webkitURL).revokeObjectURL(t);
559
+ }), n;
560
+ } catch {
561
+ return new Worker("data:text/javascript;base64,KGZ1bmN0aW9uKCkgewogICJ1c2Ugc3RyaWN0IjsKICAvKiEgQHJncm92ZS9wYXJzZS14bWwgdjQuMS4wIHwgSVNDIExpY2Vuc2UgfCBDb3B5cmlnaHQgUnlhbiBHcm92ZSAqLwogIHZhciBfX2RlZlByb3AgPSBPYmplY3QuZGVmaW5lUHJvcGVydHk7CiAgdmFyIF9fZ2V0T3duUHJvcERlc2MgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yOwogIHZhciBfX2dldE93blByb3BOYW1lcyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzOwogIHZhciBfX2hhc093blByb3AgPSBPYmplY3QucHJvdG90eXBlLmhhc093blByb3BlcnR5OwogIHZhciBfX2V4cG9ydCA9ICh0YXJnZXQsIGFsbCkgPT4gewogICAgZm9yICh2YXIgbmFtZSBpbiBhbGwpCiAgICAgIF9fZGVmUHJvcCh0YXJnZXQsIG5hbWUsIHsgZ2V0OiBhbGxbbmFtZV0sIGVudW1lcmFibGU6IHRydWUgfSk7CiAgfTsKICB2YXIgX19jb3B5UHJvcHMgPSAodG8sIGZyb20sIGV4Y2VwdCwgZGVzYykgPT4gewogICAgaWYgKGZyb20gJiYgdHlwZW9mIGZyb20gPT09ICJvYmplY3QiIHx8IHR5cGVvZiBmcm9tID09PSAiZnVuY3Rpb24iKSB7CiAgICAgIGZvciAobGV0IGtleSBvZiBfX2dldE93blByb3BOYW1lcyhmcm9tKSkKICAgICAgICBpZiAoIV9faGFzT3duUHJvcC5jYWxsKHRvLCBrZXkpICYmIGtleSAhPT0gZXhjZXB0KQogICAgICAgICAgX19kZWZQcm9wKHRvLCBrZXksIHsgZ2V0OiAoKSA9PiBmcm9tW2tleV0sIGVudW1lcmFibGU6ICEoZGVzYyA9IF9fZ2V0T3duUHJvcERlc2MoZnJvbSwga2V5KSkgfHwgZGVzYy5lbnVtZXJhYmxlIH0pOwogICAgfQogICAgcmV0dXJuIHRvOwogIH07CiAgdmFyIF9fdG9Db21tb25KUyA9IChtb2QpID0+IF9fY29weVByb3BzKF9fZGVmUHJvcCh7fSwgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pLCBtb2QpOwogIHZhciBzcmNfZXhwb3J0cyA9IHt9OwogIF9fZXhwb3J0KHNyY19leHBvcnRzLCB7CiAgICBYbWxDZGF0YTogKCkgPT4gWG1sQ2RhdGEsCiAgICBYbWxDb21tZW50OiAoKSA9PiBYbWxDb21tZW50LAogICAgWG1sRGVjbGFyYXRpb246ICgpID0+IFhtbERlY2xhcmF0aW9uLAogICAgWG1sRG9jdW1lbnQ6ICgpID0+IFhtbERvY3VtZW50LAogICAgWG1sRG9jdW1lbnRUeXBlOiAoKSA9PiBYbWxEb2N1bWVudFR5cGUsCiAgICBYbWxFbGVtZW50OiAoKSA9PiBYbWxFbGVtZW50LAogICAgWG1sRXJyb3I6ICgpID0+IFhtbEVycm9yLAogICAgWG1sTm9kZTogKCkgPT4gWG1sTm9kZSwKICAgIFhtbFByb2Nlc3NpbmdJbnN0cnVjdGlvbjogKCkgPT4gWG1sUHJvY2Vzc2luZ0luc3RydWN0aW9uLAogICAgWG1sVGV4dDogKCkgPT4gWG1sVGV4dCwKICAgIHBhcnNlWG1sOiAoKSA9PiBwYXJzZVhtbAogIH0pOwogIHZhciBicm93c2VyID0gX190b0NvbW1vbkpTKHNyY19leHBvcnRzKTsKICB2YXIgZW1wdHlTdHJpbmcgPSAiIjsKICB2YXIgc3Vycm9nYXRlUGFpciA9IC9bXHVEODAwLVx1REJGRl1bXHVEQzAwLVx1REZGRl0vZzsKICB2YXIgU3RyaW5nU2Nhbm5lciA9IGNsYXNzIHsKICAgIGNvbnN0cnVjdG9yKHN0cmluZykgewogICAgICB0aGlzLmsgPSB0aGlzLnEoc3RyaW5nLCB0cnVlKTsKICAgICAgdGhpcy5kID0gMDsKICAgICAgdGhpcy5sZW5ndGggPSBzdHJpbmcubGVuZ3RoOwogICAgICB0aGlzLm4gPSB0aGlzLmsgIT09IHRoaXMubGVuZ3RoOwogICAgICB0aGlzLm0gPSBzdHJpbmc7CiAgICAgIGlmICh0aGlzLm4pIHsKICAgICAgICBsZXQgY2hhcnNUb0J5dGVzID0gW107CiAgICAgICAgZm9yIChsZXQgYnl0ZUluZGV4ID0gMCwgY2hhckluZGV4ID0gMDsgY2hhckluZGV4IDwgdGhpcy5rOyArK2NoYXJJbmRleCkgewogICAgICAgICAgY2hhcnNUb0J5dGVzW2NoYXJJbmRleF0gPSBieXRlSW5kZXg7CiAgICAgICAgICBieXRlSW5kZXggKz0gc3RyaW5nLmNvZGVQb2ludEF0KGJ5dGVJbmRleCkgPiA2NTUzNSA/IDIgOiAxOwogICAgICAgIH0KICAgICAgICB0aGlzLnkgPSBjaGFyc1RvQnl0ZXM7CiAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogV2hldGhlciB0aGUgY3VycmVudCBjaGFyYWN0ZXIgaW5kZXggaXMgYXQgdGhlIGVuZCBvZiB0aGUgaW5wdXQgc3RyaW5nLgogICAgICovCiAgICBnZXQgeigpIHsKICAgICAgcmV0dXJuIHRoaXMuZCA+PSB0aGlzLms7CiAgICB9CiAgICAvLyAtLSBQcm90ZWN0ZWQgTWV0aG9kcyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgbnVtYmVyIG9mIGNoYXJhY3RlcnMgaW4gdGhlIGdpdmVuIHN0cmluZywgd2hpY2ggbWF5IGRpZmZlciBmcm9tCiAgICAgKiB0aGUgYnl0ZSBsZW5ndGggaWYgdGhlIHN0cmluZyBjb250YWlucyBtdWx0aWJ5dGUgY2hhcmFjdGVycy4KICAgICAqLwogICAgcShzdHJpbmcsIG11bHRpQnl0ZVNhZmUgPSB0aGlzLm4pIHsKICAgICAgcmV0dXJuIG11bHRpQnl0ZVNhZmUgPyBzdHJpbmcucmVwbGFjZShzdXJyb2dhdGVQYWlyLCAiXyIpLmxlbmd0aCA6IHN0cmluZy5sZW5ndGg7CiAgICB9CiAgICAvLyAtLSBQdWJsaWMgTWV0aG9kcyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgIC8qKgogICAgICogQWR2YW5jZXMgdGhlIHNjYW5uZXIgYnkgdGhlIGdpdmVuIG51bWJlciBvZiBjaGFyYWN0ZXJzLCBzdG9wcGluZyBpZiB0aGUgZW5kCiAgICAgKiBvZiB0aGUgc3RyaW5nIGlzIHJlYWNoZWQuCiAgICAgKi8KICAgIGcoY291bnQgPSAxKSB7CiAgICAgIHRoaXMuZCA9IE1hdGgubWluKHRoaXMuaywgdGhpcy5kICsgY291bnQpOwogICAgfQogICAgLyoqCiAgICAgKiBSZXR1cm5zIHRoZSBieXRlIGluZGV4IG9mIHRoZSBnaXZlbiBjaGFyYWN0ZXIgaW5kZXggaW4gdGhlIHN0cmluZy4gVGhlIHR3bwogICAgICogbWF5IGRpZmZlciBpbiBzdHJpbmdzIHRoYXQgY29udGFpbiBtdWx0aWJ5dGUgY2hhcmFjdGVycy4KICAgICAqLwogICAgaShjaGFySW5kZXggPSB0aGlzLmQpIHsKICAgICAgdmFyIF9hOwogICAgICByZXR1cm4gdGhpcy5uID8gKF9hID0gdGhpcy55W2NoYXJJbmRleF0pICE9IG51bGwgPyBfYSA6IEluZmluaXR5IDogY2hhckluZGV4OwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhbmQgcmV0dXJucyB0aGUgZ2l2ZW4gbnVtYmVyIG9mIGNoYXJhY3RlcnMgaWYgcG9zc2libGUsIGFkdmFuY2luZwogICAgICogdGhlIHNjYW5uZXIgYW5kIHN0b3BwaW5nIGlmIHRoZSBlbmQgb2YgdGhlIHN0cmluZyBpcyByZWFjaGVkLgogICAgICoKICAgICAqIElmIG5vIGNoYXJhY3RlcnMgY291bGQgYmUgY29uc3VtZWQsIGFuIGVtcHR5IHN0cmluZyB3aWxsIGJlIHJldHVybmVkLgogICAgICovCiAgICBGKGNvdW50ID0gMSkgewogICAgICBsZXQgY2hhcnMgPSB0aGlzLmgoY291bnQpOwogICAgICB0aGlzLmcoY291bnQpOwogICAgICByZXR1cm4gY2hhcnM7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgbWF0Y2ggZm9yIHRoZSBnaXZlbiBzdGlja3kgcmVnZXgsIGFkdmFuY2VzIHRoZSBzY2FubmVyLCB1cGRhdGVzCiAgICAgKiB0aGUgYGxhc3RJbmRleGAgcHJvcGVydHkgb2YgdGhlIHJlZ2V4LCBhbmQgcmV0dXJucyB0aGUgbWF0Y2hpbmcgc3RyaW5nLgogICAgICoKICAgICAqIFRoZSByZWdleCBtdXN0IGhhdmUgYSBzdGlja3kgZmxhZyAoInkiKSBzbyB0aGF0IGl0cyBgbGFzdEluZGV4YCBwcm9wIGNhbiBiZQogICAgICogdXNlZCB0byBhbmNob3IgdGhlIG1hdGNoIGF0IHRoZSBjdXJyZW50IHNjYW5uZXIgcG9zaXRpb24uCiAgICAgKgogICAgICogUmV0dXJucyB0aGUgY29uc3VtZWQgc3RyaW5nLCBvciBhbiBlbXB0eSBzdHJpbmcgaWYgbm90aGluZyB3YXMgY29uc3VtZWQuCiAgICAgKi8KICAgIEcocmVnZXgpIHsKICAgICAgaWYgKCFyZWdleC5zdGlja3kpIHsKICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ2ByZWdleGAgbXVzdCBoYXZlIGEgc3RpY2t5IGZsYWcgKCJ5IiknKTsKICAgICAgfQogICAgICByZWdleC5sYXN0SW5kZXggPSB0aGlzLmkoKTsKICAgICAgbGV0IHJlc3VsdCA9IHJlZ2V4LmV4ZWModGhpcy5tKTsKICAgICAgaWYgKHJlc3VsdCA9PT0gbnVsbCB8fCByZXN1bHQubGVuZ3RoID09PSAwKSB7CiAgICAgICAgcmV0dXJuIGVtcHR5U3RyaW5nOwogICAgICB9CiAgICAgIGxldCBtYXRjaCA9IHJlc3VsdFswXTsKICAgICAgdGhpcy5nKHRoaXMucShtYXRjaCkpOwogICAgICByZXR1cm4gbWF0Y2g7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGFuZCByZXR1cm5zIGFsbCBjaGFyYWN0ZXJzIGZvciB3aGljaCB0aGUgZ2l2ZW4gZnVuY3Rpb24gcmV0dXJucyBhCiAgICAgKiB0cnV0aHkgdmFsdWUsIHN0b3BwaW5nIG9uIHRoZSBmaXJzdCBmYWxzeSByZXR1cm4gdmFsdWUgb3IgaWYgdGhlIGVuZCBvZiB0aGUKICAgICAqIGlucHV0IGlzIHJlYWNoZWQuCiAgICAgKi8KICAgIHYoZm4pIHsKICAgICAgbGV0IGNoYXI7CiAgICAgIGxldCBtYXRjaCA9IGVtcHR5U3RyaW5nOwogICAgICB3aGlsZSAoKGNoYXIgPSB0aGlzLmgoKSkgJiYgZm4oY2hhcikpIHsKICAgICAgICBtYXRjaCArPSBjaGFyOwogICAgICAgIHRoaXMuZygpOwogICAgICB9CiAgICAgIHJldHVybiBtYXRjaDsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgdGhlIGdpdmVuIHN0cmluZyBpZiBpdCBleGlzdHMgYXQgdGhlIGN1cnJlbnQgY2hhcmFjdGVyIGluZGV4LCBhbmQKICAgICAqIGFkdmFuY2VzIHRoZSBzY2FubmVyLgogICAgICoKICAgICAqIElmIHRoZSBnaXZlbiBzdHJpbmcgZG9lc24ndCBleGlzdCBhdCB0aGUgY3VycmVudCBjaGFyYWN0ZXIgaW5kZXgsIGFuIGVtcHR5CiAgICAgKiBzdHJpbmcgd2lsbCBiZSByZXR1cm5lZCBhbmQgdGhlIHNjYW5uZXIgd2lsbCBub3QgYmUgYWR2YW5jZWQuCiAgICAgKi8KICAgIFEoc3RyaW5nVG9Db25zdW1lKSB7CiAgICAgIGlmICh0aGlzLmIoc3RyaW5nVG9Db25zdW1lKSkgewogICAgICAgIHJldHVybiBzdHJpbmdUb0NvbnN1bWU7CiAgICAgIH0KICAgICAgaWYgKHRoaXMubikgewogICAgICAgIGxldCB7IGxlbmd0aCB9ID0gc3RyaW5nVG9Db25zdW1lOwogICAgICAgIGxldCBjaGFyTGVuZ3RoVG9NYXRjaCA9IHRoaXMucShzdHJpbmdUb0NvbnN1bWUpOwogICAgICAgIGlmIChjaGFyTGVuZ3RoVG9NYXRjaCAhPT0gbGVuZ3RoICYmIHN0cmluZ1RvQ29uc3VtZSA9PT0gdGhpcy5oKGNoYXJMZW5ndGhUb01hdGNoKSkgewogICAgICAgICAgdGhpcy5nKGNoYXJMZW5ndGhUb01hdGNoKTsKICAgICAgICAgIHJldHVybiBzdHJpbmdUb0NvbnN1bWU7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiBlbXB0eVN0cmluZzsKICAgIH0KICAgIC8qKgogICAgICogRG9lcyB0aGUgc2FtZSB0aGluZyBhcyBgY29uc3VtZVN0cmluZygpYCwgYnV0IGRvZXNuJ3Qgc3VwcG9ydCBjb25zdW1pbmcKICAgICAqIG11bHRpYnl0ZSBjaGFyYWN0ZXJzLiBUaGlzIGNhbiBiZSBmYXN0ZXIgaWYgeW91IG9ubHkgbmVlZCB0byBtYXRjaCBzaW5nbGUKICAgICAqIGJ5dGUgY2hhcmFjdGVycy4KICAgICAqLwogICAgYihzdHJpbmdUb0NvbnN1bWUpIHsKICAgICAgbGV0IHsgbGVuZ3RoIH0gPSBzdHJpbmdUb0NvbnN1bWU7CiAgICAgIGlmICh0aGlzLmgobGVuZ3RoKSA9PT0gc3RyaW5nVG9Db25zdW1lKSB7CiAgICAgICAgdGhpcy5nKGxlbmd0aCk7CiAgICAgICAgcmV0dXJuIHN0cmluZ1RvQ29uc3VtZTsKICAgICAgfQogICAgICByZXR1cm4gZW1wdHlTdHJpbmc7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGNoYXJhY3RlcnMgdW50aWwgdGhlIGdpdmVuIGdsb2JhbCByZWdleCBpcyBtYXRjaGVkLCBhZHZhbmNpbmcgdGhlCiAgICAgKiBzY2FubmVyIHVwIHRvIChidXQgbm90IGJleW9uZCkgdGhlIGJlZ2lubmluZyBvZiB0aGUgbWF0Y2guIElmIHRoZSByZWdleAogICAgICogZG9lc24ndCBtYXRjaCwgbm90aGluZyB3aWxsIGJlIGNvbnN1bWVkLgogICAgICoKICAgICAqIFJldHVybnMgdGhlIGNvbnN1bWVkIHN0cmluZywgb3IgYW4gZW1wdHkgc3RyaW5nIGlmIG5vdGhpbmcgd2FzIGNvbnN1bWVkLgogICAgICovCiAgICBBKHJlZ2V4KSB7CiAgICAgIGxldCByZXN0T2ZTdHJpbmcgPSB0aGlzLm0uc2xpY2UodGhpcy5pKCkpOwogICAgICBsZXQgbWF0Y2hCeXRlSW5kZXggPSByZXN0T2ZTdHJpbmcuc2VhcmNoKHJlZ2V4KTsKICAgICAgaWYgKG1hdGNoQnl0ZUluZGV4IDw9IDApIHsKICAgICAgICByZXR1cm4gZW1wdHlTdHJpbmc7CiAgICAgIH0KICAgICAgbGV0IHJlc3VsdCA9IHJlc3RPZlN0cmluZy5zbGljZSgwLCBtYXRjaEJ5dGVJbmRleCk7CiAgICAgIHRoaXMuZyh0aGlzLnEocmVzdWx0KSk7CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGNoYXJhY3RlcnMgdW50aWwgdGhlIGdpdmVuIHN0cmluZyBpcyBmb3VuZCwgYWR2YW5jaW5nIHRoZSBzY2FubmVyCiAgICAgKiB1cCB0byAoYnV0IG5vdCBiZXlvbmQpIHRoYXQgcG9pbnQuIElmIHRoZSBzdHJpbmcgaXMgbmV2ZXIgZm91bmQsIG5vdGhpbmcKICAgICAqIHdpbGwgYmUgY29uc3VtZWQuCiAgICAgKgogICAgICogUmV0dXJucyB0aGUgY29uc3VtZWQgc3RyaW5nLCBvciBhbiBlbXB0eSBzdHJpbmcgaWYgbm90aGluZyB3YXMgY29uc3VtZWQuCiAgICAgKi8KICAgIHQoc2VhcmNoU3RyaW5nKSB7CiAgICAgIGxldCB7IG06IHN0cmluZyB9ID0gdGhpczsKICAgICAgbGV0IGJ5dGVJbmRleCA9IHRoaXMuaSgpOwogICAgICBsZXQgbWF0Y2hCeXRlSW5kZXggPSBzdHJpbmcuaW5kZXhPZihzZWFyY2hTdHJpbmcsIGJ5dGVJbmRleCk7CiAgICAgIGlmIChtYXRjaEJ5dGVJbmRleCA8PSAwKSB7CiAgICAgICAgcmV0dXJuIGVtcHR5U3RyaW5nOwogICAgICB9CiAgICAgIGxldCByZXN1bHQgPSBzdHJpbmcuc2xpY2UoYnl0ZUluZGV4LCBtYXRjaEJ5dGVJbmRleCk7CiAgICAgIHRoaXMuZyh0aGlzLnEocmVzdWx0KSk7CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGdpdmVuIG51bWJlciBvZiBjaGFyYWN0ZXJzIHN0YXJ0aW5nIGF0IHRoZSBjdXJyZW50IGNoYXJhY3RlcgogICAgICogaW5kZXgsIHdpdGhvdXQgYWR2YW5jaW5nIHRoZSBzY2FubmVyIGFuZCB3aXRob3V0IGV4Y2VlZGluZyB0aGUgZW5kIG9mIHRoZQogICAgICogaW5wdXQgc3RyaW5nLgogICAgICovCiAgICBoKGNvdW50ID0gMSkgewogICAgICBsZXQgeyBkOiBjaGFySW5kZXgsIG46IG11bHRpQnl0ZU1vZGUsIG06IHN0cmluZyB9ID0gdGhpczsKICAgICAgaWYgKG11bHRpQnl0ZU1vZGUpIHsKICAgICAgICBpZiAoY2hhckluZGV4ID49IHRoaXMuaykgewogICAgICAgICAgcmV0dXJuIGVtcHR5U3RyaW5nOwogICAgICAgIH0KICAgICAgICByZXR1cm4gc3RyaW5nLnNsaWNlKAogICAgICAgICAgdGhpcy5pKGNoYXJJbmRleCksCiAgICAgICAgICB0aGlzLmkoY2hhckluZGV4ICsgY291bnQpCiAgICAgICAgKTsKICAgICAgfQogICAgICByZXR1cm4gc3RyaW5nLnNsaWNlKGNoYXJJbmRleCwgY2hhckluZGV4ICsgY291bnQpOwogICAgfQogICAgLyoqCiAgICAgKiBSZXNldHMgdGhlIHNjYW5uZXIgcG9zaXRpb24gdG8gdGhlIGdpdmVuIGNoYXJhY3RlciBfaW5kZXhfLCBvciB0byB0aGUgc3RhcnQKICAgICAqIG9mIHRoZSBpbnB1dCBzdHJpbmcgaWYgbm8gaW5kZXggaXMgZ2l2ZW4uCiAgICAgKgogICAgICogSWYgX2luZGV4XyBpcyBuZWdhdGl2ZSwgdGhlIHNjYW5uZXIgcG9zaXRpb24gd2lsbCBiZSBtb3ZlZCBiYWNrd2FyZCBieSB0aGF0CiAgICAgKiBtYW55IGNoYXJhY3RlcnMsIHN0b3BwaW5nIGlmIHRoZSBiZWdpbm5pbmcgb2YgdGhlIHN0cmluZyBpcyByZWFjaGVkLgogICAgICovCiAgICBvKGluZGV4ID0gMCkgewogICAgICB0aGlzLmQgPSBpbmRleCA+PSAwID8gTWF0aC5taW4odGhpcy5rLCBpbmRleCkgOiBNYXRoLm1heCgwLCB0aGlzLmQgKyBpbmRleCk7CiAgICB9CiAgfTsKICB2YXIgYXR0VmFsdWVDaGFyRG91YmxlUXVvdGUgPSAvW14iJjxdKy95OwogIHZhciBhdHRWYWx1ZUNoYXJTaW5nbGVRdW90ZSA9IC9bXicmPF0rL3k7CiAgdmFyIGF0dFZhbHVlTm9ybWFsaXplZFdoaXRlc3BhY2UgPSAvXHJcbnxbXG5cclx0XS9nOwogIHZhciBlbmRDaGFyRGF0YSA9IC88fCZ8XV0+LzsKICB2YXIgcHJlZGVmaW5lZEVudGl0aWVzID0gT2JqZWN0LmZyZWV6ZShPYmplY3QuYXNzaWduKC8qIEBfX1BVUkVfXyAqLyBPYmplY3QuY3JlYXRlKG51bGwpLCB7CiAgICBhbXA6ICImIiwKICAgIGFwb3M6ICInIiwKICAgIGd0OiAiPiIsCiAgICBsdDogIjwiLAogICAgcXVvdDogJyInCiAgfSkpOwogIGZ1bmN0aW9uIGlzTmFtZUNoYXIoY2hhcikgewogICAgbGV0IGNwID0gZ2V0Q29kZVBvaW50KGNoYXIpOwogICAgcmV0dXJuIGNwID49IDk3ICYmIGNwIDw9IDEyMiB8fCBjcCA+PSA2NSAmJiBjcCA8PSA5MCB8fCBjcCA+PSA0OCAmJiBjcCA8PSA1NyB8fCBjcCA9PT0gNDUgfHwgY3AgPT09IDQ2IHx8IGNwID09PSAxODMgfHwgY3AgPj0gNzY4ICYmIGNwIDw9IDg3OSB8fCBjcCA+PSA4MjU1ICYmIGNwIDw9IDgyNTYgfHwgaXNOYW1lU3RhcnRDaGFyKGNoYXIsIGNwKTsKICB9CiAgZnVuY3Rpb24gaXNOYW1lU3RhcnRDaGFyKGNoYXIsIGNwID0gZ2V0Q29kZVBvaW50KGNoYXIpKSB7CiAgICByZXR1cm4gY3AgPj0gOTcgJiYgY3AgPD0gMTIyIHx8IGNwID49IDY1ICYmIGNwIDw9IDkwIHx8IGNwID09PSA1OCB8fCBjcCA9PT0gOTUgfHwgY3AgPj0gMTkyICYmIGNwIDw9IDIxNCB8fCBjcCA+PSAyMTYgJiYgY3AgPD0gMjQ2IHx8IGNwID49IDI0OCAmJiBjcCA8PSA3NjcgfHwgY3AgPj0gODgwICYmIGNwIDw9IDg5MyB8fCBjcCA+PSA4OTUgJiYgY3AgPD0gODE5MSB8fCBjcCA+PSA4MjA0ICYmIGNwIDw9IDgyMDUgfHwgY3AgPj0gODMwNCAmJiBjcCA8PSA4NTkxIHx8IGNwID49IDExMjY0ICYmIGNwIDw9IDEyMjcxIHx8IGNwID49IDEyMjg5ICYmIGNwIDw9IDU1Mjk1IHx8IGNwID49IDYzNzQ0ICYmIGNwIDw9IDY0OTc1IHx8IGNwID49IDY1MDA4ICYmIGNwIDw9IDY1NTMzIHx8IGNwID49IDY1NTM2ICYmIGNwIDw9IDk4MzAzOTsKICB9CiAgZnVuY3Rpb24gaXNSZWZlcmVuY2VDaGFyKGNoYXIpIHsKICAgIHJldHVybiBjaGFyID09PSAiIyIgfHwgaXNOYW1lQ2hhcihjaGFyKTsKICB9CiAgZnVuY3Rpb24gaXNXaGl0ZXNwYWNlKGNoYXIpIHsKICAgIGxldCBjcCA9IGdldENvZGVQb2ludChjaGFyKTsKICAgIHJldHVybiBjcCA9PT0gMzIgfHwgY3AgPT09IDkgfHwgY3AgPT09IDEwIHx8IGNwID09PSAxMzsKICB9CiAgZnVuY3Rpb24gaXNYbWxDb2RlUG9pbnQoY3ApIHsKICAgIHJldHVybiBjcCA9PT0gOSB8fCBjcCA9PT0gMTAgfHwgY3AgPT09IDEzIHx8IGNwID49IDMyICYmIGNwIDw9IDU1Mjk1IHx8IGNwID49IDU3MzQ0ICYmIGNwIDw9IDY1NTMzIHx8IGNwID49IDY1NTM2ICYmIGNwIDw9IDExMTQxMTE7CiAgfQogIGZ1bmN0aW9uIGdldENvZGVQb2ludChjaGFyKSB7CiAgICByZXR1cm4gY2hhci5jb2RlUG9pbnRBdCgwKSB8fCAtMTsKICB9CiAgdmFyIF9YbWxOb2RlID0gY2xhc3MgewogICAgY29uc3RydWN0b3IoKSB7CiAgICAgIHRoaXMucGFyZW50ID0gbnVsbDsKICAgICAgdGhpcy5zdGFydCA9IC0xOwogICAgICB0aGlzLmVuZCA9IC0xOwogICAgfQogICAgLyoqCiAgICAgKiBEb2N1bWVudCB0aGF0IGNvbnRhaW5zIHRoaXMgbm9kZSwgb3IgYG51bGxgIGlmIHRoaXMgbm9kZSBpcyBub3QgYXNzb2NpYXRlZAogICAgICogd2l0aCBhIGRvY3VtZW50LgogICAgICovCiAgICBnZXQgZG9jdW1lbnQoKSB7CiAgICAgIHZhciBfYSwgX2I7CiAgICAgIHJldHVybiAoX2IgPSAoX2EgPSB0aGlzLnBhcmVudCkgPT0gbnVsbCA/IHZvaWQgMCA6IF9hLmRvY3VtZW50KSAhPSBudWxsID8gX2IgOiBudWxsOwogICAgfQogICAgLyoqCiAgICAgKiBXaGV0aGVyIHRoaXMgbm9kZSBpcyB0aGUgcm9vdCBub2RlIG9mIHRoZSBkb2N1bWVudCAoYWxzbyBrbm93biBhcyB0aGUKICAgICAqIGRvY3VtZW50IGVsZW1lbnQpLgogICAgICovCiAgICBnZXQgaXNSb290Tm9kZSgpIHsKICAgICAgcmV0dXJuIHRoaXMucGFyZW50ICE9PSBudWxsICYmIHRoaXMucGFyZW50ID09PSB0aGlzLmRvY3VtZW50ICYmIHRoaXMudHlwZSA9PT0gX1htbE5vZGUuVFlQRV9FTEVNRU5UOwogICAgfQogICAgLyoqCiAgICAgKiBXaGV0aGVyIHdoaXRlc3BhY2Ugc2hvdWxkIGJlIHByZXNlcnZlZCBpbiB0aGUgY29udGVudCBvZiB0aGlzIGVsZW1lbnQgYW5kCiAgICAgKiBpdHMgY2hpbGRyZW4uCiAgICAgKgogICAgICogVGhpcyBpcyBpbmZsdWVuY2VkIGJ5IHRoZSB2YWx1ZSBvZiB0aGUgc3BlY2lhbCBgeG1sOnNwYWNlYCBhdHRyaWJ1dGUsIGFuZAogICAgICogd2lsbCBiZSBgdHJ1ZWAgZm9yIGFueSBub2RlIHdob3NlIGB4bWw6c3BhY2VgIGF0dHJpYnV0ZSBpcyBzZXQgdG8KICAgICAqICJwcmVzZXJ2ZSIuIElmIGEgbm9kZSBoYXMgbm8gc3VjaCBhdHRyaWJ1dGUsIGl0IHdpbGwgaW5oZXJpdCB0aGUgdmFsdWUgb2YKICAgICAqIHRoZSBuZWFyZXN0IGFuY2VzdG9yIHRoYXQgZG9lcyAoaWYgYW55KS4KICAgICAqCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI3NlYy13aGl0ZS1zcGFjZQogICAgICovCiAgICBnZXQgcHJlc2VydmVXaGl0ZXNwYWNlKCkgewogICAgICB2YXIgX2E7CiAgICAgIHJldHVybiAhISgoX2EgPSB0aGlzLnBhcmVudCkgPT0gbnVsbCA/IHZvaWQgMCA6IF9hLnByZXNlcnZlV2hpdGVzcGFjZSk7CiAgICB9CiAgICAvKioKICAgICAqIFR5cGUgb2YgdGhpcyBub2RlLgogICAgICoKICAgICAqIFRoZSB2YWx1ZSBvZiB0aGlzIHByb3BlcnR5IGlzIGEgc3RyaW5nIHRoYXQgbWF0Y2hlcyBvbmUgb2YgdGhlIHN0YXRpYwogICAgICogYFRZUEVfKmAgcHJvcGVydGllcyBvbiB0aGUgYFhtbE5vZGVgIGNsYXNzIChlLmcuIGBUWVBFX0VMRU1FTlRgLAogICAgICogYFRZUEVfVEVYVGAsIGV0Yy4pLgogICAgICoKICAgICAqIFRoZSBgWG1sTm9kZWAgY2xhc3MgaXRzZWxmIGlzIGEgYmFzZSBjbGFzcyBhbmQgZG9lc24ndCBoYXZlIGl0cyBvd24gdHlwZQogICAgICogbmFtZS4KICAgICAqLwogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiAiIjsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyBhIEpTT04tc2VyaWFsaXphYmxlIG9iamVjdCByZXByZXNlbnRpbmcgdGhpcyBub2RlLCBtaW51cyBwcm9wZXJ0aWVzCiAgICAgKiB0aGF0IGNvdWxkIHJlc3VsdCBpbiBjaXJjdWxhciByZWZlcmVuY2VzLgogICAgICovCiAgICB0b0pTT04oKSB7CiAgICAgIGxldCBqc29uID0gewogICAgICAgIHR5cGU6IHRoaXMudHlwZQogICAgICB9OwogICAgICBpZiAodGhpcy5pc1Jvb3ROb2RlKSB7CiAgICAgICAganNvbi5pc1Jvb3ROb2RlID0gdHJ1ZTsKICAgICAgfQogICAgICBpZiAodGhpcy5wcmVzZXJ2ZVdoaXRlc3BhY2UpIHsKICAgICAgICBqc29uLnByZXNlcnZlV2hpdGVzcGFjZSA9IHRydWU7CiAgICAgIH0KICAgICAgaWYgKHRoaXMuc3RhcnQgIT09IC0xKSB7CiAgICAgICAganNvbi5zdGFydCA9IHRoaXMuc3RhcnQ7CiAgICAgICAganNvbi5lbmQgPSB0aGlzLmVuZDsKICAgICAgfQogICAgICByZXR1cm4ganNvbjsKICAgIH0KICB9OwogIHZhciBYbWxOb2RlID0gX1htbE5vZGU7CiAgWG1sTm9kZS5UWVBFX0NEQVRBID0gImNkYXRhIjsKICBYbWxOb2RlLlRZUEVfQ09NTUVOVCA9ICJjb21tZW50IjsKICBYbWxOb2RlLlRZUEVfRE9DVU1FTlQgPSAiZG9jdW1lbnQiOwogIFhtbE5vZGUuVFlQRV9ET0NVTUVOVF9UWVBFID0gImRvY3R5cGUiOwogIFhtbE5vZGUuVFlQRV9FTEVNRU5UID0gImVsZW1lbnQiOwogIFhtbE5vZGUuVFlQRV9QUk9DRVNTSU5HX0lOU1RSVUNUSU9OID0gInBpIjsKICBYbWxOb2RlLlRZUEVfVEVYVCA9ICJ0ZXh0IjsKICBYbWxOb2RlLlRZUEVfWE1MX0RFQ0xBUkFUSU9OID0gInhtbGRlY2wiOwogIHZhciBYbWxUZXh0ID0gY2xhc3MgZXh0ZW5kcyBYbWxOb2RlIHsKICAgIGNvbnN0cnVjdG9yKHRleHQgPSAiIikgewogICAgICBzdXBlcigpOwogICAgICB0aGlzLnRleHQgPSB0ZXh0OwogICAgfQogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiBYbWxOb2RlLlRZUEVfVEVYVDsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24oWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyksIHsKICAgICAgICB0ZXh0OiB0aGlzLnRleHQKICAgICAgfSk7CiAgICB9CiAgfTsKICB2YXIgWG1sQ2RhdGEgPSBjbGFzcyBleHRlbmRzIFhtbFRleHQgewogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiBYbWxOb2RlLlRZUEVfQ0RBVEE7CiAgICB9CiAgfTsKICB2YXIgWG1sQ29tbWVudCA9IGNsYXNzIGV4dGVuZHMgWG1sTm9kZSB7CiAgICBjb25zdHJ1Y3Rvcihjb250ZW50ID0gIiIpIHsKICAgICAgc3VwZXIoKTsKICAgICAgdGhpcy5jb250ZW50ID0gY29udGVudDsKICAgIH0KICAgIGdldCB0eXBlKCkgewogICAgICByZXR1cm4gWG1sTm9kZS5UWVBFX0NPTU1FTlQ7CiAgICB9CiAgICB0b0pTT04oKSB7CiAgICAgIHJldHVybiBPYmplY3QuYXNzaWduKFhtbE5vZGUucHJvdG90eXBlLnRvSlNPTi5jYWxsKHRoaXMpLCB7CiAgICAgICAgY29udGVudDogdGhpcy5jb250ZW50CiAgICAgIH0pOwogICAgfQogIH07CiAgdmFyIFhtbERlY2xhcmF0aW9uID0gY2xhc3MgZXh0ZW5kcyBYbWxOb2RlIHsKICAgIGNvbnN0cnVjdG9yKHZlcnNpb24sIGVuY29kaW5nLCBzdGFuZGFsb25lKSB7CiAgICAgIHN1cGVyKCk7CiAgICAgIHRoaXMudmVyc2lvbiA9IHZlcnNpb247CiAgICAgIHRoaXMuZW5jb2RpbmcgPSBlbmNvZGluZyAhPSBudWxsID8gZW5jb2RpbmcgOiBudWxsOwogICAgICB0aGlzLnN0YW5kYWxvbmUgPSBzdGFuZGFsb25lICE9IG51bGwgPyBzdGFuZGFsb25lIDogbnVsbDsKICAgIH0KICAgIGdldCB0eXBlKCkgewogICAgICByZXR1cm4gWG1sTm9kZS5UWVBFX1hNTF9ERUNMQVJBVElPTjsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgbGV0IGpzb24gPSBYbWxOb2RlLnByb3RvdHlwZS50b0pTT04uY2FsbCh0aGlzKTsKICAgICAganNvbi52ZXJzaW9uID0gdGhpcy52ZXJzaW9uOwogICAgICBmb3IgKGxldCBrZXkgb2YgWyJlbmNvZGluZyIsICJzdGFuZGFsb25lIl0pIHsKICAgICAgICBpZiAodGhpc1trZXldICE9PSBudWxsKSB7CiAgICAgICAgICBqc29uW2tleV0gPSB0aGlzW2tleV07CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiBqc29uOwogICAgfQogIH07CiAgdmFyIFhtbEVsZW1lbnQgPSBjbGFzcyBleHRlbmRzIFhtbE5vZGUgewogICAgY29uc3RydWN0b3IobmFtZSwgYXR0cmlidXRlcyA9IC8qIEBfX1BVUkVfXyAqLyBPYmplY3QuY3JlYXRlKG51bGwpLCBjaGlsZHJlbiA9IFtdKSB7CiAgICAgIHN1cGVyKCk7CiAgICAgIHRoaXMubmFtZSA9IG5hbWU7CiAgICAgIHRoaXMuYXR0cmlidXRlcyA9IGF0dHJpYnV0ZXM7CiAgICAgIHRoaXMuY2hpbGRyZW4gPSBjaGlsZHJlbjsKICAgIH0KICAgIC8qKgogICAgICogV2hldGhlciB0aGlzIGVsZW1lbnQgaXMgZW1wdHkgKG1lYW5pbmcgaXQgaGFzIG5vIGNoaWxkcmVuKS4KICAgICAqLwogICAgZ2V0IGlzRW1wdHkoKSB7CiAgICAgIHJldHVybiB0aGlzLmNoaWxkcmVuLmxlbmd0aCA9PT0gMDsKICAgIH0KICAgIGdldCBwcmVzZXJ2ZVdoaXRlc3BhY2UoKSB7CiAgICAgIGxldCBub2RlID0gdGhpczsKICAgICAgd2hpbGUgKG5vZGUgaW5zdGFuY2VvZiBYbWxFbGVtZW50KSB7CiAgICAgICAgaWYgKCJ4bWw6c3BhY2UiIGluIG5vZGUuYXR0cmlidXRlcykgewogICAgICAgICAgcmV0dXJuIG5vZGUuYXR0cmlidXRlc1sieG1sOnNwYWNlIl0gPT09ICJwcmVzZXJ2ZSI7CiAgICAgICAgfQogICAgICAgIG5vZGUgPSBub2RlLnBhcmVudDsKICAgICAgfQogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgICAvKioKICAgICAqIFRleHQgY29udGVudCBvZiB0aGlzIGVsZW1lbnQgYW5kIGFsbCBpdHMgZGVzY2VuZGFudHMuCiAgICAgKi8KICAgIGdldCB0ZXh0KCkgewogICAgICByZXR1cm4gdGhpcy5jaGlsZHJlbi5tYXAoKGNoaWxkKSA9PiAidGV4dCIgaW4gY2hpbGQgPyBjaGlsZC50ZXh0IDogIiIpLmpvaW4oIiIpOwogICAgfQogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiBYbWxOb2RlLlRZUEVfRUxFTUVOVDsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24oWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyksIHsKICAgICAgICBuYW1lOiB0aGlzLm5hbWUsCiAgICAgICAgYXR0cmlidXRlczogdGhpcy5hdHRyaWJ1dGVzLAogICAgICAgIGNoaWxkcmVuOiB0aGlzLmNoaWxkcmVuLm1hcCgoY2hpbGQpID0+IGNoaWxkLnRvSlNPTigpKQogICAgICB9KTsKICAgIH0KICB9OwogIHZhciBYbWxEb2N1bWVudCA9IGNsYXNzIGV4dGVuZHMgWG1sTm9kZSB7CiAgICBjb25zdHJ1Y3RvcihjaGlsZHJlbiA9IFtdKSB7CiAgICAgIHN1cGVyKCk7CiAgICAgIHRoaXMuY2hpbGRyZW4gPSBjaGlsZHJlbjsKICAgIH0KICAgIGdldCBkb2N1bWVudCgpIHsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CiAgICAvKioKICAgICAqIFJvb3QgZWxlbWVudCBvZiB0aGlzIGRvY3VtZW50LCBvciBgbnVsbGAgaWYgdGhpcyBkb2N1bWVudCBpcyBlbXB0eS4KICAgICAqLwogICAgZ2V0IHJvb3QoKSB7CiAgICAgIGZvciAobGV0IGNoaWxkIG9mIHRoaXMuY2hpbGRyZW4pIHsKICAgICAgICBpZiAoY2hpbGQgaW5zdGFuY2VvZiBYbWxFbGVtZW50KSB7CiAgICAgICAgICByZXR1cm4gY2hpbGQ7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiBudWxsOwogICAgfQogICAgLyoqCiAgICAgKiBUZXh0IGNvbnRlbnQgb2YgdGhpcyBkb2N1bWVudCBhbmQgYWxsIGl0cyBkZXNjZW5kYW50cy4KICAgICAqLwogICAgZ2V0IHRleHQoKSB7CiAgICAgIHJldHVybiB0aGlzLmNoaWxkcmVuLm1hcCgoY2hpbGQpID0+ICJ0ZXh0IiBpbiBjaGlsZCA/IGNoaWxkLnRleHQgOiAiIikuam9pbigiIik7CiAgICB9CiAgICBnZXQgdHlwZSgpIHsKICAgICAgcmV0dXJuIFhtbE5vZGUuVFlQRV9ET0NVTUVOVDsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24oWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyksIHsKICAgICAgICBjaGlsZHJlbjogdGhpcy5jaGlsZHJlbi5tYXAoKGNoaWxkKSA9PiBjaGlsZC50b0pTT04oKSkKICAgICAgfSk7CiAgICB9CiAgfTsKICB2YXIgWG1sRG9jdW1lbnRUeXBlID0gY2xhc3MgZXh0ZW5kcyBYbWxOb2RlIHsKICAgIGNvbnN0cnVjdG9yKG5hbWUsIHB1YmxpY0lkLCBzeXN0ZW1JZCwgaW50ZXJuYWxTdWJzZXQpIHsKICAgICAgc3VwZXIoKTsKICAgICAgdGhpcy5uYW1lID0gbmFtZTsKICAgICAgdGhpcy5wdWJsaWNJZCA9IHB1YmxpY0lkICE9IG51bGwgPyBwdWJsaWNJZCA6IG51bGw7CiAgICAgIHRoaXMuc3lzdGVtSWQgPSBzeXN0ZW1JZCAhPSBudWxsID8gc3lzdGVtSWQgOiBudWxsOwogICAgICB0aGlzLmludGVybmFsU3Vic2V0ID0gaW50ZXJuYWxTdWJzZXQgIT0gbnVsbCA/IGludGVybmFsU3Vic2V0IDogbnVsbDsKICAgIH0KICAgIGdldCB0eXBlKCkgewogICAgICByZXR1cm4gWG1sTm9kZS5UWVBFX0RPQ1VNRU5UX1RZUEU7CiAgICB9CiAgICB0b0pTT04oKSB7CiAgICAgIGxldCBqc29uID0gWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyk7CiAgICAgIGpzb24ubmFtZSA9IHRoaXMubmFtZTsKICAgICAgZm9yIChsZXQga2V5IG9mIFsicHVibGljSWQiLCAic3lzdGVtSWQiLCAiaW50ZXJuYWxTdWJzZXQiXSkgewogICAgICAgIGlmICh0aGlzW2tleV0gIT09IG51bGwpIHsKICAgICAgICAgIGpzb25ba2V5XSA9IHRoaXNba2V5XTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGpzb247CiAgICB9CiAgfTsKICB2YXIgWG1sRXJyb3IgPSBjbGFzcyBleHRlbmRzIEVycm9yIHsKICAgIGNvbnN0cnVjdG9yKG1lc3NhZ2UsIGNoYXJJbmRleCwgeG1sKSB7CiAgICAgIGxldCBjb2x1bW4gPSAxOwogICAgICBsZXQgZXhjZXJwdCA9ICIiOwogICAgICBsZXQgbGluZSA9IDE7CiAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgY2hhckluZGV4OyArK2kpIHsKICAgICAgICBsZXQgY2hhciA9IHhtbFtpXTsKICAgICAgICBpZiAoY2hhciA9PT0gIlxuIikgewogICAgICAgICAgY29sdW1uID0gMTsKICAgICAgICAgIGV4Y2VycHQgPSAiIjsKICAgICAgICAgIGxpbmUgKz0gMTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgY29sdW1uICs9IDE7CiAgICAgICAgICBleGNlcnB0ICs9IGNoYXI7CiAgICAgICAgfQogICAgICB9CiAgICAgIGxldCBlb2wgPSB4bWwuaW5kZXhPZigiXG4iLCBjaGFySW5kZXgpOwogICAgICBleGNlcnB0ICs9IGVvbCA9PT0gLTEgPyB4bWwuc2xpY2UoY2hhckluZGV4KSA6IHhtbC5zbGljZShjaGFySW5kZXgsIGVvbCk7CiAgICAgIGxldCBleGNlcnB0U3RhcnQgPSAwOwogICAgICBpZiAoZXhjZXJwdC5sZW5ndGggPiA1MCkgewogICAgICAgIGlmIChjb2x1bW4gPCA0MCkgewogICAgICAgICAgZXhjZXJwdCA9IGV4Y2VycHQuc2xpY2UoMCwgNTApOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBleGNlcnB0U3RhcnQgPSBjb2x1bW4gLSAyMDsKICAgICAgICAgIGV4Y2VycHQgPSBleGNlcnB0LnNsaWNlKGV4Y2VycHRTdGFydCwgY29sdW1uICsgMzApOwogICAgICAgIH0KICAgICAgfQogICAgICBzdXBlcigKICAgICAgICBgJHttZXNzYWdlfSAobGluZSAke2xpbmV9LCBjb2x1bW4gJHtjb2x1bW59KQogICR7ZXhjZXJwdH0KYCArICIgIi5yZXBlYXQoY29sdW1uIC0gZXhjZXJwdFN0YXJ0ICsgMSkgKyAiXlxuIgogICAgICApOwogICAgICB0aGlzLmNvbHVtbiA9IGNvbHVtbjsKICAgICAgdGhpcy5leGNlcnB0ID0gZXhjZXJwdDsKICAgICAgdGhpcy5saW5lID0gbGluZTsKICAgICAgdGhpcy5uYW1lID0gIlhtbEVycm9yIjsKICAgICAgdGhpcy5wb3MgPSBjaGFySW5kZXg7CiAgICB9CiAgfTsKICB2YXIgWG1sUHJvY2Vzc2luZ0luc3RydWN0aW9uID0gY2xhc3MgZXh0ZW5kcyBYbWxOb2RlIHsKICAgIGNvbnN0cnVjdG9yKG5hbWUsIGNvbnRlbnQgPSAiIikgewogICAgICBzdXBlcigpOwogICAgICB0aGlzLm5hbWUgPSBuYW1lOwogICAgICB0aGlzLmNvbnRlbnQgPSBjb250ZW50OwogICAgfQogICAgZ2V0IHR5cGUoKSB7CiAgICAgIHJldHVybiBYbWxOb2RlLlRZUEVfUFJPQ0VTU0lOR19JTlNUUlVDVElPTjsKICAgIH0KICAgIHRvSlNPTigpIHsKICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24oWG1sTm9kZS5wcm90b3R5cGUudG9KU09OLmNhbGwodGhpcyksIHsKICAgICAgICBuYW1lOiB0aGlzLm5hbWUsCiAgICAgICAgY29udGVudDogdGhpcy5jb250ZW50CiAgICAgIH0pOwogICAgfQogIH07CiAgdmFyIGVtcHR5U3RyaW5nMiA9ICIiOwogIHZhciBQYXJzZXIgPSBjbGFzcyB7CiAgICAvKioKICAgICAqIEBwYXJhbSB4bWwgWE1MIHN0cmluZyB0byBwYXJzZS4KICAgICAqIEBwYXJhbSBvcHRpb25zIFBhcnNlciBvcHRpb25zLgogICAgICovCiAgICBjb25zdHJ1Y3Rvcih4bWwsIG9wdGlvbnMgPSB7fSkgewogICAgICBsZXQgZG9jID0gdGhpcy5kb2N1bWVudCA9IG5ldyBYbWxEb2N1bWVudCgpOwogICAgICBsZXQgc2Nhbm5lciA9IHRoaXMuYyA9IG5ldyBTdHJpbmdTY2FubmVyKHhtbCk7CiAgICAgIHRoaXMubCA9IGRvYzsKICAgICAgdGhpcy5mID0gb3B0aW9uczsKICAgICAgaWYgKHRoaXMuZi5pbmNsdWRlT2Zmc2V0cykgewogICAgICAgIGRvYy5zdGFydCA9IDA7CiAgICAgICAgZG9jLmVuZCA9IHhtbC5sZW5ndGg7CiAgICAgIH0KICAgICAgc2Nhbm5lci5iKCJcdUZFRkYiKTsKICAgICAgdGhpcy5IKCk7CiAgICAgIGlmICghdGhpcy5CKCkpIHsKICAgICAgICB0aHJvdyB0aGlzLmEoIlJvb3QgZWxlbWVudCBpcyBtaXNzaW5nIG9yIGludmFsaWQiKTsKICAgICAgfQogICAgICB3aGlsZSAodGhpcy53KCkpIHsKICAgICAgfQogICAgICBpZiAoIXNjYW5uZXIueikgewogICAgICAgIHRocm93IHRoaXMuYSgiRXh0cmEgY29udGVudCBhdCB0aGUgZW5kIG9mIHRoZSBkb2N1bWVudCIpOwogICAgICB9CiAgICB9CiAgICAvKioKICAgICAqIEFkZHMgdGhlIGdpdmVuIGBYbWxOb2RlYCBhcyBhIGNoaWxkIG9mIGB0aGlzLmN1cnJlbnROb2RlYC4KICAgICAqLwogICAgaihub2RlLCBjaGFySW5kZXgpIHsKICAgICAgbm9kZS5wYXJlbnQgPSB0aGlzLmw7CiAgICAgIGlmICh0aGlzLmYuaW5jbHVkZU9mZnNldHMpIHsKICAgICAgICBub2RlLnN0YXJ0ID0gdGhpcy5jLmkoY2hhckluZGV4KTsKICAgICAgICBub2RlLmVuZCA9IHRoaXMuYy5pKCk7CiAgICAgIH0KICAgICAgdGhpcy5sLmNoaWxkcmVuLnB1c2gobm9kZSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgLyoqCiAgICAgKiBBZGRzIHRoZSBnaXZlbiBfdGV4dF8gdG8gdGhlIGRvY3VtZW50LCBlaXRoZXIgYnkgYXBwZW5kaW5nIGl0IHRvIGEKICAgICAqIHByZWNlZGluZyBgWG1sVGV4dGAgbm9kZSAoaWYgcG9zc2libGUpIG9yIGJ5IGNyZWF0aW5nIGEgbmV3IGBYbWxUZXh0YCBub2RlLgogICAgICovCiAgICB4KHRleHQsIGNoYXJJbmRleCkgewogICAgICBsZXQgeyBjaGlsZHJlbiB9ID0gdGhpcy5sOwogICAgICBsZXQgeyBsZW5ndGggfSA9IGNoaWxkcmVuOwogICAgICB0ZXh0ID0gbm9ybWFsaXplTGluZUJyZWFrcyh0ZXh0KTsKICAgICAgaWYgKGxlbmd0aCA+IDApIHsKICAgICAgICBsZXQgcHJldk5vZGUgPSBjaGlsZHJlbltsZW5ndGggLSAxXTsKICAgICAgICBpZiAoKHByZXZOb2RlID09IG51bGwgPyB2b2lkIDAgOiBwcmV2Tm9kZS50eXBlKSA9PT0gWG1sTm9kZS5UWVBFX1RFWFQpIHsKICAgICAgICAgIGxldCB0ZXh0Tm9kZSA9IHByZXZOb2RlOwogICAgICAgICAgdGV4dE5vZGUudGV4dCArPSB0ZXh0OwogICAgICAgICAgaWYgKHRoaXMuZi5pbmNsdWRlT2Zmc2V0cykgewogICAgICAgICAgICB0ZXh0Tm9kZS5lbmQgPSB0aGlzLmMuaSgpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmoobmV3IFhtbFRleHQodGV4dCksIGNoYXJJbmRleCk7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGVsZW1lbnQgYXR0cmlidXRlcy4KICAgICAqCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI3NlYy1zdGFydHRhZ3MKICAgICAqLwogICAgSSgpIHsKICAgICAgbGV0IGF0dHJpYnV0ZXMgPSAvKiBAX19QVVJFX18gKi8gT2JqZWN0LmNyZWF0ZShudWxsKTsKICAgICAgd2hpbGUgKHRoaXMuZSgpKSB7CiAgICAgICAgbGV0IGF0dHJOYW1lID0gdGhpcy5yKCk7CiAgICAgICAgaWYgKCFhdHRyTmFtZSkgewogICAgICAgICAgYnJlYWs7CiAgICAgICAgfQogICAgICAgIGxldCBhdHRyVmFsdWUgPSB0aGlzLnUoKSAmJiB0aGlzLkooKTsKICAgICAgICBpZiAoYXR0clZhbHVlID09PSBmYWxzZSkgewogICAgICAgICAgdGhyb3cgdGhpcy5hKCJBdHRyaWJ1dGUgdmFsdWUgZXhwZWN0ZWQiKTsKICAgICAgICB9CiAgICAgICAgaWYgKGF0dHJOYW1lIGluIGF0dHJpYnV0ZXMpIHsKICAgICAgICAgIHRocm93IHRoaXMuYShgRHVwbGljYXRlIGF0dHJpYnV0ZTogJHthdHRyTmFtZX1gKTsKICAgICAgICB9CiAgICAgICAgaWYgKGF0dHJOYW1lID09PSAieG1sOnNwYWNlIiAmJiBhdHRyVmFsdWUgIT09ICJkZWZhdWx0IiAmJiBhdHRyVmFsdWUgIT09ICJwcmVzZXJ2ZSIpIHsKICAgICAgICAgIHRocm93IHRoaXMuYSgnVmFsdWUgb2YgdGhlIGB4bWw6c3BhY2VgIGF0dHJpYnV0ZSBtdXN0IGJlICJkZWZhdWx0IiBvciAicHJlc2VydmUiJyk7CiAgICAgICAgfQogICAgICAgIGF0dHJpYnV0ZXNbYXR0ck5hbWVdID0gYXR0clZhbHVlOwogICAgICB9CiAgICAgIGlmICh0aGlzLmYuc29ydEF0dHJpYnV0ZXMpIHsKICAgICAgICBsZXQgYXR0ck5hbWVzID0gT2JqZWN0LmtleXMoYXR0cmlidXRlcykuc29ydCgpOwogICAgICAgIGxldCBzb3J0ZWRBdHRyaWJ1dGVzID0gLyogQF9fUFVSRV9fICovIE9iamVjdC5jcmVhdGUobnVsbCk7CiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBhdHRyTmFtZXMubGVuZ3RoOyArK2kpIHsKICAgICAgICAgIGxldCBhdHRyTmFtZSA9IGF0dHJOYW1lc1tpXTsKICAgICAgICAgIHNvcnRlZEF0dHJpYnV0ZXNbYXR0ck5hbWVdID0gYXR0cmlidXRlc1thdHRyTmFtZV07CiAgICAgICAgfQogICAgICAgIGF0dHJpYnV0ZXMgPSBzb3J0ZWRBdHRyaWJ1dGVzOwogICAgICB9CiAgICAgIHJldHVybiBhdHRyaWJ1dGVzOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhbiBgQXR0VmFsdWVgIChhdHRyaWJ1dGUgdmFsdWUpIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEByZXR1cm5zCiAgICAgKiAgIENvbnRlbnRzIG9mIHRoZSBgQXR0VmFsdWVgIG1pbnVzIHF1b3Rlcywgb3IgYGZhbHNlYCBpZiBub3RoaW5nIHdhcwogICAgICogICBjb25zdW1lZC4gQW4gZW1wdHkgc3RyaW5nIGluZGljYXRlcyB0aGF0IGFuIGBBdHRWYWx1ZWAgd2FzIGNvbnN1bWVkIGJ1dAogICAgICogICB3YXMgZW1wdHkuCiAgICAgKgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1BdHRWYWx1ZQogICAgICovCiAgICBKKCkgewogICAgICBsZXQgeyBjOiBzY2FubmVyIH0gPSB0aGlzOwogICAgICBsZXQgcXVvdGUgPSBzY2FubmVyLmgoKTsKICAgICAgaWYgKHF1b3RlICE9PSAnIicgJiYgcXVvdGUgIT09ICInIikgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICBzY2FubmVyLmcoKTsKICAgICAgbGV0IGNoYXJzOwogICAgICBsZXQgaXNDbG9zZWQgPSBmYWxzZTsKICAgICAgbGV0IHZhbHVlID0gZW1wdHlTdHJpbmcyOwogICAgICBsZXQgcmVnZXggPSBxdW90ZSA9PT0gJyInID8gYXR0VmFsdWVDaGFyRG91YmxlUXVvdGUgOiBhdHRWYWx1ZUNoYXJTaW5nbGVRdW90ZTsKICAgICAgbWF0Y2hMb29wOgogICAgICAgIHdoaWxlICghc2Nhbm5lci56KSB7CiAgICAgICAgICBjaGFycyA9IHNjYW5uZXIuRyhyZWdleCk7CiAgICAgICAgICBpZiAoY2hhcnMpIHsKICAgICAgICAgICAgdGhpcy5wKGNoYXJzKTsKICAgICAgICAgICAgdmFsdWUgKz0gY2hhcnMucmVwbGFjZShhdHRWYWx1ZU5vcm1hbGl6ZWRXaGl0ZXNwYWNlLCAiICIpOwogICAgICAgICAgfQogICAgICAgICAgc3dpdGNoIChzY2FubmVyLmgoKSkgewogICAgICAgICAgICBjYXNlIHF1b3RlOgogICAgICAgICAgICAgIGlzQ2xvc2VkID0gdHJ1ZTsKICAgICAgICAgICAgICBicmVhayBtYXRjaExvb3A7CiAgICAgICAgICAgIGNhc2UgIiYiOgogICAgICAgICAgICAgIHZhbHVlICs9IHRoaXMuQygpOwogICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICBjYXNlICI8IjoKICAgICAgICAgICAgICB0aHJvdyB0aGlzLmEoIlVuZXNjYXBlZCBgPGAgaXMgbm90IGFsbG93ZWQgaW4gYW4gYXR0cmlidXRlIHZhbHVlIik7CiAgICAgICAgICAgIGNhc2UgZW1wdHlTdHJpbmcyOgogICAgICAgICAgICAgIGJyZWFrIG1hdGNoTG9vcDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIGlmICghaXNDbG9zZWQpIHsKICAgICAgICB0aHJvdyB0aGlzLmEoIlVuY2xvc2VkIGF0dHJpYnV0ZSIpOwogICAgICB9CiAgICAgIHNjYW5uZXIuZygpOwogICAgICByZXR1cm4gdmFsdWU7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgQ0RBVEEgc2VjdGlvbiBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGEgQ0RBVEEgc2VjdGlvbiB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI3NlYy1jZGF0YS1zZWN0CiAgICAgKi8KICAgIEsoKSB7CiAgICAgIGxldCB7IGM6IHNjYW5uZXIgfSA9IHRoaXM7CiAgICAgIGxldCBzdGFydEluZGV4ID0gc2Nhbm5lci5kOwogICAgICBpZiAoIXNjYW5uZXIuYigiPCFbQ0RBVEFbIikpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IHRleHQgPSBzY2FubmVyLnQoIl1dPiIpOwogICAgICB0aGlzLnAodGV4dCk7CiAgICAgIGlmICghc2Nhbm5lci5iKCJdXT4iKSkgewogICAgICAgIHRocm93IHRoaXMuYSgiVW5jbG9zZWQgQ0RBVEEgc2VjdGlvbiIpOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmYucHJlc2VydmVDZGF0YSA/IHRoaXMuaihuZXcgWG1sQ2RhdGEobm9ybWFsaXplTGluZUJyZWFrcyh0ZXh0KSksIHN0YXJ0SW5kZXgpIDogdGhpcy54KHRleHQsIHN0YXJ0SW5kZXgpOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBjaGFyYWN0ZXIgZGF0YSBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGNoYXJhY3RlciBkYXRhIHdhcyBjb25zdW1lZC4KICAgICAqIEBzZWUgaHR0cHM6Ly93d3cudzMub3JnL1RSLzIwMDgvUkVDLXhtbC0yMDA4MTEyNi8jZHQtY2hhcmRhdGEKICAgICAqLwogICAgTCgpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgbGV0IHN0YXJ0SW5kZXggPSBzY2FubmVyLmQ7CiAgICAgIGxldCBjaGFyRGF0YSA9IHNjYW5uZXIuQShlbmRDaGFyRGF0YSk7CiAgICAgIGlmICghY2hhckRhdGEpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgdGhpcy5wKGNoYXJEYXRhKTsKICAgICAgaWYgKHNjYW5uZXIuaCgzKSA9PT0gIl1dPiIpIHsKICAgICAgICB0aHJvdyB0aGlzLmEoIkVsZW1lbnQgY29udGVudCBtYXkgbm90IGNvbnRhaW4gdGhlIENEQVRBIHNlY3Rpb24gY2xvc2UgZGVsaW1pdGVyIGBdXT5gIik7CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXMueChjaGFyRGF0YSwgc3RhcnRJbmRleCk7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgY29tbWVudCBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGEgY29tbWVudCB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI05ULUNvbW1lbnQKICAgICAqLwogICAgRCgpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgbGV0IHN0YXJ0SW5kZXggPSBzY2FubmVyLmQ7CiAgICAgIGlmICghc2Nhbm5lci5iKCI8IS0tIikpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IGNvbnRlbnQgPSBzY2FubmVyLnQoIi0tIik7CiAgICAgIHRoaXMucChjb250ZW50KTsKICAgICAgaWYgKCFzY2FubmVyLmIoIi0tPiIpKSB7CiAgICAgICAgaWYgKHNjYW5uZXIuaCgyKSA9PT0gIi0tIikgewogICAgICAgICAgdGhyb3cgdGhpcy5hKCJUaGUgc3RyaW5nIGAtLWAgaXNuJ3QgYWxsb3dlZCBpbnNpZGUgYSBjb21tZW50Iik7CiAgICAgICAgfQogICAgICAgIHRocm93IHRoaXMuYSgiVW5jbG9zZWQgY29tbWVudCIpOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmYucHJlc2VydmVDb21tZW50cyA/IHRoaXMuaihuZXcgWG1sQ29tbWVudChub3JtYWxpemVMaW5lQnJlYWtzKGNvbnRlbnQpKSwgc3RhcnRJbmRleCkgOiB0cnVlOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhIHJlZmVyZW5jZSBpbiBhIGNvbnRlbnQgY29udGV4dCBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBUaGlzIGRpZmZlcnMgZnJvbSBgY29uc3VtZVJlZmVyZW5jZSgpYCBpbiB0aGF0IGEgY29uc3VtZWQgcmVmZXJlbmNlIHdpbGwgYmUKICAgICAqIGFkZGVkIHRvIHRoZSBkb2N1bWVudCBhcyBhIHRleHQgbm9kZSBpbnN0ZWFkIG9mIHJldHVybmVkLgogICAgICoKICAgICAqIEByZXR1cm5zIFdoZXRoZXIgYSByZWZlcmVuY2Ugd2FzIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNlbnRwcm9jCiAgICAgKi8KICAgIE0oKSB7CiAgICAgIGxldCBzdGFydEluZGV4ID0gdGhpcy5jLmQ7CiAgICAgIGxldCByZWYgPSB0aGlzLkMoKTsKICAgICAgcmV0dXJuIHJlZiA/IHRoaXMueChyZWYsIHN0YXJ0SW5kZXgpIDogZmFsc2U7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgZG9jdHlwZSBkZWNsYXJhdGlvbiBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBUaGlzIGlzIGEgbG9vc2UgaW1wbGVtZW50YXRpb24gc2luY2UgZG9jdHlwZSBkZWNsYXJhdGlvbnMgYXJlIGN1cnJlbnRseQogICAgICogZGlzY2FyZGVkIHdpdGhvdXQgZnVydGhlciBwYXJzaW5nLgogICAgICoKICAgICAqIEByZXR1cm5zIFdoZXRoZXIgYSBkb2N0eXBlIGRlY2xhcmF0aW9uIHdhcyBjb25zdW1lZC4KICAgICAqIEBzZWUgaHR0cHM6Ly93d3cudzMub3JnL1RSLzIwMDgvUkVDLXhtbC0yMDA4MTEyNi8jZHRkCiAgICAgKi8KICAgIE4oKSB7CiAgICAgIGxldCB7IGM6IHNjYW5uZXIgfSA9IHRoaXM7CiAgICAgIGxldCBzdGFydEluZGV4ID0gc2Nhbm5lci5kOwogICAgICBpZiAoIXNjYW5uZXIuYigiPCFET0NUWVBFIikpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IG5hbWUgPSB0aGlzLmUoKSAmJiB0aGlzLnIoKTsKICAgICAgaWYgKCFuYW1lKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJFeHBlY3RlZCBhIG5hbWUiKTsKICAgICAgfQogICAgICBsZXQgcHVibGljSWQ7CiAgICAgIGxldCBzeXN0ZW1JZDsKICAgICAgaWYgKHRoaXMuZSgpKSB7CiAgICAgICAgaWYgKHNjYW5uZXIuYigiUFVCTElDIikpIHsKICAgICAgICAgIHB1YmxpY0lkID0gdGhpcy5lKCkgJiYgdGhpcy5PKCk7CiAgICAgICAgICBpZiAocHVibGljSWQgPT09IGZhbHNlKSB7CiAgICAgICAgICAgIHRocm93IHRoaXMuYSgiRXhwZWN0ZWQgYSBwdWJsaWMgaWRlbnRpZmllciIpOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5lKCk7CiAgICAgICAgfQogICAgICAgIGlmIChwdWJsaWNJZCAhPT0gdm9pZCAwIHx8IHNjYW5uZXIuYigiU1lTVEVNIikpIHsKICAgICAgICAgIHRoaXMuZSgpOwogICAgICAgICAgc3lzdGVtSWQgPSB0aGlzLnMoKTsKICAgICAgICAgIGlmIChzeXN0ZW1JZCA9PT0gZmFsc2UpIHsKICAgICAgICAgICAgdGhyb3cgdGhpcy5hKCJFeHBlY3RlZCBhIHN5c3RlbSBpZGVudGlmaWVyIik7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLmUoKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgbGV0IGludGVybmFsU3Vic2V0OwogICAgICBpZiAoc2Nhbm5lci5iKCJbIikpIHsKICAgICAgICBpbnRlcm5hbFN1YnNldCA9IHNjYW5uZXIuQSgvXF1bXHgyMFx0XHJcbl0qPi8pOwogICAgICAgIGlmICghc2Nhbm5lci5iKCJdIikpIHsKICAgICAgICAgIHRocm93IHRoaXMuYSgiVW5jbG9zZWQgaW50ZXJuYWwgc3Vic2V0Iik7CiAgICAgICAgfQogICAgICAgIHRoaXMuZSgpOwogICAgICB9CiAgICAgIGlmICghc2Nhbm5lci5iKCI+IikpIHsKICAgICAgICB0aHJvdyB0aGlzLmEoIlVuY2xvc2VkIGRvY3R5cGUgZGVjbGFyYXRpb24iKTsKICAgICAgfQogICAgICByZXR1cm4gdGhpcy5mLnByZXNlcnZlRG9jdW1lbnRUeXBlID8gdGhpcy5qKG5ldyBYbWxEb2N1bWVudFR5cGUobmFtZSwgcHVibGljSWQsIHN5c3RlbUlkLCBpbnRlcm5hbFN1YnNldCksIHN0YXJ0SW5kZXgpIDogdHJ1ZTsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgYW4gZWxlbWVudCBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGFuIGVsZW1lbnQgd2FzIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1lbGVtZW50CiAgICAgKi8KICAgIEIoKSB7CiAgICAgIGxldCB7IGM6IHNjYW5uZXIgfSA9IHRoaXM7CiAgICAgIGxldCBzdGFydEluZGV4ID0gc2Nhbm5lci5kOwogICAgICBpZiAoIXNjYW5uZXIuYigiPCIpKSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CiAgICAgIGxldCBuYW1lID0gdGhpcy5yKCk7CiAgICAgIGlmICghbmFtZSkgewogICAgICAgIHNjYW5uZXIubyhzdGFydEluZGV4KTsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IGF0dHJpYnV0ZXMgPSB0aGlzLkkoKTsKICAgICAgbGV0IGlzRW1wdHkgPSAhIXNjYW5uZXIuYigiLz4iKTsKICAgICAgbGV0IGVsZW1lbnQgPSBuZXcgWG1sRWxlbWVudChuYW1lLCBhdHRyaWJ1dGVzKTsKICAgICAgZWxlbWVudC5wYXJlbnQgPSB0aGlzLmw7CiAgICAgIGlmICghaXNFbXB0eSkgewogICAgICAgIGlmICghc2Nhbm5lci5iKCI+IikpIHsKICAgICAgICAgIHRocm93IHRoaXMuYShgVW5jbG9zZWQgc3RhcnQgdGFnIGZvciBlbGVtZW50IFxgJHtuYW1lfVxgYCk7CiAgICAgICAgfQogICAgICAgIHRoaXMubCA9IGVsZW1lbnQ7CiAgICAgICAgZG8gewogICAgICAgICAgdGhpcy5MKCk7CiAgICAgICAgfSB3aGlsZSAodGhpcy5CKCkgfHwgdGhpcy5NKCkgfHwgdGhpcy5LKCkgfHwgdGhpcy5FKCkgfHwgdGhpcy5EKCkpOwogICAgICAgIGxldCBlbmRUYWdNYXJrID0gc2Nhbm5lci5kOwogICAgICAgIGxldCBlbmRUYWdOYW1lOwogICAgICAgIGlmICghc2Nhbm5lci5iKCI8LyIpIHx8ICEoZW5kVGFnTmFtZSA9IHRoaXMucigpKSB8fCBlbmRUYWdOYW1lICE9PSBuYW1lKSB7CiAgICAgICAgICBzY2FubmVyLm8oZW5kVGFnTWFyayk7CiAgICAgICAgICB0aHJvdyB0aGlzLmEoYE1pc3NpbmcgZW5kIHRhZyBmb3IgZWxlbWVudCAke25hbWV9YCk7CiAgICAgICAgfQogICAgICAgIHRoaXMuZSgpOwogICAgICAgIGlmICghc2Nhbm5lci5iKCI+IikpIHsKICAgICAgICAgIHRocm93IHRoaXMuYShgVW5jbG9zZWQgZW5kIHRhZyBmb3IgZWxlbWVudCAke25hbWV9YCk7CiAgICAgICAgfQogICAgICAgIHRoaXMubCA9IGVsZW1lbnQucGFyZW50OwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmooZWxlbWVudCwgc3RhcnRJbmRleCk7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGFuIGBFcWAgcHJvZHVjdGlvbiBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGFuIGBFcWAgcHJvZHVjdGlvbiB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI05ULUVxCiAgICAgKi8KICAgIHUoKSB7CiAgICAgIHRoaXMuZSgpOwogICAgICBpZiAodGhpcy5jLmIoIj0iKSkgewogICAgICAgIHRoaXMuZSgpOwogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgYE1pc2NgIGNvbnRlbnQgaWYgcG9zc2libGUuCiAgICAgKgogICAgICogQHJldHVybnMgV2hldGhlciBhbnl0aGluZyB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI05ULU1pc2MKICAgICAqLwogICAgdygpIHsKICAgICAgcmV0dXJuIHRoaXMuRCgpIHx8IHRoaXMuRSgpIHx8IHRoaXMuZSgpOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBvbmUgb3IgbW9yZSBgTmFtZWAgY2hhcmFjdGVycyBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBgTmFtZWAgY2hhcmFjdGVycywgb3IgYW4gZW1wdHkgc3RyaW5nIGlmIG5vbmUgd2VyZSBjb25zdW1lZC4KICAgICAqIEBzZWUgaHR0cHM6Ly93d3cudzMub3JnL1RSLzIwMDgvUkVDLXhtbC0yMDA4MTEyNi8jTlQtTmFtZQogICAgICovCiAgICByKCkgewogICAgICByZXR1cm4gaXNOYW1lU3RhcnRDaGFyKHRoaXMuYy5oKCkpID8gdGhpcy5jLnYoaXNOYW1lQ2hhcikgOiBlbXB0eVN0cmluZzI7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyBXaGV0aGVyIGEgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiB3YXMgY29uc3VtZWQuCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI3NlYy1waQogICAgICovCiAgICBFKCkgewogICAgICBsZXQgeyBjOiBzY2FubmVyIH0gPSB0aGlzOwogICAgICBsZXQgc3RhcnRJbmRleCA9IHNjYW5uZXIuZDsKICAgICAgaWYgKCFzY2FubmVyLmIoIjw/IikpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IG5hbWUgPSB0aGlzLnIoKTsKICAgICAgaWYgKG5hbWUpIHsKICAgICAgICBpZiAobmFtZS50b0xvd2VyQ2FzZSgpID09PSAieG1sIikgewogICAgICAgICAgc2Nhbm5lci5vKHN0YXJ0SW5kZXgpOwogICAgICAgICAgdGhyb3cgdGhpcy5hKCJYTUwgZGVjbGFyYXRpb24gaXNuJ3QgYWxsb3dlZCBoZXJlIik7CiAgICAgICAgfQogICAgICB9IGVsc2UgewogICAgICAgIHRocm93IHRoaXMuYSgiSW52YWxpZCBwcm9jZXNzaW5nIGluc3RydWN0aW9uIik7CiAgICAgIH0KICAgICAgaWYgKCF0aGlzLmUoKSkgewogICAgICAgIGlmIChzY2FubmVyLmIoIj8+IikpIHsKICAgICAgICAgIHJldHVybiB0aGlzLmoobmV3IFhtbFByb2Nlc3NpbmdJbnN0cnVjdGlvbihuYW1lKSwgc3RhcnRJbmRleCk7CiAgICAgICAgfQogICAgICAgIHRocm93IHRoaXMuYSgiV2hpdGVzcGFjZSBpcyByZXF1aXJlZCBhZnRlciBhIHByb2Nlc3NpbmcgaW5zdHJ1Y3Rpb24gbmFtZSIpOwogICAgICB9CiAgICAgIGxldCBjb250ZW50ID0gc2Nhbm5lci50KCI/PiIpOwogICAgICB0aGlzLnAoY29udGVudCk7CiAgICAgIGlmICghc2Nhbm5lci5iKCI/PiIpKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJVbnRlcm1pbmF0ZWQgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiIpOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmoobmV3IFhtbFByb2Nlc3NpbmdJbnN0cnVjdGlvbihuYW1lLCBub3JtYWxpemVMaW5lQnJlYWtzKGNvbnRlbnQpKSwgc3RhcnRJbmRleCk7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgcHJvbG9nIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEByZXR1cm5zIFdoZXRoZXIgYSBwcm9sb2cgd2FzIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNzZWMtcHJvbG9nLWR0ZAogICAgICovCiAgICBIKCkgewogICAgICBsZXQgeyBjOiBzY2FubmVyIH0gPSB0aGlzOwogICAgICBsZXQgc3RhcnRJbmRleCA9IHNjYW5uZXIuZDsKICAgICAgdGhpcy5QKCk7CiAgICAgIHdoaWxlICh0aGlzLncoKSkgewogICAgICB9CiAgICAgIGlmICh0aGlzLk4oKSkgewogICAgICAgIHdoaWxlICh0aGlzLncoKSkgewogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gc3RhcnRJbmRleCA8IHNjYW5uZXIuZDsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgYSBwdWJsaWMgaWRlbnRpZmllciBsaXRlcmFsIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEByZXR1cm5zCiAgICAgKiAgIFZhbHVlIG9mIHRoZSBwdWJsaWMgaWRlbnRpZmllciBsaXRlcmFsIG1pbnVzIHF1b3Rlcywgb3IgYGZhbHNlYCBpZgogICAgICogICBub3RoaW5nIHdhcyBjb25zdW1lZC4gQW4gZW1wdHkgc3RyaW5nIGluZGljYXRlcyB0aGF0IGEgcHVibGljIGlkIGxpdGVyYWwKICAgICAqICAgd2FzIGNvbnN1bWVkIGJ1dCB3YXMgZW1wdHkuCiAgICAgKgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1QdWJpZExpdGVyYWwKICAgICAqLwogICAgTygpIHsKICAgICAgbGV0IHN0YXJ0SW5kZXggPSB0aGlzLmMuZDsKICAgICAgbGV0IHZhbHVlID0gdGhpcy5zKCk7CiAgICAgIGlmICh2YWx1ZSAhPT0gZmFsc2UgJiYgIS9eWy1ceDIwXHJcbmEtekEtWjAtOScoKSssLi86PT87ISojQCRfJV0qJC8udGVzdCh2YWx1ZSkpIHsKICAgICAgICB0aGlzLmMubyhzdGFydEluZGV4KTsKICAgICAgICB0aHJvdyB0aGlzLmEoIkludmFsaWQgY2hhcmFjdGVyIGluIHB1YmxpYyBpZGVudGlmaWVyIik7CiAgICAgIH0KICAgICAgcmV0dXJuIHZhbHVlOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhIHJlZmVyZW5jZSBpZiBwb3NzaWJsZS4KICAgICAqCiAgICAgKiBUaGlzIGRpZmZlcnMgZnJvbSBgY29uc3VtZUNvbnRlbnRSZWZlcmVuY2UoKWAgaW4gdGhhdCBhIGNvbnN1bWVkIHJlZmVyZW5jZQogICAgICogd2lsbCBiZSByZXR1cm5lZCByYXRoZXIgdGhhbiBhZGRlZCB0byB0aGUgZG9jdW1lbnQuCiAgICAgKgogICAgICogQHJldHVybnMKICAgICAqICAgUGFyc2VkIHJlZmVyZW5jZSB2YWx1ZSwgb3IgYGZhbHNlYCBpZiBub3RoaW5nIHdhcyBjb25zdW1lZCAodG8KICAgICAqICAgZGlzdGluZ3Vpc2ggZnJvbSBhIHJlZmVyZW5jZSB0aGF0IHJlc29sdmVzIHRvIGFuIGVtcHR5IHN0cmluZykuCiAgICAgKgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1SZWZlcmVuY2UKICAgICAqLwogICAgQygpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgaWYgKCFzY2FubmVyLmIoIiYiKSkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICBsZXQgcmVmID0gc2Nhbm5lci52KGlzUmVmZXJlbmNlQ2hhcik7CiAgICAgIGlmIChzY2FubmVyLkYoKSAhPT0gIjsiKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJVbnRlcm1pbmF0ZWQgcmVmZXJlbmNlIChhIHJlZmVyZW5jZSBtdXN0IGVuZCB3aXRoIGA7YCkiKTsKICAgICAgfQogICAgICBsZXQgcGFyc2VkVmFsdWU7CiAgICAgIGlmIChyZWZbMF0gPT09ICIjIikgewogICAgICAgIGxldCBjb2RlUG9pbnQgPSByZWZbMV0gPT09ICJ4IiA/IHBhcnNlSW50KHJlZi5zbGljZSgyKSwgMTYpIDogcGFyc2VJbnQocmVmLnNsaWNlKDEpLCAxMCk7CiAgICAgICAgaWYgKGlzTmFOKGNvZGVQb2ludCkpIHsKICAgICAgICAgIHRocm93IHRoaXMuYSgiSW52YWxpZCBjaGFyYWN0ZXIgcmVmZXJlbmNlIik7CiAgICAgICAgfQogICAgICAgIGlmICghaXNYbWxDb2RlUG9pbnQoY29kZVBvaW50KSkgewogICAgICAgICAgdGhyb3cgdGhpcy5hKCJDaGFyYWN0ZXIgcmVmZXJlbmNlIHJlc29sdmVzIHRvIGFuIGludmFsaWQgY2hhcmFjdGVyIik7CiAgICAgICAgfQogICAgICAgIHBhcnNlZFZhbHVlID0gU3RyaW5nLmZyb21Db2RlUG9pbnQoY29kZVBvaW50KTsKICAgICAgfSBlbHNlIHsKICAgICAgICBwYXJzZWRWYWx1ZSA9IHByZWRlZmluZWRFbnRpdGllc1tyZWZdOwogICAgICAgIGlmIChwYXJzZWRWYWx1ZSA9PT0gdm9pZCAwKSB7CiAgICAgICAgICBsZXQgewogICAgICAgICAgICBpZ25vcmVVbmRlZmluZWRFbnRpdGllcywKICAgICAgICAgICAgcmVzb2x2ZVVuZGVmaW5lZEVudGl0eQogICAgICAgICAgfSA9IHRoaXMuZjsKICAgICAgICAgIGxldCB3cmFwcGVkUmVmID0gYCYke3JlZn07YDsKICAgICAgICAgIGlmIChyZXNvbHZlVW5kZWZpbmVkRW50aXR5KSB7CiAgICAgICAgICAgIGxldCByZXNvbHZlZFZhbHVlID0gcmVzb2x2ZVVuZGVmaW5lZEVudGl0eSh3cmFwcGVkUmVmKTsKICAgICAgICAgICAgaWYgKHJlc29sdmVkVmFsdWUgIT09IG51bGwgJiYgcmVzb2x2ZWRWYWx1ZSAhPT0gdm9pZCAwKSB7CiAgICAgICAgICAgICAgbGV0IHR5cGUgPSB0eXBlb2YgcmVzb2x2ZWRWYWx1ZTsKICAgICAgICAgICAgICBpZiAodHlwZSAhPT0gInN0cmluZyIpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoYFxgcmVzb2x2ZVVuZGVmaW5lZEVudGl0eSgpXGAgbXVzdCByZXR1cm4gYSBzdHJpbmcsIFxgbnVsbFxgLCBvciBcYHVuZGVmaW5lZFxgLCBidXQgcmV0dXJuZWQgYSB2YWx1ZSBvZiB0eXBlICR7dHlwZX1gKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgcmV0dXJuIHJlc29sdmVkVmFsdWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIGlmIChpZ25vcmVVbmRlZmluZWRFbnRpdGllcykgewogICAgICAgICAgICByZXR1cm4gd3JhcHBlZFJlZjsKICAgICAgICAgIH0KICAgICAgICAgIHNjYW5uZXIubygtd3JhcHBlZFJlZi5sZW5ndGgpOwogICAgICAgICAgdGhyb3cgdGhpcy5hKGBOYW1lZCBlbnRpdHkgaXNuJ3QgZGVmaW5lZDogJHt3cmFwcGVkUmVmfWApOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gcGFyc2VkVmFsdWU7CiAgICB9CiAgICAvKioKICAgICAqIENvbnN1bWVzIGEgYFN5c3RlbUxpdGVyYWxgIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEEgYFN5c3RlbUxpdGVyYWxgIGlzIHNpbWlsYXIgdG8gYW4gYXR0cmlidXRlIHZhbHVlLCBidXQgYWxsb3dzIHRoZQogICAgICogY2hhcmFjdGVycyBgPGAgYW5kIGAmYCBhbmQgZG9lc24ndCByZXBsYWNlIHJlZmVyZW5jZXMuCiAgICAgKgogICAgICogQHJldHVybnMKICAgICAqICAgVmFsdWUgb2YgdGhlIGBTeXN0ZW1MaXRlcmFsYCBtaW51cyBxdW90ZXMsIG9yIGBmYWxzZWAgaWYgbm90aGluZyB3YXMKICAgICAqICAgY29uc3VtZWQuIEFuIGVtcHR5IHN0cmluZyBpbmRpY2F0ZXMgdGhhdCBhIGBTeXN0ZW1MaXRlcmFsYCB3YXMgY29uc3VtZWQKICAgICAqICAgYnV0IHdhcyBlbXB0eS4KICAgICAqCiAgICAgKiBAc2VlIGh0dHBzOi8vd3d3LnczLm9yZy9UUi8yMDA4L1JFQy14bWwtMjAwODExMjYvI05ULVN5c3RlbUxpdGVyYWwKICAgICAqLwogICAgcygpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgbGV0IHF1b3RlID0gc2Nhbm5lci5iKCciJykgfHwgc2Nhbm5lci5iKCInIik7CiAgICAgIGlmICghcXVvdGUpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IHZhbHVlID0gc2Nhbm5lci50KHF1b3RlKTsKICAgICAgdGhpcy5wKHZhbHVlKTsKICAgICAgaWYgKCFzY2FubmVyLmIocXVvdGUpKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJNaXNzaW5nIGVuZCBxdW90ZSIpOwogICAgICB9CiAgICAgIHJldHVybiB2YWx1ZTsKICAgIH0KICAgIC8qKgogICAgICogQ29uc3VtZXMgb25lIG9yIG1vcmUgd2hpdGVzcGFjZSBjaGFyYWN0ZXJzIGlmIHBvc3NpYmxlLgogICAgICoKICAgICAqIEByZXR1cm5zIFdoZXRoZXIgYW55IHdoaXRlc3BhY2UgY2hhcmFjdGVycyB3ZXJlIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyN3aGl0ZQogICAgICovCiAgICBlKCkgewogICAgICByZXR1cm4gISF0aGlzLmMudihpc1doaXRlc3BhY2UpOwogICAgfQogICAgLyoqCiAgICAgKiBDb25zdW1lcyBhbiBYTUwgZGVjbGFyYXRpb24gaWYgcG9zc2libGUuCiAgICAgKgogICAgICogQHJldHVybnMgV2hldGhlciBhbiBYTUwgZGVjbGFyYXRpb24gd2FzIGNvbnN1bWVkLgogICAgICogQHNlZSBodHRwczovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMteG1sLTIwMDgxMTI2LyNOVC1YTUxEZWNsCiAgICAgKi8KICAgIFAoKSB7CiAgICAgIGxldCB7IGM6IHNjYW5uZXIgfSA9IHRoaXM7CiAgICAgIGxldCBzdGFydEluZGV4ID0gc2Nhbm5lci5kOwogICAgICBpZiAoIXNjYW5uZXIuYigiPD94bWwiKSkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICBpZiAoIXRoaXMuZSgpKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJJbnZhbGlkIFhNTCBkZWNsYXJhdGlvbiIpOwogICAgICB9CiAgICAgIGxldCB2ZXJzaW9uID0gISFzY2FubmVyLmIoInZlcnNpb24iKSAmJiB0aGlzLnUoKSAmJiB0aGlzLnMoKTsKICAgICAgaWYgKHZlcnNpb24gPT09IGZhbHNlKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJYTUwgdmVyc2lvbiBpcyBtaXNzaW5nIG9yIGludmFsaWQiKTsKICAgICAgfSBlbHNlIGlmICghL14xXC5bMC05XSskLy50ZXN0KHZlcnNpb24pKSB7CiAgICAgICAgdGhyb3cgdGhpcy5hKCJJbnZhbGlkIGNoYXJhY3RlciBpbiB2ZXJzaW9uIG51bWJlciIpOwogICAgICB9CiAgICAgIGxldCBlbmNvZGluZzsKICAgICAgbGV0IHN0YW5kYWxvbmU7CiAgICAgIGlmICh0aGlzLmUoKSkgewogICAgICAgIGVuY29kaW5nID0gISFzY2FubmVyLmIoImVuY29kaW5nIikgJiYgdGhpcy51KCkgJiYgdGhpcy5zKCk7CiAgICAgICAgaWYgKGVuY29kaW5nKSB7CiAgICAgICAgICB0aGlzLmUoKTsKICAgICAgICB9CiAgICAgICAgc3RhbmRhbG9uZSA9ICEhc2Nhbm5lci5iKCJzdGFuZGFsb25lIikgJiYgdGhpcy51KCkgJiYgdGhpcy5zKCk7CiAgICAgICAgaWYgKHN0YW5kYWxvbmUpIHsKICAgICAgICAgIGlmIChzdGFuZGFsb25lICE9PSAieWVzIiAmJiBzdGFuZGFsb25lICE9PSAibm8iKSB7CiAgICAgICAgICAgIHRocm93IHRoaXMuYSgnT25seSAieWVzIiBhbmQgIm5vIiBhcmUgcGVybWl0dGVkIGFzIHZhbHVlcyBvZiBgc3RhbmRhbG9uZWAnKTsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuZSgpOwogICAgICAgIH0KICAgICAgfQogICAgICBpZiAoIXNjYW5uZXIuYigiPz4iKSkgewogICAgICAgIHRocm93IHRoaXMuYSgiSW52YWxpZCBvciB1bmNsb3NlZCBYTUwgZGVjbGFyYXRpb24iKTsKICAgICAgfQogICAgICByZXR1cm4gdGhpcy5mLnByZXNlcnZlWG1sRGVjbGFyYXRpb24gPyB0aGlzLmoobmV3IFhtbERlY2xhcmF0aW9uKAogICAgICAgIHZlcnNpb24sCiAgICAgICAgZW5jb2RpbmcgfHwgdm9pZCAwLAogICAgICAgIHN0YW5kYWxvbmUgfHwgdm9pZCAwCiAgICAgICksIHN0YXJ0SW5kZXgpIDogdHJ1ZTsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyBhbiBgWG1sRXJyb3JgIGZvciB0aGUgY3VycmVudCBzY2FubmVyIHBvc2l0aW9uLgogICAgICovCiAgICBhKG1lc3NhZ2UpIHsKICAgICAgbGV0IHsgYzogc2Nhbm5lciB9ID0gdGhpczsKICAgICAgcmV0dXJuIG5ldyBYbWxFcnJvcihtZXNzYWdlLCBzY2FubmVyLmQsIHNjYW5uZXIubSk7CiAgICB9CiAgICAvKioKICAgICAqIFRocm93cyBhbiBpbnZhbGlkIGNoYXJhY3RlciBlcnJvciBpZiBhbnkgY2hhcmFjdGVyIGluIHRoZSBnaXZlbiBfc3RyaW5nXwogICAgICogaXNuJ3QgYSB2YWxpZCBYTUwgY2hhcmFjdGVyLgogICAgICovCiAgICBwKHN0cmluZykgewogICAgICBsZXQgeyBsZW5ndGggfSA9IHN0cmluZzsKICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBsZW5ndGg7ICsraSkgewogICAgICAgIGxldCBjcCA9IHN0cmluZy5jb2RlUG9pbnRBdChpKTsKICAgICAgICBpZiAoIWlzWG1sQ29kZVBvaW50KGNwKSkgewogICAgICAgICAgdGhpcy5jLm8oLShbLi4uc3RyaW5nXS5sZW5ndGggLSBpKSk7CiAgICAgICAgICB0aHJvdyB0aGlzLmEoIkludmFsaWQgY2hhcmFjdGVyIik7CiAgICAgICAgfQogICAgICAgIGlmIChjcCA+IDY1NTM1KSB7CiAgICAgICAgICBpICs9IDE7CiAgICAgICAgfQogICAgICB9CiAgICB9CiAgfTsKICBmdW5jdGlvbiBub3JtYWxpemVMaW5lQnJlYWtzKHRleHQpIHsKICAgIGxldCBpID0gMDsKICAgIHdoaWxlICgoaSA9IHRleHQuaW5kZXhPZigiXHIiLCBpKSkgIT09IC0xKSB7CiAgICAgIHRleHQgPSB0ZXh0W2kgKyAxXSA9PT0gIlxuIiA/IHRleHQuc2xpY2UoMCwgaSkgKyB0ZXh0LnNsaWNlKGkgKyAxKSA6IHRleHQuc2xpY2UoMCwgaSkgKyAiXG4iICsgdGV4dC5zbGljZShpICsgMSk7CiAgICB9CiAgICByZXR1cm4gdGV4dDsKICB9CiAgZnVuY3Rpb24gcGFyc2VYbWwoeG1sLCBvcHRpb25zKSB7CiAgICByZXR1cm4gbmV3IFBhcnNlcih4bWwsIG9wdGlvbnMpLmRvY3VtZW50OwogIH0KICBjbGFzcyBYbWxQYXJzZUVycm9yIGV4dGVuZHMgRXJyb3IgewogICAgY29uc3RydWN0b3IobWVzc2FnZSkgewogICAgICBzdXBlcihtZXNzYWdlKTsKICAgIH0KICB9CiAgZnVuY3Rpb24gcGFyc2VYbWxTdHJpbmcoeG1sU3RyaW5nKSB7CiAgICBsZXQgZG9jID0gbnVsbDsKICAgIHRyeSB7CiAgICAgIGRvYyA9IGJyb3dzZXIucGFyc2VYbWwoeG1sU3RyaW5nKTsKICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgdGhyb3cgbmV3IFhtbFBhcnNlRXJyb3IoZS5tZXNzYWdlKTsKICAgIH0KICAgIHJldHVybiBkb2M7CiAgfQogIGZ1bmN0aW9uIHN0cmlwTmFtZXNwYWNlKG5hbWUpIHsKICAgIGNvbnN0IGNvbG9uID0gbmFtZS5pbmRleE9mKCI6Iik7CiAgICByZXR1cm4gY29sb24gPiAtMSA/IG5hbWUuc3Vic3RyKGNvbG9uICsgMSkgOiBuYW1lOwogIH0KICBmdW5jdGlvbiBnZXRSb290RWxlbWVudCh4bWxEb2MpIHsKICAgIHJldHVybiB4bWxEb2MuY2hpbGRyZW5bMF07CiAgfQogIGZ1bmN0aW9uIGdldEVsZW1lbnROYW1lKGVsZW1lbnQpIHsKICAgIHJldHVybiBlbGVtZW50Lm5hbWUgfHwgIiI7CiAgfQogIGZ1bmN0aW9uIGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgbmFtZSwgbmVzdGVkID0gZmFsc2UpIHsKICAgIGNvbnN0IHN0cmlwcGVkTmFtZSA9IHN0cmlwTmFtZXNwYWNlKG5hbWUpOwogICAgZnVuY3Rpb24gcmVkdWNlcihwcmV2LCBjdXJyKSB7CiAgICAgIGlmIChzdHJpcE5hbWVzcGFjZShnZXRFbGVtZW50TmFtZShjdXJyKSkgPT09IHN0cmlwcGVkTmFtZSkgewogICAgICAgIHByZXYucHVzaChjdXJyKTsKICAgICAgfQogICAgICBpZiAobmVzdGVkICYmIEFycmF5LmlzQXJyYXkoY3Vyci5jaGlsZHJlbikpIHsKICAgICAgICByZXR1cm4gWy4uLnByZXYsIC4uLmN1cnIuY2hpbGRyZW4ucmVkdWNlKHJlZHVjZXIsIFtdKV07CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIHByZXY7CiAgICAgIH0KICAgIH0KICAgIHJldHVybiBlbGVtZW50ICYmIEFycmF5LmlzQXJyYXkoZWxlbWVudC5jaGlsZHJlbikgPyBlbGVtZW50LmNoaWxkcmVuLnJlZHVjZShyZWR1Y2VyLCBbXSkgOiBbXTsKICB9CiAgZnVuY3Rpb24gZmluZENoaWxkRWxlbWVudChlbGVtZW50LCBuYW1lLCBuZXN0ZWQgPSBmYWxzZSkgewogICAgcmV0dXJuIGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgbmFtZSwgbmVzdGVkKVswXSB8fCBudWxsOwogIH0KICBmdW5jdGlvbiBnZXRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCkgewogICAgcmV0dXJuIGVsZW1lbnQgJiYgQXJyYXkuaXNBcnJheShlbGVtZW50LmNoaWxkcmVuKSA/IFsKICAgICAgLi4uZWxlbWVudC5jaGlsZHJlbi5maWx0ZXIoCiAgICAgICAgKGVsKSA9PiBlbCBpbnN0YW5jZW9mIGJyb3dzZXIuWG1sRWxlbWVudAogICAgICApCiAgICBdIDogW107CiAgfQogIGZ1bmN0aW9uIGdldEVsZW1lbnRUZXh0KGVsZW1lbnQpIHsKICAgIGNvbnN0IHRleHROb2RlID0gZWxlbWVudCAmJiBBcnJheS5pc0FycmF5KGVsZW1lbnQuY2hpbGRyZW4pID8gZWxlbWVudC5jaGlsZHJlbi5maW5kKChub2RlKSA9PiBub2RlLnR5cGUgPT09ICJ0ZXh0IikgOiBudWxsOwogICAgcmV0dXJuIHRleHROb2RlID8gdGV4dE5vZGUudGV4dCA6ICIiOwogIH0KICBmdW5jdGlvbiBnZXRFbGVtZW50QXR0cmlidXRlKGVsZW1lbnQsIGF0dHJOYW1lKSB7CiAgICByZXR1cm4gZWxlbWVudCAmJiBlbGVtZW50LmF0dHJpYnV0ZXNbYXR0ck5hbWVdIHx8ICIiOwogIH0KICBjbGFzcyBFbmRwb2ludEVycm9yIGV4dGVuZHMgRXJyb3IgewogICAgY29uc3RydWN0b3IobWVzc2FnZSwgaHR0cFN0YXR1cywgaXNDcm9zc09yaWdpblJlbGF0ZWQpIHsKICAgICAgc3VwZXIobWVzc2FnZSk7CiAgICAgIHRoaXMuaHR0cFN0YXR1cyA9IGh0dHBTdGF0dXM7CiAgICAgIHRoaXMuaXNDcm9zc09yaWdpblJlbGF0ZWQgPSBpc0Nyb3NzT3JpZ2luUmVsYXRlZDsKICAgICAgdGhpcy5uYW1lID0gIkVuZHBvaW50RXJyb3IiOwogICAgfQogIH0KICBjbGFzcyBTZXJ2aWNlRXhjZXB0aW9uRXJyb3IgZXh0ZW5kcyBFcnJvciB7CiAgICAvKioKICAgICAqIENvbnN0cnVjdG9yCiAgICAgKiBAcGFyYW0gbWVzc2FnZSBFcnJvciBtZXNzYWdlCiAgICAgKiBAcGFyYW0gcmVxdWVzdFVybCBVUkwgd2hpY2ggcmVzdWx0ZWQgaW4gdGhlIFNlcnZpY2VFeGNlcHRpb24KICAgICAqIEBwYXJhbSBjb2RlIE9wdGlvbmFsIFNlcnZpY2VFeGNlcHRpb24gY29kZQogICAgICogQHBhcmFtIGxvY2F0b3IgT3B0aW9uYWwgU2VydmljZUV4Y2VwdGlvbiBsb2NhdG9yCiAgICAgKiBAcGFyYW0gcmVzcG9uc2UgT3B0aW9uYWwgcmVzcG9uc2UgY29udGVudCByZWNlaXZlZAogICAgICovCiAgICBjb25zdHJ1Y3RvcihtZXNzYWdlLCByZXF1ZXN0VXJsLCBjb2RlLCBsb2NhdG9yLCByZXNwb25zZSkgewogICAgICBzdXBlcihtZXNzYWdlKTsKICAgICAgdGhpcy5yZXF1ZXN0VXJsID0gcmVxdWVzdFVybDsKICAgICAgdGhpcy5jb2RlID0gY29kZTsKICAgICAgdGhpcy5sb2NhdG9yID0gbG9jYXRvcjsKICAgICAgdGhpcy5yZXNwb25zZSA9IHJlc3BvbnNlOwogICAgICB0aGlzLm5hbWUgPSAiU2VydmljZUV4Y2VwdGlvbkVycm9yIjsKICAgIH0KICB9CiAgZnVuY3Rpb24gcGFyc2Uoc2VydmljZUV4Y2VwdGlvbiwgdXJsKSB7CiAgICBjb25zdCBlcnJvckNvZGUgPSBnZXRFbGVtZW50QXR0cmlidXRlKHNlcnZpY2VFeGNlcHRpb24sICJjb2RlIikgfHwgZ2V0RWxlbWVudEF0dHJpYnV0ZShzZXJ2aWNlRXhjZXB0aW9uLCAiZXhjZXB0aW9uQ29kZSIpOwogICAgY29uc3QgZXJyb3JMb2NhdG9yID0gZ2V0RWxlbWVudEF0dHJpYnV0ZShzZXJ2aWNlRXhjZXB0aW9uLCAibG9jYXRvciIpOwogICAgY29uc3QgdGV4dEVsZW1lbnQgPSBmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2VFeGNlcHRpb24sICJFeGNlcHRpb25UZXh0IikgfHwgc2VydmljZUV4Y2VwdGlvbjsKICAgIGNvbnN0IGVycm9yTWVzc2FnZSA9IGdldEVsZW1lbnRUZXh0KHRleHRFbGVtZW50KS50cmltKCk7CiAgICByZXR1cm4gbmV3IFNlcnZpY2VFeGNlcHRpb25FcnJvcigKICAgICAgZXJyb3JNZXNzYWdlLAogICAgICB1cmwsCiAgICAgIGVycm9yQ29kZSwKICAgICAgZXJyb3JMb2NhdG9yLAogICAgICBzZXJ2aWNlRXhjZXB0aW9uLmRvY3VtZW50CiAgICApOwogIH0KICBmdW5jdGlvbiBjaGVjayhyZXNwb25zZSwgdXJsKSB7CiAgICBjb25zdCByb290RWwgPSBnZXRSb290RWxlbWVudChyZXNwb25zZSk7CiAgICBjb25zdCByb290RWxOYW1lID0gc3RyaXBOYW1lc3BhY2UoZ2V0RWxlbWVudE5hbWUocm9vdEVsKSk7CiAgICBpZiAocm9vdEVsTmFtZSA9PT0gIlNlcnZpY2VFeGNlcHRpb25SZXBvcnQiKSB7CiAgICAgIGNvbnN0IGVycm9yID0gZmluZENoaWxkRWxlbWVudChyb290RWwsICJTZXJ2aWNlRXhjZXB0aW9uIik7CiAgICAgIGlmIChlcnJvcikgewogICAgICAgIHRocm93IHBhcnNlKGVycm9yLCB1cmwpOwogICAgICB9CiAgICB9CiAgICBpZiAocm9vdEVsTmFtZSA9PT0gIkV4Y2VwdGlvblJlcG9ydCIpIHsKICAgICAgY29uc3QgZXJyb3IgPSBmaW5kQ2hpbGRFbGVtZW50KHJvb3RFbCwgIkV4Y2VwdGlvbiIpOwogICAgICBpZiAoZXJyb3IpIHsKICAgICAgICB0aHJvdyBwYXJzZShlcnJvciwgdXJsKTsKICAgICAgfQogICAgfQogICAgcmV0dXJuIHJlc3BvbnNlOwogIH0KICBmdW5jdGlvbiBlbmNvZGVFcnJvcihlcnJvcikgewogICAgY29uc3QgYmFzZSA9IHsKICAgICAgbWVzc2FnZTogZXJyb3IubWVzc2FnZSwKICAgICAgc3RhY2s6IGVycm9yLnN0YWNrLAogICAgICBuYW1lOiBlcnJvci5uYW1lCiAgICB9OwogICAgaWYgKGVycm9yIGluc3RhbmNlb2YgU2VydmljZUV4Y2VwdGlvbkVycm9yKSB7CiAgICAgIHJldHVybiB7CiAgICAgICAgLi4uYmFzZSwKICAgICAgICBjb2RlOiBlcnJvci5jb2RlLAogICAgICAgIGxvY2F0b3I6IGVycm9yLmxvY2F0b3IsCiAgICAgICAgcmVzcG9uc2U6IGVycm9yLnJlc3BvbnNlLAogICAgICAgIHJlcXVlc3RVcmw6IGVycm9yLnJlcXVlc3RVcmwKICAgICAgfTsKICAgIH0KICAgIGlmIChlcnJvciBpbnN0YW5jZW9mIEVuZHBvaW50RXJyb3IpIHsKICAgICAgcmV0dXJuIHsKICAgICAgICAuLi5iYXNlLAogICAgICAgIGh0dHBTdGF0dXM6IGVycm9yLmh0dHBTdGF0dXMsCiAgICAgICAgaXNDcm9zc09yaWdpblJlbGF0ZWQ6IGVycm9yLmlzQ3Jvc3NPcmlnaW5SZWxhdGVkCiAgICAgIH07CiAgICB9CiAgICByZXR1cm4gYmFzZTsKICB9CiAgY29uc3QgZmFsbGJhY2tFdmVudFRhcmdldCA9IG5ldyBFdmVudFRhcmdldCgpOwogIGZ1bmN0aW9uIGFkZFRhc2tIYW5kbGVyKHRhc2tOYW1lLCBzY29wZSwgaGFuZGxlcikgewogICAgY29uc3QgdXNlV29ya2VyID0gdHlwZW9mIFdvcmtlckdsb2JhbFNjb3BlICE9PSAidW5kZWZpbmVkIjsKICAgIGNvbnN0IGV2ZW50SGFuZGxlciA9IGFzeW5jIChyZXF1ZXN0KSA9PiB7CiAgICAgIGlmIChyZXF1ZXN0LnRhc2tOYW1lID09PSB0YXNrTmFtZSkgewogICAgICAgIGxldCByZXNwb25zZSwgZXJyb3I7CiAgICAgICAgdHJ5IHsKICAgICAgICAgIHJlc3BvbnNlID0gYXdhaXQgaGFuZGxlcihyZXF1ZXN0LnBhcmFtcyk7CiAgICAgICAgfSBjYXRjaCAoZSkgewogICAgICAgICAgZXJyb3IgPSBlbmNvZGVFcnJvcihlKTsKICAgICAgICB9CiAgICAgICAgY29uc3QgbWVzc2FnZSA9ICgKICAgICAgICAgIC8qKiBAdHlwZSB7V29ya2VyUmVzcG9uc2V9ICovCiAgICAgICAgICB7CiAgICAgICAgICAgIHRhc2tOYW1lLAogICAgICAgICAgICByZXF1ZXN0SWQ6IHJlcXVlc3QucmVxdWVzdElkLAogICAgICAgICAgICAuLi5yZXNwb25zZSAmJiB7IHJlc3BvbnNlIH0sCiAgICAgICAgICAgIC4uLmVycm9yICYmIHsgZXJyb3IgfQogICAgICAgICAgfQogICAgICAgICk7CiAgICAgICAgaWYgKHVzZVdvcmtlcikgewogICAgICAgICAgc2NvcGUucG9zdE1lc3NhZ2UobWVzc2FnZSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGZhbGxiYWNrRXZlbnRUYXJnZXQuZGlzcGF0Y2hFdmVudCgKICAgICAgICAgICAgbmV3IEN1c3RvbUV2ZW50KCJvZ2MtY2xpZW50LnJlc3BvbnNlIiwgewogICAgICAgICAgICAgIGRldGFpbDogbWVzc2FnZQogICAgICAgICAgICB9KQogICAgICAgICAgKTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CiAgICBpZiAodXNlV29ya2VyKSB7CiAgICAgIHNjb3BlLmFkZEV2ZW50TGlzdGVuZXIoIm1lc3NhZ2UiLCAoZXZlbnQpID0+IGV2ZW50SGFuZGxlcihldmVudC5kYXRhKSk7CiAgICB9IGVsc2UgewogICAgICBmYWxsYmFja0V2ZW50VGFyZ2V0LmFkZEV2ZW50TGlzdGVuZXIoCiAgICAgICAgIm9nYy1jbGllbnQucmVxdWVzdCIsCiAgICAgICAgKGV2ZW50KSA9PiBldmVudEhhbmRsZXIoZXZlbnQuZGV0YWlsKQogICAgICApOwogICAgfQogIH0KICBjb25zdCBFTkNPRElOR1MgPSBbInV0Zi04IiwgInV0Zi0xNiIsICJpc28tODg1OS0xIl07CiAgY29uc3QgRkFMTEJBQ0tfRU5DT0RJTkcgPSAidXRmLTgiOwogIGZ1bmN0aW9uIGV4dHJhY3RFbmNvZGluZyhjb250ZW50VHlwZSkgewogICAgY29uc3QgbWF0Y2hlcyA9IC9jaGFyc2V0PShbXjtdKykvLmV4ZWMoY29udGVudFR5cGUpOwogICAgcmV0dXJuIG1hdGNoZXMgPyBtYXRjaGVzWzFdIDogbnVsbDsKICB9CiAgZnVuY3Rpb24gZGVjb2RlU3RyaW5nKGJ1ZmZlciwgY29udGVudFR5cGUpIHsKICAgIGNvbnN0IGVuY29kaW5nSGludCA9IGNvbnRlbnRUeXBlID8gZXh0cmFjdEVuY29kaW5nKGNvbnRlbnRUeXBlKSA6IG51bGw7CiAgICBjb25zdCBlbmNvZGluZ0F0dGVtcHRzID0gZW5jb2RpbmdIaW50ID8gW2VuY29kaW5nSGludCwgLi4uRU5DT0RJTkdTXSA6IEVOQ09ESU5HUzsKICAgIGZvciAoY29uc3QgZW5jb2Rpbmcgb2YgZW5jb2RpbmdBdHRlbXB0cykgewogICAgICB0cnkgewogICAgICAgIGNvbnN0IGRlY29kZXIgPSBuZXcgVGV4dERlY29kZXIoZW5jb2RpbmcsIHsgZmF0YWw6IHRydWUgfSk7CiAgICAgICAgcmV0dXJuIGRlY29kZXIuZGVjb2RlKGJ1ZmZlcik7CiAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgfQogICAgfQogICAgY29uc29sZS53YXJuKAogICAgICBgW29nYy1jbGllbnRdIFhNTCBkb2N1bWVudCBlbmNvZGluZyBjb3VsZCBub3QgYmUgZGV0ZXJtaW5lZCwgZmFsbGluZyBiYWNrIHRvICR7RkFMTEJBQ0tfRU5DT0RJTkd9LmAKICAgICk7CiAgICByZXR1cm4gbmV3IFRleHREZWNvZGVyKEZBTExCQUNLX0VOQ09ESU5HKS5kZWNvZGUoYnVmZmVyKTsKICB9CiAgY29uc3QgZmV0Y2hQcm9taXNlcyA9IC8qIEBfX1BVUkVfXyAqLyBuZXcgTWFwKCk7CiAgbGV0IGZldGNoT3B0aW9ucyA9IHt9OwogIGZ1bmN0aW9uIHNldEZldGNoT3B0aW9ucyhvcHRpb25zKSB7CiAgICBmZXRjaE9wdGlvbnMgPSBvcHRpb25zOwogIH0KICBmdW5jdGlvbiBnZXRGZXRjaE9wdGlvbnMoKSB7CiAgICByZXR1cm4gZmV0Y2hPcHRpb25zOwogIH0KICBmdW5jdGlvbiBzaGFyZWRGZXRjaCh1cmwsIG1ldGhvZCA9ICJHRVQiLCBhc0pzb24pIHsKICAgIGxldCBmZXRjaEtleSA9IGAke21ldGhvZH0jJHt1cmx9YDsKICAgIGlmIChhc0pzb24pIHsKICAgICAgZmV0Y2hLZXkgPSBgJHttZXRob2R9I2FzSnNvbiMke3VybH1gOwogICAgfQogICAgaWYgKGZldGNoUHJvbWlzZXMuaGFzKGZldGNoS2V5KSkgewogICAgICByZXR1cm4gZmV0Y2hQcm9taXNlcy5nZXQoZmV0Y2hLZXkpOwogICAgfQogICAgY29uc3Qgb3B0aW9ucyA9IHsgLi4uZ2V0RmV0Y2hPcHRpb25zKCkgfTsKICAgIG9wdGlvbnMubWV0aG9kID0gbWV0aG9kOwogICAgaWYgKGFzSnNvbikgewogICAgICBvcHRpb25zLmhlYWRlcnMgPSAiaGVhZGVycyIgaW4gb3B0aW9ucyA/IG9wdGlvbnMuaGVhZGVycyA6IHt9OwogICAgICBvcHRpb25zLmhlYWRlcnNbIkFjY2VwdCJdID0gImFwcGxpY2F0aW9uL2pzb24sYXBwbGljYXRpb24vc2NoZW1hK2pzb24iOwogICAgfQogICAgY29uc3QgcHJvbWlzZSA9IGZldGNoKHVybCwgb3B0aW9ucykuY2F0Y2goKGUpID0+IGUpLnRoZW4oKHJlc3ApID0+IHsKICAgICAgZmV0Y2hQcm9taXNlcy5kZWxldGUoZmV0Y2hLZXkpOwogICAgICByZXR1cm4gcmVzcDsKICAgIH0pOwogICAgZmV0Y2hQcm9taXNlcy5zZXQoZmV0Y2hLZXksIHByb21pc2UpOwogICAgcmV0dXJuIHByb21pc2UudGhlbigocmVzcCkgPT4gewogICAgICBpZiAocmVzcCBpbnN0YW5jZW9mIEVycm9yKQogICAgICAgIHRocm93IHJlc3A7CiAgICAgIHJldHVybiByZXNwLmNsb25lKCk7CiAgICB9KTsKICB9CiAgZnVuY3Rpb24gcXVlcnlYbWxEb2N1bWVudCh1cmwpIHsKICAgIHJldHVybiBzaGFyZWRGZXRjaCh1cmwpLmNhdGNoKAogICAgICAoKSA9PiAoCiAgICAgICAgLy8gYXR0ZW1wdCBhIEhFQUQgdG8gc2VlIGlmIHRoZSBmYWlsdXJlIGNvbWVzIGZyb20gQ09SUyBvciB0aGUgc2VydmljZSBpcyBnZW5lcmFsbHkgdW5yZWFjaGFibGUKICAgICAgICBmZXRjaCh1cmwsIHsgLi4uZ2V0RmV0Y2hPcHRpb25zKCksIG1ldGhvZDogIkhFQUQiLCBtb2RlOiAibm8tY29ycyIgfSkuY2F0Y2goKGVycm9yKSA9PiB7CiAgICAgICAgICB0aHJvdyBuZXcgRW5kcG9pbnRFcnJvcigKICAgICAgICAgICAgYEZldGNoaW5nIHRoZSBkb2N1bWVudCBmYWlsZWQgZWl0aGVyIGR1ZSB0byBuZXR3b3JrIGVycm9ycyBvciB1bnJlYWNoYWJsZSBob3N0LCBlcnJvciBpczogJHtlcnJvci5tZXNzYWdlfWAsCiAgICAgICAgICAgIDAsCiAgICAgICAgICAgIGZhbHNlCiAgICAgICAgICApOwogICAgICAgIH0pLnRoZW4oKCkgPT4gewogICAgICAgICAgdGhyb3cgbmV3IEVuZHBvaW50RXJyb3IoCiAgICAgICAgICAgIGBUaGUgZG9jdW1lbnQgY291bGQgbm90IGJlIGZldGNoZWQgZHVlIHRvIENPUlMgbGltaXRhdGlvbnNgLAogICAgICAgICAgICAwLAogICAgICAgICAgICB0cnVlCiAgICAgICAgICApOwogICAgICAgIH0pCiAgICAgICkKICAgICkudGhlbihhc3luYyAocmVzcCkgPT4gewogICAgICBpZiAoIXJlc3Aub2spIHsKICAgICAgICBjb25zdCB0ZXh0ID0gYXdhaXQgcmVzcC50ZXh0KCk7CiAgICAgICAgdGhyb3cgbmV3IEVuZHBvaW50RXJyb3IoCiAgICAgICAgICBgUmVjZWl2ZWQgYW4gZXJyb3Igd2l0aCBjb2RlICR7cmVzcC5zdGF0dXN9OiAke3RleHR9YCwKICAgICAgICAgIHJlc3Auc3RhdHVzLAogICAgICAgICAgZmFsc2UKICAgICAgICApOwogICAgICB9CiAgICAgIGNvbnN0IGJ1ZmZlciA9IGF3YWl0IHJlc3AuYXJyYXlCdWZmZXIoKTsKICAgICAgY29uc3QgY29udGVudFR5cGVIZWFkZXIgPSByZXNwLmhlYWRlcnMuZ2V0KCJDb250ZW50LVR5cGUiKTsKICAgICAgcmV0dXJuIGRlY29kZVN0cmluZyhidWZmZXIsIGNvbnRlbnRUeXBlSGVhZGVyKTsKICAgIH0pLnRoZW4oKHhtbCkgPT4gcGFyc2VYbWxTdHJpbmcoeG1sKSk7CiAgfQogIGZ1bmN0aW9uIHNldFF1ZXJ5UGFyYW1zKHVybCwgcGFyYW1zKSB7CiAgICBjb25zdCBlbmNvZGVkVXJsTWF0Y2ggPSB1cmwubWF0Y2goLyhodHRwcz8lM0ElMkYlMkZbXi9dKykkLyk7CiAgICBpZiAoZW5jb2RlZFVybE1hdGNoKSB7CiAgICAgIGNvbnN0IGVuY29kZWRVcmwgPSBlbmNvZGVkVXJsTWF0Y2hbMV07CiAgICAgIGNvbnN0IG1vZGlmaWVkVXJsID0gc2V0UXVlcnlQYXJhbXMoZGVjb2RlVVJJQ29tcG9uZW50KGVuY29kZWRVcmwpLCBwYXJhbXMpOwogICAgICByZXR1cm4gdXJsLnJlcGxhY2UoZW5jb2RlZFVybCwgZW5jb2RlVVJJQ29tcG9uZW50KG1vZGlmaWVkVXJsKSk7CiAgICB9CiAgICBjb25zdCB1cmxPYmogPSBuZXcgVVJMKHVybCk7CiAgICBjb25zdCBrZXlzID0gT2JqZWN0LmtleXMocGFyYW1zKTsKICAgIGNvbnN0IGtleXNMb3dlciA9IGtleXMubWFwKChrZXkpID0+IGtleS50b0xvd2VyQ2FzZSgpKTsKICAgIGNvbnN0IHRvRGVsZXRlID0gW107CiAgICBmb3IgKGNvbnN0IHBhcmFtIG9mIHVybE9iai5zZWFyY2hQYXJhbXMua2V5cygpKSB7CiAgICAgIGlmIChrZXlzTG93ZXIuaW5kZXhPZihwYXJhbS50b0xvd2VyQ2FzZSgpKSA+IC0xKSB7CiAgICAgICAgdG9EZWxldGUucHVzaChwYXJhbSk7CiAgICAgIH0KICAgIH0KICAgIHRvRGVsZXRlLm1hcCgocGFyYW0pID0+IHVybE9iai5zZWFyY2hQYXJhbXMuZGVsZXRlKHBhcmFtKSk7CiAgICBrZXlzLmZvckVhY2goCiAgICAgIChrZXkpID0+IHVybE9iai5zZWFyY2hQYXJhbXMuc2V0KAogICAgICAgIGtleSwKICAgICAgICBwYXJhbXNba2V5XSA9PT0gdHJ1ZSA/ICIiIDogcGFyYW1zW2tleV0KICAgICAgKQogICAgKTsKICAgIHJldHVybiB1cmxPYmoudG9TdHJpbmcoKTsKICB9CiAgY29uc3QgTGF0TG9uQ3JzTGlzdCA9IFsKICAgICJFUFNHOjQwNDYiLAogICAgLy8gUkdSREMgMjAwNQogICAgIkVQU0c6NDA3NSIsCiAgICAvLyBTUkVGOTgKICAgICJFUFNHOjQxMjAiLAogICAgLy8gR3JlZWsKICAgICJFUFNHOjQxMjIiLAogICAgLy8gQVRTNzcKICAgICJFUFNHOjQxMjQiLAogICAgLy8gUlQ5MAogICAgIkVQU0c6NDEyNiIsCiAgICAvLyBMS1M5NCAoRVRSUzg5KQogICAgIkVQU0c6NDE0OSIsCiAgICAvLyBDSDE5MDMKICAgICJFUFNHOjQxNTEiLAogICAgLy8gQ0hUUkY5NQogICAgIkVQU0c6NDE1MyIsCiAgICAvLyBSYXNzYWRpcmFuCiAgICAiRVBTRzo0MTU1IiwKICAgIC8vIERhYm9sYSAxOTgxCiAgICAiRVBTRzo0MTU3IiwKICAgIC8vIE1vdW50IERpbGxvbgogICAgIkVQU0c6NDE1OSIsCiAgICAvLyBFTEQ3OQogICAgIkVQU0c6NDE2MSIsCiAgICAvLyBQYW1wYSBkZWwgQ2FzdGlsbG8KICAgICJFUFNHOjQxNjMiLAogICAgLy8gWWVtZW4gTkdOOTYKICAgICJFUFNHOjQxNjUiLAogICAgLy8gQmlzc2F1CiAgICAiRVBTRzo0MTY3IiwKICAgIC8vIE5aR0QyMDAwCiAgICAiRVBTRzo0MTY5IiwKICAgIC8vIEFtZXJpY2FuIFNhbW9hIDE5NjIKICAgICJFUFNHOjQxNzEiLAogICAgLy8gUkdGOTMKICAgICJFUFNHOjQxNzMiLAogICAgLy8gSVJFTkVUOTUKICAgICJFUFNHOjQxNzUiLAogICAgLy8gU2llcnJhIExlb25lIDE5NjgKICAgICJFUFNHOjQxNzgiLAogICAgLy8gUHVsa292byAxOTQyKDgzKQogICAgIkVQU0c6NDE4MCIsCiAgICAvLyBFU1Q5NwogICAgIkVQU0c6NDE4MiIsCiAgICAvLyBBem9yZXMgT2NjaWRlbnRhbCAxOTM5CiAgICAiRVBTRzo0MTg0IiwKICAgIC8vIEF6b3JlcyBPcmllbnRhbCAxOTQwCiAgICAiRVBTRzo0MTg4IiwKICAgIC8vIE9TTkkgMTk1MgogICAgIkVQU0c6NDE5MCIsCiAgICAvLyBQT1NHQVIgOTgKICAgICJFUFNHOjQxOTEiLAogICAgLy8gQWxiYW5pYW4gMTk4NwogICAgIkVQU0c6NDE5NiIsCiAgICAvLyBBbW1hc3NhbGlrIDE5NTgKICAgICJFUFNHOjQxOTgiLAogICAgLy8gS291c3NlcmkKICAgICJFUFNHOjQyMDIiLAogICAgLy8gQUdENjYKICAgICJFUFNHOjQyMTAiLAogICAgLy8gQXJjIDE5NjAKICAgICJFUFNHOjQyMTEiLAogICAgLy8gQmF0YXZpYQogICAgIkVQU0c6NDIxNCIsCiAgICAvLyBCZWlqaW5nIDE5NTQKICAgICJFUFNHOjQyMjYiLAogICAgLy8gQ290ZSBkJ0l2b2lyZQogICAgIkVQU0c6NDIyOSIsCiAgICAvLyBFZ3lwdCAxOTA3CiAgICAiRVBTRzo0MjMxIiwKICAgIC8vIEVEODcKICAgICJFUFNHOjQyMzMiLAogICAgLy8gR2FuZGFqaWthIDE5NzAKICAgICJFUFNHOjQyMzYiLAogICAgLy8gSHUgVHp1IFNoYW4gMTk1MAogICAgIkVQU0c6NDIzOCIsCiAgICAvLyBJRDc0CiAgICAiRVBTRzo0MjQwIiwKICAgIC8vIEluZGlhbiAxOTc1CiAgICAiRVBTRzo0MjQyIiwKICAgIC8vIEpBRDY5CiAgICAiRVBTRzo0MjQ0IiwKICAgIC8vIEthbmRhd2FsYQogICAgIkVQU0c6NDI0NiIsCiAgICAvLyBLT0MKICAgICJFUFNHOjQyNDgiLAogICAgLy8gUFNBRDU2CiAgICAiRVBTRzo0MjUwIiwKICAgIC8vIExlaWdvbgogICAgIkVQU0c6NDI1MiIsCiAgICAvLyBMb21lCiAgICAiRVBTRzo0MjU1IiwKICAgIC8vIEhlcmF0IE5vcnRoCiAgICAiRVBTRzo0MjU4IiwKICAgIC8vIEVUUlM4OQogICAgIkVQU0c6NDI2MSIsCiAgICAvLyBNZXJjaGljaAogICAgIkVQU0c6NDI2NCIsCiAgICAvLyBNaGFzdAogICAgIkVQU0c6NDI2NyIsCiAgICAvLyBOQUQyNwogICAgIkVQU0c6NDI3MCIsCiAgICAvLyBOYWhyd2FuIDE5NjcKICAgICJFUFNHOjQyNzMiLAogICAgLy8gTkdPIDE5NDgKICAgICJFUFNHOjQyNzYiLAogICAgLy8gTlNXQyA5Wi0yCiAgICAiRVBTRzo0Mjc5IiwKICAgIC8vIE9TKFNOKTgwCiAgICAiRVBTRzo0MjgxIiwKICAgIC8vIFBhbGVzdGluZSAxOTIzCiAgICAiRVBTRzo0Mjg0IiwKICAgIC8vIFB1bGtvdm8gMTk0MgogICAgIkVQU0c6NDI4NiIsCiAgICAvLyBRYXRhciAxOTQ4CiAgICAiRVBTRzo0Mjg4IiwKICAgIC8vIExvbWEgUXVpbnRhbmEKICAgICJFUFNHOjQyOTIiLAogICAgLy8gU2FwcGVyIEhpbGwgMTk0MwogICAgIkVQU0c6NDI5NSIsCiAgICAvLyBTZXJpbmR1bmcKICAgICJFUFNHOjQyOTciLAogICAgLy8gVGFuYW5hcml2ZQogICAgIkVQU0c6NDI5OSIsCiAgICAvLyBUTTY1CiAgICAiRVBTRzo0MzAyIiwKICAgIC8vIFRyaW5pZGFkIDE5MDMKICAgICJFUFNHOjQzMjQiLAogICAgLy8gV0dTIDcyQkUKICAgICJFUFNHOjQzMjYiCiAgICAvLyBXR1MgODQKICBdOwogIGZ1bmN0aW9uIGhhc0ludmVydGVkQ29vcmRpbmF0ZXMoY3JzTmFtZSkgewogICAgcmV0dXJuIExhdExvbkNyc0xpc3QuaW5kZXhPZihzaW1wbGlmeUVwc2dVcm4oY3JzTmFtZSkpID4gLTE7CiAgfQogIGZ1bmN0aW9uIHNpbXBsaWZ5RXBzZ1VybihmdWxsQ3JzTmFtZSkgewogICAgaWYgKC9edXJuOig/OngtKT9vZ2M6ZGVmOmNyczplcHNnOi8udGVzdChmdWxsQ3JzTmFtZS50b0xvd2VyQ2FzZSgpKSkgewogICAgICBjb25zdCBjb2RlID0gLyhbMC05XSspJC8uZXhlYyhmdWxsQ3JzTmFtZSlbMV07CiAgICAgIHJldHVybiBgRVBTRzoke2NvZGV9YDsKICAgIH0KICAgIHJldHVybiBmdWxsQ3JzTmFtZTsKICB9CiAgZnVuY3Rpb24gcmVhZE9wZXJhdGlvblVybHNGcm9tQ2FwYWJpbGl0aWVzJDEoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCB1cmxzID0ge307CiAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgIkNhcGFiaWxpdHkiCiAgICApOwogICAgY29uc3QgcmVxdWVzdCA9IGZpbmRDaGlsZEVsZW1lbnQoY2FwYWJpbGl0eSwgIlJlcXVlc3QiKTsKICAgIGdldENoaWxkcmVuRWxlbWVudChyZXF1ZXN0KS5mb3JFYWNoKChvcGVyYXRpb24pID0+IHsKICAgICAgY29uc3Qgb3BlcmF0aW9uTmFtZSA9IHN0cmlwTmFtZXNwYWNlKGdldEVsZW1lbnROYW1lKG9wZXJhdGlvbikpOwogICAgICB1cmxzW29wZXJhdGlvbk5hbWVdID0gcGFyc2VPcGVyYXRpb24ob3BlcmF0aW9uKTsKICAgIH0pOwogICAgcmV0dXJuIHVybHM7CiAgfQogIGZ1bmN0aW9uIHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYykgewogICAgcmV0dXJuIGdldFJvb3RFbGVtZW50KGNhcGFiaWxpdGllc0RvYykuYXR0cmlidXRlc1sidmVyc2lvbiJdOwogIH0KICBmdW5jdGlvbiByZWFkTGF5ZXJzRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdmVyc2lvbiA9IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYyk7CiAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgIkNhcGFiaWxpdHkiCiAgICApOwogICAgcmV0dXJuIGZpbmRDaGlsZHJlbkVsZW1lbnQoY2FwYWJpbGl0eSwgIkxheWVyIikubWFwKAogICAgICAobGF5ZXJFbCkgPT4gcGFyc2VMYXllcihsYXllckVsLCB2ZXJzaW9uKQogICAgKTsKICB9CiAgZnVuY3Rpb24gcmVhZE91dHB1dEZvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzJDEoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgIkNhcGFiaWxpdHkiCiAgICApOwogICAgY29uc3QgZ2V0TWFwID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZmluZENoaWxkRWxlbWVudChjYXBhYmlsaXR5LCAiUmVxdWVzdCIpLAogICAgICAiR2V0TWFwIgogICAgKTsKICAgIGNvbnN0IG91dHB1dEZvcm1hdHMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGdldE1hcCwgIkZvcm1hdCIpLm1hcCgKICAgICAgZ2V0RWxlbWVudFRleHQKICAgICk7CiAgICByZXR1cm4gb3V0cHV0Rm9ybWF0czsKICB9CiAgZnVuY3Rpb24gcmVhZEluZm9Gb3JtYXRzRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpIHsKICAgIGNvbnN0IGNhcGFiaWxpdHkgPSBmaW5kQ2hpbGRFbGVtZW50KAogICAgICBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLAogICAgICAiQ2FwYWJpbGl0eSIKICAgICk7CiAgICBjb25zdCBnZXRGZWF0dXJlSW5mbyA9IGZpbmRDaGlsZEVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQoY2FwYWJpbGl0eSwgIlJlcXVlc3QiKSwKICAgICAgIkdldEZlYXR1cmVJbmZvIgogICAgKTsKICAgIGNvbnN0IG91dHB1dEZvcm1hdHMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGdldEZlYXR1cmVJbmZvLCAiRm9ybWF0IikubWFwKAogICAgICBnZXRFbGVtZW50VGV4dAogICAgKTsKICAgIHJldHVybiBvdXRwdXRGb3JtYXRzOwogIH0KICBmdW5jdGlvbiByZWFkRXhjZXB0aW9uRm9ybWF0c0Zyb21DYXBhYmlsaXRpZXMoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgIkNhcGFiaWxpdHkiCiAgICApOwogICAgY29uc3QgZXhjZXB0aW9uID0gZmluZENoaWxkRWxlbWVudChjYXBhYmlsaXR5LCAiRXhjZXB0aW9uIik7CiAgICBjb25zdCBleGNlcHRpb25Gb3JtYXRzID0gZmluZENoaWxkcmVuRWxlbWVudChleGNlcHRpb24sICJGb3JtYXQiKS5tYXAoCiAgICAgIGdldEVsZW1lbnRUZXh0CiAgICApOwogICAgcmV0dXJuIGV4Y2VwdGlvbkZvcm1hdHM7CiAgfQogIGZ1bmN0aW9uIHJlYWRJbmZvRnJvbUNhcGFiaWxpdGllcyQyKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3Qgc2VydmljZSA9IGZpbmRDaGlsZEVsZW1lbnQoZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwgIlNlcnZpY2UiKTsKICAgIGNvbnN0IG91dHB1dEZvcm1hdHMgPSByZWFkT3V0cHV0Rm9ybWF0c0Zyb21DYXBhYmlsaXRpZXMkMShjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3QgaW5mb0Zvcm1hdHMgPSByZWFkSW5mb0Zvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYyk7CiAgICBjb25zdCBleGNlcHRpb25Gb3JtYXRzID0gcmVhZEV4Y2VwdGlvbkZvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYyk7CiAgICBjb25zdCBrZXl3b3JkcyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIktleXdvcmRMaXN0IiksCiAgICAgICJLZXl3b3JkIgogICAgKS5tYXAoZ2V0RWxlbWVudFRleHQpLmZpbHRlcigodiwgaSwgYXJyKSA9PiBhcnIuaW5kZXhPZih2KSA9PT0gaSk7CiAgICBjb25zdCBwcm92aWRlciA9IHJlYWRQcm92aWRlckZyb21DYXBhYmlsaXRpZXMkMShjYXBhYmlsaXRpZXNEb2MpOwogICAgcmV0dXJuIHsKICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIlRpdGxlIikpLAogICAgICBuYW1lOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJOYW1lIikpLAogICAgICBhYnN0cmFjdDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiQWJzdHJhY3QiKSksCiAgICAgIG91dHB1dEZvcm1hdHMsCiAgICAgIGluZm9Gb3JtYXRzLAogICAgICBleGNlcHRpb25Gb3JtYXRzLAogICAgICBmZWVzOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJGZWVzIikpLAogICAgICBjb25zdHJhaW50czogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiQWNjZXNzQ29uc3RyYWludHMiKSksCiAgICAgIHByb3ZpZGVyLAogICAgICBrZXl3b3JkcwogICAgfTsKICB9CiAgZnVuY3Rpb24gcGFyc2VPcGVyYXRpb24ob3BlcmF0aW9uKSB7CiAgICBjb25zdCB1cmxzID0ge307CiAgICBjb25zdCBkY3BUeXBlID0gZmluZENoaWxkcmVuRWxlbWVudChvcGVyYXRpb24sICJEQ1BUeXBlIik7CiAgICBjb25zdCBodHRwID0gZGNwVHlwZS5mbGF0TWFwKChkKSA9PiBmaW5kQ2hpbGRFbGVtZW50KGQsICJIVFRQIikpOwogICAgY29uc3QgbWV0aG9kcyA9IGh0dHAuZmxhdE1hcCgoaCkgPT4gZ2V0Q2hpbGRyZW5FbGVtZW50KGgpKTsKICAgIG1ldGhvZHMuZm9yRWFjaCgobWV0aG9kKSA9PiB7CiAgICAgIGNvbnN0IG9ubGluZVJlc291cmNlID0gZmluZENoaWxkRWxlbWVudChtZXRob2QsICJPbmxpbmVSZXNvdXJjZSIpOwogICAgICBjb25zdCBtZXRob2ROYW1lID0gc3RyaXBOYW1lc3BhY2UoZ2V0RWxlbWVudE5hbWUobWV0aG9kKSk7CiAgICAgIHVybHNbbWV0aG9kTmFtZV0gPSBnZXRFbGVtZW50QXR0cmlidXRlKG9ubGluZVJlc291cmNlLCAieGxpbms6aHJlZiIpOwogICAgfSk7CiAgICByZXR1cm4gdXJsczsKICB9CiAgZnVuY3Rpb24gcGFyc2VMYXllcihsYXllckVsLCB2ZXJzaW9uLCBpbmhlcml0ZWRTcnMgPSBbXSwgaW5oZXJpdGVkU3R5bGVzID0gW10sIGluaGVyaXRlZEF0dHJpYnV0aW9uID0gbnVsbCwgaW5oZXJpdGVkQm91bmRpbmdCb3hlcyA9IG51bGwsIGluaGVyaXRlZE1heFNjYWxlRGVub20gPSBudWxsLCBpbmhlcml0ZWRNaW5TY2FsZURlbm9tID0gbnVsbCkgewogICAgY29uc3Qgc3JzVGFnID0gdmVyc2lvbiA9PT0gIjEuMy4wIiA/ICJDUlMiIDogIlNSUyI7CiAgICBjb25zdCBzcnNMaXN0ID0gZmluZENoaWxkcmVuRWxlbWVudChsYXllckVsLCBzcnNUYWcpLm1hcChnZXRFbGVtZW50VGV4dCk7CiAgICBjb25zdCBhdmFpbGFibGVDcnMgPSBzcnNMaXN0Lmxlbmd0aCA+IDAgPyBzcnNMaXN0IDogaW5oZXJpdGVkU3JzOwogICAgY29uc3QgbGF5ZXJTdHlsZXMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGxheWVyRWwsICJTdHlsZSIpLm1hcCgKICAgICAgcGFyc2VMYXllclN0eWxlCiAgICApOwogICAgY29uc3Qgc3R5bGVzID0gbGF5ZXJTdHlsZXMubGVuZ3RoID4gMCA/IGxheWVyU3R5bGVzIDogaW5oZXJpdGVkU3R5bGVzOwogICAgZnVuY3Rpb24gcGFyc2VCQm94MihiYm94RWwpIHsKICAgICAgY29uc3Qgc3JzID0gZ2V0RWxlbWVudEF0dHJpYnV0ZShiYm94RWwsIHNyc1RhZyk7CiAgICAgIGNvbnN0IGF0dHJzID0gaGFzSW52ZXJ0ZWRDb29yZGluYXRlcyhzcnMpICYmIHZlcnNpb24gPT09ICIxLjMuMCIgPyBbIm1pbnkiLCAibWlueCIsICJtYXh5IiwgIm1heHgiXSA6IFsibWlueCIsICJtaW55IiwgIm1heHgiLCAibWF4eSJdOwogICAgICByZXR1cm4gYXR0cnMubWFwKChuYW1lKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGJib3hFbCwgbmFtZSkpOwogICAgfQogICAgZnVuY3Rpb24gcGFyc2VFeEdlb2dyYXBoaWNCb3VuZGluZ0JveChiYm94RWwpIHsKICAgICAgcmV0dXJuIFsKICAgICAgICAid2VzdEJvdW5kTG9uZ2l0dWRlIiwKICAgICAgICAic291dGhCb3VuZExhdGl0dWRlIiwKICAgICAgICAiZWFzdEJvdW5kTG9uZ2l0dWRlIiwKICAgICAgICAibm9ydGhCb3VuZExhdGl0dWRlIgogICAgICBdLm1hcCgobmFtZSkgPT4gZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChiYm94RWwsIG5hbWUpKSk7CiAgICB9CiAgICBmdW5jdGlvbiBwYXJzZUxhdExvbkJvdW5kaW5nQm94KGJib3hFbCkgewogICAgICByZXR1cm4gWyJtaW54IiwgIm1pbnkiLCAibWF4eCIsICJtYXh5Il0ubWFwKAogICAgICAgIChuYW1lKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGJib3hFbCwgbmFtZSkKICAgICAgKTsKICAgIH0KICAgIGZ1bmN0aW9uIHBhcnNlU2NhbGVIaW50VmFsdWUodGV4dFZhbHVlLCBkZWZhdWx0VmFsdWUpIHsKICAgICAgaWYgKHRleHRWYWx1ZSA9PT0gIiIpIHsKICAgICAgICByZXR1cm4gZGVmYXVsdFZhbHVlOwogICAgICB9CiAgICAgIHJldHVybiBNYXRoLnNxcnQoMC41ICogcGFyc2VGbG9hdCh0ZXh0VmFsdWUpICoqIDIpIC8gMjhlLTU7CiAgICB9CiAgICBmdW5jdGlvbiBwYXJzZVNjYWxlSGludCgpIHsKICAgICAgY29uc3Qgc2NhbGVIaW50ID0gZmluZENoaWxkRWxlbWVudChsYXllckVsLCAiU2NhbGVIaW50Iik7CiAgICAgIGlmICghc2NhbGVIaW50KSB7CiAgICAgICAgcmV0dXJuIFtpbmhlcml0ZWRNaW5TY2FsZURlbm9tLCBpbmhlcml0ZWRNYXhTY2FsZURlbm9tXTsKICAgICAgfQogICAgICBjb25zdCBtaW4gPSBnZXRFbGVtZW50QXR0cmlidXRlKHNjYWxlSGludCwgIm1pbiIpOwogICAgICBjb25zdCBtYXggPSBnZXRFbGVtZW50QXR0cmlidXRlKHNjYWxlSGludCwgIm1heCIpOwogICAgICByZXR1cm4gWwogICAgICAgIHBhcnNlU2NhbGVIaW50VmFsdWUobWluLCBpbmhlcml0ZWRNaW5TY2FsZURlbm9tKSwKICAgICAgICBwYXJzZVNjYWxlSGludFZhbHVlKG1heCwgaW5oZXJpdGVkTWF4U2NhbGVEZW5vbSkKICAgICAgXTsKICAgIH0KICAgIGZ1bmN0aW9uIHBhcnNlU2NhbGVEZW5vbWluYXRvcihuYW1lLCBpbmhlcml0ZWRWYWx1ZSkgewogICAgICBjb25zdCB0ZXh0VmFsdWUgPSBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGxheWVyRWwsIG5hbWUpKTsKICAgICAgcmV0dXJuIHRleHRWYWx1ZSA9PT0gIiIgPyBpbmhlcml0ZWRWYWx1ZSA6IHBhcnNlRmxvYXQodGV4dFZhbHVlKTsKICAgIH0KICAgIGNvbnN0IGF0dHJpYnV0aW9uRWwgPSBmaW5kQ2hpbGRFbGVtZW50KGxheWVyRWwsICJBdHRyaWJ1dGlvbiIpOwogICAgY29uc3QgYXR0cmlidXRpb24gPSBhdHRyaWJ1dGlvbkVsICE9PSBudWxsID8gcGFyc2VMYXllckF0dHJpYnV0aW9uKGF0dHJpYnV0aW9uRWwpIDogaW5oZXJpdGVkQXR0cmlidXRpb247CiAgICBjb25zdCBsYXRMb25CYm94RWwgPSB2ZXJzaW9uID09PSAiMS4zLjAiID8gZmluZENoaWxkRWxlbWVudChsYXllckVsLCAiRVhfR2VvZ3JhcGhpY0JvdW5kaW5nQm94IikgOiBmaW5kQ2hpbGRFbGVtZW50KGxheWVyRWwsICJMYXRMb25Cb3VuZGluZ0JveCIpOwogICAgY29uc3QgYmFzZUJvdW5kaW5nQm94ID0ge307CiAgICBpZiAobGF0TG9uQmJveEVsKSB7CiAgICAgIGJhc2VCb3VuZGluZ0JveFsiRVBTRzo0MzI2Il0gPSB2ZXJzaW9uID09PSAiMS4zLjAiID8gcGFyc2VFeEdlb2dyYXBoaWNCb3VuZGluZ0JveChsYXRMb25CYm94RWwpIDogcGFyc2VMYXRMb25Cb3VuZGluZ0JveChsYXRMb25CYm94RWwpOwogICAgfQogICAgbGV0IGJvdW5kaW5nQm94ZXMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGxheWVyRWwsICJCb3VuZGluZ0JveCIpLnJlZHVjZSgKICAgICAgKHByZXYsIGJib3hFbCkgPT4gKHsKICAgICAgICAuLi5wcmV2LAogICAgICAgIFtnZXRFbGVtZW50QXR0cmlidXRlKGJib3hFbCwgc3JzVGFnKV06IHBhcnNlQkJveDIoYmJveEVsKQogICAgICB9KSwKICAgICAgYmFzZUJvdW5kaW5nQm94CiAgICApOwogICAgYm91bmRpbmdCb3hlcyA9IE9iamVjdC5rZXlzKGJvdW5kaW5nQm94ZXMpLmxlbmd0aCA+IDAgfHwgaW5oZXJpdGVkQm91bmRpbmdCb3hlcyA9PT0gbnVsbCA/IGJvdW5kaW5nQm94ZXMgOiBpbmhlcml0ZWRCb3VuZGluZ0JveGVzOwogICAgY29uc3QgcXVlcnlhYmxlID0gbGF5ZXJFbC5hdHRyaWJ1dGVzLnF1ZXJ5YWJsZSA9PT0gIjEiIHx8IGxheWVyRWwuYXR0cmlidXRlcy5xdWVyeWFibGUgPT09ICJ0cnVlIiA/IHRydWUgOiBmYWxzZTsKICAgIGNvbnN0IG9wYXF1ZSA9IGxheWVyRWwuYXR0cmlidXRlcy5vcGFxdWUgPT09ICIxIiB8fCBsYXllckVsLmF0dHJpYnV0ZXMub3BhcXVlID09PSAidHJ1ZSIgPyB0cnVlIDogZmFsc2U7CiAgICBjb25zdCBrZXl3b3JkcyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQobGF5ZXJFbCwgIktleXdvcmRMaXN0IiksCiAgICAgICJLZXl3b3JkIgogICAgKS5tYXAoZ2V0RWxlbWVudFRleHQpLmZpbHRlcigodiwgaSwgYXJyKSA9PiBhcnIuaW5kZXhPZih2KSA9PT0gaSk7CiAgICBsZXQgbWluU2NhbGVEZW5vbWluYXRvciwgbWF4U2NhbGVEZW5vbWluYXRvcjsKICAgIGlmICh2ZXJzaW9uID09PSAiMS4zLjAiKSB7CiAgICAgIG1pblNjYWxlRGVub21pbmF0b3IgPSBwYXJzZVNjYWxlRGVub21pbmF0b3IoCiAgICAgICAgIk1pblNjYWxlRGVub21pbmF0b3IiLAogICAgICAgIGluaGVyaXRlZE1pblNjYWxlRGVub20KICAgICAgKTsKICAgICAgbWF4U2NhbGVEZW5vbWluYXRvciA9IHBhcnNlU2NhbGVEZW5vbWluYXRvcigKICAgICAgICAiTWF4U2NhbGVEZW5vbWluYXRvciIsCiAgICAgICAgaW5oZXJpdGVkTWF4U2NhbGVEZW5vbQogICAgICApOwogICAgfSBlbHNlIHsKICAgICAgW21pblNjYWxlRGVub21pbmF0b3IsIG1heFNjYWxlRGVub21pbmF0b3JdID0gcGFyc2VTY2FsZUhpbnQoKTsKICAgIH0KICAgIGNvbnN0IG1ldGFkYXRhID0gZmluZENoaWxkcmVuRWxlbWVudChsYXllckVsLCAiTWV0YWRhdGFVUkwiKS5tYXAoCiAgICAgIChtZXRhZGF0YVVybEVsKSA9PiAoewogICAgICAgIHR5cGU6IGdldEVsZW1lbnRBdHRyaWJ1dGUobWV0YWRhdGFVcmxFbCwgInR5cGUiKSwKICAgICAgICBmb3JtYXQ6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQobWV0YWRhdGFVcmxFbCwgIkZvcm1hdCIpKSwKICAgICAgICB1cmw6IGdldEVsZW1lbnRBdHRyaWJ1dGUoCiAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KG1ldGFkYXRhVXJsRWwsICJPbmxpbmVSZXNvdXJjZSIpLAogICAgICAgICAgInhsaW5rOmhyZWYiCiAgICAgICAgKQogICAgICB9KQogICAgKTsKICAgIGNvbnN0IGNoaWxkcmVuID0gZmluZENoaWxkcmVuRWxlbWVudChsYXllckVsLCAiTGF5ZXIiKS5tYXAoCiAgICAgIChsYXllcikgPT4gcGFyc2VMYXllcigKICAgICAgICBsYXllciwKICAgICAgICB2ZXJzaW9uLAogICAgICAgIGF2YWlsYWJsZUNycywKICAgICAgICBzdHlsZXMsCiAgICAgICAgYXR0cmlidXRpb24sCiAgICAgICAgYm91bmRpbmdCb3hlcywKICAgICAgICBtYXhTY2FsZURlbm9taW5hdG9yLAogICAgICAgIG1pblNjYWxlRGVub21pbmF0b3IKICAgICAgKQogICAgKTsKICAgIHJldHVybiB7CiAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQobGF5ZXJFbCwgIk5hbWUiKSksCiAgICAgIHRpdGxlOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGxheWVyRWwsICJUaXRsZSIpKSwKICAgICAgYWJzdHJhY3Q6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQobGF5ZXJFbCwgIkFic3RyYWN0IikpLAogICAgICBhdmFpbGFibGVDcnMsCiAgICAgIHN0eWxlcywKICAgICAgYXR0cmlidXRpb24sCiAgICAgIGJvdW5kaW5nQm94ZXMsCiAgICAgIGtleXdvcmRzLAogICAgICBxdWVyeWFibGUsCiAgICAgIG9wYXF1ZSwKICAgICAgLi4ubWluU2NhbGVEZW5vbWluYXRvciAhPT0gbnVsbCA/IHsgbWluU2NhbGVEZW5vbWluYXRvciB9IDoge30sCiAgICAgIC4uLm1heFNjYWxlRGVub21pbmF0b3IgIT09IG51bGwgPyB7IG1heFNjYWxlRGVub21pbmF0b3IgfSA6IHt9LAogICAgICAuLi5tZXRhZGF0YS5sZW5ndGggJiYgeyBtZXRhZGF0YSB9LAogICAgICAuLi5jaGlsZHJlbi5sZW5ndGggJiYgeyBjaGlsZHJlbiB9CiAgICB9OwogIH0KICBmdW5jdGlvbiBwYXJzZUxheWVyU3R5bGUoc3R5bGVFbCkgewogICAgY29uc3QgbGVnZW5kVXJsID0gZ2V0RWxlbWVudEF0dHJpYnV0ZSgKICAgICAgZmluZENoaWxkRWxlbWVudChmaW5kQ2hpbGRFbGVtZW50KHN0eWxlRWwsICJMZWdlbmRVUkwiKSwgIk9ubGluZVJlc291cmNlIiksCiAgICAgICJ4bGluazpocmVmIgogICAgKTsKICAgIGNvbnN0IGFic3RyYWN0ID0gZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzdHlsZUVsLCAiQWJzdHJhY3QiKSk7CiAgICByZXR1cm4gewogICAgICBuYW1lOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHN0eWxlRWwsICJOYW1lIikpLAogICAgICB0aXRsZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzdHlsZUVsLCAiVGl0bGUiKSksCiAgICAgIC4uLmFic3RyYWN0ICYmIHsgYWJzdHJhY3QgfSwKICAgICAgLi4ubGVnZW5kVXJsICYmIHsgbGVnZW5kVXJsIH0KICAgIH07CiAgfQogIGZ1bmN0aW9uIHBhcnNlTGF5ZXJBdHRyaWJ1dGlvbihhdHRyaWJ1dGlvbkVsKSB7CiAgICBjb25zdCBsb2dvVXJsID0gZ2V0RWxlbWVudEF0dHJpYnV0ZSgKICAgICAgZmluZENoaWxkRWxlbWVudCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGF0dHJpYnV0aW9uRWwsICJMb2dvVVJMIiksCiAgICAgICAgIk9ubGluZVJlc291cmNlIgogICAgICApLAogICAgICAieGxpbms6aHJlZiIKICAgICk7CiAgICBjb25zdCB1cmwgPSBnZXRFbGVtZW50QXR0cmlidXRlKAogICAgICBmaW5kQ2hpbGRFbGVtZW50KGF0dHJpYnV0aW9uRWwsICJPbmxpbmVSZXNvdXJjZSIpLAogICAgICAieGxpbms6aHJlZiIKICAgICk7CiAgICBjb25zdCB0aXRsZSA9IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoYXR0cmlidXRpb25FbCwgIlRpdGxlIikpOwogICAgcmV0dXJuIHsKICAgICAgLi4udGl0bGUgJiYgeyB0aXRsZSB9LAogICAgICAuLi51cmwgJiYgeyB1cmwgfSwKICAgICAgLi4ubG9nb1VybCAmJiB7IGxvZ29VcmwgfQogICAgfTsKICB9CiAgZnVuY3Rpb24gcmVhZFByb3ZpZGVyRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3Qgc2VydmljZSA9IGZpbmRDaGlsZEVsZW1lbnQoZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKSwgIlNlcnZpY2UiKTsKICAgIGNvbnN0IGNvbnRhY3RJbmZvcm1hdGlvbiA9IGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIkNvbnRhY3RJbmZvcm1hdGlvbiIpOwogICAgY29uc3QgY29udGFjdFBlcnNvblByaW1hcnkgPSBmaW5kQ2hpbGRFbGVtZW50KAogICAgICBjb250YWN0SW5mb3JtYXRpb24sCiAgICAgICJDb250YWN0UGVyc29uUHJpbWFyeSIKICAgICk7CiAgICBjb25zdCBhZGRyZXNzID0gZmluZENoaWxkRWxlbWVudChjb250YWN0SW5mb3JtYXRpb24sICJDb250YWN0QWRkcmVzcyIpOwogICAgcmV0dXJuIHsKICAgICAgY29udGFjdDogewogICAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgZmluZENoaWxkRWxlbWVudChjb250YWN0UGVyc29uUHJpbWFyeSwgIkNvbnRhY3RQZXJzb24iKQogICAgICAgICksCiAgICAgICAgb3JnYW5pemF0aW9uOiBnZXRFbGVtZW50VGV4dCgKICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoY29udGFjdFBlcnNvblByaW1hcnksICJDb250YWN0T3JnYW5pemF0aW9uIikKICAgICAgICApLAogICAgICAgIHBvc2l0aW9uOiBnZXRFbGVtZW50VGV4dCgKICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoY29udGFjdEluZm9ybWF0aW9uLCAiQ29udGFjdFBvc2l0aW9uIikKICAgICAgICApLAogICAgICAgIHBob25lOiBnZXRFbGVtZW50VGV4dCgKICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoY29udGFjdEluZm9ybWF0aW9uLCAiQ29udGFjdFZvaWNlVGVsZXBob25lIikKICAgICAgICApLAogICAgICAgIGZheDogZ2V0RWxlbWVudFRleHQoCiAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGNvbnRhY3RJbmZvcm1hdGlvbiwgIkNvbnRhY3RGYWNzaW1pbGVUZWxlcGhvbmUiKQogICAgICAgICksCiAgICAgICAgYWRkcmVzczogewogICAgICAgICAgZGVsaXZlcnlQb2ludDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiQWRkcmVzcyIpKSwKICAgICAgICAgIGNpdHk6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoYWRkcmVzcywgIkNpdHkiKSksCiAgICAgICAgICBhZG1pbmlzdHJhdGl2ZUFyZWE6IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGFkZHJlc3MsICJTdGF0ZU9yUHJvdmluY2UiKQogICAgICAgICAgKSwKICAgICAgICAgIHBvc3RhbENvZGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoYWRkcmVzcywgIlBvc3RDb2RlIikpLAogICAgICAgICAgY291bnRyeTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiQ291bnRyeSIpKQogICAgICAgIH0sCiAgICAgICAgZW1haWw6IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgZmluZENoaWxkRWxlbWVudChjb250YWN0SW5mb3JtYXRpb24sICJDb250YWN0RWxlY3Ryb25pY01haWxBZGRyZXNzIikKICAgICAgICApCiAgICAgIH0KICAgIH07CiAgfQogIGZ1bmN0aW9uIHJlYWRQcm92aWRlckZyb21DYXBhYmlsaXRpZXMoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCBzZXJ2aWNlUHJvdmlkZXIgPSBmaW5kQ2hpbGRFbGVtZW50KAogICAgICBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLAogICAgICAiU2VydmljZVByb3ZpZGVyIgogICAgKTsKICAgIGNvbnN0IHNlcnZpY2VDb250YWN0ID0gZmluZENoaWxkRWxlbWVudChzZXJ2aWNlUHJvdmlkZXIsICJTZXJ2aWNlQ29udGFjdCIpOwogICAgY29uc3QgY29udGFjdEluZm8gPSBmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2VDb250YWN0LCAiQ29udGFjdEluZm8iKTsKICAgIGNvbnN0IHBob25lID0gZmluZENoaWxkRWxlbWVudChjb250YWN0SW5mbywgIlBob25lIik7CiAgICBjb25zdCBhZGRyZXNzID0gZmluZENoaWxkRWxlbWVudChjb250YWN0SW5mbywgIkFkZHJlc3MiKTsKICAgIHJldHVybiB7CiAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZVByb3ZpZGVyLCAiUHJvdmlkZXJOYW1lIikpLAogICAgICBzaXRlOiBnZXRFbGVtZW50QXR0cmlidXRlKAogICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZVByb3ZpZGVyLCAiUHJvdmlkZXJTaXRlIiksCiAgICAgICAgInhsaW5rOmhyZWYiCiAgICAgICksCiAgICAgIGNvbnRhY3Q6IHsKICAgICAgICBuYW1lOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2VDb250YWN0LCAiSW5kaXZpZHVhbE5hbWUiKSksCiAgICAgICAgcG9zaXRpb246IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgZmluZENoaWxkRWxlbWVudChzZXJ2aWNlQ29udGFjdCwgIlBvc2l0aW9uTmFtZSIpCiAgICAgICAgKSwKICAgICAgICBwaG9uZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChwaG9uZSwgIlZvaWNlIikpLAogICAgICAgIGZheDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChwaG9uZSwgIkZhY3NpbWlsZSIpKSwKICAgICAgICBhZGRyZXNzOiB7CiAgICAgICAgICBkZWxpdmVyeVBvaW50OiBnZXRFbGVtZW50VGV4dCgKICAgICAgICAgICAgZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiRGVsaXZlcnlQb2ludCIpCiAgICAgICAgICApLAogICAgICAgICAgY2l0eTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiQ2l0eSIpKSwKICAgICAgICAgIGFkbWluaXN0cmF0aXZlQXJlYTogZ2V0RWxlbWVudFRleHQoCiAgICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoYWRkcmVzcywgIkFkbWluaXN0cmF0aXZlQXJlYSIpCiAgICAgICAgICApLAogICAgICAgICAgcG9zdGFsQ29kZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChhZGRyZXNzLCAiUG9zdGFsQ29kZSIpKSwKICAgICAgICAgIGNvdW50cnk6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoYWRkcmVzcywgIkNvdW50cnkiKSkKICAgICAgICB9LAogICAgICAgIGVtYWlsOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGFkZHJlc3MsICJFbGVjdHJvbmljTWFpbEFkZHJlc3MiKSkKICAgICAgfQogICAgfTsKICB9CiAgZnVuY3Rpb24gcmVhZE9wZXJhdGlvblVybHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdXJscyA9IHt9OwogICAgY29uc3QgY2FwYWJpbGl0aWVzID0gZ2V0Um9vdEVsZW1lbnQoY2FwYWJpbGl0aWVzRG9jKTsKICAgIGNvbnN0IG9wZXJhdGlvbnNNZXRhZGF0YSA9IGZpbmRDaGlsZEVsZW1lbnQoCiAgICAgIGNhcGFiaWxpdGllcywKICAgICAgIk9wZXJhdGlvbnNNZXRhZGF0YSIKICAgICk7CiAgICBpZiAob3BlcmF0aW9uc01ldGFkYXRhKSB7CiAgICAgIGZpbmRDaGlsZHJlbkVsZW1lbnQob3BlcmF0aW9uc01ldGFkYXRhLCAiT3BlcmF0aW9uIikuZm9yRWFjaCgKICAgICAgICAob3BlcmF0aW9uKSA9PiB7CiAgICAgICAgICBjb25zdCBuYW1lID0gZ2V0RWxlbWVudEF0dHJpYnV0ZShvcGVyYXRpb24sICJuYW1lIik7CiAgICAgICAgICB1cmxzW25hbWVdID0gcGFyc2VPcGVyYXRpb24xMTAob3BlcmF0aW9uKTsKICAgICAgICB9CiAgICAgICk7CiAgICB9IGVsc2UgewogICAgICBjb25zdCBjYXBhYmlsaXR5ID0gZmluZENoaWxkRWxlbWVudChjYXBhYmlsaXRpZXMsICJDYXBhYmlsaXR5Iik7CiAgICAgIGNvbnN0IHJlcXVlc3QgPSBmaW5kQ2hpbGRFbGVtZW50KGNhcGFiaWxpdHksICJSZXF1ZXN0Iik7CiAgICAgIGdldENoaWxkcmVuRWxlbWVudChyZXF1ZXN0KS5mb3JFYWNoKChvcGVyYXRpb24pID0+IHsKICAgICAgICBjb25zdCBuYW1lID0gc3RyaXBOYW1lc3BhY2UoZ2V0RWxlbWVudE5hbWUob3BlcmF0aW9uKSk7CiAgICAgICAgdXJsc1tuYW1lXSA9IHBhcnNlT3BlcmF0aW9uMTAwKG9wZXJhdGlvbik7CiAgICAgIH0pOwogICAgfQogICAgcmV0dXJuIHVybHM7CiAgfQogIGZ1bmN0aW9uIHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpIHsKICAgIHJldHVybiBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLmF0dHJpYnV0ZXNbInZlcnNpb24iXTsKICB9CiAgZnVuY3Rpb24gcmVhZE91dHB1dEZvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdmVyc2lvbiA9IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgbGV0IG91dHB1dEZvcm1hdHM7CiAgICBpZiAodmVyc2lvbi5zdGFydHNXaXRoKCIxLjAiKSkgewogICAgICBjb25zdCBnZXRGZWF0dXJlID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KAogICAgICAgICAgZmluZENoaWxkRWxlbWVudChnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLCAiQ2FwYWJpbGl0eSIpLAogICAgICAgICAgIlJlcXVlc3QiCiAgICAgICAgKSwKICAgICAgICAiR2V0RmVhdHVyZSIKICAgICAgKTsKICAgICAgb3V0cHV0Rm9ybWF0cyA9IGdldENoaWxkcmVuRWxlbWVudCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGdldEZlYXR1cmUsICJSZXN1bHRGb3JtYXQiKQogICAgICApLm1hcChnZXRFbGVtZW50TmFtZSk7CiAgICB9IGVsc2UgewogICAgICBjb25zdCBvcGVyYXRpb25zID0gZmluZENoaWxkRWxlbWVudCgKICAgICAgICBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLAogICAgICAgICJPcGVyYXRpb25zTWV0YWRhdGEiCiAgICAgICk7CiAgICAgIGNvbnN0IGdldEZlYXR1cmUgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KG9wZXJhdGlvbnMsICJPcGVyYXRpb24iKS5maW5kKAogICAgICAgIChlbCkgPT4gZ2V0RWxlbWVudEF0dHJpYnV0ZShlbCwgIm5hbWUiKSA9PT0gIkdldEZlYXR1cmUiCiAgICAgICk7CiAgICAgIGNvbnN0IHBhcmFtZXRlciA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoZ2V0RmVhdHVyZSwgIlBhcmFtZXRlciIpLmZpbmQoCiAgICAgICAgKGVsKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGVsLCAibmFtZSIpID09PSAib3V0cHV0Rm9ybWF0IgogICAgICApOwogICAgICBvdXRwdXRGb3JtYXRzID0gZmluZENoaWxkcmVuRWxlbWVudChwYXJhbWV0ZXIsICJWYWx1ZSIsIHRydWUpLm1hcCgKICAgICAgICBnZXRFbGVtZW50VGV4dAogICAgICApOwogICAgfQogICAgcmV0dXJuIG91dHB1dEZvcm1hdHM7CiAgfQogIGZ1bmN0aW9uIHJlYWRJbmZvRnJvbUNhcGFiaWxpdGllcyQxKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdmVyc2lvbiA9IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3Qgc2VydmljZVRhZyA9IHZlcnNpb24uc3RhcnRzV2l0aCgiMS4wIikgPyAiU2VydmljZSIgOiAiU2VydmljZUlkZW50aWZpY2F0aW9uIjsKICAgIGNvbnN0IG5hbWVUYWcgPSB2ZXJzaW9uLnN0YXJ0c1dpdGgoIjEuMCIpID8gIk5hbWUiIDogIlNlcnZpY2VUeXBlIjsKICAgIGNvbnN0IHNlcnZpY2UgPSBmaW5kQ2hpbGRFbGVtZW50KGdldFJvb3RFbGVtZW50KGNhcGFiaWxpdGllc0RvYyksIHNlcnZpY2VUYWcpOwogICAgbGV0IGtleXdvcmRzOwogICAgaWYgKHZlcnNpb24uc3RhcnRzV2l0aCgiMS4wIikpIHsKICAgICAga2V5d29yZHMgPSBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJLZXl3b3JkcyIpKS5zcGxpdCgiLCIpLm1hcCgoa2V5d29yZCkgPT4ga2V5d29yZC50cmltKCkpOwogICAgfSBlbHNlIHsKICAgICAga2V5d29yZHMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KAogICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIktleXdvcmRzIiksCiAgICAgICAgIktleXdvcmQiCiAgICAgICkubWFwKGdldEVsZW1lbnRUZXh0KTsKICAgIH0KICAgIGxldCBwcm92aWRlcjsKICAgIGlmICh2ZXJzaW9uICE9PSAiMS4wLjAiKSB7CiAgICAgIHByb3ZpZGVyID0gcmVhZFByb3ZpZGVyRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgfQogICAgcmV0dXJuIHsKICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIlRpdGxlIikpLAogICAgICBuYW1lOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsIG5hbWVUYWcpKSwKICAgICAgYWJzdHJhY3Q6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIkFic3RyYWN0IikpLAogICAgICBmZWVzOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJGZWVzIikpLAogICAgICBjb25zdHJhaW50czogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiQWNjZXNzQ29uc3RyYWludHMiKSksCiAgICAgIGtleXdvcmRzLAogICAgICBwcm92aWRlciwKICAgICAgb3V0cHV0Rm9ybWF0czogcmVhZE91dHB1dEZvcm1hdHNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYykKICAgIH07CiAgfQogIGZ1bmN0aW9uIHJlYWRGZWF0dXJlVHlwZXNGcm9tQ2FwYWJpbGl0aWVzKGNhcGFiaWxpdGllc0RvYykgewogICAgY29uc3QgdmVyc2lvbiA9IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3Qgb3V0cHV0Rm9ybWF0cyA9IHJlYWRPdXRwdXRGb3JtYXRzRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3QgY2FwYWJpbGl0eSA9IGZpbmRDaGlsZEVsZW1lbnQoCiAgICAgIGdldFJvb3RFbGVtZW50KGNhcGFiaWxpdGllc0RvYyksCiAgICAgICJGZWF0dXJlVHlwZUxpc3QiCiAgICApOwogICAgcmV0dXJuIGZpbmRDaGlsZHJlbkVsZW1lbnQoY2FwYWJpbGl0eSwgIkZlYXR1cmVUeXBlIikubWFwKAogICAgICAoZmVhdHVyZVR5cGVFbCkgPT4gcGFyc2VGZWF0dXJlVHlwZShmZWF0dXJlVHlwZUVsLCB2ZXJzaW9uLCBvdXRwdXRGb3JtYXRzKQogICAgKTsKICB9CiAgZnVuY3Rpb24gcGFyc2VPcGVyYXRpb24xMDAob3BlcmF0aW9uKSB7CiAgICBjb25zdCB1cmxzID0ge307CiAgICBjb25zdCBkY3BUeXBlID0gZmluZENoaWxkcmVuRWxlbWVudChvcGVyYXRpb24sICJEQ1BUeXBlIik7CiAgICBjb25zdCBodHRwID0gZGNwVHlwZS5mbGF0TWFwKChkKSA9PiBmaW5kQ2hpbGRyZW5FbGVtZW50KGQsICJIVFRQIikpOwogICAgY29uc3QgbWV0aG9kcyA9IGh0dHAuZmxhdE1hcCgoaCkgPT4gZ2V0Q2hpbGRyZW5FbGVtZW50KGgpKTsKICAgIG1ldGhvZHMuZm9yRWFjaCgobWV0aG9kKSA9PiB7CiAgICAgIGNvbnN0IG1ldGhvZE5hbWUgPSBzdHJpcE5hbWVzcGFjZShnZXRFbGVtZW50TmFtZShtZXRob2QpKTsKICAgICAgdXJsc1ttZXRob2ROYW1lXSA9IGdldEVsZW1lbnRBdHRyaWJ1dGUobWV0aG9kLCAib25saW5lUmVzb3VyY2UiKTsKICAgIH0pOwogICAgcmV0dXJuIHVybHM7CiAgfQogIGZ1bmN0aW9uIHBhcnNlT3BlcmF0aW9uMTEwKG9wZXJhdGlvbikgewogICAgY29uc3QgdXJscyA9IHt9OwogICAgY29uc3QgZGNwVHlwZSA9IGZpbmRDaGlsZHJlbkVsZW1lbnQob3BlcmF0aW9uLCAiRENQIik7CiAgICBjb25zdCBodHRwID0gZGNwVHlwZS5mbGF0TWFwKChkKSA9PiBmaW5kQ2hpbGRFbGVtZW50KGQsICJIVFRQIikpOwogICAgY29uc3QgbWV0aG9kcyA9IGh0dHAuZmxhdE1hcCgoaCkgPT4gZ2V0Q2hpbGRyZW5FbGVtZW50KGgpKTsKICAgIG1ldGhvZHMuZm9yRWFjaCgobWV0aG9kKSA9PiB7CiAgICAgIGNvbnN0IG1ldGhvZE5hbWUgPSBzdHJpcE5hbWVzcGFjZShnZXRFbGVtZW50TmFtZShtZXRob2QpKTsKICAgICAgdXJsc1ttZXRob2ROYW1lXSA9IGdldEVsZW1lbnRBdHRyaWJ1dGUobWV0aG9kLCAieGxpbms6aHJlZiIpOwogICAgfSk7CiAgICByZXR1cm4gdXJsczsKICB9CiAgZnVuY3Rpb24gcGFyc2VGZWF0dXJlVHlwZShmZWF0dXJlVHlwZUVsLCBzZXJ2aWNlVmVyc2lvbiwgZGVmYXVsdE91dHB1dEZvcm1hdHMpIHsKICAgIGNvbnN0IHNyc1RhZyA9IHNlcnZpY2VWZXJzaW9uLnN0YXJ0c1dpdGgoIjIuIikgPyAiQ1JTIiA6ICJTUlMiOwogICAgY29uc3QgZGVmYXVsdFNyc1RhZyA9IHNlcnZpY2VWZXJzaW9uLnN0YXJ0c1dpdGgoIjEuMCIpID8gIlNSUyIgOiBgRGVmYXVsdCR7c3JzVGFnfWA7CiAgICBmdW5jdGlvbiBwYXJzZUJCb3gxMDAoKSB7CiAgICAgIGNvbnN0IGJib3hFbCA9IGZpbmRDaGlsZEVsZW1lbnQoZmVhdHVyZVR5cGVFbCwgIkxhdExvbmdCb3VuZGluZ0JveCIpOwogICAgICByZXR1cm4gWyJtaW54IiwgIm1pbnkiLCAibWF4eCIsICJtYXh5Il0ubWFwKChuYW1lKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGJib3hFbCwgbmFtZSkpLm1hcChwYXJzZUZsb2F0KTsKICAgIH0KICAgIGZ1bmN0aW9uIHBhcnNlQkJveDIoKSB7CiAgICAgIGNvbnN0IGJib3hFbCA9IGZpbmRDaGlsZEVsZW1lbnQoZmVhdHVyZVR5cGVFbCwgIldHUzg0Qm91bmRpbmdCb3giKTsKICAgICAgcmV0dXJuIFsiTG93ZXJDb3JuZXIiLCAiVXBwZXJDb3JuZXIiXS5tYXAoKGVsTmFtZSkgPT4gZmluZENoaWxkRWxlbWVudChiYm94RWwsIGVsTmFtZSkpLm1hcCgoY29ybmVyRWwpID0+IGdldEVsZW1lbnRUZXh0KGNvcm5lckVsKS5zcGxpdCgiICIpKS5yZWR1Y2UoKHByZXYsIGN1cnIpID0+IFsuLi5wcmV2LCAuLi5jdXJyXSkubWFwKHBhcnNlRmxvYXQpOwogICAgfQogICAgY29uc3Qgb3RoZXJDcnMgPSBzZXJ2aWNlVmVyc2lvbi5zdGFydHNXaXRoKCIxLjAiKSA/IFtdIDogZmluZENoaWxkcmVuRWxlbWVudChmZWF0dXJlVHlwZUVsLCBgT3RoZXIke3Nyc1RhZ31gKS5tYXAoZ2V0RWxlbWVudFRleHQpLm1hcChzaW1wbGlmeUVwc2dVcm4pOwogICAgY29uc3Qgb3V0cHV0Rm9ybWF0cyA9IHNlcnZpY2VWZXJzaW9uLnN0YXJ0c1dpdGgoIjEuMCIpID8gW10gOiBmaW5kQ2hpbGRyZW5FbGVtZW50KAogICAgICBmaW5kQ2hpbGRFbGVtZW50KGZlYXR1cmVUeXBlRWwsICJPdXRwdXRGb3JtYXRzIiksCiAgICAgICJGb3JtYXQiCiAgICApLm1hcChnZXRFbGVtZW50VGV4dCk7CiAgICBjb25zdCBrZXl3b3JkcyA9IHNlcnZpY2VWZXJzaW9uLnN0YXJ0c1dpdGgoIjEuMCIpID8gZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiS2V5d29yZHMiKSkuc3BsaXQoIiwiKS5tYXAoKGtleXdvcmQpID0+IGtleXdvcmQudHJpbSgpKSA6IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQoZmVhdHVyZVR5cGVFbCwgIktleXdvcmRzIiksCiAgICAgICJLZXl3b3JkIgogICAgKS5tYXAoZ2V0RWxlbWVudFRleHQpLmZpbHRlcigodiwgaSwgYXJyKSA9PiBhcnIuaW5kZXhPZih2KSA9PT0gaSk7CiAgICBjb25zdCBtZXRhZGF0YSA9IHNlcnZpY2VWZXJzaW9uID09PSAiMi4wLjAiID8gZmluZENoaWxkcmVuRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiTWV0YWRhdGFVUkwiKS5tYXAoCiAgICAgIChtZXRhZGF0YVVybEVsKSA9PiAoewogICAgICAgIHVybDogZ2V0RWxlbWVudEF0dHJpYnV0ZShtZXRhZGF0YVVybEVsLCAieGxpbms6aHJlZiIpCiAgICAgIH0pCiAgICApIDogZmluZENoaWxkcmVuRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiTWV0YWRhdGFVUkwiKS5tYXAoCiAgICAgIChtZXRhZGF0YVVybEVsKSA9PiAoewogICAgICAgIGZvcm1hdDogZ2V0RWxlbWVudEF0dHJpYnV0ZShtZXRhZGF0YVVybEVsLCAiZm9ybWF0IiksCiAgICAgICAgdHlwZTogZ2V0RWxlbWVudEF0dHJpYnV0ZShtZXRhZGF0YVVybEVsLCAidHlwZSIpLAogICAgICAgIHVybDogZ2V0RWxlbWVudFRleHQobWV0YWRhdGFVcmxFbCkudHJpbSgpCiAgICAgIH0pCiAgICApOwogICAgcmV0dXJuIHsKICAgICAgbmFtZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiTmFtZSIpKSwKICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZmVhdHVyZVR5cGVFbCwgIlRpdGxlIikpLAogICAgICBhYnN0cmFjdDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChmZWF0dXJlVHlwZUVsLCAiQWJzdHJhY3QiKSksCiAgICAgIGRlZmF1bHRDcnM6IHNpbXBsaWZ5RXBzZ1VybigKICAgICAgICBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGZlYXR1cmVUeXBlRWwsIGRlZmF1bHRTcnNUYWcpKQogICAgICApLAogICAgICBvdGhlckNycywKICAgICAgb3V0cHV0Rm9ybWF0czogb3V0cHV0Rm9ybWF0cy5sZW5ndGggPiAwID8gb3V0cHV0Rm9ybWF0cyA6IGRlZmF1bHRPdXRwdXRGb3JtYXRzLAogICAgICBsYXRMb25Cb3VuZGluZ0JveDogc2VydmljZVZlcnNpb24uc3RhcnRzV2l0aCgiMS4wIikgPyBwYXJzZUJCb3gxMDAoKSA6IHBhcnNlQkJveDIoKSwKICAgICAga2V5d29yZHMsCiAgICAgIC4uLm1ldGFkYXRhLmxlbmd0aCAmJiB7IG1ldGFkYXRhIH0KICAgIH07CiAgfQogIGZ1bmN0aW9uIHBhcnNlQkJveCh4bWxFbGVtZW50KSB7CiAgICBjb25zdCByZXN1bHQgPSBbIkxvd2VyQ29ybmVyIiwgIlVwcGVyQ29ybmVyIl0ubWFwKChlbE5hbWUpID0+IGZpbmRDaGlsZEVsZW1lbnQoeG1sRWxlbWVudCwgZWxOYW1lKSkubWFwKChjb3JuZXJFbCkgPT4gZ2V0RWxlbWVudFRleHQoY29ybmVyRWwpLnNwbGl0KCIgIikpLnJlZHVjZSgocHJldiwgY3VycikgPT4gWy4uLnByZXYsIC4uLmN1cnJdKS5tYXAocGFyc2VGbG9hdCk7CiAgICBpZiAocmVzdWx0LnNvbWUoTnVtYmVyLmlzTmFOKSkKICAgICAgcmV0dXJuIG51bGw7CiAgICByZXR1cm4gcmVzdWx0OwogIH0KICBmdW5jdGlvbiByZWFkSW5mb0Zyb21DYXBhYmlsaXRpZXMoY2FwYWJpbGl0aWVzRG9jKSB7CiAgICBjb25zdCByb290RWwgPSBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpOwogICAgY29uc3Qgc2VydmljZSA9IGZpbmRDaGlsZEVsZW1lbnQocm9vdEVsLCAiU2VydmljZUlkZW50aWZpY2F0aW9uIik7CiAgICBjb25zdCBrZXl3b3JkcyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIktleXdvcmRzIiksCiAgICAgICJLZXl3b3JkIgogICAgKS5tYXAoZ2V0RWxlbWVudFRleHQpOwogICAgY29uc3QgbWV0YWRhdGEgPSBmaW5kQ2hpbGRFbGVtZW50KHJvb3RFbCwgIk9wZXJhdGlvbnNNZXRhZGF0YSIpOwogICAgY29uc3QgZ2V0VGlsZU9wZXJhdGlvbiA9IGZpbmRDaGlsZHJlbkVsZW1lbnQobWV0YWRhdGEsICJPcGVyYXRpb24iKS5maW5kKAogICAgICAoZWwpID0+IGdldEVsZW1lbnRBdHRyaWJ1dGUoZWwsICJuYW1lIikgPT0gIkdldFRpbGUiCiAgICApOwogICAgY29uc3QgZ2V0VGlsZVVybHMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGdldFRpbGVPcGVyYXRpb24sICJHZXQiLCB0cnVlKS5yZWR1Y2UoCiAgICAgIChwcmV2LCBjdXJyKSA9PiB7CiAgICAgICAgY29uc3QgZW5jb2RpbmdUeXBlID0gZ2V0RWxlbWVudFRleHQoCiAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGN1cnIsICJWYWx1ZSIsIHRydWUpCiAgICAgICAgKTsKICAgICAgICBjb25zdCB1cmwgPSBnZXRFbGVtZW50QXR0cmlidXRlKGN1cnIsICJ4bGluazpocmVmIik7CiAgICAgICAgaWYgKGVuY29kaW5nVHlwZS50b0xvd2VyQ2FzZSgpID09PSAicmVzdGZ1bCIpCiAgICAgICAgICByZXR1cm4geyAuLi5wcmV2LCByZXN0OiB1cmwgfTsKICAgICAgICByZXR1cm4geyAuLi5wcmV2LCBrdnA6IHVybCB9OwogICAgICB9LAogICAgICB7fQogICAgKTsKICAgIHJldHVybiB7CiAgICAgIHRpdGxlOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJUaXRsZSIpKSwKICAgICAgbmFtZTogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiU2VydmljZVR5cGUiKSksCiAgICAgIGFic3RyYWN0OiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KHNlcnZpY2UsICJBYnN0cmFjdCIpKSwKICAgICAgZmVlczogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChzZXJ2aWNlLCAiRmVlcyIpKSwKICAgICAgY29uc3RyYWludHM6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoc2VydmljZSwgIkFjY2Vzc0NvbnN0cmFpbnRzIikpLAogICAgICBrZXl3b3JkcywKICAgICAgcHJvdmlkZXI6IHJlYWRQcm92aWRlckZyb21DYXBhYmlsaXRpZXMoY2FwYWJpbGl0aWVzRG9jKSwKICAgICAgZ2V0VGlsZVVybHMKICAgIH07CiAgfQogIGZ1bmN0aW9uIHJlYWRNYXRyaXhTZXRzRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpIHsKICAgIGZ1bmN0aW9uIHBhcnNlTWF0cml4U2V0KGVsZW1lbnQpIHsKICAgICAgY29uc3QgdG9wTGVmdCA9IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIlRvcExlZnRDb3JuZXIiKSkuc3BsaXQoIiAiKS5tYXAocGFyc2VGbG9hdCk7CiAgICAgIHJldHVybiB7CiAgICAgICAgaWRlbnRpZmllcjogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50LCAiSWRlbnRpZmllciIpKSwKICAgICAgICB0aWxlV2lkdGg6IHBhcnNlSW50KAogICAgICAgICAgZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50LCAiVGlsZVdpZHRoIikpCiAgICAgICAgKSwKICAgICAgICB0aWxlSGVpZ2h0OiBwYXJzZUludCgKICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIlRpbGVIZWlnaHQiKSkKICAgICAgICApLAogICAgICAgIG1hdHJpeFdpZHRoOiBwYXJzZUludCgKICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIk1hdHJpeFdpZHRoIikpCiAgICAgICAgKSwKICAgICAgICBtYXRyaXhIZWlnaHQ6IHBhcnNlSW50KAogICAgICAgICAgZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50LCAiTWF0cml4SGVpZ2h0IikpCiAgICAgICAgKSwKICAgICAgICBzY2FsZURlbm9taW5hdG9yOiBwYXJzZUZsb2F0KAogICAgICAgICAgZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50LCAiU2NhbGVEZW5vbWluYXRvciIpKQogICAgICAgICksCiAgICAgICAgdG9wTGVmdAogICAgICB9OwogICAgfQogICAgY29uc3QgY29udGVudHMgPSBmaW5kQ2hpbGRFbGVtZW50KAogICAgICBnZXRSb290RWxlbWVudChjYXBhYmlsaXRpZXNEb2MpLAogICAgICAiQ29udGVudHMiCiAgICApOwogICAgY29uc3QgbWF0cml4U2V0cyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoY29udGVudHMsICJUaWxlTWF0cml4U2V0Iik7CiAgICByZXR1cm4gbWF0cml4U2V0cy5tYXAoKGVsZW1lbnQpID0+IHsKICAgICAgY29uc3Qgd2VsbEtub3duU2NhbGVTZXQgPSBnZXRFbGVtZW50VGV4dCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQsICJXZWxsS25vd25TY2FsZVNldCIpCiAgICAgICk7CiAgICAgIGNvbnN0IGJvdW5kaW5nQm94ID0gcGFyc2VCQm94KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIkJvdW5kaW5nQm94IikpOwogICAgICByZXR1cm4gewogICAgICAgIGlkZW50aWZpZXI6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIklkZW50aWZpZXIiKSksCiAgICAgICAgY3JzOiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQsICJTdXBwb3J0ZWRDUlMiKSksCiAgICAgICAgdGlsZU1hdHJpY2VzOiBmaW5kQ2hpbGRyZW5FbGVtZW50KGVsZW1lbnQsICJUaWxlTWF0cml4IikubWFwKAogICAgICAgICAgcGFyc2VNYXRyaXhTZXQKICAgICAgICApLAogICAgICAgIC4uLmJvdW5kaW5nQm94ICYmIHsgYm91bmRpbmdCb3ggfSwKICAgICAgICAuLi53ZWxsS25vd25TY2FsZVNldCAmJiB7IHdlbGxLbm93blNjYWxlU2V0IH0KICAgICAgfTsKICAgIH0pOwogIH0KICBmdW5jdGlvbiByZWFkTGF5ZXJzRnJvbUNhcGFiaWxpdGllcyhjYXBhYmlsaXRpZXNEb2MpIHsKICAgIGNvbnN0IHJvb3RFbCA9IGdldFJvb3RFbGVtZW50KGNhcGFiaWxpdGllc0RvYyk7CiAgICBjb25zdCBjb250ZW50c0VsID0gZmluZENoaWxkRWxlbWVudChyb290RWwsICJDb250ZW50cyIpOwogICAgZnVuY3Rpb24gZ2V0TWF0cml4U2V0Q3JzKGNvbnRlbnRzRWwyLCBpZGVudGlmaWVyKSB7CiAgICAgIGNvbnN0IG1hdHJpeFNldCA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoY29udGVudHNFbDIsICJUaWxlTWF0cml4U2V0IikuZmluZCgKICAgICAgICAobWF0cml4U2V0RWwpID0+IHsKICAgICAgICAgIGNvbnN0IGlkZW50aWZpZXJFbCA9IGZpbmRDaGlsZEVsZW1lbnQobWF0cml4U2V0RWwsICJJZGVudGlmaWVyIik7CiAgICAgICAgICByZXR1cm4gZ2V0RWxlbWVudFRleHQoaWRlbnRpZmllckVsKSA9PT0gaWRlbnRpZmllcjsKICAgICAgICB9CiAgICAgICk7CiAgICAgIHJldHVybiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KG1hdHJpeFNldCwgIlN1cHBvcnRlZENSUyIpKTsKICAgIH0KICAgIGZ1bmN0aW9uIHBhcnNlTWF0cml4U2V0TGluayhlbGVtZW50KSB7CiAgICAgIGNvbnN0IGlkZW50aWZpZXIgPSBnZXRFbGVtZW50VGV4dCgKICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQsICJUaWxlTWF0cml4U2V0IikKICAgICAgKTsKICAgICAgY29uc3QgY3JzID0gZ2V0TWF0cml4U2V0Q3JzKGNvbnRlbnRzRWwsIGlkZW50aWZpZXIpOwogICAgICByZXR1cm4gewogICAgICAgIGlkZW50aWZpZXIsCiAgICAgICAgY3JzLAogICAgICAgIGxpbWl0czogZmluZENoaWxkcmVuRWxlbWVudChlbGVtZW50LCAiVGlsZU1hdHJpeExpbWl0cyIsIHRydWUpLm1hcCgKICAgICAgICAgIChlbGVtZW50MikgPT4gKHsKICAgICAgICAgICAgdGlsZU1hdHJpeDogZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50MiwgIlRpbGVNYXRyaXgiKSksCiAgICAgICAgICAgIG1pblRpbGVSb3c6IHBhcnNlSW50KAogICAgICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJNaW5UaWxlUm93IikpCiAgICAgICAgICAgICksCiAgICAgICAgICAgIG1pblRpbGVDb2w6IHBhcnNlSW50KAogICAgICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJNaW5UaWxlQ29sIikpCiAgICAgICAgICAgICksCiAgICAgICAgICAgIG1heFRpbGVSb3c6IHBhcnNlSW50KAogICAgICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJNYXhUaWxlUm93IikpCiAgICAgICAgICAgICksCiAgICAgICAgICAgIG1heFRpbGVDb2w6IHBhcnNlSW50KAogICAgICAgICAgICAgIGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJNYXhUaWxlQ29sIikpCiAgICAgICAgICAgICkKICAgICAgICAgIH0pCiAgICAgICAgKQogICAgICB9OwogICAgfQogICAgY29uc3QgZ2V0VGlsZU9wZXJhdGlvbiA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoCiAgICAgIGZpbmRDaGlsZEVsZW1lbnQocm9vdEVsLCAiT3BlcmF0aW9uc01ldGFkYXRhIiksCiAgICAgICJPcGVyYXRpb24iCiAgICApLmZpbmQoKGVsKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGVsLCAibmFtZSIpID09ICJHZXRUaWxlIik7CiAgICBjb25zdCBnZXRLdnBFbHQgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGdldFRpbGVPcGVyYXRpb24sICJHZXQiLCB0cnVlKS5maWx0ZXIoCiAgICAgIChlbHQpID0+IHsKICAgICAgICBjb25zdCBlbmNvZGluZ1R5cGUgPSBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGVsdCwgIlZhbHVlIiwgdHJ1ZSkpOwogICAgICAgIHJldHVybiBlbmNvZGluZ1R5cGUudG9Mb3dlckNhc2UoKSA9PT0gImt2cCI7CiAgICAgIH0KICAgIClbMF07CiAgICBjb25zdCBnZXRLdnBVcmwgPSBnZXRLdnBFbHQgPyBnZXRFbGVtZW50QXR0cmlidXRlKGdldEt2cEVsdCwgInhsaW5rOmhyZWYiKSA6ICIiOwogICAgY29uc3QgY29udGVudHMgPSBmaW5kQ2hpbGRFbGVtZW50KHJvb3RFbCwgIkNvbnRlbnRzIik7CiAgICBjb25zdCBsYXllcnMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGNvbnRlbnRzLCAiTGF5ZXIiKTsKICAgIHJldHVybiBsYXllcnMubWFwKChlbGVtZW50KSA9PiB7CiAgICAgIGNvbnN0IGxhdExvbkJvdW5kaW5nQm94ID0gcGFyc2VCQm94KAogICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIldHUzg0Qm91bmRpbmdCb3giKQogICAgICApOwogICAgICBsZXQgZGVmYXVsdFN0eWxlID0gIiI7CiAgICAgIGNvbnN0IHN0eWxlcyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgIlN0eWxlIikubWFwKChlbGVtZW50MikgPT4gewogICAgICAgIGNvbnN0IGxlZ2VuZFVybCA9IGdldEVsZW1lbnRBdHRyaWJ1dGUoCiAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQyLCAiTGVnZW5kVVJMIiksCiAgICAgICAgICAieGxpbms6aHJlZiIKICAgICAgICApOwogICAgICAgIGNvbnN0IGFic3RyYWN0ID0gZ2V0RWxlbWVudFRleHQoZmluZENoaWxkRWxlbWVudChlbGVtZW50MiwgIkFic3RyYWN0IikpOwogICAgICAgIGNvbnN0IHN0eWxlID0gewogICAgICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJUaXRsZSIpKSwKICAgICAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJJZGVudGlmaWVyIikpLAogICAgICAgICAgLi4uYWJzdHJhY3QgJiYgeyBhYnN0cmFjdCB9LAogICAgICAgICAgLi4ubGVnZW5kVXJsICYmIHsgbGVnZW5kVXJsIH0KICAgICAgICB9OwogICAgICAgIGlmIChnZXRFbGVtZW50QXR0cmlidXRlKGVsZW1lbnQyLCAiaXNEZWZhdWx0IikgPT09ICJ0cnVlIikgewogICAgICAgICAgZGVmYXVsdFN0eWxlID0gc3R5bGUubmFtZTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHN0eWxlOwogICAgICB9KTsKICAgICAgY29uc3Qgb3V0cHV0Rm9ybWF0cyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgIkZvcm1hdCIpLm1hcCgKICAgICAgICBnZXRFbGVtZW50VGV4dAogICAgICApOwogICAgICBjb25zdCByZXNvdXJjZUxpbmtzID0gZmluZENoaWxkcmVuRWxlbWVudCgKICAgICAgICBlbGVtZW50LAogICAgICAgICJSZXNvdXJjZVVSTCIKICAgICAgKS5maWx0ZXIoCiAgICAgICAgKGVsZW1lbnQyKSA9PiBnZXRFbGVtZW50QXR0cmlidXRlKGVsZW1lbnQyLCAicmVzb3VyY2VUeXBlIikgPT09ICJ0aWxlIgogICAgICApLm1hcCgoZWxlbWVudDIpID0+IHsKICAgICAgICBjb25zdCBmb3JtYXQgPSBnZXRFbGVtZW50QXR0cmlidXRlKGVsZW1lbnQyLCAiZm9ybWF0Iik7CiAgICAgICAgY29uc3QgdXJsID0gZ2V0RWxlbWVudEF0dHJpYnV0ZShlbGVtZW50MiwgInRlbXBsYXRlIik7CiAgICAgICAgcmV0dXJuIHsgZm9ybWF0LCB1cmwsIGVuY29kaW5nOiAiUkVTVCIgfTsKICAgICAgfSk7CiAgICAgIGlmIChnZXRLdnBVcmwpIHsKICAgICAgICByZXNvdXJjZUxpbmtzLnB1c2goCiAgICAgICAgICAuLi5vdXRwdXRGb3JtYXRzLm1hcCgoZm9ybWF0KSA9PiAoewogICAgICAgICAgICBlbmNvZGluZzogIktWUCIsCiAgICAgICAgICAgIHVybDogZ2V0S3ZwVXJsLAogICAgICAgICAgICBmb3JtYXQKICAgICAgICAgIH0pKQogICAgICAgICk7CiAgICAgIH0KICAgICAgY29uc3QgbWF0cml4U2V0cyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoZWxlbWVudCwgIlRpbGVNYXRyaXhTZXRMaW5rIikubWFwKAogICAgICAgIHBhcnNlTWF0cml4U2V0TGluawogICAgICApOwogICAgICBjb25zdCBkaW1lbnNpb25zID0gZmluZENoaWxkcmVuRWxlbWVudChlbGVtZW50LCAiRGltZW5zaW9uIikubWFwKAogICAgICAgIChlbGVtZW50MikgPT4gewogICAgICAgICAgY29uc3QgaWRlbnRpZmllciA9IGdldEVsZW1lbnRUZXh0KAogICAgICAgICAgICBmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQyLCAiSWRlbnRpZmllciIpCiAgICAgICAgICApOwogICAgICAgICAgY29uc3QgZGVmYXVsdFZhbHVlID0gZ2V0RWxlbWVudFRleHQoCiAgICAgICAgICAgIGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudDIsICJEZWZhdWx0IikKICAgICAgICAgICk7CiAgICAgICAgICBjb25zdCB2YWx1ZXMgPSBmaW5kQ2hpbGRyZW5FbGVtZW50KGVsZW1lbnQyLCAiVmFsdWVzIikubWFwKAogICAgICAgICAgICBnZXRFbGVtZW50VGV4dAogICAgICAgICAgKTsKICAgICAgICAgIHJldHVybiB7IGlkZW50aWZpZXIsIGRlZmF1bHRWYWx1ZSwgdmFsdWVzIH07CiAgICAgICAgfQogICAgICApOwogICAgICByZXR1cm4gewogICAgICAgIG5hbWU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIklkZW50aWZpZXIiKSksCiAgICAgICAgdGl0bGU6IGdldEVsZW1lbnRUZXh0KGZpbmRDaGlsZEVsZW1lbnQoZWxlbWVudCwgIlRpdGxlIikpLAogICAgICAgIGFic3RyYWN0OiBnZXRFbGVtZW50VGV4dChmaW5kQ2hpbGRFbGVtZW50KGVsZW1lbnQsICJBYnN0cmFjdCIpKSwKICAgICAgICBzdHlsZXMsCiAgICAgICAgcmVzb3VyY2VMaW5rcywKICAgICAgICBtYXRyaXhTZXRzLAogICAgICAgIGRlZmF1bHRTdHlsZSwKICAgICAgICAuLi5sYXRMb25Cb3VuZGluZ0JveCAmJiB7IGxhdExvbkJvdW5kaW5nQm94IH0sCiAgICAgICAgLi4uZGltZW5zaW9ucyAmJiB7IGRpbWVuc2lvbnMgfQogICAgICB9OwogICAgfSk7CiAgfQogIGZ1bmN0aW9uIHBhcnNlRmVhdHVyZVByb3BzKGdldEZlYXR1cmVzRG9jLCBmZWF0dXJlVHlwZUZ1bGwsIHNlcnZpY2VWZXJzaW9uKSB7CiAgICBjb25zdCBjb2xsZWN0aW9uID0gZ2V0Um9vdEVsZW1lbnQoZ2V0RmVhdHVyZXNEb2MpOwogICAgbGV0IG1lbWJlcnM7CiAgICBpZiAoc2VydmljZVZlcnNpb24uc3RhcnRzV2l0aCgiMi4wIikpIHsKICAgICAgbWVtYmVycyA9IGZpbmRDaGlsZHJlbkVsZW1lbnQoY29sbGVjdGlvbiwgIm1lbWJlciIpLm1hcCgKICAgICAgICAocGFyZW50KSA9PiBnZXRDaGlsZHJlbkVsZW1lbnQocGFyZW50KVswXQogICAgICApOwogICAgfSBlbHNlIHsKICAgICAgY29uc3QgbWVtYmVyc1Jvb3QgPSBmaW5kQ2hpbGRFbGVtZW50KGNvbGxlY3Rpb24sICJmZWF0dXJlTWVtYmVycyIpOwogICAgICBtZW1iZXJzID0gbWVtYmVyc1Jvb3QgPyBnZXRDaGlsZHJlbkVsZW1lbnQobWVtYmVyc1Jvb3QpIDogZmluZENoaWxkcmVuRWxlbWVudChjb2xsZWN0aW9uLCAiZmVhdHVyZU1lbWJlciIpLm1hcCgKICAgICAgICAocGFyZW50KSA9PiBnZXRDaGlsZHJlbkVsZW1lbnQocGFyZW50KVswXQogICAgICApOwogICAgfQogICAgY29uc3QgaWRBdHRyID0gc2VydmljZVZlcnNpb24gPT09ICIxLjAuMCIgPyAiZmlkIiA6ICJnbWw6aWQiOwogICAgZnVuY3Rpb24gaXNFbGVtZW50UHJvcGVydHkocHJvcE5hbWUpIHsKICAgICAgcmV0dXJuIHByb3BOYW1lIGluIGZlYXR1cmVUeXBlRnVsbC5wcm9wZXJ0aWVzOwogICAgfQogICAgZnVuY3Rpb24gcGFyc2VFbGVtZW50UHJvcGVydHlWYWx1ZShwcm9wTmFtZSwgdmFsdWVBc1N0cmluZykgewogICAgICBjb25zdCB0eXBlID0gZmVhdHVyZVR5cGVGdWxsLnByb3BlcnRpZXNbcHJvcE5hbWVdOwogICAgICBzd2l0Y2ggKHR5cGUpIHsKICAgICAgICBjYXNlICJpbnRlZ2VyIjoKICAgICAgICAgIHJldHVybiBwYXJzZUludCh2YWx1ZUFzU3RyaW5nKTsKICAgICAgICBjYXNlICJmbG9hdCI6CiAgICAgICAgICByZXR1cm4gcGFyc2VGbG9hdCh2YWx1ZUFzU3RyaW5nKTsKICAgICAgICBjYXNlICJib29sZWFuIjoKICAgICAgICAgIHJldHVybiB2YWx1ZUFzU3RyaW5nID09PSAidHJ1ZSI7CiAgICAgICAgZGVmYXVsdDoKICAgICAgICAgIHJldHVybiB2YWx1ZUFzU3RyaW5nOwogICAgICB9CiAgICB9CiAgICBmdW5jdGlvbiBnZXRQcm9wZXJ0aWVzKG1lbWJlckVsKSB7CiAgICAgIHJldHVybiBnZXRDaGlsZHJlbkVsZW1lbnQobWVtYmVyRWwpLmZpbHRlcigoZWwpID0+IGlzRWxlbWVudFByb3BlcnR5KHN0cmlwTmFtZXNwYWNlKGdldEVsZW1lbnROYW1lKGVsKSkpKS5yZWR1Y2UoKHByZXYsIGN1cnIpID0+IHsKICAgICAgICBjb25zdCBwcm9wTmFtZSA9IHN0cmlwTmFtZXNwYWNlKGdldEVsZW1lbnROYW1lKGN1cnIpKTsKICAgICAgICByZXR1cm4gewogICAgICAgICAgLi4ucHJldiwKICAgICAgICAgIFtwcm9wTmFtZV06IHBhcnNlRWxlbWVudFByb3BlcnR5VmFsdWUocHJvcE5hbWUsIGdldEVsZW1lbnRUZXh0KGN1cnIpKQogICAgICAgIH07CiAgICAgIH0sIHt9KTsKICAgIH0KICAgIHJldHVybiBtZW1iZXJzLm1hcCgoZWwpID0+ICh7CiAgICAgIGlkOiBnZXRFbGVtZW50QXR0cmlidXRlKGVsLCBpZEF0dHIpLAogICAgICBwcm9wZXJ0aWVzOiBnZXRQcm9wZXJ0aWVzKGVsKQogICAgfSkpOwogIH0KICBmdW5jdGlvbiBjb21wdXRlRmVhdHVyZVByb3BzRGV0YWlscyhmZWF0dXJlc1dpdGhQcm9wcykgewogICAgcmV0dXJuIGZlYXR1cmVzV2l0aFByb3BzLnJlZHVjZSgocHJldiwgY3VycikgPT4gewogICAgICBmb3IgKGNvbnN0IHByb3BOYW1lIGluIGN1cnIucHJvcGVydGllcykgewogICAgICAgIGNvbnN0IHByb3BWYWx1ZSA9IGN1cnIucHJvcGVydGllc1twcm9wTmFtZV07CiAgICAgICAgaWYgKCEocHJvcE5hbWUgaW4gcHJldikpIHsKICAgICAgICAgIHByZXZbcHJvcE5hbWVdID0geyB1bmlxdWVWYWx1ZXM6IFtdIH07CiAgICAgICAgfQogICAgICAgIGNvbnN0IHVuaXF1ZVZhbHVlID0gcHJldltwcm9wTmFtZV0udW5pcXVlVmFsdWVzLmZpbmQoCiAgICAgICAgICAodikgPT4gdi52YWx1ZSA9PT0gcHJvcFZhbHVlCiAgICAgICAgKTsKICAgICAgICBpZiAodW5pcXVlVmFsdWUpCiAgICAgICAgICB1bmlxdWVWYWx1ZS5jb3VudCsrOwogICAgICAgIGVsc2UKICAgICAgICAgIHByZXZbcHJvcE5hbWVdLnVuaXF1ZVZhbHVlcy5wdXNoKHsgdmFsdWU6IHByb3BWYWx1ZSwgY291bnQ6IDEgfSk7CiAgICAgIH0KICAgICAgcmV0dXJuIHByZXY7CiAgICB9LCB7fSk7CiAgfQogIGZ1bmN0aW9uIGdlbmVyYXRlR2V0RmVhdHVyZVVybChzZXJ2aWNlVXJsLCB2ZXJzaW9uLCBmZWF0dXJlVHlwZSwgb3V0cHV0Rm9ybWF0LCBtYXhGZWF0dXJlcywgYXR0cmlidXRlcywgaGl0c09ubHksIG91dHB1dENycywgZXh0ZW50LCBleHRlbnRDcnMsIHN0YXJ0SW5kZXgsIHNvcnRCeSkgewogICAgY29uc3QgdHlwZVBhcmFtID0gdmVyc2lvbiA9PT0gIjIuMC4wIiA/ICJUWVBFTkFNRVMiIDogIlRZUEVOQU1FIjsKICAgIGNvbnN0IGNvdW50UGFyYW0gPSB2ZXJzaW9uID09PSAiMi4wLjAiID8gIkNPVU5UIiA6ICJNQVhGRUFUVVJFUyI7CiAgICBjb25zdCBuZXdQYXJhbXMgPSB7CiAgICAgIFNFUlZJQ0U6ICJXRlMiLAogICAgICBSRVFVRVNUOiAiR2V0RmVhdHVyZSIsCiAgICAgIFZFUlNJT046IHZlcnNpb24sCiAgICAgIFt0eXBlUGFyYW1dOiBmZWF0dXJlVHlwZQogICAgfTsKICAgIGlmIChvdXRwdXRGb3JtYXQgIT09IHZvaWQgMCkKICAgICAgbmV3UGFyYW1zLk9VVFBVVEZPUk1BVCA9IG91dHB1dEZvcm1hdDsKICAgIGlmIChhdHRyaWJ1dGVzICE9PSB2b2lkIDApCiAgICAgIG5ld1BhcmFtcy5QUk9QRVJUWU5BTUUgPSBhdHRyaWJ1dGVzLmpvaW4oIiwiKTsKICAgIGlmIChoaXRzT25seSkgewogICAgICBuZXdQYXJhbXMuUkVTVUxUVFlQRSA9ICJoaXRzIjsKICAgICAgbmV3UGFyYW1zW2NvdW50UGFyYW1dID0gIjEiOwogICAgfSBlbHNlIGlmIChtYXhGZWF0dXJlcyAhPT0gdm9pZCAwKQogICAgICBuZXdQYXJhbXNbY291bnRQYXJhbV0gPSBtYXhGZWF0dXJlcy50b1N0cmluZygxMCk7CiAgICBpZiAob3V0cHV0Q3JzKSB7CiAgICAgIG5ld1BhcmFtcy5TUlNOQU1FID0gb3V0cHV0Q3JzOwogICAgfQogICAgaWYgKGV4dGVudCkgewogICAgICBjb25zdCBleHRlbnRKb2luZWQgPSBleHRlbnQuam9pbigiLCIpOwogICAgICBuZXdQYXJhbXMuQkJPWCA9IGV4dGVudENycyA/IGAke2V4dGVudEpvaW5lZH0sJHtleHRlbnRDcnN9YCA6IGV4dGVudEpvaW5lZDsKICAgIH0KICAgIGlmIChzdGFydEluZGV4KSB7CiAgICAgIG5ld1BhcmFtcy5TVEFSVElOREVYID0gc3RhcnRJbmRleC50b1N0cmluZygxMCk7CiAgICB9CiAgICBjb25zdCB1cmwgPSBuZXcgVVJMKHNldFF1ZXJ5UGFyYW1zKHNlcnZpY2VVcmwsIG5ld1BhcmFtcykpOwogICAgaWYgKEFycmF5LmlzQXJyYXkoc29ydEJ5KSAmJiBzb3J0QnkubGVuZ3RoID4gMCkgewogICAgICBjb25zdCBzb3J0cyA9IHNvcnRCeS5tYXAoKGZpZWxkU29ydCkgPT4gYCR7ZmllbGRTb3J0WzFdfSAke2ZpZWxkU29ydFswXX1gKS5qb2luKCIsIik7CiAgICAgIHVybC5zZWFyY2hQYXJhbXMuc2V0KCJTT1JUQlkiLCBzb3J0cyk7CiAgICB9CiAgICByZXR1cm4gdXJsLnRvU3RyaW5nKCk7CiAgfQogIGFkZFRhc2tIYW5kbGVyKAogICAgInBhcnNlV21zQ2FwYWJpbGl0aWVzIiwKICAgIGdsb2JhbFRoaXMsCiAgICAoeyB1cmwgfSkgPT4gcXVlcnlYbWxEb2N1bWVudCh1cmwpLnRoZW4oKHhtbERvYykgPT4gY2hlY2soeG1sRG9jLCB1cmwpKS50aGVuKCh4bWxEb2MpID0+ICh7CiAgICAgIGluZm86IHJlYWRJbmZvRnJvbUNhcGFiaWxpdGllcyQyKHhtbERvYyksCiAgICAgIGxheWVyczogcmVhZExheWVyc0Zyb21DYXBhYmlsaXRpZXMkMSh4bWxEb2MpLAogICAgICB1cmw6IHJlYWRPcGVyYXRpb25VcmxzRnJvbUNhcGFiaWxpdGllcyQxKHhtbERvYyksCiAgICAgIHZlcnNpb246IHJlYWRWZXJzaW9uRnJvbUNhcGFiaWxpdGllcyQxKHhtbERvYykKICAgIH0pKQogICk7CiAgYWRkVGFza0hhbmRsZXIoCiAgICAicGFyc2VXZnNDYXBhYmlsaXRpZXMiLAogICAgZ2xvYmFsVGhpcywKICAgICh7IHVybCB9KSA9PiBxdWVyeVhtbERvY3VtZW50KHVybCkudGhlbigoeG1sRG9jKSA9PiBjaGVjayh4bWxEb2MsIHVybCkpLnRoZW4oKHhtbERvYykgPT4gKHsKICAgICAgaW5mbzogcmVhZEluZm9Gcm9tQ2FwYWJpbGl0aWVzJDEoeG1sRG9jKSwKICAgICAgZmVhdHVyZVR5cGVzOiByZWFkRmVhdHVyZVR5cGVzRnJvbUNhcGFiaWxpdGllcyh4bWxEb2MpLAogICAgICB1cmw6IHJlYWRPcGVyYXRpb25VcmxzRnJvbUNhcGFiaWxpdGllcyh4bWxEb2MpLAogICAgICB2ZXJzaW9uOiByZWFkVmVyc2lvbkZyb21DYXBhYmlsaXRpZXMoeG1sRG9jKQogICAgfSkpCiAgKTsKICBhZGRUYXNrSGFuZGxlcigKICAgICJxdWVyeVdmc0ZlYXR1cmVUeXBlRGV0YWlscyIsCiAgICBnbG9iYWxUaGlzLAogICAgKHsKICAgICAgdXJsLAogICAgICBzZXJ2aWNlVmVyc2lvbiwKICAgICAgZmVhdHVyZVR5cGVGdWxsCiAgICB9KSA9PiB7CiAgICAgIGNvbnN0IGdldEZlYXR1cmVVcmwgPSBnZW5lcmF0ZUdldEZlYXR1cmVVcmwoCiAgICAgICAgdXJsLAogICAgICAgIHNlcnZpY2VWZXJzaW9uLAogICAgICAgIGZlYXR1cmVUeXBlRnVsbC5uYW1lLAogICAgICAgIHZvaWQgMCwKICAgICAgICB2b2lkIDAsCiAgICAgICAgT2JqZWN0LmtleXMoZmVhdHVyZVR5cGVGdWxsLnByb3BlcnRpZXMpCiAgICAgICk7CiAgICAgIHJldHVybiBxdWVyeVhtbERvY3VtZW50KGdldEZlYXR1cmVVcmwpLnRoZW4oKGdldEZlYXR1cmVEb2MpID0+ICh7CiAgICAgICAgcHJvcHM6IGNvbXB1dGVGZWF0dXJlUHJvcHNEZXRhaWxzKAogICAgICAgICAgcGFyc2VGZWF0dXJlUHJvcHMoZ2V0RmVhdHVyZURvYywgZmVhdHVyZVR5cGVGdWxsLCBzZXJ2aWNlVmVyc2lvbikKICAgICAgICApCiAgICAgIH0pKTsKICAgIH0KICApOwogIGFkZFRhc2tIYW5kbGVyKAogICAgInVwZGF0ZUZldGNoT3B0aW9ucyIsCiAgICBnbG9iYWxUaGlzLAogICAgKHsgb3B0aW9ucyB9KSA9PiB7CiAgICAgIHNldEZldGNoT3B0aW9ucyhvcHRpb25zKTsKICAgICAgcmV0dXJuIFByb21pc2UucmVzb2x2ZSh7fSk7CiAgICB9CiAgKTsKICBhZGRUYXNrSGFuZGxlcigKICAgICJwYXJzZVdtdHNDYXBhYmlsaXRpZXMiLAogICAgZ2xvYmFsVGhpcywKICAgICh7IHVybCB9KSA9PiBxdWVyeVhtbERvY3VtZW50KHVybCkudGhlbigoeG1sRG9jKSA9PiBjaGVjayh4bWxEb2MsIHVybCkpLnRoZW4oKHhtbERvYykgPT4gKHsKICAgICAgaW5mbzogcmVhZEluZm9Gcm9tQ2FwYWJpbGl0aWVzKHhtbERvYyksCiAgICAgIGxheWVyczogcmVhZExheWVyc0Zyb21DYXBhYmlsaXRpZXMoeG1sRG9jKSwKICAgICAgbWF0cml4U2V0czogcmVhZE1hdHJpeFNldHNGcm9tQ2FwYWJpbGl0aWVzKHhtbERvYykKICAgIH0pKQogICk7Cn0pKCk7Ci8vIyBzb3VyY2VNYXBwaW5nVVJMPXdvcmtlci1MRGtNT3gwZC5qcy5tYXAK", { name: e?.name });
562
+ } finally {
563
+ t && (window.URL || window.webkitURL).revokeObjectURL(t);
564
+ }
565
+ }
566
+ var he = !1, ge;
567
+ function _e() {
568
+ return he ? null : (ge ||= new me(), ge);
569
+ }
570
+ function ve(e) {
571
+ return fe("parseWmsCapabilities", _e(), { url: e });
572
+ }
573
+ function ye(e) {
574
+ return fe("parseWfsCapabilities", _e(), { url: e });
575
+ }
576
+ function be(e, t, n) {
577
+ return fe("queryWfsFeatureTypeDetails", _e(), {
578
+ url: e,
579
+ serviceVersion: t,
580
+ featureTypeFull: n
581
+ });
582
+ }
583
+ function xe(e) {
584
+ return fe("parseWmtsCapabilities", _e(), { url: e });
585
+ }
586
+ //#endregion
587
+ //#region node_modules/@camptocamp/ogc-client/dist/shared/xml-utils.js
588
+ var Se = (/* @__PURE__ */ e(((e, t) => {
589
+ var n = Object.defineProperty, r = Object.getOwnPropertyDescriptor, i = Object.getOwnPropertyNames, a = Object.prototype.hasOwnProperty, o = (e, t) => {
590
+ for (var r in t) n(e, r, {
591
+ get: t[r],
592
+ enumerable: !0
593
+ });
594
+ }, s = (e, t, o, s) => {
595
+ if (t && typeof t == "object" || typeof t == "function") for (let c of i(t)) !a.call(e, c) && c !== o && n(e, c, {
596
+ get: () => t[c],
597
+ enumerable: !(s = r(t, c)) || s.enumerable
598
+ });
599
+ return e;
600
+ }, c = (e) => s(n({}, "__esModule", { value: !0 }), e), l = {};
601
+ o(l, {
602
+ XmlCdata: () => E,
603
+ XmlComment: () => D,
604
+ XmlDeclaration: () => O,
605
+ XmlDocument: () => A,
606
+ XmlDocumentType: () => ee,
607
+ XmlElement: () => k,
608
+ XmlError: () => te,
609
+ XmlNode: () => w,
610
+ XmlProcessingInstruction: () => j,
611
+ XmlText: () => T,
612
+ parseXml: () => re
613
+ }), t.exports = c(l);
614
+ var u = "", d = /[\uD800-\uDBFF][\uDC00-\uDFFF]/g, f = class {
615
+ constructor(e) {
616
+ if (this.k = this.u(e, !0), this.d = 0, this.length = e.length, this.l = this.k !== this.length, this.h = e, this.l) {
617
+ let t = [];
618
+ for (let n = 0, r = 0; r < this.k; ++r) t[r] = n, n += e.codePointAt(n) > 65535 ? 2 : 1;
619
+ this.A = t;
620
+ }
621
+ }
622
+ get B() {
623
+ return this.d >= this.k;
624
+ }
625
+ u(e, t = this.l) {
626
+ return t ? e.replace(d, "_").length : e.length;
627
+ }
628
+ p(e = 1) {
629
+ this.d = Math.min(this.k, this.d + e);
630
+ }
631
+ f(e = this.d) {
632
+ return this.l ? this.A[e] ?? Infinity : e;
633
+ }
634
+ G(e = 1) {
635
+ let t = this.m(e);
636
+ return this.p(e), t;
637
+ }
638
+ v(e) {
639
+ let t = this.f(), n = this.h.slice(t, t + e);
640
+ return this.p(this.u(n)), n;
641
+ }
642
+ w(e) {
643
+ let { length: t, l: n, h: r } = this, i = this.f(), a = i;
644
+ if (n) for (; a < t;) {
645
+ let t = r[a], n = t >= "\ud800" && t <= "\udbff";
646
+ if (n && (t += r[a + 1]), !e(t)) break;
647
+ a += n ? 2 : 1;
648
+ }
649
+ else for (; a < t && e(r[a]);) ++a;
650
+ return this.v(a - i);
651
+ }
652
+ b(e) {
653
+ let { length: t } = e, n = this.f();
654
+ return e === this.h.slice(n, n + t) ? (this.p(t === 1 ? 1 : this.u(e)), e) : u;
655
+ }
656
+ x(e) {
657
+ let t = this.h.slice(this.f()).search(e);
658
+ return t > 0 ? this.v(t) : u;
659
+ }
660
+ s(e) {
661
+ let t = this.f(), n = this.h.indexOf(e, t);
662
+ return n > 0 ? this.v(n - t) : u;
663
+ }
664
+ m(e = 1) {
665
+ let { d: t, h: n } = this;
666
+ return this.l ? n.slice(this.f(t), this.f(t + e)) : n.slice(t, t + e);
667
+ }
668
+ n(e = 0) {
669
+ this.d = e >= 0 ? Math.min(this.k, e) : Math.max(0, this.d + e);
670
+ }
671
+ }, p = /["&<]/, m = /['&<]/, h = /\r\n|[\n\r\t]/g, g = /<|&|]]>/, _ = Object.freeze(Object.assign(/* @__PURE__ */ Object.create(null), {
672
+ amp: "&",
673
+ apos: "'",
674
+ gt: ">",
675
+ lt: "<",
676
+ quot: "\""
677
+ }));
678
+ function v(e) {
679
+ let t = e.codePointAt(0);
680
+ return t >= 97 && t <= 122 || t >= 65 && t <= 90 || t >= 48 && t <= 57 || t === 45 || t === 46 || t === 183 || t >= 768 && t <= 879 || t === 8255 || t === 8256 || y(e, t);
681
+ }
682
+ function y(e, t = e.codePointAt(0)) {
683
+ return t >= 97 && t <= 122 || t >= 65 && t <= 90 || t === 58 || t === 95 || t >= 192 && t <= 214 || t >= 216 && t <= 246 || t >= 248 && t <= 767 || t >= 880 && t <= 893 || t >= 895 && t <= 8191 || t === 8204 || t === 8205 || t >= 8304 && t <= 8591 || t >= 11264 && t <= 12271 || t >= 12289 && t <= 55295 || t >= 63744 && t <= 64975 || t >= 65008 && t <= 65533 || t >= 65536 && t <= 983039;
684
+ }
685
+ function b(e) {
686
+ return e === "#" || v(e);
687
+ }
688
+ function x(e) {
689
+ let t = e.codePointAt(0);
690
+ return t === 32 || t === 9 || t === 10 || t === 13;
691
+ }
692
+ function S(e) {
693
+ return e >= 32 && e <= 55295 || e === 10 || e === 9 || e === 13 || e >= 57344 && e <= 65533 || e >= 65536 && e <= 1114111;
694
+ }
695
+ var C = class e {
696
+ constructor() {
697
+ this.parent = null, this.start = -1, this.end = -1;
698
+ }
699
+ get document() {
700
+ return this.parent?.document ?? null;
701
+ }
702
+ get isRootNode() {
703
+ return this.parent !== null && this.parent === this.document && this.type === e.TYPE_ELEMENT;
704
+ }
705
+ get preserveWhitespace() {
706
+ return !!this.parent?.preserveWhitespace;
707
+ }
708
+ get type() {
709
+ return "";
710
+ }
711
+ toJSON() {
712
+ let e = { type: this.type };
713
+ return this.isRootNode && (e.isRootNode = !0), this.preserveWhitespace && (e.preserveWhitespace = !0), this.start !== -1 && (e.start = this.start, e.end = this.end), e;
714
+ }
715
+ };
716
+ C.TYPE_CDATA = "cdata", C.TYPE_COMMENT = "comment", C.TYPE_DOCUMENT = "document", C.TYPE_DOCUMENT_TYPE = "doctype", C.TYPE_ELEMENT = "element", C.TYPE_PROCESSING_INSTRUCTION = "pi", C.TYPE_TEXT = "text", C.TYPE_XML_DECLARATION = "xmldecl";
717
+ var w = C, T = class extends w {
718
+ constructor(e = "") {
719
+ super(), this.text = e;
720
+ }
721
+ get type() {
722
+ return w.TYPE_TEXT;
723
+ }
724
+ toJSON() {
725
+ return Object.assign(w.prototype.toJSON.call(this), { text: this.text });
726
+ }
727
+ }, E = class extends T {
728
+ get type() {
729
+ return w.TYPE_CDATA;
730
+ }
731
+ }, D = class extends w {
732
+ constructor(e = "") {
733
+ super(), this.content = e;
734
+ }
735
+ get type() {
736
+ return w.TYPE_COMMENT;
737
+ }
738
+ toJSON() {
739
+ return Object.assign(w.prototype.toJSON.call(this), { content: this.content });
740
+ }
741
+ }, O = class extends w {
742
+ constructor(e, t, n) {
743
+ super(), this.version = e, this.encoding = t ?? null, this.standalone = n ?? null;
744
+ }
745
+ get type() {
746
+ return w.TYPE_XML_DECLARATION;
747
+ }
748
+ toJSON() {
749
+ let e = w.prototype.toJSON.call(this);
750
+ e.version = this.version;
751
+ for (let t of ["encoding", "standalone"]) this[t] !== null && (e[t] = this[t]);
752
+ return e;
753
+ }
754
+ }, k = class e extends w {
755
+ constructor(e, t = /* @__PURE__ */ Object.create(null), n = []) {
756
+ super(), this.name = e, this.attributes = t, this.children = n;
757
+ }
758
+ get isEmpty() {
759
+ return this.children.length === 0;
760
+ }
761
+ get preserveWhitespace() {
762
+ let t = this;
763
+ for (; t instanceof e;) {
764
+ if ("xml:space" in t.attributes) return t.attributes["xml:space"] === "preserve";
765
+ t = t.parent;
766
+ }
767
+ return !1;
768
+ }
769
+ get text() {
770
+ return this.children.map((e) => "text" in e ? e.text : "").join("");
771
+ }
772
+ get type() {
773
+ return w.TYPE_ELEMENT;
774
+ }
775
+ toJSON() {
776
+ return Object.assign(w.prototype.toJSON.call(this), {
777
+ name: this.name,
778
+ attributes: this.attributes,
779
+ children: this.children.map((e) => e.toJSON())
780
+ });
781
+ }
782
+ }, A = class extends w {
783
+ constructor(e = []) {
784
+ super(), this.children = e;
785
+ }
786
+ get document() {
787
+ return this;
788
+ }
789
+ get root() {
790
+ for (let e of this.children) if (e instanceof k) return e;
791
+ return null;
792
+ }
793
+ get text() {
794
+ return this.children.map((e) => "text" in e ? e.text : "").join("");
795
+ }
796
+ get type() {
797
+ return w.TYPE_DOCUMENT;
798
+ }
799
+ toJSON() {
800
+ return Object.assign(w.prototype.toJSON.call(this), { children: this.children.map((e) => e.toJSON()) });
801
+ }
802
+ }, ee = class extends w {
803
+ constructor(e, t, n, r) {
804
+ super(), this.name = e, this.publicId = t ?? null, this.systemId = n ?? null, this.internalSubset = r ?? null;
805
+ }
806
+ get type() {
807
+ return w.TYPE_DOCUMENT_TYPE;
808
+ }
809
+ toJSON() {
810
+ let e = w.prototype.toJSON.call(this);
811
+ e.name = this.name;
812
+ for (let t of [
813
+ "publicId",
814
+ "systemId",
815
+ "internalSubset"
816
+ ]) this[t] !== null && (e[t] = this[t]);
817
+ return e;
818
+ }
819
+ }, te = class extends Error {
820
+ constructor(e, t, n) {
821
+ let r = 1, i = "", a = 1;
822
+ for (let e = 0; e < t; ++e) {
823
+ let t = n[e];
824
+ t === "\n" ? (r = 1, i = "", a += 1) : (r += 1, i += t);
825
+ }
826
+ let o = n.indexOf("\n", t);
827
+ i += o === -1 ? n.slice(t) : n.slice(t, o);
828
+ let s = 0;
829
+ i.length > 50 && (r < 40 ? i = i.slice(0, 50) : (s = r - 20, i = i.slice(s, r + 30))), super(`${e} (line ${a}, column ${r})
830
+ ${i}
831
+ ` + " ".repeat(r - s + 1) + "^\n"), this.column = r, this.excerpt = i, this.line = a, this.name = "XmlError", this.pos = t;
832
+ }
833
+ }, j = class extends w {
834
+ constructor(e, t = "") {
835
+ super(), this.name = e, this.content = t;
836
+ }
837
+ get type() {
838
+ return w.TYPE_PROCESSING_INSTRUCTION;
839
+ }
840
+ toJSON() {
841
+ return Object.assign(w.prototype.toJSON.call(this), {
842
+ name: this.name,
843
+ content: this.content
844
+ });
845
+ }
846
+ }, M = "", ne = class {
847
+ constructor(e, t = {}) {
848
+ let n = this.document = new A();
849
+ this.j = n, this.g = t, this.c = new f(e), this.g.includeOffsets && (n.start = 0, n.end = e.length), this.parse();
850
+ }
851
+ i(e, t) {
852
+ return e.parent = this.j, this.g.includeOffsets && (e.start = this.c.f(t), e.end = this.c.f()), this.j.children.push(e), !0;
853
+ }
854
+ y(e, t) {
855
+ let { children: n } = this.j, { length: r } = n;
856
+ if (e = N(e), r > 0) {
857
+ let t = n[r - 1];
858
+ if (t?.type === w.TYPE_TEXT) {
859
+ let n = t;
860
+ return n.text += e, this.g.includeOffsets && (n.end = this.c.f()), !0;
861
+ }
862
+ }
863
+ return this.i(new T(e), t);
864
+ }
865
+ H() {
866
+ let e = /* @__PURE__ */ Object.create(null);
867
+ for (; this.e();) {
868
+ let t = this.q();
869
+ if (!t) break;
870
+ let n = this.t() && this.I();
871
+ if (n === !1) throw this.a("Attribute value expected");
872
+ if (t in e) throw this.a(`Duplicate attribute: ${t}`);
873
+ if (t === "xml:space" && n !== "default" && n !== "preserve") throw this.a("Value of the `xml:space` attribute must be \"default\" or \"preserve\"");
874
+ e[t] = n;
875
+ }
876
+ if (this.g.sortAttributes) {
877
+ let t = Object.keys(e).sort(), n = /* @__PURE__ */ Object.create(null);
878
+ for (let r = 0; r < t.length; ++r) {
879
+ let i = t[r];
880
+ n[i] = e[i];
881
+ }
882
+ e = n;
883
+ }
884
+ return e;
885
+ }
886
+ I() {
887
+ let { c: e } = this, t = e.m();
888
+ if (t !== "\"" && t !== "'") return !1;
889
+ e.p();
890
+ let n, r = !1, i = M, a = t === "\"" ? p : m;
891
+ matchLoop: for (; !e.B;) switch (n = e.x(a), n && (this.o(n), i += n.replace(h, " ")), e.m()) {
892
+ case t:
893
+ r = !0;
894
+ break matchLoop;
895
+ case "&":
896
+ i += this.C();
897
+ continue;
898
+ case "<": throw this.a("Unescaped `<` is not allowed in an attribute value");
899
+ default: break matchLoop;
900
+ }
901
+ if (!r) throw this.a("Unclosed attribute");
902
+ return e.p(), i;
903
+ }
904
+ J() {
905
+ let { c: e } = this, t = e.d;
906
+ if (!e.b("<![CDATA[")) return !1;
907
+ let n = e.s("]]>");
908
+ if (this.o(n), !e.b("]]>")) throw this.a("Unclosed CDATA section");
909
+ return this.g.preserveCdata ? this.i(new E(N(n)), t) : this.y(n, t);
910
+ }
911
+ K() {
912
+ let { c: e } = this, t = e.d, n = e.x(g);
913
+ if (!n) return !1;
914
+ if (this.o(n), e.m(3) === "]]>") throw this.a("Element content may not contain the CDATA section close delimiter `]]>`");
915
+ return this.y(n, t);
916
+ }
917
+ D() {
918
+ let { c: e } = this, t = e.d;
919
+ if (!e.b("<!--")) return !1;
920
+ let n = e.s("--");
921
+ if (this.o(n), !e.b("-->")) throw e.m(2) === "--" ? this.a("The string `--` isn't allowed inside a comment") : this.a("Unclosed comment");
922
+ return this.g.preserveComments ? this.i(new D(N(n)), t) : !0;
923
+ }
924
+ L() {
925
+ let e = this.c.d, t = this.C();
926
+ return t ? this.y(t, e) : !1;
927
+ }
928
+ M() {
929
+ let { c: e } = this, t = e.d;
930
+ if (!e.b("<!DOCTYPE")) return !1;
931
+ let n = this.e() && this.q();
932
+ if (!n) throw this.a("Expected a name");
933
+ let r, i;
934
+ if (this.e()) {
935
+ if (e.b("PUBLIC")) {
936
+ if (r = this.e() && this.N(), r === !1) throw this.a("Expected a public identifier");
937
+ this.e();
938
+ }
939
+ if (r !== void 0 || e.b("SYSTEM")) {
940
+ if (this.e(), i = this.r(), i === !1) throw this.a("Expected a system identifier");
941
+ this.e();
942
+ }
943
+ }
944
+ let a;
945
+ if (e.b("[")) {
946
+ if (a = e.x(/\][\x20\t\r\n]*>/), !e.b("]")) throw this.a("Unclosed internal subset");
947
+ this.e();
948
+ }
949
+ if (!e.b(">")) throw this.a("Unclosed doctype declaration");
950
+ return this.g.preserveDocumentType ? this.i(new ee(n, r, i, a), t) : !0;
951
+ }
952
+ E() {
953
+ let { c: e } = this, t = e.d;
954
+ if (!e.b("<")) return !1;
955
+ let n = this.q();
956
+ if (!n) return e.n(t), !1;
957
+ let r = this.H(), i = !!e.b("/>"), a = new k(n, r);
958
+ if (a.parent = this.j, !i) {
959
+ if (!e.b(">")) throw this.a(`Unclosed start tag for element \`${n}\``);
960
+ this.j = a;
961
+ do
962
+ this.K();
963
+ while (this.E() || this.L() || this.J() || this.F() || this.D());
964
+ let t = e.d, r;
965
+ if (!e.b("</") || !(r = this.q()) || r !== n) throw e.n(t), this.a(`Missing end tag for element ${n}`);
966
+ if (this.e(), !e.b(">")) throw this.a(`Unclosed end tag for element ${n}`);
967
+ this.j = a.parent;
968
+ }
969
+ return this.i(a, t);
970
+ }
971
+ t() {
972
+ return this.e(), this.c.b("=") ? (this.e(), !0) : !1;
973
+ }
974
+ z() {
975
+ return this.D() || this.F() || this.e();
976
+ }
977
+ q() {
978
+ return y(this.c.m()) ? this.c.w(v) : M;
979
+ }
980
+ F() {
981
+ let { c: e } = this, t = e.d;
982
+ if (!e.b("<?")) return !1;
983
+ let n = this.q();
984
+ if (n) {
985
+ if (n.toLowerCase() === "xml") throw e.n(t), this.a("XML declaration isn't allowed here");
986
+ } else throw this.a("Invalid processing instruction");
987
+ if (!this.e()) {
988
+ if (e.b("?>")) return this.i(new j(n), t);
989
+ throw this.a("Whitespace is required after a processing instruction name");
990
+ }
991
+ let r = e.s("?>");
992
+ if (this.o(r), !e.b("?>")) throw this.a("Unterminated processing instruction");
993
+ return this.i(new j(n, N(r)), t);
994
+ }
995
+ O() {
996
+ let { c: e } = this, t = e.d;
997
+ for (this.P(); this.z(););
998
+ if (this.M()) for (; this.z(););
999
+ return t < e.d;
1000
+ }
1001
+ N() {
1002
+ let e = this.c.d, t = this.r();
1003
+ if (t !== !1 && !/^[-\x20\r\na-zA-Z0-9'()+,./:=?;!*#@$_%]*$/.test(t)) throw this.c.n(e), this.a("Invalid character in public identifier");
1004
+ return t;
1005
+ }
1006
+ C() {
1007
+ let { c: e } = this;
1008
+ if (!e.b("&")) return !1;
1009
+ let t = e.w(b);
1010
+ if (e.G() !== ";") throw this.a("Unterminated reference (a reference must end with `;`)");
1011
+ let n;
1012
+ if (t[0] === "#") {
1013
+ let e = t[1] === "x" ? parseInt(t.slice(2), 16) : parseInt(t.slice(1), 10);
1014
+ if (isNaN(e)) throw this.a("Invalid character reference");
1015
+ if (!S(e)) throw this.a("Character reference resolves to an invalid character");
1016
+ n = String.fromCodePoint(e);
1017
+ } else if (n = _[t], n === void 0) {
1018
+ let { ignoreUndefinedEntities: n, resolveUndefinedEntity: r } = this.g, i = `&${t};`;
1019
+ if (r) {
1020
+ let e = r(i);
1021
+ if (e != null) {
1022
+ let t = typeof e;
1023
+ if (t !== "string") throw TypeError(`\`resolveUndefinedEntity()\` must return a string, \`null\`, or \`undefined\`, but returned a value of type ${t}`);
1024
+ return e;
1025
+ }
1026
+ }
1027
+ if (n) return i;
1028
+ throw e.n(-i.length), this.a(`Named entity isn't defined: ${i}`);
1029
+ }
1030
+ return n;
1031
+ }
1032
+ r() {
1033
+ let { c: e } = this, t = e.b("\"") || e.b("'");
1034
+ if (!t) return !1;
1035
+ let n = e.s(t);
1036
+ if (this.o(n), !e.b(t)) throw this.a("Missing end quote");
1037
+ return n;
1038
+ }
1039
+ e() {
1040
+ return !!this.c.w(x);
1041
+ }
1042
+ P() {
1043
+ let { c: e } = this, t = e.d;
1044
+ if (!e.b("<?xml")) return !1;
1045
+ if (!this.e()) throw this.a("Invalid XML declaration");
1046
+ let n = !!e.b("version") && this.t() && this.r();
1047
+ if (n === !1) throw this.a("XML version is missing or invalid");
1048
+ if (!/^1\.[0-9]+$/.test(n)) throw this.a("Invalid character in version number");
1049
+ let r, i;
1050
+ if (this.e()) {
1051
+ if (r = !!e.b("encoding") && this.t() && this.r(), r) {
1052
+ if (!/^[A-Za-z][\w.-]*$/.test(r)) throw this.a("Invalid character in encoding name");
1053
+ this.e();
1054
+ }
1055
+ if (i = !!e.b("standalone") && this.t() && this.r(), i) {
1056
+ if (i !== "yes" && i !== "no") throw this.a("Only \"yes\" and \"no\" are permitted as values of `standalone`");
1057
+ this.e();
1058
+ }
1059
+ }
1060
+ if (!e.b("?>")) throw this.a("Invalid or unclosed XML declaration");
1061
+ return this.g.preserveXmlDeclaration ? this.i(new O(n, r || void 0, i || void 0), t) : !0;
1062
+ }
1063
+ a(e) {
1064
+ let { c: t } = this;
1065
+ return new te(e, t.d, t.h);
1066
+ }
1067
+ parse() {
1068
+ if (this.c.b(""), this.O(), !this.E()) throw this.a("Root element is missing or invalid");
1069
+ for (; this.z(););
1070
+ if (!this.c.B) throw this.a("Extra content at the end of the document");
1071
+ }
1072
+ o(e) {
1073
+ let { length: t } = e;
1074
+ for (let n = 0; n < t; ++n) {
1075
+ let t = e.codePointAt(n);
1076
+ if (!S(t)) throw this.c.n(-([...e].length - n)), this.a("Invalid character");
1077
+ t > 65535 && (n += 1);
1078
+ }
1079
+ }
1080
+ };
1081
+ function N(e) {
1082
+ let t = 0;
1083
+ for (; (t = e.indexOf("\r", t)) !== -1;) e = e[t + 1] === "\n" ? e.slice(0, t) + e.slice(t + 1) : e.slice(0, t) + "\n" + e.slice(t + 1);
1084
+ return e;
1085
+ }
1086
+ function re(e, t) {
1087
+ return new ne(e, t).document;
1088
+ }
1089
+ })))(), Ce = class extends Error {
1090
+ constructor(e) {
1091
+ super(e);
1092
+ }
1093
+ };
1094
+ function we(e) {
1095
+ let t = null;
1096
+ try {
1097
+ t = (0, Se.parseXml)(e);
1098
+ } catch (e) {
1099
+ throw new Ce(e.message);
1100
+ }
1101
+ return t;
1102
+ }
1103
+ function F(e) {
1104
+ let t = e.indexOf(":");
1105
+ return t > -1 ? e.substr(t + 1) : e;
1106
+ }
1107
+ function I(e) {
1108
+ return e.children[0];
1109
+ }
1110
+ function L(e) {
1111
+ return e.name || "";
1112
+ }
1113
+ function R(e, t, n = !1) {
1114
+ let r = F(t);
1115
+ function i(e, t) {
1116
+ return F(L(t)) === r && e.push(t), n && Array.isArray(t.children) ? [...e, ...t.children.reduce(i, [])] : e;
1117
+ }
1118
+ return e && Array.isArray(e.children) ? e.children.reduce(i, []) : [];
1119
+ }
1120
+ function z(e, t, n = !1) {
1121
+ return R(e, t, n)[0] || null;
1122
+ }
1123
+ function B(e) {
1124
+ return e && Array.isArray(e.children) ? [...e.children.filter((e) => e instanceof Se.XmlElement)] : [];
1125
+ }
1126
+ function V(e) {
1127
+ let t = e && Array.isArray(e.children) ? e.children.find((e) => e.type === "text") : null;
1128
+ return t ? t.text : "";
1129
+ }
1130
+ function H(e, t) {
1131
+ return e && e.attributes[t] || "";
1132
+ }
1133
+ //#endregion
1134
+ //#region node_modules/@camptocamp/ogc-client/dist/shared/errors.js
1135
+ var Te = class extends Error {
1136
+ constructor(e, t, n) {
1137
+ super(e), this.httpStatus = t, this.isCrossOriginRelated = n, this.name = "EndpointError";
1138
+ }
1139
+ }, Ee = class extends Error {
1140
+ constructor(e, t, n, r, i) {
1141
+ super(e), this.requestUrl = t, this.code = n, this.locator = r, this.response = i, this.name = "ServiceExceptionError";
1142
+ }
1143
+ };
1144
+ function De(e, t) {
1145
+ let n = H(e, "code") || H(e, "exceptionCode"), r = H(e, "locator");
1146
+ return new Ee(V(z(e, "ExceptionText") || e).trim(), t, n, r, e.document);
1147
+ }
1148
+ function Oe(e, t) {
1149
+ let n = I(e), r = F(L(n));
1150
+ if (r === "ServiceExceptionReport") {
1151
+ let e = z(n, "ServiceException");
1152
+ if (e) throw De(e, t);
1153
+ }
1154
+ if (r === "ExceptionReport") {
1155
+ let e = z(n, "Exception");
1156
+ if (e) throw De(e, t);
1157
+ }
1158
+ return e;
1159
+ }
1160
+ function ke(e) {
1161
+ let t = {
1162
+ message: e.message,
1163
+ stack: e.stack,
1164
+ name: e.name
1165
+ };
1166
+ return e instanceof Ee ? {
1167
+ ...t,
1168
+ code: e.code,
1169
+ locator: e.locator,
1170
+ response: e.response,
1171
+ requestUrl: e.requestUrl
1172
+ } : e instanceof Te ? {
1173
+ ...t,
1174
+ httpStatus: e.httpStatus,
1175
+ isCrossOriginRelated: e.isCrossOriginRelated
1176
+ } : t;
1177
+ }
1178
+ //#endregion
1179
+ //#region node_modules/@camptocamp/ogc-client/dist/shared/encoding.js
1180
+ var Ae = [
1181
+ "utf-8",
1182
+ "utf-16",
1183
+ "iso-8859-1"
1184
+ ], je = "utf-8";
1185
+ function Me(e) {
1186
+ let t = /charset=([^;]+)/.exec(e);
1187
+ return t ? t[1] : null;
1188
+ }
1189
+ function Ne(e, t) {
1190
+ let n = t ? Me(t) : null, r = n ? [n, ...Ae] : Ae;
1191
+ for (let t of r) try {
1192
+ return new TextDecoder(t, { fatal: !0 }).decode(e);
1193
+ } catch {}
1194
+ return console.warn(`[ogc-client] XML document encoding could not be determined, falling back to ${je}.`), new TextDecoder(je).decode(e);
1195
+ }
1196
+ //#endregion
1197
+ //#region node_modules/@camptocamp/ogc-client/dist/shared/http-utils.js
1198
+ var Pe = /* @__PURE__ */ new Map(), Fe = {}, Ie = null;
1199
+ function Le(e) {
1200
+ Fe = e, Ie && Ie(e);
1201
+ }
1202
+ function Re() {
1203
+ return Fe;
1204
+ }
1205
+ function ze(e, t = "GET", n) {
1206
+ let r = `${t}#${e}`;
1207
+ if (n && (r = `${t}#asJson#${e}`), Pe.has(r)) return Pe.get(r);
1208
+ let i = { ...Re() };
1209
+ i.method = t, n && (i.headers = "headers" in i ? i.headers : {}, i.headers.Accept = "application/json,application/schema+json");
1210
+ let a = fetch(e, i).catch((e) => e).then((e) => (Pe.delete(r), e));
1211
+ return Pe.set(r, a), a.then((e) => {
1212
+ if (e instanceof Error) throw e;
1213
+ return e.clone();
1214
+ });
1215
+ }
1216
+ function U(e) {
1217
+ return ze(e).catch(() => fetch(e, {
1218
+ ...Re(),
1219
+ method: "HEAD",
1220
+ mode: "no-cors"
1221
+ }).catch((e) => {
1222
+ throw new Te(`Fetching the document failed either due to network errors or unreachable host, error is: ${e.message}`, 0, !1);
1223
+ }).then(() => {
1224
+ throw new Te("The document could not be fetched due to CORS limitations", 0, !0);
1225
+ })).then(async (e) => {
1226
+ if (!e.ok) {
1227
+ let t = await e.text();
1228
+ throw new Te(`Received an error with code ${e.status}: ${t}`, e.status, !1);
1229
+ }
1230
+ return Ne(await e.arrayBuffer(), e.headers.get("Content-Type"));
1231
+ }).then((e) => we(e));
1232
+ }
1233
+ function W(e, t) {
1234
+ let n = e.match(/(https?%3A%2F%2F[^/]+)$/);
1235
+ if (n) {
1236
+ let r = n[1], i = W(decodeURIComponent(r), t);
1237
+ return e.replace(r, encodeURIComponent(i));
1238
+ }
1239
+ let r = new URL(e), i = Object.keys(t), a = i.map((e) => e.toLowerCase()), o = [];
1240
+ for (let e of r.searchParams.keys()) a.indexOf(e.toLowerCase()) > -1 && o.push(e);
1241
+ return o.map((e) => r.searchParams.delete(e)), i.forEach((e) => r.searchParams.set(e, t[e] === !0 ? "" : t[e])), r.toString();
1242
+ }
1243
+ //#endregion
1244
+ //#region node_modules/@camptocamp/ogc-client/dist/wfs/featuretypeinfo.js
1245
+ function Be(e, t, n, r) {
1246
+ let { name: i, title: a, abstract: o, defaultCrs: s, otherCrs: c, outputFormats: l, latLonBoundingBox: u, keywords: d, metadata: f } = e, p = r.startsWith("2.0") ? "numberMatched" : "numberOfFeatures", m = parseInt(H(I(n), p)), h = R(I(t), "complexType", !0)[0], g = R(h, "element", !0), _ = g.filter((e) => /^xsd:|^xs:/.test(H(e, "type"))).reduce((e, t) => ({
1247
+ ...e,
1248
+ [H(t, "name")]: Ve(H(t, "type"))
1249
+ }), {}), v = g.filter((e) => H(e, "type").startsWith("gml:"))[0], y = v ? H(v, "name") : void 0, b = v ? He(H(v, "type")) : void 0;
1250
+ return {
1251
+ name: i,
1252
+ ...a && { title: a },
1253
+ ...o && { abstract: o },
1254
+ ...u && { boundingBox: u },
1255
+ ...s && { defaultCrs: s },
1256
+ ...c && { otherCrs: c },
1257
+ ...l && { outputFormats: l },
1258
+ properties: _,
1259
+ ...y && { geometryName: y },
1260
+ ...b && { geometryType: b },
1261
+ ...!Number.isNaN(m) && { objectCount: m },
1262
+ ...d && { keywords: d },
1263
+ ...f && { metadata: f }
1264
+ };
1265
+ }
1266
+ function Ve(e) {
1267
+ switch (e.indexOf(":") > -1 ? e.substr(e.indexOf(":") + 1) : e) {
1268
+ case "string": return "string";
1269
+ case "boolean": return "boolean";
1270
+ case "float":
1271
+ case "double":
1272
+ case "decimal": return "float";
1273
+ case "long":
1274
+ case "byte":
1275
+ case "integer":
1276
+ case "int":
1277
+ case "positiveInteger":
1278
+ case "negativeInteger":
1279
+ case "nonPositiveInteger":
1280
+ case "nonNegativeInteger":
1281
+ case "short":
1282
+ case "unsignedLong":
1283
+ case "unsignedInt":
1284
+ case "unsignedShort":
1285
+ case "unsignedByte": return "integer";
1286
+ default: return "string";
1287
+ }
1288
+ }
1289
+ function He(e) {
1290
+ switch (e.indexOf(":") > -1 ? e.substr(e.indexOf(":") + 1) : e) {
1291
+ case "PointPropertyType": return "point";
1292
+ case "MultiPointPropertyType": return "multipoint";
1293
+ case "CurvePropertyType":
1294
+ case "LineStringPropertyType": return "linestring";
1295
+ case "MultiCurvePropertyType":
1296
+ case "MultiLineStringPropertyType": return "linestring";
1297
+ case "PolygonPropertyType":
1298
+ case "SurfacePropertyType": return "polygon";
1299
+ case "MultiPolygonPropertyType":
1300
+ case "MultiSurfacePropertyType": return "multipolygon";
1301
+ default: return "unknown";
1302
+ }
1303
+ }
1304
+ //#endregion
1305
+ //#region node_modules/@camptocamp/ogc-client/dist/shared/cache.js
1306
+ var Ue = 1e3 * 60 * 60;
1307
+ function We() {
1308
+ return Ue;
1309
+ }
1310
+ var G;
1311
+ function K() {
1312
+ return G === void 0 ? "caches" in globalThis ? (G = caches.open("ogc-client").catch((e) => (console.info("[ogc-client] Cache could not be accessed for the following reason:", e), null)), G) : (G = Promise.resolve(null), G) : G;
1313
+ }
1314
+ async function Ge(e, ...t) {
1315
+ let n = await K();
1316
+ if (!n) return;
1317
+ let r = "https://cache/" + t.join("/");
1318
+ try {
1319
+ await n.put(r, new Response(JSON.stringify(e), { headers: { "x-expiry": (Date.now() + We()).toString(10) } }));
1320
+ } catch (e) {
1321
+ console.info("[ogc-client] Caching failed once for the following reason and will not be retried:", e), G = Promise.resolve(null);
1322
+ }
1323
+ }
1324
+ async function Ke(...e) {
1325
+ let t = await K();
1326
+ if (!t) return;
1327
+ let n = "https://cache/" + e.join("/");
1328
+ return t.match(n).then((e) => !!e && parseInt(e.headers.get("x-expiry")) > Date.now());
1329
+ }
1330
+ async function qe(...e) {
1331
+ let t = await K();
1332
+ if (!t) return;
1333
+ let n = "https://cache/" + e.join("/"), r = await t.match(n);
1334
+ return r ? r.clone().json() : null;
1335
+ }
1336
+ var q = /* @__PURE__ */ new Map();
1337
+ async function J(e, ...t) {
1338
+ if (await Je(), await Ke(...t)) return qe(...t);
1339
+ let n = t.join("#");
1340
+ if (q.has(n)) return q.get(n);
1341
+ let r = e();
1342
+ r instanceof Promise && (r.then(() => q.delete(n)), q.set(n, r));
1343
+ let i = await r;
1344
+ return await Ge(i, ...t), i;
1345
+ }
1346
+ async function Je() {
1347
+ let e = await K();
1348
+ if (!e) return;
1349
+ let t = await e.keys();
1350
+ for (let n of t) {
1351
+ let t = await e.match(n);
1352
+ parseInt(t.headers.get("x-expiry")) <= Date.now() && await e.delete(n);
1353
+ }
1354
+ }
1355
+ //#endregion
1356
+ //#region node_modules/@camptocamp/ogc-client/dist/wfs/url.js
1357
+ function Ye(e, t, n, r, i, a, o, s, c, l, u, d) {
1358
+ let f = t === "2.0.0" ? "TYPENAMES" : "TYPENAME", p = t === "2.0.0" ? "COUNT" : "MAXFEATURES", m = {
1359
+ SERVICE: "WFS",
1360
+ REQUEST: "GetFeature",
1361
+ VERSION: t,
1362
+ [f]: n
1363
+ };
1364
+ if (r !== void 0 && (m.OUTPUTFORMAT = r), a !== void 0 && (m.PROPERTYNAME = a.join(",")), o ? (m.RESULTTYPE = "hits", m[p] = "1") : i !== void 0 && (m[p] = i.toString(10)), s && (m.SRSNAME = s), c) {
1365
+ let e = c.join(",");
1366
+ m.BBOX = l ? `${e},${l}` : e;
1367
+ }
1368
+ u && (m.STARTINDEX = u.toString(10));
1369
+ let h = new URL(W(e, m));
1370
+ if (Array.isArray(d) && d.length > 0) {
1371
+ let e = d.map((e) => `${e[1]} ${e[0]}`).join(",");
1372
+ h.searchParams.set("SORTBY", e);
1373
+ }
1374
+ return h.toString();
1375
+ }
1376
+ function Xe(e, t, n) {
1377
+ return W(e, {
1378
+ SERVICE: "WFS",
1379
+ REQUEST: "DescribeFeatureType",
1380
+ VERSION: t,
1381
+ [t === "2.0.0" ? "TYPENAMES" : "TYPENAME"]: n
1382
+ });
1383
+ }
1384
+ //#endregion
1385
+ //#region node_modules/@camptocamp/ogc-client/dist/shared/mime-type.js
1386
+ function Ze(e) {
1387
+ return e.toLowerCase().indexOf("json") > -1;
1388
+ }
1389
+ //#endregion
1390
+ //#region node_modules/@camptocamp/ogc-client/dist/wfs/endpoint.js
1391
+ var Qe = class {
1392
+ _capabilitiesUrl;
1393
+ _capabilitiesPromise;
1394
+ _info;
1395
+ _featureTypes;
1396
+ _url;
1397
+ _version;
1398
+ constructor(e) {
1399
+ this._capabilitiesUrl = W(e, {
1400
+ SERVICE: "WFS",
1401
+ REQUEST: "GetCapabilities"
1402
+ }), this._capabilitiesPromise = J(() => ye(this._capabilitiesUrl), "WFS", "CAPABILITIES", this._capabilitiesUrl).then(({ info: e, featureTypes: t, url: n, version: r }) => {
1403
+ this._info = e, this._featureTypes = t, this._url = n, this._version = r;
1404
+ });
1405
+ }
1406
+ isReady() {
1407
+ return this._capabilitiesPromise.then(() => this);
1408
+ }
1409
+ getServiceInfo() {
1410
+ return this._info;
1411
+ }
1412
+ getFeatureTypes() {
1413
+ return this._featureTypes.map((e) => ({
1414
+ name: e.name,
1415
+ ..."title" in e && { title: e.title },
1416
+ ..."abstract" in e && { abstract: e.abstract },
1417
+ ..."latLonBoundingBox" in e && { boundingBox: e.latLonBoundingBox }
1418
+ }));
1419
+ }
1420
+ _getFeatureTypeByName(e) {
1421
+ if (!this._featureTypes) return null;
1422
+ let t = F(e) !== e;
1423
+ return this._featureTypes.find((n) => t ? n.name === e : F(n.name) === e) || null;
1424
+ }
1425
+ getFeatureTypeSummary(e) {
1426
+ let t = this._getFeatureTypeByName(e);
1427
+ return t ? {
1428
+ name: t.name,
1429
+ ..."title" in t && { title: t.title },
1430
+ ..."abstract" in t && { abstract: t.abstract },
1431
+ ..."latLonBoundingBox" in t && { boundingBox: t.latLonBoundingBox },
1432
+ defaultCrs: t.defaultCrs,
1433
+ otherCrs: t.otherCrs,
1434
+ outputFormats: t.outputFormats,
1435
+ keywords: t.keywords,
1436
+ ..."metadata" in t && { metadata: t.metadata }
1437
+ } : null;
1438
+ }
1439
+ getFeatureTypeFull(e) {
1440
+ let t = this._getFeatureTypeByName(e);
1441
+ return t ? J(() => {
1442
+ let n = Xe(this.getOperationUrl("DescribeFeatureType"), this._version, e), r = Ye(this.getOperationUrl("GetFeature"), this._version, e, void 0, void 0, void 0, !0);
1443
+ return Promise.all([U(n), U(r)]).then(([e, n]) => Be(t, e, n, this._version));
1444
+ }, "WFS", "FEATURETYPEINFO", this._capabilitiesUrl, e) : null;
1445
+ }
1446
+ getSingleFeatureTypeName() {
1447
+ return this._featureTypes && this._featureTypes.length === 1 ? this._featureTypes[0].name : null;
1448
+ }
1449
+ async getFeatureTypePropDetails(e) {
1450
+ let t = await this.getFeatureTypeFull(e);
1451
+ return t === null ? null : J(() => be(this._capabilitiesUrl, this._version, t).then((e) => e.props), "WFS", "FEATURETYPEPROPDETAILS", this._capabilitiesUrl, e);
1452
+ }
1453
+ getVersion() {
1454
+ return this._version;
1455
+ }
1456
+ _getJsonCompatibleOutputFormat(e) {
1457
+ let t = this._getFeatureTypeByName(e);
1458
+ if (!t) throw Error(`The following feature type was not found in the service: ${e}`);
1459
+ let n = t.outputFormats.filter(Ze);
1460
+ return n.length ? n[0] : null;
1461
+ }
1462
+ supportsJson(e) {
1463
+ return this._featureTypes ? !!this._getJsonCompatibleOutputFormat(e) : null;
1464
+ }
1465
+ supportsStartIndex() {
1466
+ return this._version ? this._version >= "2.0.0" : !1;
1467
+ }
1468
+ getFeatureUrl(e, t) {
1469
+ if (!this._featureTypes) return null;
1470
+ let { maxFeatures: n, asJson: r, outputFormat: i, outputCrs: a, extent: o, extentCrs: s, startIndex: c, attributes: l, hitsOnly: u } = t || {}, d = this._getFeatureTypeByName(e);
1471
+ if (!d) throw Error(`The following feature type was not found in the service: ${e}`);
1472
+ let f = i;
1473
+ if (r) {
1474
+ if (f = this._getJsonCompatibleOutputFormat(e) || void 0, !f) throw Error(`The endpoint does not appear to support GeoJSON for the feature type ${d.name}`);
1475
+ } else i && d.outputFormats.indexOf(i) === -1 && console.warn(`[ogc-client] The following output format type was not found in the feature type ${d.name}: ${i}`);
1476
+ return Ye(this.getOperationUrl("GetFeature"), this._version, d.name, f, n, l, u, a, o, s, c);
1477
+ }
1478
+ getCapabilitiesUrl() {
1479
+ let e = this.getOperationUrl("GetCapabilities");
1480
+ return e ? W(e, {
1481
+ SERVICE: "WMS",
1482
+ REQUEST: "GetCapabilities"
1483
+ }) : this._capabilitiesUrl;
1484
+ }
1485
+ getOperationUrl(e, t = "Get") {
1486
+ return this._url ? this._url[e]?.[t] : null;
1487
+ }
1488
+ };
1489
+ //#endregion
1490
+ //#region node_modules/@camptocamp/ogc-client/dist/wms/url.js
1491
+ function $e(e, t, n, r, i, a, o, s, c) {
1492
+ let l = t === "1.3.0" ? "CRS" : "SRS", u = {
1493
+ SERVICE: "WMS",
1494
+ REQUEST: "GetMap",
1495
+ VERSION: t,
1496
+ LAYERS: n,
1497
+ STYLES: c ?? ""
1498
+ };
1499
+ return u.WIDTH = r.toString(), u.HEIGHT = i.toString(), u.FORMAT = s ?? "image/png", u[l] = a, u.BBOX = o.join(","), W(e, u);
1500
+ }
1501
+ //#endregion
1502
+ //#region node_modules/@camptocamp/ogc-client/dist/wms/endpoint.js
1503
+ var et = class {
1504
+ _capabilitiesUrl;
1505
+ _capabilitiesPromise;
1506
+ _info;
1507
+ _layers;
1508
+ _url;
1509
+ _version;
1510
+ constructor(e) {
1511
+ this._capabilitiesUrl = W(e, {
1512
+ SERVICE: "WMS",
1513
+ REQUEST: "GetCapabilities"
1514
+ }), this._capabilitiesPromise = J(() => ve(this._capabilitiesUrl), "WMS", "CAPABILITIES", this._capabilitiesUrl).then(({ info: e, layers: t, url: n, version: r }) => {
1515
+ this._info = e, this._layers = t, this._url = n, this._version = r;
1516
+ });
1517
+ }
1518
+ isReady() {
1519
+ return this._capabilitiesPromise.then(() => this);
1520
+ }
1521
+ getServiceInfo() {
1522
+ return this._info;
1523
+ }
1524
+ getLayers() {
1525
+ function e(t) {
1526
+ return {
1527
+ title: t.title,
1528
+ name: t.name,
1529
+ abstract: t.abstract,
1530
+ ..."children" in t && { children: t.children.map(e) }
1531
+ };
1532
+ }
1533
+ return this._layers.map(e);
1534
+ }
1535
+ getFlattenedLayers() {
1536
+ return this.getLayers().flatMap(tt);
1537
+ }
1538
+ getLayerByName(e) {
1539
+ let t = null;
1540
+ function n(r) {
1541
+ if (t === null) {
1542
+ if (r.name === e) {
1543
+ t = r;
1544
+ return;
1545
+ }
1546
+ "children" in r && r.children.map(n);
1547
+ }
1548
+ }
1549
+ return this._layers.map(n), t;
1550
+ }
1551
+ getSingleLayerName() {
1552
+ if (!this._layers) return null;
1553
+ let e = [];
1554
+ function t(n) {
1555
+ n.name && e.push(n), "children" in n && n.children.map(t);
1556
+ }
1557
+ return this._layers.map(t), e.length === 1 ? e[0].name : null;
1558
+ }
1559
+ getVersion() {
1560
+ return this._version;
1561
+ }
1562
+ getMapUrl(e, t) {
1563
+ if (!this._layers) return null;
1564
+ let { widthPx: n, heightPx: r, crs: i, extent: a, outputFormat: o, styles: s } = t;
1565
+ return $e(this.getOperationUrl("GetMap") || this._capabilitiesUrl, this._version, e.join(","), n, r, i, a, o, s === void 0 ? "" : s.join(","));
1566
+ }
1567
+ getCapabilitiesUrl() {
1568
+ let e = this.getOperationUrl("GetCapabilities");
1569
+ return e ? W(e, {
1570
+ SERVICE: "WMS",
1571
+ REQUEST: "GetCapabilities"
1572
+ }) : this._capabilitiesUrl;
1573
+ }
1574
+ getOperationUrl(e, t = "Get") {
1575
+ return this._url ? this._url[e]?.[t] : null;
1576
+ }
1577
+ };
1578
+ function tt(e) {
1579
+ let t = {
1580
+ title: e.title,
1581
+ name: e.name,
1582
+ abstract: e.abstract
1583
+ };
1584
+ return "children" in e && Array.isArray(e.children) ? [t, ...e.children.flatMap(tt)] : [t];
1585
+ }
1586
+ //#endregion
1587
+ //#region node_modules/@camptocamp/ogc-client/dist/wmts/url.js
1588
+ function nt(e, t, n, r, i, a, o, s, c) {
1589
+ let l = {
1590
+ layer: n,
1591
+ style: r,
1592
+ tilematrixset: i,
1593
+ Service: "WMTS",
1594
+ Request: "GetTile",
1595
+ Format: c,
1596
+ TileMatrix: a,
1597
+ TileCol: s.toString(),
1598
+ TileRow: o.toString()
1599
+ };
1600
+ if (t === "REST") {
1601
+ let t = e;
1602
+ for (let e in l) t = t.replace(RegExp(`{${e}}`, "ig"), l[e]);
1603
+ return t;
1604
+ } else return W(e, l);
1605
+ }
1606
+ //#endregion
1607
+ //#region node_modules/@camptocamp/ogc-client/dist/wmts/endpoint.js
1608
+ var rt = class {
1609
+ _capabilitiesPromise;
1610
+ _info = null;
1611
+ _layers = null;
1612
+ _matrixSets = null;
1613
+ constructor(e) {
1614
+ let t = W(e, {
1615
+ SERVICE: "WMTS",
1616
+ REQUEST: "GetCapabilities"
1617
+ });
1618
+ this._capabilitiesPromise = J(() => xe(t), "WMTS", "CAPABILITIES", t).then(({ info: e, layers: t, matrixSets: n }) => {
1619
+ this._info = e, this._layers = t, this._matrixSets = n;
1620
+ });
1621
+ }
1622
+ isReady() {
1623
+ return this._capabilitiesPromise.then(() => this);
1624
+ }
1625
+ getServiceInfo() {
1626
+ return this._info;
1627
+ }
1628
+ getLayers() {
1629
+ return this._layers;
1630
+ }
1631
+ getMatrixSets() {
1632
+ return this._matrixSets;
1633
+ }
1634
+ getMatrixSetByIdentifier(e) {
1635
+ return this._matrixSets ? this._matrixSets.find((t) => t.identifier === e) ?? null : null;
1636
+ }
1637
+ getLayerByName(e) {
1638
+ return this._layers ? this._layers.find((t) => t.name === e) ?? null : null;
1639
+ }
1640
+ getSingleLayerName() {
1641
+ return this._layers && this._layers.length === 1 ? this._layers[0].name : null;
1642
+ }
1643
+ getLayerResourceLink(e, t) {
1644
+ if (!this._layers) return null;
1645
+ let n = this.getLayerByName(e), r = 0;
1646
+ t && (r = n.resourceLinks.findIndex((e) => e.format === t) || 0);
1647
+ let i = n.resourceLinks[r];
1648
+ return t && i.format !== t && console.warn(`[ogc-client] Requested '${t}' format for the WMTS layer but it is not available in REST encoding, falling back to '${i.format}'`), i;
1649
+ }
1650
+ getTileUrl(e, t, n, r, i, a, o) {
1651
+ if (!this._layers) return null;
1652
+ let s = this.getLayerResourceLink(e, o);
1653
+ return nt(s.url, s.encoding, e, t, n, r, i, a, s.format);
1654
+ }
1655
+ getDefaultDimensions(e) {
1656
+ if (!this._layers) return null;
1657
+ let t = this.getLayerByName(e);
1658
+ return t.dimensions ? t.dimensions.reduce((e, t) => ({
1659
+ ...e,
1660
+ [t.identifier]: t.defaultValue
1661
+ }), {}) : {};
1662
+ }
1663
+ tileGridModule;
1664
+ getOpenLayersTileGrid(e, t) {
1665
+ if (!this._layers) return null;
1666
+ this.tileGridModule ||= import("./ol-tilegrid-9VtyxaLG.js").catch((e) => (console.warn("[ogc-client] Cannot use getOpenLayersTileGrid, the 'ol' package is probably not available.\n", e), null));
1667
+ let n = this.getLayerByName(e), r = n.matrixSets.find((e) => e.identifier === t) ?? n.matrixSets[0], i = this.getMatrixSetByIdentifier(r.identifier);
1668
+ return this.tileGridModule.then((e) => e ? e.buildOpenLayersTileGrid(i, r.limits) : null);
1669
+ }
1670
+ }, it = new EventTarget();
1671
+ function Y(e, t, n) {
1672
+ let r = typeof WorkerGlobalScope < "u", i = async (i) => {
1673
+ if (i.taskName === e) {
1674
+ let a, o;
1675
+ try {
1676
+ a = await n(i.params);
1677
+ } catch (e) {
1678
+ o = ke(e);
1679
+ }
1680
+ let s = {
1681
+ taskName: e,
1682
+ requestId: i.requestId,
1683
+ ...a && { response: a },
1684
+ ...o && { error: o }
1685
+ };
1686
+ r ? t.postMessage(s) : it.dispatchEvent(new CustomEvent("ogc-client.response", { detail: s }));
1687
+ }
1688
+ };
1689
+ r ? t.addEventListener("message", (e) => i(e.data)) : it.addEventListener("ogc-client.request", (e) => i(e.detail));
1690
+ }
1691
+ //#endregion
1692
+ //#region node_modules/@camptocamp/ogc-client/dist/shared/crs-utils.js
1693
+ var at = /* @__PURE__ */ "EPSG:4046.EPSG:4075.EPSG:4120.EPSG:4122.EPSG:4124.EPSG:4126.EPSG:4149.EPSG:4151.EPSG:4153.EPSG:4155.EPSG:4157.EPSG:4159.EPSG:4161.EPSG:4163.EPSG:4165.EPSG:4167.EPSG:4169.EPSG:4171.EPSG:4173.EPSG:4175.EPSG:4178.EPSG:4180.EPSG:4182.EPSG:4184.EPSG:4188.EPSG:4190.EPSG:4191.EPSG:4196.EPSG:4198.EPSG:4202.EPSG:4210.EPSG:4211.EPSG:4214.EPSG:4226.EPSG:4229.EPSG:4231.EPSG:4233.EPSG:4236.EPSG:4238.EPSG:4240.EPSG:4242.EPSG:4244.EPSG:4246.EPSG:4248.EPSG:4250.EPSG:4252.EPSG:4255.EPSG:4258.EPSG:4261.EPSG:4264.EPSG:4267.EPSG:4270.EPSG:4273.EPSG:4276.EPSG:4279.EPSG:4281.EPSG:4284.EPSG:4286.EPSG:4288.EPSG:4292.EPSG:4295.EPSG:4297.EPSG:4299.EPSG:4302.EPSG:4324.EPSG:4326".split(".");
1694
+ function ot(e) {
1695
+ return at.indexOf(st(e)) > -1;
1696
+ }
1697
+ function st(e) {
1698
+ return /^urn:(?:x-)?ogc:def:crs:epsg:/.test(e.toLowerCase()) ? `EPSG:${/([0-9]+)$/.exec(e)[1]}` : e;
1699
+ }
1700
+ //#endregion
1701
+ //#region node_modules/@camptocamp/ogc-client/dist/wms/capabilities.js
1702
+ function ct(e) {
1703
+ let t = {};
1704
+ return B(z(z(I(e), "Capability"), "Request")).forEach((e) => {
1705
+ let n = F(L(e));
1706
+ t[n] = ht(e);
1707
+ }), t;
1708
+ }
1709
+ function lt(e) {
1710
+ return I(e).attributes.version;
1711
+ }
1712
+ function ut(e) {
1713
+ let t = lt(e);
1714
+ return R(z(I(e), "Capability"), "Layer").map((e) => gt(e, t));
1715
+ }
1716
+ function dt(e) {
1717
+ return R(z(z(z(I(e), "Capability"), "Request"), "GetMap"), "Format").map(V);
1718
+ }
1719
+ function ft(e) {
1720
+ return R(z(z(z(I(e), "Capability"), "Request"), "GetFeatureInfo"), "Format").map(V);
1721
+ }
1722
+ function pt(e) {
1723
+ return R(z(z(I(e), "Capability"), "Exception"), "Format").map(V);
1724
+ }
1725
+ function mt(e) {
1726
+ let t = z(I(e), "Service"), n = dt(e), r = ft(e), i = pt(e), a = R(z(t, "KeywordList"), "Keyword").map(V).filter((e, t, n) => n.indexOf(e) === t), o = yt(e);
1727
+ return {
1728
+ title: V(z(t, "Title")),
1729
+ name: V(z(t, "Name")),
1730
+ abstract: V(z(t, "Abstract")),
1731
+ outputFormats: n,
1732
+ infoFormats: r,
1733
+ exceptionFormats: i,
1734
+ fees: V(z(t, "Fees")),
1735
+ constraints: V(z(t, "AccessConstraints")),
1736
+ provider: o,
1737
+ keywords: a
1738
+ };
1739
+ }
1740
+ function ht(e) {
1741
+ let t = {};
1742
+ return R(e, "DCPType").flatMap((e) => z(e, "HTTP")).flatMap((e) => B(e)).forEach((e) => {
1743
+ let n = z(e, "OnlineResource"), r = F(L(e));
1744
+ t[r] = H(n, "xlink:href");
1745
+ }), t;
1746
+ }
1747
+ function gt(e, t, n = [], r = [], i = null, a = null, o = null, s = null) {
1748
+ let c = t === "1.3.0" ? "CRS" : "SRS", l = R(e, c).map(V), u = l.length > 0 ? l : n, d = R(e, "Style").map(_t), f = d.length > 0 ? d : r;
1749
+ function p(e) {
1750
+ return (ot(H(e, c)) && t === "1.3.0" ? [
1751
+ "miny",
1752
+ "minx",
1753
+ "maxy",
1754
+ "maxx"
1755
+ ] : [
1756
+ "minx",
1757
+ "miny",
1758
+ "maxx",
1759
+ "maxy"
1760
+ ]).map((t) => H(e, t));
1761
+ }
1762
+ function m(e) {
1763
+ return [
1764
+ "westBoundLongitude",
1765
+ "southBoundLatitude",
1766
+ "eastBoundLongitude",
1767
+ "northBoundLatitude"
1768
+ ].map((t) => V(z(e, t)));
1769
+ }
1770
+ function h(e) {
1771
+ return [
1772
+ "minx",
1773
+ "miny",
1774
+ "maxx",
1775
+ "maxy"
1776
+ ].map((t) => H(e, t));
1777
+ }
1778
+ function g(e, t) {
1779
+ return e === "" ? t : Math.sqrt(.5 * parseFloat(e) ** 2) / 28e-5;
1780
+ }
1781
+ function _() {
1782
+ let t = z(e, "ScaleHint");
1783
+ if (!t) return [s, o];
1784
+ let n = H(t, "min"), r = H(t, "max");
1785
+ return [g(n, s), g(r, o)];
1786
+ }
1787
+ function v(t, n) {
1788
+ let r = V(z(e, t));
1789
+ return r === "" ? n : parseFloat(r);
1790
+ }
1791
+ let y = z(e, "Attribution"), b = y === null ? i : vt(y), x = t === "1.3.0" ? z(e, "EX_GeographicBoundingBox") : z(e, "LatLonBoundingBox"), S = {};
1792
+ x && (S["EPSG:4326"] = t === "1.3.0" ? m(x) : h(x));
1793
+ let C = R(e, "BoundingBox").reduce((e, t) => ({
1794
+ ...e,
1795
+ [H(t, c)]: p(t)
1796
+ }), S);
1797
+ C = Object.keys(C).length > 0 || a === null ? C : a;
1798
+ let w = e.attributes.queryable === "1" || e.attributes.queryable === "true", T = e.attributes.opaque === "1" || e.attributes.opaque === "true", E = R(z(e, "KeywordList"), "Keyword").map(V).filter((e, t, n) => n.indexOf(e) === t), D, O;
1799
+ t === "1.3.0" ? (D = v("MinScaleDenominator", s), O = v("MaxScaleDenominator", o)) : [D, O] = _();
1800
+ let k = R(e, "MetadataURL").map((e) => ({
1801
+ type: H(e, "type"),
1802
+ format: V(z(e, "Format")),
1803
+ url: H(z(e, "OnlineResource"), "xlink:href")
1804
+ })), A = R(e, "Layer").map((e) => gt(e, t, u, f, b, C, O, D));
1805
+ return {
1806
+ name: V(z(e, "Name")),
1807
+ title: V(z(e, "Title")),
1808
+ abstract: V(z(e, "Abstract")),
1809
+ availableCrs: u,
1810
+ styles: f,
1811
+ attribution: b,
1812
+ boundingBoxes: C,
1813
+ keywords: E,
1814
+ queryable: w,
1815
+ opaque: T,
1816
+ ...D === null ? {} : { minScaleDenominator: D },
1817
+ ...O === null ? {} : { maxScaleDenominator: O },
1818
+ ...k.length && { metadata: k },
1819
+ ...A.length && { children: A }
1820
+ };
1821
+ }
1822
+ function _t(e) {
1823
+ let t = H(z(z(e, "LegendURL"), "OnlineResource"), "xlink:href"), n = V(z(e, "Abstract"));
1824
+ return {
1825
+ name: V(z(e, "Name")),
1826
+ title: V(z(e, "Title")),
1827
+ ...n && { abstract: n },
1828
+ ...t && { legendUrl: t }
1829
+ };
1830
+ }
1831
+ function vt(e) {
1832
+ let t = H(z(z(e, "LogoURL"), "OnlineResource"), "xlink:href"), n = H(z(e, "OnlineResource"), "xlink:href"), r = V(z(e, "Title"));
1833
+ return {
1834
+ ...r && { title: r },
1835
+ ...n && { url: n },
1836
+ ...t && { logoUrl: t }
1837
+ };
1838
+ }
1839
+ function yt(e) {
1840
+ let t = z(z(I(e), "Service"), "ContactInformation"), n = z(t, "ContactPersonPrimary"), r = z(t, "ContactAddress");
1841
+ return { contact: {
1842
+ name: V(z(n, "ContactPerson")),
1843
+ organization: V(z(n, "ContactOrganization")),
1844
+ position: V(z(t, "ContactPosition")),
1845
+ phone: V(z(t, "ContactVoiceTelephone")),
1846
+ fax: V(z(t, "ContactFacsimileTelephone")),
1847
+ address: {
1848
+ deliveryPoint: V(z(r, "Address")),
1849
+ city: V(z(r, "City")),
1850
+ administrativeArea: V(z(r, "StateOrProvince")),
1851
+ postalCode: V(z(r, "PostCode")),
1852
+ country: V(z(r, "Country"))
1853
+ },
1854
+ email: V(z(t, "ContactElectronicMailAddress"))
1855
+ } };
1856
+ }
1857
+ //#endregion
1858
+ //#region node_modules/@camptocamp/ogc-client/dist/shared/ows.js
1859
+ function bt(e) {
1860
+ let t = z(I(e), "ServiceProvider"), n = z(t, "ServiceContact"), r = z(n, "ContactInfo"), i = z(r, "Phone"), a = z(r, "Address");
1861
+ return {
1862
+ name: V(z(t, "ProviderName")),
1863
+ site: H(z(t, "ProviderSite"), "xlink:href"),
1864
+ contact: {
1865
+ name: V(z(n, "IndividualName")),
1866
+ position: V(z(n, "PositionName")),
1867
+ phone: V(z(i, "Voice")),
1868
+ fax: V(z(i, "Facsimile")),
1869
+ address: {
1870
+ deliveryPoint: V(z(a, "DeliveryPoint")),
1871
+ city: V(z(a, "City")),
1872
+ administrativeArea: V(z(a, "AdministrativeArea")),
1873
+ postalCode: V(z(a, "PostalCode")),
1874
+ country: V(z(a, "Country"))
1875
+ },
1876
+ email: V(z(a, "ElectronicMailAddress"))
1877
+ }
1878
+ };
1879
+ }
1880
+ //#endregion
1881
+ //#region node_modules/@camptocamp/ogc-client/dist/wfs/capabilities.js
1882
+ function xt(e) {
1883
+ let t = {}, n = I(e), r = z(n, "OperationsMetadata");
1884
+ return r ? R(r, "Operation").forEach((e) => {
1885
+ let n = H(e, "name");
1886
+ t[n] = Dt(e);
1887
+ }) : B(z(z(n, "Capability"), "Request")).forEach((e) => {
1888
+ let n = F(L(e));
1889
+ t[n] = Et(e);
1890
+ }), t;
1891
+ }
1892
+ function St(e) {
1893
+ return I(e).attributes.version;
1894
+ }
1895
+ function Ct(e) {
1896
+ let t = St(e), n;
1897
+ return n = t.startsWith("1.0") ? B(z(z(z(z(I(e), "Capability"), "Request"), "GetFeature"), "ResultFormat")).map(L) : R(R(R(z(I(e), "OperationsMetadata"), "Operation").find((e) => H(e, "name") === "GetFeature"), "Parameter").find((e) => H(e, "name") === "outputFormat"), "Value", !0).map(V), n;
1898
+ }
1899
+ function wt(e) {
1900
+ let t = St(e), n = t.startsWith("1.0") ? "Service" : "ServiceIdentification", r = t.startsWith("1.0") ? "Name" : "ServiceType", i = z(I(e), n), a;
1901
+ a = t.startsWith("1.0") ? V(z(i, "Keywords")).split(",").map((e) => e.trim()) : R(z(i, "Keywords"), "Keyword").map(V);
1902
+ let o;
1903
+ return t !== "1.0.0" && (o = bt(e)), {
1904
+ title: V(z(i, "Title")),
1905
+ name: V(z(i, r)),
1906
+ abstract: V(z(i, "Abstract")),
1907
+ fees: V(z(i, "Fees")),
1908
+ constraints: V(z(i, "AccessConstraints")),
1909
+ keywords: a,
1910
+ provider: o,
1911
+ outputFormats: Ct(e)
1912
+ };
1913
+ }
1914
+ function Tt(e) {
1915
+ let t = St(e), n = Ct(e);
1916
+ return R(z(I(e), "FeatureTypeList"), "FeatureType").map((e) => Ot(e, t, n));
1917
+ }
1918
+ function Et(e) {
1919
+ let t = {};
1920
+ return R(e, "DCPType").flatMap((e) => R(e, "HTTP")).flatMap((e) => B(e)).forEach((e) => {
1921
+ let n = F(L(e));
1922
+ t[n] = H(e, "onlineResource");
1923
+ }), t;
1924
+ }
1925
+ function Dt(e) {
1926
+ let t = {};
1927
+ return R(e, "DCP").flatMap((e) => z(e, "HTTP")).flatMap((e) => B(e)).forEach((e) => {
1928
+ let n = F(L(e));
1929
+ t[n] = H(e, "xlink:href");
1930
+ }), t;
1931
+ }
1932
+ function Ot(e, t, n) {
1933
+ let r = t.startsWith("2.") ? "CRS" : "SRS", i = t.startsWith("1.0") ? "SRS" : `Default${r}`;
1934
+ function a() {
1935
+ let t = z(e, "LatLongBoundingBox");
1936
+ return [
1937
+ "minx",
1938
+ "miny",
1939
+ "maxx",
1940
+ "maxy"
1941
+ ].map((e) => H(t, e)).map(parseFloat);
1942
+ }
1943
+ function o() {
1944
+ let t = z(e, "WGS84BoundingBox");
1945
+ return ["LowerCorner", "UpperCorner"].map((e) => z(t, e)).map((e) => V(e).split(" ")).reduce((e, t) => [...e, ...t]).map(parseFloat);
1946
+ }
1947
+ let s = t.startsWith("1.0") ? [] : R(e, `Other${r}`).map(V).map(st), c = t.startsWith("1.0") ? [] : R(z(e, "OutputFormats"), "Format").map(V), l = t.startsWith("1.0") ? V(z(e, "Keywords")).split(",").map((e) => e.trim()) : R(z(e, "Keywords"), "Keyword").map(V).filter((e, t, n) => n.indexOf(e) === t), u = t === "2.0.0" ? R(e, "MetadataURL").map((e) => ({ url: H(e, "xlink:href") })) : R(e, "MetadataURL").map((e) => ({
1948
+ format: H(e, "format"),
1949
+ type: H(e, "type"),
1950
+ url: V(e).trim()
1951
+ }));
1952
+ return {
1953
+ name: V(z(e, "Name")),
1954
+ title: V(z(e, "Title")),
1955
+ abstract: V(z(e, "Abstract")),
1956
+ defaultCrs: st(V(z(e, i))),
1957
+ otherCrs: s,
1958
+ outputFormats: c.length > 0 ? c : n,
1959
+ latLonBoundingBox: t.startsWith("1.0") ? a() : o(),
1960
+ keywords: l,
1961
+ ...u.length && { metadata: u }
1962
+ };
1963
+ }
1964
+ //#endregion
1965
+ //#region node_modules/@camptocamp/ogc-client/dist/wmts/capabilities.js
1966
+ function kt(e) {
1967
+ let t = ["LowerCorner", "UpperCorner"].map((t) => z(e, t)).map((e) => V(e).split(" ")).reduce((e, t) => [...e, ...t]).map(parseFloat);
1968
+ return t.some(Number.isNaN) ? null : t;
1969
+ }
1970
+ function At(e) {
1971
+ let t = I(e), n = z(t, "ServiceIdentification"), r = R(z(n, "Keywords"), "Keyword").map(V), i = R(R(z(t, "OperationsMetadata"), "Operation").find((e) => H(e, "name") == "GetTile"), "Get", !0).reduce((e, t) => {
1972
+ let n = V(z(t, "Value", !0)), r = H(t, "xlink:href");
1973
+ return n.toLowerCase() === "restful" ? {
1974
+ ...e,
1975
+ rest: r
1976
+ } : {
1977
+ ...e,
1978
+ kvp: r
1979
+ };
1980
+ }, {});
1981
+ return {
1982
+ title: V(z(n, "Title")),
1983
+ name: V(z(n, "ServiceType")),
1984
+ abstract: V(z(n, "Abstract")),
1985
+ fees: V(z(n, "Fees")),
1986
+ constraints: V(z(n, "AccessConstraints")),
1987
+ keywords: r,
1988
+ provider: bt(e),
1989
+ getTileUrls: i
1990
+ };
1991
+ }
1992
+ function jt(e) {
1993
+ function t(e) {
1994
+ let t = V(z(e, "TopLeftCorner")).split(" ").map(parseFloat);
1995
+ return {
1996
+ identifier: V(z(e, "Identifier")),
1997
+ tileWidth: parseInt(V(z(e, "TileWidth"))),
1998
+ tileHeight: parseInt(V(z(e, "TileHeight"))),
1999
+ matrixWidth: parseInt(V(z(e, "MatrixWidth"))),
2000
+ matrixHeight: parseInt(V(z(e, "MatrixHeight"))),
2001
+ scaleDenominator: parseFloat(V(z(e, "ScaleDenominator"))),
2002
+ topLeft: t
2003
+ };
2004
+ }
2005
+ return R(z(I(e), "Contents"), "TileMatrixSet").map((e) => {
2006
+ let n = V(z(e, "WellKnownScaleSet")), r = kt(z(e, "BoundingBox"));
2007
+ return {
2008
+ identifier: V(z(e, "Identifier")),
2009
+ crs: V(z(e, "SupportedCRS")),
2010
+ tileMatrices: R(e, "TileMatrix").map(t),
2011
+ ...r && { boundingBox: r },
2012
+ ...n && { wellKnownScaleSet: n }
2013
+ };
2014
+ });
2015
+ }
2016
+ function Mt(e) {
2017
+ let t = I(e), n = z(t, "Contents");
2018
+ function r(e, t) {
2019
+ return V(z(R(e, "TileMatrixSet").find((e) => V(z(e, "Identifier")) === t), "SupportedCRS"));
2020
+ }
2021
+ function i(e) {
2022
+ let t = V(z(e, "TileMatrixSet"));
2023
+ return {
2024
+ identifier: t,
2025
+ crs: r(n, t),
2026
+ limits: R(e, "TileMatrixLimits", !0).map((e) => ({
2027
+ tileMatrix: V(z(e, "TileMatrix")),
2028
+ minTileRow: parseInt(V(z(e, "MinTileRow"))),
2029
+ minTileCol: parseInt(V(z(e, "MinTileCol"))),
2030
+ maxTileRow: parseInt(V(z(e, "MaxTileRow"))),
2031
+ maxTileCol: parseInt(V(z(e, "MaxTileCol")))
2032
+ }))
2033
+ };
2034
+ }
2035
+ let a = R(R(z(t, "OperationsMetadata"), "Operation").find((e) => H(e, "name") == "GetTile"), "Get", !0).filter((e) => V(z(e, "Value", !0)).toLowerCase() === "kvp")[0], o = a ? H(a, "xlink:href") : "";
2036
+ return R(z(t, "Contents"), "Layer").map((e) => {
2037
+ let t = kt(z(e, "WGS84BoundingBox")), n = "", r = R(e, "Style").map((e) => {
2038
+ let t = H(z(e, "LegendURL"), "xlink:href"), r = V(z(e, "Abstract")), i = {
2039
+ title: V(z(e, "Title")),
2040
+ name: V(z(e, "Identifier")),
2041
+ ...r && { abstract: r },
2042
+ ...t && { legendUrl: t }
2043
+ };
2044
+ return H(e, "isDefault") === "true" && (n = i.name), i;
2045
+ }), a = R(e, "Format").map(V), s = R(e, "ResourceURL").filter((e) => H(e, "resourceType") === "tile").map((e) => ({
2046
+ format: H(e, "format"),
2047
+ url: H(e, "template"),
2048
+ encoding: "REST"
2049
+ }));
2050
+ o && s.push(...a.map((e) => ({
2051
+ encoding: "KVP",
2052
+ url: o,
2053
+ format: e
2054
+ })));
2055
+ let c = R(e, "TileMatrixSetLink").map(i), l = R(e, "Dimension").map((e) => ({
2056
+ identifier: V(z(e, "Identifier")),
2057
+ defaultValue: V(z(e, "Default")),
2058
+ values: R(e, "Values").map(V)
2059
+ }));
2060
+ return {
2061
+ name: V(z(e, "Identifier")),
2062
+ title: V(z(e, "Title")),
2063
+ abstract: V(z(e, "Abstract")),
2064
+ styles: r,
2065
+ resourceLinks: s,
2066
+ matrixSets: c,
2067
+ defaultStyle: n,
2068
+ ...t && { latLonBoundingBox: t },
2069
+ ...l && { dimensions: l }
2070
+ };
2071
+ });
2072
+ }
2073
+ //#endregion
2074
+ //#region node_modules/@camptocamp/ogc-client/dist/wfs/featureprops.js
2075
+ function Nt(e, t, n) {
2076
+ let r = I(e), i;
2077
+ if (n.startsWith("2.0")) i = R(r, "member").map((e) => B(e)[0]);
2078
+ else {
2079
+ let e = z(r, "featureMembers");
2080
+ i = e ? B(e) : R(r, "featureMember").map((e) => B(e)[0]);
2081
+ }
2082
+ let a = n === "1.0.0" ? "fid" : "gml:id";
2083
+ function o(e) {
2084
+ return e in t.properties;
2085
+ }
2086
+ function s(e, n) {
2087
+ switch (t.properties[e]) {
2088
+ case "integer": return parseInt(n);
2089
+ case "float": return parseFloat(n);
2090
+ case "boolean": return n === "true";
2091
+ default: return n;
2092
+ }
2093
+ }
2094
+ function c(e) {
2095
+ return B(e).filter((e) => o(F(L(e)))).reduce((e, t) => {
2096
+ let n = F(L(t));
2097
+ return {
2098
+ ...e,
2099
+ [n]: s(n, V(t))
2100
+ };
2101
+ }, {});
2102
+ }
2103
+ return i.map((e) => ({
2104
+ id: H(e, a),
2105
+ properties: c(e)
2106
+ }));
2107
+ }
2108
+ function Pt(e) {
2109
+ return e.reduce((e, t) => {
2110
+ for (let n in t.properties) {
2111
+ let r = t.properties[n];
2112
+ n in e || (e[n] = { uniqueValues: [] });
2113
+ let i = e[n].uniqueValues.find((e) => e.value === r);
2114
+ i ? i.count++ : e[n].uniqueValues.push({
2115
+ value: r,
2116
+ count: 1
2117
+ });
2118
+ }
2119
+ return e;
2120
+ }, {});
2121
+ }
2122
+ Y("parseWmsCapabilities", globalThis, ({ url: e }) => U(e).then((t) => Oe(t, e)).then((e) => ({
2123
+ info: mt(e),
2124
+ layers: ut(e),
2125
+ url: ct(e),
2126
+ version: lt(e)
2127
+ }))), Y("parseWfsCapabilities", globalThis, ({ url: e }) => U(e).then((t) => Oe(t, e)).then((e) => ({
2128
+ info: wt(e),
2129
+ featureTypes: Tt(e),
2130
+ url: xt(e),
2131
+ version: St(e)
2132
+ }))), Y("queryWfsFeatureTypeDetails", globalThis, ({ url: e, serviceVersion: t, featureTypeFull: n }) => U(Ye(e, t, n.name, void 0, void 0, Object.keys(n.properties))).then((e) => ({ props: Pt(Nt(e, n, t)) }))), Y("updateFetchOptions", globalThis, ({ options: e }) => (Le(e), Promise.resolve({}))), Y("parseWmtsCapabilities", globalThis, ({ url: e }) => U(e).then((t) => Oe(t, e)).then((e) => ({
2133
+ info: At(e),
2134
+ layers: Mt(e),
2135
+ matrixSets: jt(e)
2136
+ })));
2137
+ //#endregion
2138
+ //#region src/utils/esri-drawing-info.ts
2139
+ function X(e, t = 1) {
2140
+ if (!e) return;
2141
+ let [n, r, i, a = 255] = e;
2142
+ return `rgba(${n}, ${r}, ${i}, ${a / 255 * t})`;
2143
+ }
2144
+ function Ft(e) {
2145
+ return typeof e == "number" ? (100 - Math.min(100, Math.max(0, e))) / 100 : 1;
2146
+ }
2147
+ function It(e) {
2148
+ return typeof e == "number" ? e : void 0;
2149
+ }
2150
+ var Lt = {
2151
+ esrislsdash: [4, 3],
2152
+ esrislsdot: [1, 3],
2153
+ esrislsdashdot: [
2154
+ 4,
2155
+ 3,
2156
+ 1,
2157
+ 3
2158
+ ],
2159
+ esrislsdashdotdot: [
2160
+ 4,
2161
+ 3,
2162
+ 1,
2163
+ 3,
2164
+ 1,
2165
+ 3
2166
+ ]
2167
+ };
2168
+ function Rt(e, t, n = 1) {
2169
+ if (!e) return {};
2170
+ switch (t) {
2171
+ case "fill": {
2172
+ let t = {}, r = X(e.outline?.color, n);
2173
+ r && (t["fill-outline-color"] = r);
2174
+ let i = X(e.color, n);
2175
+ return i && (t["fill-color"] = i), t;
2176
+ }
2177
+ case "line": {
2178
+ let t = {}, r = X(e.color, n);
2179
+ r && (t["line-color"] = r);
2180
+ let i = It(e.width);
2181
+ i !== void 0 && (t["line-width"] = i);
2182
+ let a = Lt[(e.style ?? "").toLowerCase()];
2183
+ return a && (t["line-dasharray"] = a), t;
2184
+ }
2185
+ case "circle": {
2186
+ let t = {}, r = X(e.color, n);
2187
+ r && (t["circle-color"] = r);
2188
+ let i = It(e.size);
2189
+ i !== void 0 && (t["circle-radius"] = i / 2);
2190
+ let a = X(e.outline?.color, n);
2191
+ a && (t["circle-stroke-color"] = a);
2192
+ let o = It(e.outline?.width);
2193
+ return o !== void 0 && (t["circle-stroke-width"] = o), t;
2194
+ }
2195
+ }
2196
+ }
2197
+ function zt(e, t) {
2198
+ let n = e?.outline, r = It(n?.width);
2199
+ if (!n || r === void 0 || r <= 1) return;
2200
+ let i = X(n.color, t);
2201
+ if (!i) return;
2202
+ let a = {
2203
+ "line-color": i,
2204
+ "line-width": r
2205
+ }, o = Lt[(n.style ?? "").toLowerCase()];
2206
+ return o && (a["line-dasharray"] = o), { paint: a };
2207
+ }
2208
+ var Bt = {
2209
+ fill: "fill-color",
2210
+ line: "line-color",
2211
+ circle: "circle-color"
2212
+ };
2213
+ function Vt(e) {
2214
+ let t = [
2215
+ e.field1,
2216
+ e.field2,
2217
+ e.field3
2218
+ ].filter((e) => !!e);
2219
+ if (t.length === 0) return;
2220
+ if (t.length === 1) return ["get", t[0]];
2221
+ let n = e.fieldDelimiter ?? ",", r = ["concat"];
2222
+ return t.forEach((e, t) => {
2223
+ t > 0 && r.push(n), r.push(["to-string", ["get", e]]);
2224
+ }), r;
2225
+ }
2226
+ function Ht(e, t) {
2227
+ let n = e?.renderer;
2228
+ if (!n) return;
2229
+ let r = Ft(n.transparency);
2230
+ switch (n.type) {
2231
+ case "simple": {
2232
+ let e = Rt(n.symbol, t, r);
2233
+ if (!Object.keys(e).length) return;
2234
+ let i = t === "fill" ? zt(n.symbol, r) : void 0;
2235
+ return {
2236
+ paint: e,
2237
+ ...i ? { outline: i } : {}
2238
+ };
2239
+ }
2240
+ case "uniqueValue": {
2241
+ let e = Vt(n), i = n.uniqueValueInfos;
2242
+ if (!e || !i?.length) return;
2243
+ let a = Bt[t], o = ["match", e], s, c = /* @__PURE__ */ new Set();
2244
+ for (let e of i) {
2245
+ let t = X(e.symbol?.color, r);
2246
+ t && (c.has(e.value) || (c.add(e.value), o.push(e.value, t), s ??= t));
2247
+ }
2248
+ if (s = X(n.defaultSymbol?.color, r) ?? s, !s) return;
2249
+ o.push(s);
2250
+ let l = Rt(i[0]?.symbol, t, r);
2251
+ l[a] = o;
2252
+ let u = t === "fill" ? zt(i[0]?.symbol, r) : void 0;
2253
+ return {
2254
+ paint: l,
2255
+ ...u ? { outline: u } : {}
2256
+ };
2257
+ }
2258
+ case "classBreaks": {
2259
+ let e = n.field, i = n.classBreakInfos;
2260
+ if (!e || !i?.length) return;
2261
+ let a = Bt[t], o = ["step", ["get", e]], s = X(i[0]?.symbol?.color, r) ?? X(n.defaultSymbol?.color, r);
2262
+ if (!s) return;
2263
+ o.push(s);
2264
+ for (let e = 0; e < i.length - 1; e++) {
2265
+ let t = X(i[e + 1]?.symbol?.color, r) ?? X(n.defaultSymbol?.color, r);
2266
+ if (!t) return;
2267
+ o.push(i[e].classMaxValue, t);
2268
+ }
2269
+ let c = Rt(i[0]?.symbol, t, r);
2270
+ c[a] = o;
2271
+ let l = t === "fill" ? zt(i[0]?.symbol, r) : void 0;
2272
+ return {
2273
+ paint: c,
2274
+ ...l ? { outline: l } : {}
2275
+ };
2276
+ }
2277
+ default: return;
2278
+ }
2279
+ }
2280
+ //#endregion
2281
+ //#region src/utils/layer-discovery.ts
2282
+ typeof window < "u" && window.addEventListener("unhandledrejection", (e) => {
2283
+ e.reason?.name === "ServiceExceptionError" && /No service:\s*\(\s*WMTS\s*\)/.test(String(e.reason?.message)) && e.preventDefault();
2284
+ });
2285
+ function Ut(e) {
2286
+ return e.toLowerCase().replace(/[^a-z0-9]+/g, "-").replace(/^-+|-+$/g, "").slice(0, 40) || "layer";
2287
+ }
2288
+ function Wt(e) {
2289
+ return e.split("?")[0].split("#")[0];
2290
+ }
2291
+ function Z(e, t, n = {}) {
2292
+ return {
2293
+ id: e,
2294
+ type: "raster",
2295
+ tiles: t,
2296
+ url: t,
2297
+ service: "xyz",
2298
+ ...n
2299
+ };
2300
+ }
2301
+ function Gt(e) {
2302
+ if (!e || e.length !== 4) return;
2303
+ let t = e.map((e) => typeof e == "number" ? e : parseFloat(String(e)));
2304
+ return t.every(Number.isFinite) ? t : void 0;
2305
+ }
2306
+ function Q(e) {
2307
+ if (!Number.isFinite(e) || e <= 0) return 0;
2308
+ let t = Math.log2(559082264.02867 / e);
2309
+ return Math.max(0, Math.round(t * 100) / 100);
2310
+ }
2311
+ function Kt(e) {
2312
+ let t = e.match(/^(.*\/)(\d+)\/(\d+)\/(\d+)(\.[a-z0-9]+)?(\?.*)?$/i);
2313
+ if (!t) return null;
2314
+ let [, n, , , , r] = t, i = `${n}{z}/{x}/{y}${r ?? ""}`;
2315
+ return {
2316
+ serviceType: "xyz",
2317
+ title: `XYZ tiles (${n.replace(/^https?:\/\//, "")})`,
2318
+ source: Z("xyz", [i]),
2319
+ layer: {
2320
+ id: "xyz",
2321
+ type: "raster",
2322
+ source: "xyz",
2323
+ title: "XYZ tiles"
2324
+ }
2325
+ };
2326
+ }
2327
+ function qt(e) {
2328
+ let t = e.match(/^(.*\/)([\w.\-]+)\/mvt\/\d+\/\d+\/\d+(\?.*)?$/i);
2329
+ if (!t) return null;
2330
+ let [, n, r, i] = t, a = `${n}${r}/mvt/{z}/{x}/{y}${i ?? ""}`, o = r, s = {
2331
+ id: o,
2332
+ type: "vector",
2333
+ tiles: [a]
2334
+ }, c = [
2335
+ {
2336
+ id: "fill",
2337
+ type: "fill",
2338
+ source: o,
2339
+ "source-layer": r,
2340
+ filter: [
2341
+ "==",
2342
+ ["geometry-type"],
2343
+ "Polygon"
2344
+ ],
2345
+ paint: {
2346
+ "fill-color": "#3388ff",
2347
+ "fill-opacity": .4
2348
+ }
2349
+ },
2350
+ {
2351
+ id: "line",
2352
+ type: "line",
2353
+ source: o,
2354
+ "source-layer": r,
2355
+ filter: [
2356
+ "in",
2357
+ ["geometry-type"],
2358
+ ["literal", ["Polygon", "LineString"]]
2359
+ ],
2360
+ paint: {
2361
+ "line-color": "#3388ff",
2362
+ "line-width": 1
2363
+ }
2364
+ },
2365
+ {
2366
+ id: "circle",
2367
+ type: "circle",
2368
+ source: o,
2369
+ "source-layer": r,
2370
+ filter: [
2371
+ "==",
2372
+ ["geometry-type"],
2373
+ "Point"
2374
+ ],
2375
+ paint: {
2376
+ "circle-color": "#3388ff",
2377
+ "circle-radius": 4
2378
+ }
2379
+ }
2380
+ ];
2381
+ return {
2382
+ serviceType: "xyz",
2383
+ title: `${r} (MVT)`,
2384
+ source: s,
2385
+ layer: {
2386
+ id: o,
2387
+ type: "style",
2388
+ version: 8,
2389
+ title: r,
2390
+ sources: { [o]: s },
2391
+ layers: c
2392
+ }
2393
+ };
2394
+ }
2395
+ function Jt(e) {
2396
+ let t = e.match(/^(.*\/(?:MapServer|ImageServer))\/tile\/\d+\/\d+\/\d+(\?.*)?$/i);
2397
+ if (!t) return null;
2398
+ let n = t[1], r = `${n}/tile/{z}/{y}/{x}`, i = "esri-tile";
2399
+ return {
2400
+ base: n,
2401
+ layer: {
2402
+ serviceType: "esri-tile",
2403
+ title: `Esri tile cache (${n.split("/").slice(-2).join("/")})`,
2404
+ source: Z(i, [r]),
2405
+ layer: {
2406
+ id: i,
2407
+ type: "raster",
2408
+ source: i,
2409
+ title: "Esri tile cache"
2410
+ }
2411
+ }
2412
+ };
2413
+ }
2414
+ function Yt(e) {
2415
+ let t = e.match(/^(.*\/rest\/services\/.*\/(?:MapServer|FeatureServer|ImageServer))/i);
2416
+ return t ? t[1] : null;
2417
+ }
2418
+ async function $(e) {
2419
+ try {
2420
+ let t = await fetch(e);
2421
+ return t.ok ? await t.json() : null;
2422
+ } catch {
2423
+ return null;
2424
+ }
2425
+ }
2426
+ async function Xt(e) {
2427
+ let t = await $(`${e}${e.includes("?") ? "&" : "?"}f=json`);
2428
+ return !t || typeof t.currentVersion != "number" ? null : t;
2429
+ }
2430
+ function Zt(e, t) {
2431
+ let n = Array.isArray(t.folders) ? t.folders : void 0, r = Array.isArray(t.services) ? t.services : void 0;
2432
+ if (!n && !r) return null;
2433
+ let i = e.replace(/\/+$/, ""), a = i.match(/^(.*\/rest\/services)/i), o = a ? a[1] : i, s = [];
2434
+ for (let e of n ?? []) s.push({
2435
+ name: e,
2436
+ url: `${i}/${e}`,
2437
+ kind: "folder"
2438
+ });
2439
+ for (let e of r ?? []) s.push({
2440
+ name: e.name,
2441
+ url: `${o}/${e.name}/${e.type}`,
2442
+ kind: "service",
2443
+ type: e.type
2444
+ });
2445
+ return s;
2446
+ }
2447
+ async function Qt(e) {
2448
+ try {
2449
+ let t = await new et(e).isReady(), n = t.getServiceInfo(), i = t.getFlattenedLayers(), a = t.getVersion(), o = [];
2450
+ for (let s of i) {
2451
+ if (!s.name) continue;
2452
+ let i = s.name, c = null;
2453
+ try {
2454
+ c = t.getLayerByName(s.name);
2455
+ } catch {
2456
+ c = null;
2457
+ }
2458
+ let l = Gt(c?.boundingBoxes?.["EPSG:4326"] ?? c?.boundingBoxes?.["CRS:84"]), u = typeof c?.maxScaleDenominator == "number" ? Q(c.maxScaleDenominator) : void 0, d = typeof c?.minScaleDenominator == "number" ? Q(c.minScaleDenominator) : void 0, f = c?.styles?.find((e) => e.legendUrl)?.legendUrl;
2459
+ o.push({
2460
+ serviceType: "wms",
2461
+ title: `${s.title || s.name} (WMS)`,
2462
+ ...s.abstract ? { abstract: s.abstract } : {},
2463
+ source: Z(i, [r({
2464
+ baseUrl: Wt(t.getOperationUrl("GetMap") || e),
2465
+ layers: s.name,
2466
+ version: a
2467
+ }, "maplibre")], {
2468
+ ...n?.title ? { attribution: n.title } : {},
2469
+ ...l ? { bounds: l } : {},
2470
+ ...c?.queryable ? {
2471
+ service: "wms",
2472
+ gfiUrl: Wt(t.getOperationUrl("GetFeatureInfo") || t.getOperationUrl("GetMap") || e),
2473
+ gfiLayers: s.name,
2474
+ gfiVersion: a
2475
+ } : {}
2476
+ }),
2477
+ layer: {
2478
+ id: i,
2479
+ type: "raster",
2480
+ source: i,
2481
+ title: s.title || s.name,
2482
+ ...u === void 0 ? {} : { minzoom: u },
2483
+ ...d === void 0 ? {} : { maxzoom: d },
2484
+ ...s.abstract || l || f ? { metadata: {
2485
+ ...s.abstract ? { abstract: s.abstract } : {},
2486
+ ...l ? { bounds: l } : {},
2487
+ ...f ? { legendurl: f } : {}
2488
+ } } : {}
2489
+ }
2490
+ });
2491
+ }
2492
+ return o;
2493
+ } catch {
2494
+ return [];
2495
+ }
2496
+ }
2497
+ async function $t(e) {
2498
+ try {
2499
+ let t = await new rt(e).isReady(), n = t.getServiceInfo(), r = [];
2500
+ for (let e of t.getLayers()) {
2501
+ let i = e.matrixSets[0];
2502
+ if (!i) continue;
2503
+ let a = t.getTileUrl(e.name, e.defaultStyle, i.identifier, "{z}", "{y}", "{x}");
2504
+ if (!a) continue;
2505
+ let o = a.replace(/%7B/gi, "{").replace(/%7D/gi, "}"), s = e.name, c = Gt(e.latLonBoundingBox);
2506
+ r.push({
2507
+ serviceType: "wmts",
2508
+ title: `${e.name} (WMTS)`,
2509
+ source: Z(s, [o], {
2510
+ ...n?.title ? { attribution: n.title } : {},
2511
+ ...c ? { bounds: c } : {}
2512
+ }),
2513
+ layer: {
2514
+ id: s,
2515
+ type: "raster",
2516
+ source: s,
2517
+ title: e.name,
2518
+ ...c ? { metadata: { bounds: c } } : {}
2519
+ }
2520
+ });
2521
+ }
2522
+ return r;
2523
+ } catch {
2524
+ return [];
2525
+ }
2526
+ }
2527
+ async function en(e) {
2528
+ try {
2529
+ let t = await new Qe(e).isReady(), n = t.getFeatureTypes(), r = t.getVersion(), i = t.supportsStartIndex(), a = [];
2530
+ for (let e of n) {
2531
+ if (!e.name || !t.supportsJson(e.name)) continue;
2532
+ let n = e.name, o = t.getFeatureUrl(e.name, {
2533
+ outputFormat: "application/json",
2534
+ outputCrs: "EPSG:4326"
2535
+ }) ?? t.getFeatureUrl(e.name);
2536
+ if (!o) continue;
2537
+ let s = Gt(e.boundingBox);
2538
+ a.push({
2539
+ serviceType: "wfs",
2540
+ title: `${e.title || e.name} (WFS)`,
2541
+ ...e.abstract ? { abstract: e.abstract } : {},
2542
+ source: {
2543
+ id: n,
2544
+ type: "geojson",
2545
+ data: o,
2546
+ service: "wfs",
2547
+ wfsVersion: r,
2548
+ wfsSupportsPaging: i,
2549
+ ...s ? { bounds: s } : {}
2550
+ },
2551
+ layer: {
2552
+ id: n,
2553
+ type: "fill",
2554
+ source: n,
2555
+ title: e.title || e.name,
2556
+ paint: {
2557
+ "fill-color": "#3388ff",
2558
+ "fill-opacity": .5
2559
+ },
2560
+ ...e.abstract || s ? { metadata: {
2561
+ ...e.abstract ? { abstract: e.abstract } : {},
2562
+ ...s ? { bounds: s } : {}
2563
+ } } : {}
2564
+ }
2565
+ });
2566
+ }
2567
+ return a;
2568
+ } catch {
2569
+ return [];
2570
+ }
2571
+ }
2572
+ var tn = {
2573
+ esriGeometryPoint: "circle",
2574
+ esriGeometryMultipoint: "circle",
2575
+ esriGeometryPolyline: "line",
2576
+ esriGeometryPolygon: "fill"
2577
+ };
2578
+ function nn(e) {
2579
+ let r = e;
2580
+ if (!r) return;
2581
+ let i = r.spatialReference, a = i?.latestWkid ?? i?.wkid, { xmin: o, ymin: s, xmax: c, ymax: l } = r;
2582
+ if (![
2583
+ o,
2584
+ s,
2585
+ c,
2586
+ l
2587
+ ].every(Number.isFinite)) return;
2588
+ if (a === 4326 || a === 4269) return [
2589
+ o,
2590
+ s,
2591
+ c,
2592
+ l
2593
+ ];
2594
+ let u = a === void 0 ? void 0 : n[String(a)];
2595
+ if (u) try {
2596
+ let e = t(u, "EPSG:4326"), [n, r] = e.forward([o, s]), [i, a] = e.forward([c, l]);
2597
+ return [
2598
+ n,
2599
+ r,
2600
+ i,
2601
+ a
2602
+ ].every(Number.isFinite) ? [
2603
+ n,
2604
+ r,
2605
+ i,
2606
+ a
2607
+ ] : void 0;
2608
+ } catch {
2609
+ return;
2610
+ }
2611
+ }
2612
+ async function rn(e, t, n, r, i) {
2613
+ let a = t.id, o = typeof t.geometryType == "string" ? t.geometryType : void 0;
2614
+ if (a === void 0 || !o || !(o in tn)) return null;
2615
+ let s = Ut(String(t.name ?? a)), c = `${e}/${a}/query?where=1%3D1&outFields=*&f=geojson&outSR=4326`, l = nn(t.extent) ?? n, u = typeof t.description == "string" && t.description ? t.description : r, d = typeof t.minScale == "number" && t.minScale > 0 ? Q(t.minScale) : void 0, f = typeof t.maxScale == "number" && t.maxScale > 0 ? Q(t.maxScale) : void 0, p = tn[o], m = (i === void 0 ? await $(`${e}/${a}?f=json`) : i)?.drawingInfo, h = Ht(m, p);
2616
+ p === "circle" && !h?.paint?.["circle-color"] && (h = {
2617
+ ...h,
2618
+ paint: {
2619
+ "circle-color": "#3388ff",
2620
+ "circle-radius": 5,
2621
+ ...h?.paint
2622
+ }
2623
+ });
2624
+ let g = String(t.name ?? `Layer ${a}`), _ = {
2625
+ id: s,
2626
+ type: "geojson",
2627
+ data: c,
2628
+ service: "esri-feature",
2629
+ ...l ? { bounds: l } : {}
2630
+ }, v = u || l ? {
2631
+ ...u ? { abstract: u } : {},
2632
+ ...l ? { bounds: l } : {}
2633
+ } : void 0;
2634
+ return h?.outline ? {
2635
+ serviceType: "esri-feature",
2636
+ title: `${g} (Esri features)`,
2637
+ ...u ? { abstract: u } : {},
2638
+ source: _,
2639
+ layer: {
2640
+ id: s,
2641
+ type: "style",
2642
+ version: 8,
2643
+ title: g,
2644
+ ...d === void 0 ? {} : { minzoom: d },
2645
+ ...f === void 0 ? {} : { maxzoom: f },
2646
+ sources: { [s]: _ },
2647
+ layers: [{
2648
+ id: "fill",
2649
+ type: p,
2650
+ source: s,
2651
+ ...h.paint ? { paint: h.paint } : {}
2652
+ }, {
2653
+ id: "outline",
2654
+ type: "line",
2655
+ source: s,
2656
+ paint: h.outline.paint
2657
+ }],
2658
+ ...v ? { metadata: v } : {}
2659
+ }
2660
+ } : {
2661
+ serviceType: "esri-feature",
2662
+ title: `${g} (Esri features)`,
2663
+ ...u ? { abstract: u } : {},
2664
+ source: _,
2665
+ layer: {
2666
+ id: s,
2667
+ type: p,
2668
+ source: s,
2669
+ title: g,
2670
+ ...d === void 0 ? {} : { minzoom: d },
2671
+ ...f === void 0 ? {} : { maxzoom: f },
2672
+ ...h?.paint ? { paint: h.paint } : {},
2673
+ ...h?.layout ? { layout: h.layout } : {},
2674
+ ...v ? { metadata: v } : {}
2675
+ }
2676
+ };
2677
+ }
2678
+ async function an(e, t, n) {
2679
+ let r = (await $(`${e}/${String(t.defaultStyles).replace(/^\/+/, "")}`))?.layers;
2680
+ if (!r?.length) return null;
2681
+ let i = Ut(String(t.name ?? "vector-tiles")), a = t.tileInfo, o = a?.lods, s = a?.maxLOD ?? (o?.length ? o[o.length - 1]?.level : void 0), c = {
2682
+ id: i,
2683
+ type: "vector",
2684
+ tiles: [`${e}/tile/{z}/{y}/{x}.pbf`],
2685
+ ...typeof s == "number" ? { maxzoom: s } : {}
2686
+ }, l = r.filter((e) => e.type !== "background").map((e) => ({
2687
+ ...e,
2688
+ source: i
2689
+ })), u = String(t.name ?? "Vector tiles");
2690
+ return {
2691
+ serviceType: "esri-vector-tile",
2692
+ title: `${u} (Esri vector tiles)`,
2693
+ ...n ? { abstract: n } : {},
2694
+ source: c,
2695
+ layer: {
2696
+ id: i,
2697
+ type: "style",
2698
+ version: 8,
2699
+ title: u,
2700
+ sources: { [i]: c },
2701
+ layers: l,
2702
+ ...n ? { metadata: { abstract: n } } : {}
2703
+ }
2704
+ };
2705
+ }
2706
+ async function on(e) {
2707
+ let t = await $(`${e}?f=json`);
2708
+ if (!t) return [];
2709
+ let n = [], r = nn(t.fullExtent), i = typeof t.description == "string" && t.description ? t.description : void 0;
2710
+ if (t.tileInfo) {
2711
+ let a = "esri-tile", o = `${e}/tile/{z}/{y}/{x}`;
2712
+ n.push({
2713
+ serviceType: "esri-tile",
2714
+ title: `${t.mapName || t.name || "Esri"} tile cache`,
2715
+ ...i ? { abstract: i } : {},
2716
+ source: Z(a, [o], r ? { bounds: r } : {}),
2717
+ layer: {
2718
+ id: a,
2719
+ type: "raster",
2720
+ source: a,
2721
+ title: String(t.mapName || t.name || "Esri tile cache"),
2722
+ ...i || r ? { metadata: {
2723
+ ...i ? { abstract: i } : {},
2724
+ ...r ? { bounds: r } : {}
2725
+ } } : {}
2726
+ }
2727
+ });
2728
+ }
2729
+ if (Array.isArray(t.tiles) && typeof t.defaultStyles == "string") {
2730
+ let r = await an(e, t, i);
2731
+ r && n.push(r);
2732
+ }
2733
+ let a = typeof t.capabilities == "string" ? t.capabilities.split(",").map((e) => e.trim().toUpperCase()) : [], o = t.documentInfo, s = typeof o?.Title == "string" && o.Title ? o.Title : void 0;
2734
+ if (a.includes("WMS")) {
2735
+ let t = await Qt(`${e}/WMSServer`);
2736
+ for (let e of t) s && (e.title = s, e.layer.title = s);
2737
+ n.push(...t);
2738
+ } else if (Array.isArray(t.layers) && t.layers.length > 0) {
2739
+ let a = "esri-export", o = t.layers.map((e) => e.id).filter((e) => typeof e == "number"), c = `${e}/export?bbox={bbox-epsg-3857}&bboxSR=3857&imageSR=3857&size=256,256&dpi=96&format=png32&transparent=true&f=image&layers=${encodeURIComponent(`show:${o.join(",")}`)}`, l = typeof t.minScale == "number" && t.minScale > 0 ? Q(t.minScale) : void 0, u = typeof t.maxScale == "number" && t.maxScale > 0 ? Q(t.maxScale) : void 0, d;
2740
+ if (t.layers.length === 1) {
2741
+ let t = (await $(`${e}/legend?f=json`))?.layers?.[0]?.legend?.[0];
2742
+ typeof t?.imageData == "string" && typeof t?.contentType == "string" && (d = `data:${t.contentType};base64,${t.imageData}`);
2743
+ }
2744
+ n.push({
2745
+ serviceType: "esri-tile",
2746
+ title: s ?? `${t.mapName || t.name || "Esri"} (export)`,
2747
+ ...i ? { abstract: i } : {},
2748
+ source: Z(a, [c], r ? { bounds: r } : {}),
2749
+ layer: {
2750
+ id: a,
2751
+ type: "raster",
2752
+ source: a,
2753
+ title: s ?? String(t.mapName || t.name || "Esri export"),
2754
+ ...l === void 0 ? {} : { minzoom: l },
2755
+ ...u === void 0 ? {} : { maxzoom: u },
2756
+ ...i || r || d ? { metadata: {
2757
+ ...i ? { abstract: i } : {},
2758
+ ...r ? { bounds: r } : {},
2759
+ ...d ? { legendurl: d } : {}
2760
+ } } : {}
2761
+ }
2762
+ });
2763
+ }
2764
+ if (Array.isArray(t.layers)) {
2765
+ let a = await Promise.all(t.layers.map((t) => rn(e, t, r, i)));
2766
+ for (let e of a) e && n.push(e);
2767
+ } else if (typeof t.geometryType == "string") {
2768
+ let a = await rn(e.replace(/\/\d+$/, ""), t, r, i, t);
2769
+ a && n.push(a);
2770
+ }
2771
+ return n;
2772
+ }
2773
+ async function sn(e) {
2774
+ let t = e.trim();
2775
+ if (!t) return { layers: [] };
2776
+ let n = Wt(t), r = await Xt(n);
2777
+ if (r) {
2778
+ let e = Zt(n, r);
2779
+ return e ? {
2780
+ layers: [],
2781
+ catalog: e
2782
+ } : { layers: cn(await on(n), t) };
2783
+ }
2784
+ let i = [], a = [], o = qt(t);
2785
+ o && i.push(o);
2786
+ let s = o ? null : Kt(t);
2787
+ s && i.push(s);
2788
+ let c = Jt(t);
2789
+ c && i.push(c.layer), a.push(Qt(n)), a.push($t(n)), a.push(en(n));
2790
+ let l = Yt(t) ?? (c ? c.base : null);
2791
+ l && a.push(on(l));
2792
+ let u = await Promise.all(a);
2793
+ for (let e of u) i.push(...e);
2794
+ return { layers: cn(i, t) };
2795
+ }
2796
+ function cn(e, t) {
2797
+ let n;
2798
+ try {
2799
+ n = new URL(t).searchParams;
2800
+ } catch {
2801
+ return e;
2802
+ }
2803
+ let r = /* @__PURE__ */ new Set();
2804
+ for (let e of [
2805
+ "LAYERS",
2806
+ "layers",
2807
+ "LAYER",
2808
+ "layer"
2809
+ ]) {
2810
+ let t = n.get(e);
2811
+ if (t) for (let e of t.split(",")) {
2812
+ let t = e.trim();
2813
+ t && r.add(t.toLowerCase());
2814
+ }
2815
+ }
2816
+ if (r.size === 0) return e;
2817
+ let i = (e) => {
2818
+ let t = e.layer.id?.toLowerCase() ?? "";
2819
+ return Array.from(r).some((e) => t === e || t.includes(e));
2820
+ }, a = [], o = [];
2821
+ for (let t of e) (i(t) ? a : o).push(t);
2822
+ return [...a, ...o];
2823
+ }
2824
+ //#endregion
2825
+ export { sn as discoverLayers, Qt as discoverWms };