@flowmap.gl/data 8.0.0-alpha.12 → 8.0.0-alpha.13

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 (41) hide show
  1. package/dist-es5/FlowmapAggregateAccessors.d.ts +16 -0
  2. package/dist-es5/FlowmapAggregateAccessors.d.ts.map +1 -0
  3. package/dist-es5/FlowmapAggregateAccessors.js +57 -0
  4. package/dist-es5/FlowmapSelectors.d.ts +188 -0
  5. package/dist-es5/FlowmapSelectors.d.ts.map +1 -0
  6. package/dist-es5/FlowmapSelectors.js +1507 -0
  7. package/dist-es5/FlowmapState.d.ts +27 -0
  8. package/dist-es5/FlowmapState.d.ts.map +1 -0
  9. package/dist-es5/FlowmapState.js +3 -0
  10. package/dist-es5/cluster/ClusterIndex.d.ts +42 -0
  11. package/dist-es5/cluster/ClusterIndex.d.ts.map +1 -0
  12. package/dist-es5/cluster/ClusterIndex.js +297 -0
  13. package/dist-es5/cluster/cluster.d.ts +31 -0
  14. package/dist-es5/cluster/cluster.d.ts.map +1 -0
  15. package/dist-es5/cluster/cluster.js +266 -0
  16. package/dist-es5/colors.d.ts +103 -0
  17. package/dist-es5/colors.d.ts.map +1 -0
  18. package/dist-es5/colors.js +510 -0
  19. package/dist-es5/getViewStateForLocations.d.ts +23 -0
  20. package/dist-es5/getViewStateForLocations.d.ts.map +1 -0
  21. package/dist-es5/getViewStateForLocations.js +64 -0
  22. package/dist-es5/index.d.ts +11 -0
  23. package/dist-es5/index.d.ts.map +1 -0
  24. package/dist-es5/index.js +28 -0
  25. package/dist-es5/provider/FlowmapDataProvider.d.ts +16 -0
  26. package/dist-es5/provider/FlowmapDataProvider.d.ts.map +1 -0
  27. package/dist-es5/provider/FlowmapDataProvider.js +22 -0
  28. package/dist-es5/provider/LocalFlowmapDataProvider.d.ts +20 -0
  29. package/dist-es5/provider/LocalFlowmapDataProvider.d.ts.map +1 -0
  30. package/dist-es5/provider/LocalFlowmapDataProvider.js +154 -0
  31. package/dist-es5/time.d.ts +24 -0
  32. package/dist-es5/time.d.ts.map +1 -0
  33. package/dist-es5/time.js +168 -0
  34. package/dist-es5/types.d.ts +118 -0
  35. package/dist-es5/types.d.ts.map +1 -0
  36. package/dist-es5/types.js +29 -0
  37. package/dist-es5/util.d.ts +5 -0
  38. package/dist-es5/util.d.ts.map +1 -0
  39. package/dist-es5/util.js +14 -0
  40. package/package.json +7 -5
  41. package/tsconfig.es5.json +11 -0
@@ -0,0 +1,1507 @@
1
+ "use strict";
2
+ /*
3
+ * Copyright 2022 FlowmapBlue
4
+ * Copyright 2018-2020 Teralytics, modified by FlowmapBlue
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ *
18
+ */
19
+ var __assign = (this && this.__assign) || function () {
20
+ __assign = Object.assign || function(t) {
21
+ for (var s, i = 1, n = arguments.length; i < n; i++) {
22
+ s = arguments[i];
23
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
24
+ t[p] = s[p];
25
+ }
26
+ return t;
27
+ };
28
+ return __assign.apply(this, arguments);
29
+ };
30
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
31
+ if (k2 === undefined) k2 = k;
32
+ Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });
33
+ }) : (function(o, m, k, k2) {
34
+ if (k2 === undefined) k2 = k;
35
+ o[k2] = m[k];
36
+ }));
37
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
38
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
39
+ }) : function(o, v) {
40
+ o["default"] = v;
41
+ });
42
+ var __importStar = (this && this.__importStar) || function (mod) {
43
+ if (mod && mod.__esModule) return mod;
44
+ var result = {};
45
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
46
+ __setModuleDefault(result, mod);
47
+ return result;
48
+ };
49
+ var __generator = (this && this.__generator) || function (thisArg, body) {
50
+ var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;
51
+ return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
52
+ function verb(n) { return function (v) { return step([n, v]); }; }
53
+ function step(op) {
54
+ if (f) throw new TypeError("Generator is already executing.");
55
+ while (_) try {
56
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
57
+ if (y = 0, t) op = [op[0] & 2, t.value];
58
+ switch (op[0]) {
59
+ case 0: case 1: t = op; break;
60
+ case 4: _.label++; return { value: op[1], done: false };
61
+ case 5: _.label++; y = op[1]; op = [0]; continue;
62
+ case 7: op = _.ops.pop(); _.trys.pop(); continue;
63
+ default:
64
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
65
+ if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
66
+ if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
67
+ if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
68
+ if (t[2]) _.ops.pop();
69
+ _.trys.pop(); continue;
70
+ }
71
+ op = body.call(thisArg, _);
72
+ } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
73
+ if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
74
+ }
75
+ };
76
+ var __values = (this && this.__values) || function(o) {
77
+ var s = typeof Symbol === "function" && Symbol.iterator, m = s && o[s], i = 0;
78
+ if (m) return m.call(o);
79
+ if (o && typeof o.length === "number") return {
80
+ next: function () {
81
+ if (o && i >= o.length) o = void 0;
82
+ return { value: o && o[i++], done: !o };
83
+ }
84
+ };
85
+ throw new TypeError(s ? "Object is not iterable." : "Symbol.iterator is not defined.");
86
+ };
87
+ var __read = (this && this.__read) || function (o, n) {
88
+ var m = typeof Symbol === "function" && o[Symbol.iterator];
89
+ if (!m) return o;
90
+ var i = m.call(o), r, ar = [], e;
91
+ try {
92
+ while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value);
93
+ }
94
+ catch (error) { e = { error: error }; }
95
+ finally {
96
+ try {
97
+ if (r && !r.done && (m = i["return"])) m.call(i);
98
+ }
99
+ finally { if (e) throw e.error; }
100
+ }
101
+ return ar;
102
+ };
103
+ var __spreadArray = (this && this.__spreadArray) || function (to, from, pack) {
104
+ if (pack || arguments.length === 2) for (var i = 0, l = from.length, ar; i < l; i++) {
105
+ if (ar || !(i in from)) {
106
+ if (!ar) ar = Array.prototype.slice.call(from, 0, i);
107
+ ar[i] = from[i];
108
+ }
109
+ }
110
+ return to.concat(ar || Array.prototype.slice.call(from));
111
+ };
112
+ var __importDefault = (this && this.__importDefault) || function (mod) {
113
+ return (mod && mod.__esModule) ? mod : { "default": mod };
114
+ };
115
+ Object.defineProperty(exports, "__esModule", { value: true });
116
+ exports.getFlowLineAttributesByIndex = exports.getLocationCoordsByIndex = exports.getOuterCircleRadiusByIndex = void 0;
117
+ var web_mercator_1 = require("@math.gl/web-mercator");
118
+ var d3_array_1 = require("d3-array");
119
+ var d3_collection_1 = require("d3-collection");
120
+ var d3_scale_1 = require("d3-scale");
121
+ var kdbush_1 = __importDefault(require("kdbush"));
122
+ var reselect_1 = require("reselect");
123
+ var seedrandom_1 = require("seedrandom");
124
+ var cluster_1 = require("./cluster/cluster");
125
+ var ClusterIndex_1 = require("./cluster/ClusterIndex");
126
+ var colors_1 = __importStar(require("./colors"));
127
+ var FlowmapAggregateAccessors_1 = __importDefault(require("./FlowmapAggregateAccessors"));
128
+ var time_1 = require("./time");
129
+ var types_1 = require("./types");
130
+ var MAX_CLUSTER_ZOOM_LEVEL = 20;
131
+ var FlowmapSelectors = /** @class */ (function () {
132
+ function FlowmapSelectors(accessors) {
133
+ var _this = this;
134
+ this.getFetchedFlows = function (state, props) {
135
+ return props.flows;
136
+ };
137
+ this.getFetchedLocations = function (state, props) {
138
+ return props.locations;
139
+ };
140
+ this.getMaxTopFlowsDisplayNum = function (state, props) {
141
+ return state.settingsState.maxTopFlowsDisplayNum;
142
+ };
143
+ this.getSelectedLocations = function (state, props) {
144
+ return state.filterState.selectedLocations;
145
+ };
146
+ this.getLocationFilterMode = function (state, props) {
147
+ return state.filterState.locationFilterMode;
148
+ };
149
+ this.getClusteringEnabled = function (state, props) {
150
+ return state.settingsState.clusteringEnabled;
151
+ };
152
+ this.getLocationTotalsEnabled = function (state, props) {
153
+ return state.settingsState.locationTotalsEnabled;
154
+ };
155
+ this.getZoom = function (state, props) {
156
+ return state.viewport.zoom;
157
+ };
158
+ this.getViewport = function (state, props) {
159
+ return state.viewport;
160
+ };
161
+ this.getSelectedTimeRange = function (state, props) {
162
+ return state.filterState.selectedTimeRange;
163
+ };
164
+ this.getColorScheme = function (state, props) { return state.settingsState.colorScheme; };
165
+ this.getDarkMode = function (state, props) { return state.settingsState.darkMode; };
166
+ this.getFadeEnabled = function (state, props) { return state.settingsState.fadeEnabled; };
167
+ this.getFadeOpacityEnabled = function (state, props) { return state.settingsState.fadeOpacityEnabled; };
168
+ this.getFadeAmount = function (state, props) { return state.settingsState.fadeAmount; };
169
+ this.getAnimate = function (state, props) { return state.settingsState.animationEnabled; };
170
+ this.getInvalidLocationIds = (0, reselect_1.createSelector)(this.getFetchedLocations, function (locations) {
171
+ var e_1, _a;
172
+ if (!locations)
173
+ return undefined;
174
+ var invalid = [];
175
+ try {
176
+ for (var locations_1 = __values(locations), locations_1_1 = locations_1.next(); !locations_1_1.done; locations_1_1 = locations_1.next()) {
177
+ var location_1 = locations_1_1.value;
178
+ var id = _this.accessors.getLocationId(location_1);
179
+ var lon = _this.accessors.getLocationLon(location_1);
180
+ var lat = _this.accessors.getLocationLat(location_1);
181
+ if (!(-90 <= lat && lat <= 90) || !(-180 <= lon && lon <= 180)) {
182
+ invalid.push(id);
183
+ }
184
+ }
185
+ }
186
+ catch (e_1_1) { e_1 = { error: e_1_1 }; }
187
+ finally {
188
+ try {
189
+ if (locations_1_1 && !locations_1_1.done && (_a = locations_1.return)) _a.call(locations_1);
190
+ }
191
+ finally { if (e_1) throw e_1.error; }
192
+ }
193
+ return invalid.length > 0 ? invalid : undefined;
194
+ });
195
+ this.getLocations = (0, reselect_1.createSelector)(this.getFetchedLocations, this.getInvalidLocationIds, function (locations, invalidIds) {
196
+ if (!locations)
197
+ return undefined;
198
+ if (!invalidIds || invalidIds.length === 0)
199
+ return locations;
200
+ var invalid = new Set(invalidIds);
201
+ return locations.filter(function (location) { return !invalid.has(_this.accessors.getLocationId(location)); });
202
+ });
203
+ this.getLocationIds = (0, reselect_1.createSelector)(this.getLocations, function (locations) {
204
+ return locations
205
+ ? new Set(locations.map(_this.accessors.getLocationId))
206
+ : undefined;
207
+ });
208
+ this.getSelectedLocationsSet = (0, reselect_1.createSelector)(this.getSelectedLocations, function (ids) {
209
+ return ids && ids.length > 0 ? new Set(ids) : undefined;
210
+ });
211
+ this.getSortedFlowsForKnownLocations = (0, reselect_1.createSelector)(this.getFetchedFlows, this.getLocationIds, function (flows, ids) {
212
+ if (!ids || !flows)
213
+ return undefined;
214
+ return flows
215
+ .filter(function (flow) {
216
+ return ids.has(_this.accessors.getFlowOriginId(flow)) &&
217
+ ids.has(_this.accessors.getFlowDestId(flow));
218
+ })
219
+ .sort(function (a, b) {
220
+ return (0, d3_array_1.descending)(Math.abs(_this.accessors.getFlowMagnitude(a)), Math.abs(_this.accessors.getFlowMagnitude(b)));
221
+ });
222
+ });
223
+ this.getActualTimeExtent = (0, reselect_1.createSelector)(this.getSortedFlowsForKnownLocations, function (flows) {
224
+ var e_2, _a;
225
+ if (!flows)
226
+ return undefined;
227
+ var start = null;
228
+ var end = null;
229
+ try {
230
+ for (var flows_1 = __values(flows), flows_1_1 = flows_1.next(); !flows_1_1.done; flows_1_1 = flows_1.next()) {
231
+ var flow = flows_1_1.value;
232
+ var time = _this.accessors.getFlowTime(flow);
233
+ if (time) {
234
+ if (start == null || start > time)
235
+ start = time;
236
+ if (end == null || end < time)
237
+ end = time;
238
+ }
239
+ }
240
+ }
241
+ catch (e_2_1) { e_2 = { error: e_2_1 }; }
242
+ finally {
243
+ try {
244
+ if (flows_1_1 && !flows_1_1.done && (_a = flows_1.return)) _a.call(flows_1);
245
+ }
246
+ finally { if (e_2) throw e_2.error; }
247
+ }
248
+ if (!start || !end)
249
+ return undefined;
250
+ return [start, end];
251
+ });
252
+ this.getTimeGranularityKey = (0, reselect_1.createSelector)(this.getSortedFlowsForKnownLocations, this.getActualTimeExtent, function (flows, timeExtent) {
253
+ if (!flows || !timeExtent)
254
+ return undefined;
255
+ var minOrder = (0, d3_array_1.min)(flows, function (d) {
256
+ var t = _this.accessors.getFlowTime(d);
257
+ return t ? (0, time_1.getTimeGranularityForDate)(t).order : null;
258
+ });
259
+ if (minOrder == null)
260
+ return undefined;
261
+ var timeGranularity = (0, time_1.getTimeGranularityByOrder)(minOrder);
262
+ return timeGranularity ? timeGranularity.key : undefined;
263
+ });
264
+ this.getTimeExtent = (0, reselect_1.createSelector)(this.getActualTimeExtent, this.getTimeGranularityKey, function (timeExtent, timeGranularityKey) {
265
+ var timeGranularity = timeGranularityKey
266
+ ? (0, time_1.getTimeGranularityByKey)(timeGranularityKey)
267
+ : undefined;
268
+ if (!timeExtent || !(timeGranularity === null || timeGranularity === void 0 ? void 0 : timeGranularity.interval))
269
+ return undefined;
270
+ var interval = timeGranularity.interval;
271
+ return [timeExtent[0], interval.offset(interval.floor(timeExtent[1]), 1)];
272
+ });
273
+ this.getSortedFlowsForKnownLocationsFilteredByTime = (0, reselect_1.createSelector)(this.getSortedFlowsForKnownLocations, this.getTimeExtent, this.getSelectedTimeRange, function (flows, timeExtent, timeRange) {
274
+ if (!flows)
275
+ return undefined;
276
+ if (!timeExtent ||
277
+ !timeRange ||
278
+ (timeExtent[0] === timeRange[0] && timeExtent[1] === timeRange[1])) {
279
+ return flows;
280
+ }
281
+ return flows.filter(function (flow) {
282
+ var time = _this.accessors.getFlowTime(flow);
283
+ return time && timeRange[0] <= time && time < timeRange[1];
284
+ });
285
+ });
286
+ this.getLocationsHavingFlows = (0, reselect_1.createSelector)(this.getSortedFlowsForKnownLocations, this.getLocations, function (flows, locations) {
287
+ var e_3, _a;
288
+ if (!locations || !flows)
289
+ return locations;
290
+ var withFlows = new Set();
291
+ try {
292
+ for (var flows_2 = __values(flows), flows_2_1 = flows_2.next(); !flows_2_1.done; flows_2_1 = flows_2.next()) {
293
+ var flow = flows_2_1.value;
294
+ withFlows.add(_this.accessors.getFlowOriginId(flow));
295
+ withFlows.add(_this.accessors.getFlowDestId(flow));
296
+ }
297
+ }
298
+ catch (e_3_1) { e_3 = { error: e_3_1 }; }
299
+ finally {
300
+ try {
301
+ if (flows_2_1 && !flows_2_1.done && (_a = flows_2.return)) _a.call(flows_2);
302
+ }
303
+ finally { if (e_3) throw e_3.error; }
304
+ }
305
+ return locations.filter(function (location) {
306
+ return withFlows.has(_this.accessors.getLocationId(location));
307
+ });
308
+ });
309
+ this.getLocationsById = (0, reselect_1.createSelector)(this.getLocationsHavingFlows, function (locations) {
310
+ if (!locations)
311
+ return undefined;
312
+ return (0, d3_collection_1.nest)()
313
+ .key(function (d) { return _this.accessors.getLocationId(d); })
314
+ .rollup(function (_a) {
315
+ var _b = __read(_a, 1), d = _b[0];
316
+ return d;
317
+ })
318
+ .map(locations);
319
+ });
320
+ this.getClusterIndex = (0, reselect_1.createSelector)(this.getLocationsHavingFlows, this.getLocationsById, this.getSortedFlowsForKnownLocations, function (locations, locationsById, flows) {
321
+ var e_4, _a, e_5, _b;
322
+ if (!locations || !locationsById || !flows)
323
+ return undefined;
324
+ var getLocationWeight = (0, ClusterIndex_1.makeLocationWeightGetter)(flows, _this.accessors.getFlowmapDataAccessors());
325
+ var clusterLevels = (0, cluster_1.clusterLocations)(locations, _this.accessors.getFlowmapDataAccessors(), getLocationWeight, {
326
+ maxZoom: MAX_CLUSTER_ZOOM_LEVEL,
327
+ });
328
+ var clusterIndex = (0, ClusterIndex_1.buildIndex)(clusterLevels);
329
+ var _c = _this.accessors.getFlowmapDataAccessors(), getLocationName = _c.getLocationName, getLocationClusterName = _c.getLocationClusterName;
330
+ // Adding meaningful names
331
+ var getName = function (id) {
332
+ var loc = locationsById.get(id);
333
+ if (loc) {
334
+ return getLocationName
335
+ ? getLocationName(loc)
336
+ : _this.accessors.getLocationId(loc) || id;
337
+ }
338
+ return "\"".concat(id, "\"");
339
+ };
340
+ try {
341
+ for (var clusterLevels_1 = __values(clusterLevels), clusterLevels_1_1 = clusterLevels_1.next(); !clusterLevels_1_1.done; clusterLevels_1_1 = clusterLevels_1.next()) {
342
+ var level = clusterLevels_1_1.value;
343
+ try {
344
+ for (var _d = (e_5 = void 0, __values(level.nodes)), _e = _d.next(); !_e.done; _e = _d.next()) {
345
+ var node = _e.value;
346
+ // Here mutating the nodes (adding names)
347
+ if ((0, types_1.isCluster)(node)) {
348
+ var leaves = clusterIndex.expandCluster(node);
349
+ leaves.sort(function (a, b) {
350
+ return (0, d3_array_1.descending)(getLocationWeight(a), getLocationWeight(b));
351
+ });
352
+ if (getLocationClusterName) {
353
+ node.name = getLocationClusterName(leaves);
354
+ }
355
+ else {
356
+ var topId = leaves[0];
357
+ var otherId = leaves.length === 2 ? leaves[1] : undefined;
358
+ node.name = "\"".concat(getName(topId), "\" and ").concat(otherId
359
+ ? "\"".concat(getName(otherId), "\"")
360
+ : "".concat(leaves.length - 1, " others"));
361
+ }
362
+ }
363
+ else {
364
+ node.name = getName(node.id);
365
+ }
366
+ }
367
+ }
368
+ catch (e_5_1) { e_5 = { error: e_5_1 }; }
369
+ finally {
370
+ try {
371
+ if (_e && !_e.done && (_b = _d.return)) _b.call(_d);
372
+ }
373
+ finally { if (e_5) throw e_5.error; }
374
+ }
375
+ }
376
+ }
377
+ catch (e_4_1) { e_4 = { error: e_4_1 }; }
378
+ finally {
379
+ try {
380
+ if (clusterLevels_1_1 && !clusterLevels_1_1.done && (_a = clusterLevels_1.return)) _a.call(clusterLevels_1);
381
+ }
382
+ finally { if (e_4) throw e_4.error; }
383
+ }
384
+ return clusterIndex;
385
+ });
386
+ this.getAvailableClusterZoomLevels = (0, reselect_1.createSelector)(this.getClusterIndex, this.getSelectedLocations, function (clusterIndex, selectedLocations) {
387
+ var e_6, _a;
388
+ if (!clusterIndex) {
389
+ return undefined;
390
+ }
391
+ var maxZoom = Number.POSITIVE_INFINITY;
392
+ var minZoom = Number.NEGATIVE_INFINITY;
393
+ var adjust = function (zoneId) {
394
+ var cluster = clusterIndex.getClusterById(zoneId);
395
+ if (cluster) {
396
+ minZoom = Math.max(minZoom, cluster.zoom);
397
+ maxZoom = Math.min(maxZoom, cluster.zoom);
398
+ }
399
+ else {
400
+ var zoom = clusterIndex.getMinZoomForLocation(zoneId);
401
+ minZoom = Math.max(minZoom, zoom);
402
+ }
403
+ };
404
+ if (selectedLocations) {
405
+ try {
406
+ for (var selectedLocations_1 = __values(selectedLocations), selectedLocations_1_1 = selectedLocations_1.next(); !selectedLocations_1_1.done; selectedLocations_1_1 = selectedLocations_1.next()) {
407
+ var id = selectedLocations_1_1.value;
408
+ adjust(id);
409
+ }
410
+ }
411
+ catch (e_6_1) { e_6 = { error: e_6_1 }; }
412
+ finally {
413
+ try {
414
+ if (selectedLocations_1_1 && !selectedLocations_1_1.done && (_a = selectedLocations_1.return)) _a.call(selectedLocations_1);
415
+ }
416
+ finally { if (e_6) throw e_6.error; }
417
+ }
418
+ }
419
+ return clusterIndex.availableZoomLevels.filter(function (level) { return minZoom <= level && level <= maxZoom; });
420
+ });
421
+ this._getClusterZoom = (0, reselect_1.createSelector)(this.getClusterIndex, this.getZoom, this.getAvailableClusterZoomLevels, function (clusterIndex, mapZoom, availableClusterZoomLevels) {
422
+ if (!clusterIndex)
423
+ return undefined;
424
+ if (!availableClusterZoomLevels) {
425
+ return undefined;
426
+ }
427
+ var clusterZoom = (0, ClusterIndex_1.findAppropriateZoomLevel)(availableClusterZoomLevels, mapZoom);
428
+ return clusterZoom;
429
+ });
430
+ this.getClusterZoom = function (state, props) {
431
+ var settingsState = state.settingsState;
432
+ if (!settingsState.clusteringEnabled)
433
+ return undefined;
434
+ if (settingsState.clusteringAuto || settingsState.clusteringLevel == null) {
435
+ return _this._getClusterZoom(state, props);
436
+ }
437
+ return settingsState.clusteringLevel;
438
+ };
439
+ this.getLocationsForSearchBox = (0, reselect_1.createSelector)(this.getClusteringEnabled, this.getLocationsHavingFlows, this.getSelectedLocations, this.getClusterZoom, this.getClusterIndex, function (clusteringEnabled, locations, selectedLocations, clusterZoom, clusterIndex) {
440
+ var e_7, _a;
441
+ if (!locations)
442
+ return undefined;
443
+ var result = locations;
444
+ // if (clusteringEnabled) {
445
+ // if (clusterIndex) {
446
+ // const zoomItems = clusterIndex.getClusterNodesFor(clusterZoom);
447
+ // if (zoomItems) {
448
+ // result = result.concat(zoomItems.filter(isCluster));
449
+ // }
450
+ // }
451
+ // }
452
+ if (result && clusterIndex && selectedLocations) {
453
+ var toAppend = [];
454
+ var _loop_1 = function (id) {
455
+ var cluster = clusterIndex.getClusterById(id);
456
+ if (cluster &&
457
+ !result.find(function (d) {
458
+ return ((0, types_1.isLocationClusterNode)(d)
459
+ ? d.id
460
+ : _this.accessors.getLocationId(d)) === id;
461
+ })) {
462
+ toAppend.push(cluster);
463
+ }
464
+ };
465
+ try {
466
+ for (var selectedLocations_2 = __values(selectedLocations), selectedLocations_2_1 = selectedLocations_2.next(); !selectedLocations_2_1.done; selectedLocations_2_1 = selectedLocations_2.next()) {
467
+ var id = selectedLocations_2_1.value;
468
+ _loop_1(id);
469
+ }
470
+ }
471
+ catch (e_7_1) { e_7 = { error: e_7_1 }; }
472
+ finally {
473
+ try {
474
+ if (selectedLocations_2_1 && !selectedLocations_2_1.done && (_a = selectedLocations_2.return)) _a.call(selectedLocations_2);
475
+ }
476
+ finally { if (e_7) throw e_7.error; }
477
+ }
478
+ if (toAppend.length > 0) {
479
+ result = result.concat(toAppend);
480
+ }
481
+ }
482
+ return result;
483
+ });
484
+ this.getDiffMode = (0, reselect_1.createSelector)(this.getFetchedFlows, function (flows) {
485
+ if (flows &&
486
+ flows.find(function (f) { return _this.accessors.getFlowMagnitude(f) < 0; })) {
487
+ return true;
488
+ }
489
+ return false;
490
+ });
491
+ this._getFlowmapColors = (0, reselect_1.createSelector)(this.getDiffMode, this.getColorScheme, this.getDarkMode, this.getFadeEnabled, this.getFadeOpacityEnabled, this.getFadeAmount, this.getAnimate, colors_1.default);
492
+ this.getFlowmapColorsRGBA = (0, reselect_1.createSelector)(this._getFlowmapColors, function (flowmapColors) {
493
+ return (0, colors_1.isDiffColors)(flowmapColors)
494
+ ? (0, colors_1.getDiffColorsRGBA)(flowmapColors)
495
+ : (0, colors_1.getColorsRGBA)(flowmapColors);
496
+ });
497
+ this.getUnknownLocations = (0, reselect_1.createSelector)(this.getLocationIds, this.getFetchedFlows, this.getSortedFlowsForKnownLocations, function (ids, flows, flowsForKnownLocations) {
498
+ var e_8, _a;
499
+ if (!ids || !flows)
500
+ return undefined;
501
+ if (flowsForKnownLocations &&
502
+ flows.length === flowsForKnownLocations.length)
503
+ return undefined;
504
+ var missing = new Set();
505
+ try {
506
+ for (var flows_3 = __values(flows), flows_3_1 = flows_3.next(); !flows_3_1.done; flows_3_1 = flows_3.next()) {
507
+ var flow = flows_3_1.value;
508
+ if (!ids.has(_this.accessors.getFlowOriginId(flow)))
509
+ missing.add(_this.accessors.getFlowOriginId(flow));
510
+ if (!ids.has(_this.accessors.getFlowDestId(flow)))
511
+ missing.add(_this.accessors.getFlowDestId(flow));
512
+ }
513
+ }
514
+ catch (e_8_1) { e_8 = { error: e_8_1 }; }
515
+ finally {
516
+ try {
517
+ if (flows_3_1 && !flows_3_1.done && (_a = flows_3.return)) _a.call(flows_3);
518
+ }
519
+ finally { if (e_8) throw e_8.error; }
520
+ }
521
+ return missing;
522
+ });
523
+ this.getSortedAggregatedFilteredFlows = (0, reselect_1.createSelector)(this.getClusterIndex, this.getClusteringEnabled, this.getSortedFlowsForKnownLocationsFilteredByTime, this.getClusterZoom, this.getTimeExtent, function (clusterTree, isClusteringEnabled, flows, clusterZoom, timeExtent) {
524
+ if (!flows)
525
+ return undefined;
526
+ var aggregated;
527
+ if (isClusteringEnabled && clusterTree && clusterZoom != null) {
528
+ aggregated = clusterTree.aggregateFlows(
529
+ // TODO: aggregate across time
530
+ // timeExtent != null
531
+ // ? aggregateFlows(flows) // clusterTree.aggregateFlows won't aggregate unclustered across time
532
+ // : flows,
533
+ flows, clusterZoom, _this.accessors.getFlowmapDataAccessors());
534
+ }
535
+ else {
536
+ aggregated = aggregateFlows(flows, _this.accessors.getFlowmapDataAccessors());
537
+ }
538
+ aggregated.sort(function (a, b) {
539
+ return (0, d3_array_1.descending)(Math.abs(_this.accessors.getFlowMagnitude(a)), Math.abs(_this.accessors.getFlowMagnitude(b)));
540
+ });
541
+ return aggregated;
542
+ });
543
+ this.getExpandedSelectedLocationsSet = (0, reselect_1.createSelector)(this.getClusteringEnabled, this.getSelectedLocationsSet, this.getClusterIndex, function (clusteringEnabled, selectedLocations, clusterIndex) {
544
+ var e_9, _a, e_10, _b;
545
+ if (!selectedLocations || !clusterIndex) {
546
+ return selectedLocations;
547
+ }
548
+ var result = new Set();
549
+ try {
550
+ for (var selectedLocations_3 = __values(selectedLocations), selectedLocations_3_1 = selectedLocations_3.next(); !selectedLocations_3_1.done; selectedLocations_3_1 = selectedLocations_3.next()) {
551
+ var locationId = selectedLocations_3_1.value;
552
+ var cluster = clusterIndex.getClusterById(locationId);
553
+ if (cluster) {
554
+ var expanded = clusterIndex.expandCluster(cluster);
555
+ try {
556
+ for (var expanded_1 = (e_10 = void 0, __values(expanded)), expanded_1_1 = expanded_1.next(); !expanded_1_1.done; expanded_1_1 = expanded_1.next()) {
557
+ var id = expanded_1_1.value;
558
+ result.add(id);
559
+ }
560
+ }
561
+ catch (e_10_1) { e_10 = { error: e_10_1 }; }
562
+ finally {
563
+ try {
564
+ if (expanded_1_1 && !expanded_1_1.done && (_b = expanded_1.return)) _b.call(expanded_1);
565
+ }
566
+ finally { if (e_10) throw e_10.error; }
567
+ }
568
+ }
569
+ else {
570
+ result.add(locationId);
571
+ }
572
+ }
573
+ }
574
+ catch (e_9_1) { e_9 = { error: e_9_1 }; }
575
+ finally {
576
+ try {
577
+ if (selectedLocations_3_1 && !selectedLocations_3_1.done && (_a = selectedLocations_3.return)) _a.call(selectedLocations_3);
578
+ }
579
+ finally { if (e_9) throw e_9.error; }
580
+ }
581
+ return result;
582
+ });
583
+ this.getTotalCountsByTime = (0, reselect_1.createSelector)(this.getSortedFlowsForKnownLocations, this.getTimeGranularityKey, this.getTimeExtent, this.getExpandedSelectedLocationsSet, this.getLocationFilterMode, function (flows, timeGranularityKey, timeExtent, selectedLocationSet, locationFilterMode) {
584
+ var timeGranularity = timeGranularityKey
585
+ ? (0, time_1.getTimeGranularityByKey)(timeGranularityKey)
586
+ : undefined;
587
+ if (!flows || !timeGranularity || !timeExtent)
588
+ return undefined;
589
+ var byTime = flows.reduce(function (m, flow) {
590
+ var _a;
591
+ if (_this.isFlowInSelection(flow, selectedLocationSet, locationFilterMode)) {
592
+ var key = timeGranularity
593
+ .interval(_this.accessors.getFlowTime(flow))
594
+ .getTime();
595
+ m.set(key, ((_a = m.get(key)) !== null && _a !== void 0 ? _a : 0) + _this.accessors.getFlowMagnitude(flow));
596
+ }
597
+ return m;
598
+ }, new Map());
599
+ return Array.from(byTime.entries()).map(function (_a) {
600
+ var _b = __read(_a, 2), millis = _b[0], count = _b[1];
601
+ return ({
602
+ time: new Date(millis),
603
+ count: count,
604
+ });
605
+ });
606
+ });
607
+ this.getMaxLocationCircleSize = (0, reselect_1.createSelector)(this.getLocationTotalsEnabled, function (locationTotalsEnabled) { return (locationTotalsEnabled ? 17 : 1); });
608
+ this.getViewportBoundingBox = (0, reselect_1.createSelector)(this.getViewport, this.getMaxLocationCircleSize, function (viewport, maxLocationCircleSize) {
609
+ var pad = maxLocationCircleSize;
610
+ var bounds = new web_mercator_1.WebMercatorViewport(__assign(__assign({}, viewport), { width: viewport.width + pad * 2, height: viewport.height + pad * 2 })).getBounds();
611
+ return [bounds[0][0], bounds[0][1], bounds[1][0], bounds[1][1]];
612
+ });
613
+ this.getLocationsForZoom = (0, reselect_1.createSelector)(this.getClusteringEnabled, this.getLocationsHavingFlows, this.getClusterIndex, this.getClusterZoom, function (clusteringEnabled, locationsHavingFlows, clusterIndex, clusterZoom) {
614
+ if (clusteringEnabled && clusterIndex) {
615
+ return clusterIndex.getClusterNodesFor(clusterZoom);
616
+ }
617
+ else {
618
+ return locationsHavingFlows;
619
+ }
620
+ });
621
+ this.getLocationTotals = (0, reselect_1.createSelector)(this.getLocationsForZoom, this.getSortedAggregatedFilteredFlows, this.getSelectedLocationsSet, this.getLocationFilterMode, function (locations, flows, selectedLocationsSet, locationFilterMode) {
622
+ var e_11, _a;
623
+ if (!flows)
624
+ return undefined;
625
+ var totals = new Map();
626
+ var add = function (id, d) {
627
+ var _a;
628
+ var rv = (_a = totals.get(id)) !== null && _a !== void 0 ? _a : {
629
+ incomingCount: 0,
630
+ outgoingCount: 0,
631
+ internalCount: 0,
632
+ };
633
+ if (d.incomingCount != null)
634
+ rv.incomingCount += d.incomingCount;
635
+ if (d.outgoingCount != null)
636
+ rv.outgoingCount += d.outgoingCount;
637
+ if (d.internalCount != null)
638
+ rv.internalCount += d.internalCount;
639
+ return rv;
640
+ };
641
+ try {
642
+ for (var flows_4 = __values(flows), flows_4_1 = flows_4.next(); !flows_4_1.done; flows_4_1 = flows_4.next()) {
643
+ var f = flows_4_1.value;
644
+ if (_this.isFlowInSelection(f, selectedLocationsSet, locationFilterMode)) {
645
+ var originId = _this.accessors.getFlowOriginId(f);
646
+ var destId = _this.accessors.getFlowDestId(f);
647
+ var count = _this.accessors.getFlowMagnitude(f);
648
+ if (originId === destId) {
649
+ totals.set(originId, add(originId, { internalCount: count }));
650
+ }
651
+ else {
652
+ totals.set(originId, add(originId, { outgoingCount: count }));
653
+ totals.set(destId, add(destId, { incomingCount: count }));
654
+ }
655
+ }
656
+ }
657
+ }
658
+ catch (e_11_1) { e_11 = { error: e_11_1 }; }
659
+ finally {
660
+ try {
661
+ if (flows_4_1 && !flows_4_1.done && (_a = flows_4.return)) _a.call(flows_4);
662
+ }
663
+ finally { if (e_11) throw e_11.error; }
664
+ }
665
+ return totals;
666
+ });
667
+ this.getLocationsTree = (0, reselect_1.createSelector)(this.getLocationsForZoom, function (locations) {
668
+ if (!locations) {
669
+ return undefined;
670
+ }
671
+ return new kdbush_1.default(
672
+ // @ts-ignore
673
+ locations, function (location) {
674
+ return lngX(_this.accessors.getLocationLon(location));
675
+ }, function (location) {
676
+ return latY(_this.accessors.getLocationLat(location));
677
+ });
678
+ });
679
+ this._getLocationIdsInViewport = (0, reselect_1.createSelector)(this.getLocationsTree, this.getViewportBoundingBox, function (tree, bbox) {
680
+ var ids = _this._getLocationsInBboxIndices(tree, bbox);
681
+ if (ids) {
682
+ return new Set(ids.map(function (idx) { return tree.points[idx].id; }));
683
+ }
684
+ return undefined;
685
+ });
686
+ this.getLocationIdsInViewport = (0, reselect_1.createSelectorCreator)(reselect_1.defaultMemoize,
687
+ // @ts-ignore
688
+ function (s1, s2, index) {
689
+ var e_12, _a;
690
+ if (s1 === s2)
691
+ return true;
692
+ if (s1 == null || s2 == null)
693
+ return false;
694
+ if (s1.size !== s2.size)
695
+ return false;
696
+ try {
697
+ for (var s1_1 = __values(s1), s1_1_1 = s1_1.next(); !s1_1_1.done; s1_1_1 = s1_1.next()) {
698
+ var item = s1_1_1.value;
699
+ if (!s2.has(item))
700
+ return false;
701
+ }
702
+ }
703
+ catch (e_12_1) { e_12 = { error: e_12_1 }; }
704
+ finally {
705
+ try {
706
+ if (s1_1_1 && !s1_1_1.done && (_a = s1_1.return)) _a.call(s1_1);
707
+ }
708
+ finally { if (e_12) throw e_12.error; }
709
+ }
710
+ return true;
711
+ })(this._getLocationIdsInViewport, function (locationIds) {
712
+ if (!locationIds)
713
+ return undefined;
714
+ return locationIds;
715
+ });
716
+ this.getTotalUnfilteredCount = (0, reselect_1.createSelector)(this.getSortedFlowsForKnownLocations, function (flows) {
717
+ if (!flows)
718
+ return undefined;
719
+ return flows.reduce(function (m, flow) { return m + _this.accessors.getFlowMagnitude(flow); }, 0);
720
+ });
721
+ this.getTotalFilteredCount = (0, reselect_1.createSelector)(this.getSortedAggregatedFilteredFlows, this.getSelectedLocationsSet, this.getLocationFilterMode, function (flows, selectedLocationSet, locationFilterMode) {
722
+ if (!flows)
723
+ return undefined;
724
+ var count = flows.reduce(function (m, flow) {
725
+ if (_this.isFlowInSelection(flow, selectedLocationSet, locationFilterMode)) {
726
+ return m + _this.accessors.getFlowMagnitude(flow);
727
+ }
728
+ return m;
729
+ }, 0);
730
+ return count;
731
+ });
732
+ this._getLocationTotalsExtent = (0, reselect_1.createSelector)(this.getLocationTotals, function (locationTotals) {
733
+ return calcLocationTotalsExtent(locationTotals, undefined);
734
+ });
735
+ this._getLocationTotalsForViewportExtent = (0, reselect_1.createSelector)(this.getLocationTotals, this.getLocationIdsInViewport, function (locationTotals, locationsInViewport) {
736
+ return calcLocationTotalsExtent(locationTotals, locationsInViewport);
737
+ });
738
+ this.getLocationTotalsExtent = function (state, props) {
739
+ if (state.settingsState.adaptiveScalesEnabled) {
740
+ return _this._getLocationTotalsForViewportExtent(state, props);
741
+ }
742
+ else {
743
+ return _this._getLocationTotalsExtent(state, props);
744
+ }
745
+ };
746
+ this.getFlowsForFlowmapLayer = (0, reselect_1.createSelector)(this.getSortedAggregatedFilteredFlows, this.getLocationIdsInViewport, this.getSelectedLocationsSet, this.getLocationFilterMode, this.getMaxTopFlowsDisplayNum, function (flows, locationIdsInViewport, selectedLocationsSet, locationFilterMode, maxTopFlowsDisplayNum) {
747
+ var e_13, _a;
748
+ if (!flows || !locationIdsInViewport)
749
+ return undefined;
750
+ var picked = [];
751
+ var pickedCount = 0;
752
+ try {
753
+ for (var flows_5 = __values(flows), flows_5_1 = flows_5.next(); !flows_5_1.done; flows_5_1 = flows_5.next()) {
754
+ var flow = flows_5_1.value;
755
+ var origin_1 = _this.accessors.getFlowOriginId(flow);
756
+ var dest = _this.accessors.getFlowDestId(flow);
757
+ if (locationIdsInViewport.has(origin_1) ||
758
+ locationIdsInViewport.has(dest)) {
759
+ if (_this.isFlowInSelection(flow, selectedLocationsSet, locationFilterMode)) {
760
+ if (origin_1 !== dest) {
761
+ // exclude self-loops
762
+ picked.push(flow);
763
+ pickedCount++;
764
+ }
765
+ }
766
+ }
767
+ // Only keep top
768
+ if (pickedCount > maxTopFlowsDisplayNum)
769
+ break;
770
+ }
771
+ }
772
+ catch (e_13_1) { e_13 = { error: e_13_1 }; }
773
+ finally {
774
+ try {
775
+ if (flows_5_1 && !flows_5_1.done && (_a = flows_5.return)) _a.call(flows_5);
776
+ }
777
+ finally { if (e_13) throw e_13.error; }
778
+ }
779
+ // assuming they are sorted in descending order,
780
+ // we need ascending for rendering
781
+ return picked.reverse();
782
+ });
783
+ this._getFlowMagnitudeExtent = (0, reselect_1.createSelector)(this.getSortedAggregatedFilteredFlows, this.getSelectedLocationsSet, this.getLocationFilterMode, function (flows, selectedLocationsSet, locationFilterMode) {
784
+ var e_14, _a;
785
+ if (!flows)
786
+ return undefined;
787
+ var rv = undefined;
788
+ try {
789
+ for (var flows_6 = __values(flows), flows_6_1 = flows_6.next(); !flows_6_1.done; flows_6_1 = flows_6.next()) {
790
+ var f = flows_6_1.value;
791
+ if (_this.accessors.getFlowOriginId(f) !==
792
+ _this.accessors.getFlowDestId(f) &&
793
+ _this.isFlowInSelection(f, selectedLocationsSet, locationFilterMode)) {
794
+ var count = _this.accessors.getFlowMagnitude(f);
795
+ if (rv == null) {
796
+ rv = [count, count];
797
+ }
798
+ else {
799
+ if (count < rv[0])
800
+ rv[0] = count;
801
+ if (count > rv[1])
802
+ rv[1] = count;
803
+ }
804
+ }
805
+ }
806
+ }
807
+ catch (e_14_1) { e_14 = { error: e_14_1 }; }
808
+ finally {
809
+ try {
810
+ if (flows_6_1 && !flows_6_1.done && (_a = flows_6.return)) _a.call(flows_6);
811
+ }
812
+ finally { if (e_14) throw e_14.error; }
813
+ }
814
+ return rv;
815
+ });
816
+ this._getAdaptiveFlowMagnitudeExtent = (0, reselect_1.createSelector)(this.getFlowsForFlowmapLayer, function (flows) {
817
+ if (!flows)
818
+ return undefined;
819
+ var rv = (0, d3_array_1.extent)(flows, _this.accessors.getFlowMagnitude);
820
+ return rv[0] !== undefined && rv[1] !== undefined ? rv : undefined;
821
+ });
822
+ this.getFlowMagnitudeExtent = function (state, props) {
823
+ if (state.settingsState.adaptiveScalesEnabled) {
824
+ return _this._getAdaptiveFlowMagnitudeExtent(state, props);
825
+ }
826
+ else {
827
+ return _this._getFlowMagnitudeExtent(state, props);
828
+ }
829
+ };
830
+ this.getLocationMaxAbsTotalGetter = (0, reselect_1.createSelector)(this.getLocationTotals, function (locationTotals) {
831
+ return function (locationId) {
832
+ var total = locationTotals === null || locationTotals === void 0 ? void 0 : locationTotals.get(locationId);
833
+ if (!total)
834
+ return undefined;
835
+ return Math.max(Math.abs(total.incomingCount + total.internalCount), Math.abs(total.outgoingCount + total.internalCount));
836
+ };
837
+ });
838
+ this.getFlowThicknessScale = (0, reselect_1.createSelector)(this.getFlowMagnitudeExtent, function (magnitudeExtent) {
839
+ if (!magnitudeExtent)
840
+ return undefined;
841
+ return (0, d3_scale_1.scaleLinear)()
842
+ .range([0.025, 0.5])
843
+ .domain([
844
+ 0,
845
+ // should support diff mode too
846
+ Math.max.apply(null, magnitudeExtent.map(function (x) { return Math.abs(x || 0); })),
847
+ ]);
848
+ });
849
+ this.getCircleSizeScale = (0, reselect_1.createSelector)(this.getMaxLocationCircleSize, this.getLocationTotalsEnabled, this.getLocationTotalsExtent, function (maxLocationCircleSize, locationTotalsEnabled, locationTotalsExtent) {
850
+ if (!locationTotalsEnabled) {
851
+ return function () { return maxLocationCircleSize; };
852
+ }
853
+ if (!locationTotalsExtent)
854
+ return undefined;
855
+ return (0, d3_scale_1.scaleSqrt)()
856
+ .range([0, maxLocationCircleSize])
857
+ .domain([
858
+ 0,
859
+ // should support diff mode too
860
+ Math.max.apply(null, locationTotalsExtent.map(function (x) {
861
+ return Math.abs(x || 0);
862
+ })),
863
+ ]);
864
+ });
865
+ this.getInCircleSizeGetter = (0, reselect_1.createSelector)(this.getCircleSizeScale, this.getLocationTotals, function (circleSizeScale, locationTotals) {
866
+ return function (locationId) {
867
+ var total = locationTotals === null || locationTotals === void 0 ? void 0 : locationTotals.get(locationId);
868
+ if (total && circleSizeScale) {
869
+ return (circleSizeScale(Math.abs(total.incomingCount + total.internalCount)) || 0);
870
+ }
871
+ return 0;
872
+ };
873
+ });
874
+ this.getOutCircleSizeGetter = (0, reselect_1.createSelector)(this.getCircleSizeScale, this.getLocationTotals, function (circleSizeScale, locationTotals) {
875
+ return function (locationId) {
876
+ var total = locationTotals === null || locationTotals === void 0 ? void 0 : locationTotals.get(locationId);
877
+ if (total && circleSizeScale) {
878
+ return (circleSizeScale(Math.abs(total.outgoingCount + total.internalCount)) || 0);
879
+ }
880
+ return 0;
881
+ };
882
+ });
883
+ this.getSortedLocationsForZoom = (0, reselect_1.createSelector)(this.getLocationsForZoom, this.getInCircleSizeGetter, this.getOutCircleSizeGetter, function (locations, getInCircleSize, getOutCircleSize) {
884
+ if (!locations)
885
+ return undefined;
886
+ var nextLocations = __spreadArray([], __read(locations), false);
887
+ return nextLocations.sort(function (a, b) {
888
+ var idA = _this.accessors.getLocationId(a);
889
+ var idB = _this.accessors.getLocationId(b);
890
+ return (0, d3_array_1.ascending)(Math.max(getInCircleSize(idA), getOutCircleSize(idA)), Math.max(getInCircleSize(idB), getOutCircleSize(idB)));
891
+ });
892
+ });
893
+ this.getLocationsForFlowmapLayer = (0, reselect_1.createSelector)(this.getSortedLocationsForZoom,
894
+ // this.getLocationIdsInViewport,
895
+ function (locations) {
896
+ // if (!locations) return undefined;
897
+ // if (!locationIdsInViewport) return locations;
898
+ // if (locationIdsInViewport.size === locations.length) return locations;
899
+ // const filtered = [];
900
+ // for (const loc of locations) {
901
+ // if (locationIdsInViewport.has(loc.id)) {
902
+ // filtered.push(loc);
903
+ // }
904
+ // }
905
+ // return filtered;
906
+ // @ts-ignore
907
+ // return locations.filter(
908
+ // (loc: L | ClusterNode) => locationIdsInViewport!.has(loc.id)
909
+ // );
910
+ // TODO: return location in viewport + "connected" ones
911
+ return locations;
912
+ });
913
+ this.getLocationsForFlowmapLayerById = (0, reselect_1.createSelector)(this.getLocationsForFlowmapLayer, function (locations) {
914
+ if (!locations)
915
+ return undefined;
916
+ return locations.reduce(function (m, d) { return (m.set(_this.accessors.getLocationId(d), d), m); }, new Map());
917
+ });
918
+ this.getLayersData = (0, reselect_1.createSelector)(this.getLocationsForFlowmapLayer, this.getFlowsForFlowmapLayer, this.getFlowmapColorsRGBA, this.getLocationsForFlowmapLayerById, this.getLocationIdsInViewport, this.getInCircleSizeGetter, this.getOutCircleSizeGetter, this.getFlowThicknessScale, this.getAnimate, function (locations, flows, flowmapColors, locationsById, locationIdsInViewport, getInCircleSize, getOutCircleSize, flowThicknessScale, animationEnabled) {
919
+ return _this._prepareLayersData(locations, flows, flowmapColors, locationsById, locationIdsInViewport, getInCircleSize, getOutCircleSize, flowThicknessScale, animationEnabled);
920
+ });
921
+ this.accessors = new FlowmapAggregateAccessors_1.default(accessors);
922
+ this.setAccessors(accessors);
923
+ }
924
+ FlowmapSelectors.prototype.setAccessors = function (accessors) {
925
+ this.accessors = new FlowmapAggregateAccessors_1.default(accessors);
926
+ };
927
+ FlowmapSelectors.prototype.prepareLayersData = function (state, props) {
928
+ var locations = this.getLocationsForFlowmapLayer(state, props) || [];
929
+ var flows = this.getFlowsForFlowmapLayer(state, props) || [];
930
+ var flowmapColors = this.getFlowmapColorsRGBA(state, props);
931
+ var locationsById = this.getLocationsForFlowmapLayerById(state, props);
932
+ var locationIdsInViewport = this.getLocationIdsInViewport(state, props);
933
+ var getInCircleSize = this.getInCircleSizeGetter(state, props);
934
+ var getOutCircleSize = this.getOutCircleSizeGetter(state, props);
935
+ var flowThicknessScale = this.getFlowThicknessScale(state, props);
936
+ return this._prepareLayersData(locations, flows, flowmapColors, locationsById, locationIdsInViewport, getInCircleSize, getOutCircleSize, flowThicknessScale, state.settingsState.animationEnabled);
937
+ };
938
+ FlowmapSelectors.prototype._prepareLayersData = function (locations, flows, flowmapColors, locationsById, locationIdsInViewport, getInCircleSize, getOutCircleSize, flowThicknessScale, animationEnabled) {
939
+ if (!locations)
940
+ locations = [];
941
+ if (!flows)
942
+ flows = [];
943
+ var _a = this.accessors, getFlowOriginId = _a.getFlowOriginId, getFlowDestId = _a.getFlowDestId, getFlowMagnitude = _a.getFlowMagnitude, getLocationId = _a.getLocationId, getLocationLon = _a.getLocationLon, getLocationLat = _a.getLocationLat;
944
+ var flowMagnitudeExtent = (0, d3_array_1.extent)(flows, function (f) { return getFlowMagnitude(f); });
945
+ var flowColorScale = (0, colors_1.getFlowColorScale)(flowmapColors, flowMagnitudeExtent, false);
946
+ // Using a generator here helps to avoid creating intermediary arrays
947
+ var circlePositions = Float32Array.from((function () {
948
+ var locations_2, locations_2_1, location_2, e_15_1;
949
+ var e_15, _a;
950
+ return __generator(this, function (_b) {
951
+ switch (_b.label) {
952
+ case 0:
953
+ _b.trys.push([0, 6, 7, 8]);
954
+ locations_2 = __values(locations), locations_2_1 = locations_2.next();
955
+ _b.label = 1;
956
+ case 1:
957
+ if (!!locations_2_1.done) return [3 /*break*/, 5];
958
+ location_2 = locations_2_1.value;
959
+ return [4 /*yield*/, getLocationLon(location_2)];
960
+ case 2:
961
+ _b.sent();
962
+ return [4 /*yield*/, getLocationLat(location_2)];
963
+ case 3:
964
+ _b.sent();
965
+ _b.label = 4;
966
+ case 4:
967
+ locations_2_1 = locations_2.next();
968
+ return [3 /*break*/, 1];
969
+ case 5: return [3 /*break*/, 8];
970
+ case 6:
971
+ e_15_1 = _b.sent();
972
+ e_15 = { error: e_15_1 };
973
+ return [3 /*break*/, 8];
974
+ case 7:
975
+ try {
976
+ if (locations_2_1 && !locations_2_1.done && (_a = locations_2.return)) _a.call(locations_2);
977
+ }
978
+ finally { if (e_15) throw e_15.error; }
979
+ return [7 /*endfinally*/];
980
+ case 8: return [2 /*return*/];
981
+ }
982
+ });
983
+ })());
984
+ // TODO: diff mode
985
+ var circleColor = (0, colors_1.isDiffColorsRGBA)(flowmapColors)
986
+ ? flowmapColors.positive.locationCircles.inner
987
+ : flowmapColors.locationCircles.inner;
988
+ var circleColors = Uint8Array.from((function () {
989
+ var locations_3, locations_3_1, location_3, e_16_1;
990
+ var e_16, _a;
991
+ return __generator(this, function (_b) {
992
+ switch (_b.label) {
993
+ case 0:
994
+ _b.trys.push([0, 5, 6, 7]);
995
+ locations_3 = __values(locations), locations_3_1 = locations_3.next();
996
+ _b.label = 1;
997
+ case 1:
998
+ if (!!locations_3_1.done) return [3 /*break*/, 4];
999
+ location_3 = locations_3_1.value;
1000
+ return [5 /*yield**/, __values(circleColor)];
1001
+ case 2:
1002
+ _b.sent();
1003
+ _b.label = 3;
1004
+ case 3:
1005
+ locations_3_1 = locations_3.next();
1006
+ return [3 /*break*/, 1];
1007
+ case 4: return [3 /*break*/, 7];
1008
+ case 5:
1009
+ e_16_1 = _b.sent();
1010
+ e_16 = { error: e_16_1 };
1011
+ return [3 /*break*/, 7];
1012
+ case 6:
1013
+ try {
1014
+ if (locations_3_1 && !locations_3_1.done && (_a = locations_3.return)) _a.call(locations_3);
1015
+ }
1016
+ finally { if (e_16) throw e_16.error; }
1017
+ return [7 /*endfinally*/];
1018
+ case 7: return [2 /*return*/];
1019
+ }
1020
+ });
1021
+ })());
1022
+ var inCircleRadii = Float32Array.from((function () {
1023
+ var locations_4, locations_4_1, location_4, id, e_17_1;
1024
+ var e_17, _a;
1025
+ return __generator(this, function (_b) {
1026
+ switch (_b.label) {
1027
+ case 0:
1028
+ _b.trys.push([0, 5, 6, 7]);
1029
+ locations_4 = __values(locations), locations_4_1 = locations_4.next();
1030
+ _b.label = 1;
1031
+ case 1:
1032
+ if (!!locations_4_1.done) return [3 /*break*/, 4];
1033
+ location_4 = locations_4_1.value;
1034
+ id = getLocationId(location_4);
1035
+ return [4 /*yield*/, (locationIdsInViewport === null || locationIdsInViewport === void 0 ? void 0 : locationIdsInViewport.has(id)) ? getInCircleSize(id) : 1.0];
1036
+ case 2:
1037
+ _b.sent();
1038
+ _b.label = 3;
1039
+ case 3:
1040
+ locations_4_1 = locations_4.next();
1041
+ return [3 /*break*/, 1];
1042
+ case 4: return [3 /*break*/, 7];
1043
+ case 5:
1044
+ e_17_1 = _b.sent();
1045
+ e_17 = { error: e_17_1 };
1046
+ return [3 /*break*/, 7];
1047
+ case 6:
1048
+ try {
1049
+ if (locations_4_1 && !locations_4_1.done && (_a = locations_4.return)) _a.call(locations_4);
1050
+ }
1051
+ finally { if (e_17) throw e_17.error; }
1052
+ return [7 /*endfinally*/];
1053
+ case 7: return [2 /*return*/];
1054
+ }
1055
+ });
1056
+ })());
1057
+ var outCircleRadii = Float32Array.from((function () {
1058
+ var locations_5, locations_5_1, location_5, id, e_18_1;
1059
+ var e_18, _a;
1060
+ return __generator(this, function (_b) {
1061
+ switch (_b.label) {
1062
+ case 0:
1063
+ _b.trys.push([0, 5, 6, 7]);
1064
+ locations_5 = __values(locations), locations_5_1 = locations_5.next();
1065
+ _b.label = 1;
1066
+ case 1:
1067
+ if (!!locations_5_1.done) return [3 /*break*/, 4];
1068
+ location_5 = locations_5_1.value;
1069
+ id = getLocationId(location_5);
1070
+ return [4 /*yield*/, (locationIdsInViewport === null || locationIdsInViewport === void 0 ? void 0 : locationIdsInViewport.has(id)) ? getOutCircleSize(id) : 1.0];
1071
+ case 2:
1072
+ _b.sent();
1073
+ _b.label = 3;
1074
+ case 3:
1075
+ locations_5_1 = locations_5.next();
1076
+ return [3 /*break*/, 1];
1077
+ case 4: return [3 /*break*/, 7];
1078
+ case 5:
1079
+ e_18_1 = _b.sent();
1080
+ e_18 = { error: e_18_1 };
1081
+ return [3 /*break*/, 7];
1082
+ case 6:
1083
+ try {
1084
+ if (locations_5_1 && !locations_5_1.done && (_a = locations_5.return)) _a.call(locations_5);
1085
+ }
1086
+ finally { if (e_18) throw e_18.error; }
1087
+ return [7 /*endfinally*/];
1088
+ case 7: return [2 /*return*/];
1089
+ }
1090
+ });
1091
+ })());
1092
+ var sourcePositions = Float32Array.from((function () {
1093
+ var flows_7, flows_7_1, flow, loc, e_19_1;
1094
+ var e_19, _a;
1095
+ return __generator(this, function (_b) {
1096
+ switch (_b.label) {
1097
+ case 0:
1098
+ _b.trys.push([0, 6, 7, 8]);
1099
+ flows_7 = __values(flows), flows_7_1 = flows_7.next();
1100
+ _b.label = 1;
1101
+ case 1:
1102
+ if (!!flows_7_1.done) return [3 /*break*/, 5];
1103
+ flow = flows_7_1.value;
1104
+ loc = locationsById === null || locationsById === void 0 ? void 0 : locationsById.get(getFlowOriginId(flow));
1105
+ return [4 /*yield*/, loc ? getLocationLon(loc) : 0];
1106
+ case 2:
1107
+ _b.sent();
1108
+ return [4 /*yield*/, loc ? getLocationLat(loc) : 0];
1109
+ case 3:
1110
+ _b.sent();
1111
+ _b.label = 4;
1112
+ case 4:
1113
+ flows_7_1 = flows_7.next();
1114
+ return [3 /*break*/, 1];
1115
+ case 5: return [3 /*break*/, 8];
1116
+ case 6:
1117
+ e_19_1 = _b.sent();
1118
+ e_19 = { error: e_19_1 };
1119
+ return [3 /*break*/, 8];
1120
+ case 7:
1121
+ try {
1122
+ if (flows_7_1 && !flows_7_1.done && (_a = flows_7.return)) _a.call(flows_7);
1123
+ }
1124
+ finally { if (e_19) throw e_19.error; }
1125
+ return [7 /*endfinally*/];
1126
+ case 8: return [2 /*return*/];
1127
+ }
1128
+ });
1129
+ })());
1130
+ var targetPositions = Float32Array.from((function () {
1131
+ var flows_8, flows_8_1, flow, loc, e_20_1;
1132
+ var e_20, _a;
1133
+ return __generator(this, function (_b) {
1134
+ switch (_b.label) {
1135
+ case 0:
1136
+ _b.trys.push([0, 6, 7, 8]);
1137
+ flows_8 = __values(flows), flows_8_1 = flows_8.next();
1138
+ _b.label = 1;
1139
+ case 1:
1140
+ if (!!flows_8_1.done) return [3 /*break*/, 5];
1141
+ flow = flows_8_1.value;
1142
+ loc = locationsById === null || locationsById === void 0 ? void 0 : locationsById.get(getFlowDestId(flow));
1143
+ return [4 /*yield*/, loc ? getLocationLon(loc) : 0];
1144
+ case 2:
1145
+ _b.sent();
1146
+ return [4 /*yield*/, loc ? getLocationLat(loc) : 0];
1147
+ case 3:
1148
+ _b.sent();
1149
+ _b.label = 4;
1150
+ case 4:
1151
+ flows_8_1 = flows_8.next();
1152
+ return [3 /*break*/, 1];
1153
+ case 5: return [3 /*break*/, 8];
1154
+ case 6:
1155
+ e_20_1 = _b.sent();
1156
+ e_20 = { error: e_20_1 };
1157
+ return [3 /*break*/, 8];
1158
+ case 7:
1159
+ try {
1160
+ if (flows_8_1 && !flows_8_1.done && (_a = flows_8.return)) _a.call(flows_8);
1161
+ }
1162
+ finally { if (e_20) throw e_20.error; }
1163
+ return [7 /*endfinally*/];
1164
+ case 8: return [2 /*return*/];
1165
+ }
1166
+ });
1167
+ })());
1168
+ var thicknesses = Float32Array.from((function () {
1169
+ var flows_9, flows_9_1, flow, e_21_1;
1170
+ var e_21, _a;
1171
+ return __generator(this, function (_b) {
1172
+ switch (_b.label) {
1173
+ case 0:
1174
+ _b.trys.push([0, 5, 6, 7]);
1175
+ flows_9 = __values(flows), flows_9_1 = flows_9.next();
1176
+ _b.label = 1;
1177
+ case 1:
1178
+ if (!!flows_9_1.done) return [3 /*break*/, 4];
1179
+ flow = flows_9_1.value;
1180
+ return [4 /*yield*/, flowThicknessScale
1181
+ ? flowThicknessScale(getFlowMagnitude(flow)) || 0
1182
+ : 0];
1183
+ case 2:
1184
+ _b.sent();
1185
+ _b.label = 3;
1186
+ case 3:
1187
+ flows_9_1 = flows_9.next();
1188
+ return [3 /*break*/, 1];
1189
+ case 4: return [3 /*break*/, 7];
1190
+ case 5:
1191
+ e_21_1 = _b.sent();
1192
+ e_21 = { error: e_21_1 };
1193
+ return [3 /*break*/, 7];
1194
+ case 6:
1195
+ try {
1196
+ if (flows_9_1 && !flows_9_1.done && (_a = flows_9.return)) _a.call(flows_9);
1197
+ }
1198
+ finally { if (e_21) throw e_21.error; }
1199
+ return [7 /*endfinally*/];
1200
+ case 7: return [2 /*return*/];
1201
+ }
1202
+ });
1203
+ })());
1204
+ var endpointOffsets = Float32Array.from((function () {
1205
+ var flows_10, flows_10_1, flow, originId, destId, e_22_1;
1206
+ var e_22, _a;
1207
+ return __generator(this, function (_b) {
1208
+ switch (_b.label) {
1209
+ case 0:
1210
+ _b.trys.push([0, 6, 7, 8]);
1211
+ flows_10 = __values(flows), flows_10_1 = flows_10.next();
1212
+ _b.label = 1;
1213
+ case 1:
1214
+ if (!!flows_10_1.done) return [3 /*break*/, 5];
1215
+ flow = flows_10_1.value;
1216
+ originId = getFlowOriginId(flow);
1217
+ destId = getFlowDestId(flow);
1218
+ return [4 /*yield*/, Math.max(getInCircleSize(originId), getOutCircleSize(originId))];
1219
+ case 2:
1220
+ _b.sent();
1221
+ return [4 /*yield*/, Math.max(getInCircleSize(destId), getOutCircleSize(destId))];
1222
+ case 3:
1223
+ _b.sent();
1224
+ _b.label = 4;
1225
+ case 4:
1226
+ flows_10_1 = flows_10.next();
1227
+ return [3 /*break*/, 1];
1228
+ case 5: return [3 /*break*/, 8];
1229
+ case 6:
1230
+ e_22_1 = _b.sent();
1231
+ e_22 = { error: e_22_1 };
1232
+ return [3 /*break*/, 8];
1233
+ case 7:
1234
+ try {
1235
+ if (flows_10_1 && !flows_10_1.done && (_a = flows_10.return)) _a.call(flows_10);
1236
+ }
1237
+ finally { if (e_22) throw e_22.error; }
1238
+ return [7 /*endfinally*/];
1239
+ case 8: return [2 /*return*/];
1240
+ }
1241
+ });
1242
+ })());
1243
+ var flowLineColors = Uint8Array.from((function () {
1244
+ var flows_11, flows_11_1, flow, e_23_1;
1245
+ var e_23, _a;
1246
+ return __generator(this, function (_b) {
1247
+ switch (_b.label) {
1248
+ case 0:
1249
+ _b.trys.push([0, 5, 6, 7]);
1250
+ flows_11 = __values(flows), flows_11_1 = flows_11.next();
1251
+ _b.label = 1;
1252
+ case 1:
1253
+ if (!!flows_11_1.done) return [3 /*break*/, 4];
1254
+ flow = flows_11_1.value;
1255
+ return [5 /*yield**/, __values(flowColorScale(getFlowMagnitude(flow)))];
1256
+ case 2:
1257
+ _b.sent();
1258
+ _b.label = 3;
1259
+ case 3:
1260
+ flows_11_1 = flows_11.next();
1261
+ return [3 /*break*/, 1];
1262
+ case 4: return [3 /*break*/, 7];
1263
+ case 5:
1264
+ e_23_1 = _b.sent();
1265
+ e_23 = { error: e_23_1 };
1266
+ return [3 /*break*/, 7];
1267
+ case 6:
1268
+ try {
1269
+ if (flows_11_1 && !flows_11_1.done && (_a = flows_11.return)) _a.call(flows_11);
1270
+ }
1271
+ finally { if (e_23) throw e_23.error; }
1272
+ return [7 /*endfinally*/];
1273
+ case 7: return [2 /*return*/];
1274
+ }
1275
+ });
1276
+ })());
1277
+ var staggeringValues = animationEnabled
1278
+ ? Float32Array.from((function () {
1279
+ var flows_12, flows_12_1, f, e_24_1;
1280
+ var e_24, _a;
1281
+ return __generator(this, function (_b) {
1282
+ switch (_b.label) {
1283
+ case 0:
1284
+ _b.trys.push([0, 5, 6, 7]);
1285
+ flows_12 = __values(flows), flows_12_1 = flows_12.next();
1286
+ _b.label = 1;
1287
+ case 1:
1288
+ if (!!flows_12_1.done) return [3 /*break*/, 4];
1289
+ f = flows_12_1.value;
1290
+ // @ts-ignore
1291
+ return [4 /*yield*/, new seedrandom_1.alea("".concat(getFlowOriginId(f), "-").concat(getFlowDestId(f)))()];
1292
+ case 2:
1293
+ // @ts-ignore
1294
+ _b.sent();
1295
+ _b.label = 3;
1296
+ case 3:
1297
+ flows_12_1 = flows_12.next();
1298
+ return [3 /*break*/, 1];
1299
+ case 4: return [3 /*break*/, 7];
1300
+ case 5:
1301
+ e_24_1 = _b.sent();
1302
+ e_24 = { error: e_24_1 };
1303
+ return [3 /*break*/, 7];
1304
+ case 6:
1305
+ try {
1306
+ if (flows_12_1 && !flows_12_1.done && (_a = flows_12.return)) _a.call(flows_12);
1307
+ }
1308
+ finally { if (e_24) throw e_24.error; }
1309
+ return [7 /*endfinally*/];
1310
+ case 7: return [2 /*return*/];
1311
+ }
1312
+ });
1313
+ })())
1314
+ : undefined;
1315
+ return {
1316
+ circleAttributes: {
1317
+ length: locations.length,
1318
+ attributes: {
1319
+ getPosition: { value: circlePositions, size: 2 },
1320
+ getColor: { value: circleColors, size: 4 },
1321
+ getInRadius: { value: inCircleRadii, size: 1 },
1322
+ getOutRadius: { value: outCircleRadii, size: 1 },
1323
+ },
1324
+ },
1325
+ lineAttributes: {
1326
+ length: flows.length,
1327
+ attributes: __assign({ getSourcePosition: { value: sourcePositions, size: 2 }, getTargetPosition: { value: targetPositions, size: 2 }, getThickness: { value: thicknesses, size: 1 }, getColor: { value: flowLineColors, size: 4 }, getEndpointOffsets: { value: endpointOffsets, size: 2 } }, (staggeringValues
1328
+ ? { getStaggering: { value: staggeringValues, size: 1 } }
1329
+ : {})),
1330
+ },
1331
+ };
1332
+ };
1333
+ FlowmapSelectors.prototype.getLocationsInBbox = function (tree, bbox) {
1334
+ if (!tree)
1335
+ return undefined;
1336
+ return this._getLocationsInBboxIndices(tree, bbox).map(function (idx) { return tree.points[idx]; });
1337
+ };
1338
+ FlowmapSelectors.prototype._getLocationsInBboxIndices = function (tree, bbox) {
1339
+ if (!tree)
1340
+ return undefined;
1341
+ var _a = __read(bbox, 4), lon1 = _a[0], lat1 = _a[1], lon2 = _a[2], lat2 = _a[3];
1342
+ var _b = __read([lngX(lon1), latY(lat1), lngX(lon2), latY(lat2)], 4), x1 = _b[0], y1 = _b[1], x2 = _b[2], y2 = _b[3];
1343
+ return tree.range(Math.min(x1, x2), Math.min(y1, y2), Math.max(x1, x2), Math.max(y1, y2));
1344
+ };
1345
+ FlowmapSelectors.prototype.isFlowInSelection = function (flow, selectedLocationsSet, locationFilterMode) {
1346
+ var origin = this.accessors.getFlowOriginId(flow);
1347
+ var dest = this.accessors.getFlowDestId(flow);
1348
+ if (selectedLocationsSet) {
1349
+ switch (locationFilterMode) {
1350
+ case types_1.LocationFilterMode.ALL:
1351
+ return (selectedLocationsSet.has(origin) || selectedLocationsSet.has(dest));
1352
+ case types_1.LocationFilterMode.BETWEEN:
1353
+ return (selectedLocationsSet.has(origin) && selectedLocationsSet.has(dest));
1354
+ case types_1.LocationFilterMode.INCOMING:
1355
+ return selectedLocationsSet.has(dest);
1356
+ case types_1.LocationFilterMode.OUTGOING:
1357
+ return selectedLocationsSet.has(origin);
1358
+ }
1359
+ }
1360
+ return true;
1361
+ };
1362
+ return FlowmapSelectors;
1363
+ }());
1364
+ exports.default = FlowmapSelectors;
1365
+ function calcLocationTotalsExtent(locationTotals, locationIdsInViewport) {
1366
+ var e_25, _a;
1367
+ if (!locationTotals)
1368
+ return undefined;
1369
+ var rv = undefined;
1370
+ try {
1371
+ for (var _b = __values(locationTotals.entries()), _c = _b.next(); !_c.done; _c = _b.next()) {
1372
+ var _d = __read(_c.value, 2), id = _d[0], _e = _d[1], incomingCount = _e.incomingCount, outgoingCount = _e.outgoingCount, internalCount = _e.internalCount;
1373
+ if (locationIdsInViewport == null || locationIdsInViewport.has(id)) {
1374
+ var lo = Math.min(incomingCount + internalCount, outgoingCount + internalCount, internalCount);
1375
+ var hi = Math.max(incomingCount + internalCount, outgoingCount + internalCount, internalCount);
1376
+ if (!rv) {
1377
+ rv = [lo, hi];
1378
+ }
1379
+ else {
1380
+ if (lo < rv[0])
1381
+ rv[0] = lo;
1382
+ if (hi > rv[1])
1383
+ rv[1] = hi;
1384
+ }
1385
+ }
1386
+ }
1387
+ }
1388
+ catch (e_25_1) { e_25 = { error: e_25_1 }; }
1389
+ finally {
1390
+ try {
1391
+ if (_c && !_c.done && (_a = _b.return)) _a.call(_b);
1392
+ }
1393
+ finally { if (e_25) throw e_25.error; }
1394
+ }
1395
+ return rv;
1396
+ }
1397
+ // longitude/latitude to spherical mercator in [0..1] range
1398
+ function lngX(lng) {
1399
+ return lng / 360 + 0.5;
1400
+ }
1401
+ function latY(lat) {
1402
+ var sin = Math.sin((lat * Math.PI) / 180);
1403
+ var y = 0.5 - (0.25 * Math.log((1 + sin) / (1 - sin))) / Math.PI;
1404
+ return y < 0 ? 0 : y > 1 ? 1 : y;
1405
+ }
1406
+ function aggregateFlows(flows, flowAccessors) {
1407
+ var e_26, _a, e_27, _b;
1408
+ // Sum up flows with same origin, dest
1409
+ var byOriginDest = (0, d3_collection_1.nest)()
1410
+ .key(flowAccessors.getFlowOriginId)
1411
+ .key(flowAccessors.getFlowDestId)
1412
+ .rollup(function (ff) {
1413
+ var origin = flowAccessors.getFlowOriginId(ff[0]);
1414
+ var dest = flowAccessors.getFlowDestId(ff[0]);
1415
+ // const color = ff[0].color;
1416
+ var rv = {
1417
+ aggregate: true,
1418
+ origin: origin,
1419
+ dest: dest,
1420
+ count: ff.reduce(function (m, f) {
1421
+ var count = flowAccessors.getFlowMagnitude(f);
1422
+ if (count) {
1423
+ if (!isNaN(count) && isFinite(count))
1424
+ return m + count;
1425
+ }
1426
+ return m;
1427
+ }, 0),
1428
+ // time: undefined,
1429
+ };
1430
+ // if (color) rv.color = color;
1431
+ return rv;
1432
+ })
1433
+ .entries(flows);
1434
+ var rv = [];
1435
+ try {
1436
+ for (var byOriginDest_1 = __values(byOriginDest), byOriginDest_1_1 = byOriginDest_1.next(); !byOriginDest_1_1.done; byOriginDest_1_1 = byOriginDest_1.next()) {
1437
+ var values = byOriginDest_1_1.value.values;
1438
+ try {
1439
+ for (var values_1 = (e_27 = void 0, __values(values)), values_1_1 = values_1.next(); !values_1_1.done; values_1_1 = values_1.next()) {
1440
+ var value = values_1_1.value.value;
1441
+ rv.push(value);
1442
+ }
1443
+ }
1444
+ catch (e_27_1) { e_27 = { error: e_27_1 }; }
1445
+ finally {
1446
+ try {
1447
+ if (values_1_1 && !values_1_1.done && (_b = values_1.return)) _b.call(values_1);
1448
+ }
1449
+ finally { if (e_27) throw e_27.error; }
1450
+ }
1451
+ }
1452
+ }
1453
+ catch (e_26_1) { e_26 = { error: e_26_1 }; }
1454
+ finally {
1455
+ try {
1456
+ if (byOriginDest_1_1 && !byOriginDest_1_1.done && (_a = byOriginDest_1.return)) _a.call(byOriginDest_1);
1457
+ }
1458
+ finally { if (e_26) throw e_26.error; }
1459
+ }
1460
+ return rv;
1461
+ }
1462
+ /**
1463
+ * This is used to augment hover picking info so that we can displace location tooltip
1464
+ * @param circleAttributes
1465
+ * @param index
1466
+ */
1467
+ function getOuterCircleRadiusByIndex(circleAttributes, index) {
1468
+ var _a = circleAttributes.attributes, getInRadius = _a.getInRadius, getOutRadius = _a.getOutRadius;
1469
+ return Math.max(getInRadius.value[index], getOutRadius.value[index]);
1470
+ }
1471
+ exports.getOuterCircleRadiusByIndex = getOuterCircleRadiusByIndex;
1472
+ function getLocationCoordsByIndex(circleAttributes, index) {
1473
+ var getPosition = circleAttributes.attributes.getPosition;
1474
+ return [getPosition.value[index * 2], getPosition.value[index * 2 + 1]];
1475
+ }
1476
+ exports.getLocationCoordsByIndex = getLocationCoordsByIndex;
1477
+ function getFlowLineAttributesByIndex(lineAttributes, index) {
1478
+ var _a = lineAttributes.attributes, getColor = _a.getColor, getEndpointOffsets = _a.getEndpointOffsets, getSourcePosition = _a.getSourcePosition, getTargetPosition = _a.getTargetPosition, getThickness = _a.getThickness, getStaggering = _a.getStaggering;
1479
+ return {
1480
+ length: 1,
1481
+ attributes: __assign({ getColor: {
1482
+ value: getColor.value.subarray(index * 4, (index + 1) * 4),
1483
+ size: 4,
1484
+ }, getEndpointOffsets: {
1485
+ value: getEndpointOffsets.value.subarray(index * 2, (index + 1) * 2),
1486
+ size: 2,
1487
+ }, getSourcePosition: {
1488
+ value: getSourcePosition.value.subarray(index * 2, (index + 1) * 2),
1489
+ size: 2,
1490
+ }, getTargetPosition: {
1491
+ value: getTargetPosition.value.subarray(index * 2, (index + 1) * 2),
1492
+ size: 2,
1493
+ }, getThickness: {
1494
+ value: getThickness.value.subarray(index, index + 1),
1495
+ size: 1,
1496
+ } }, (getStaggering
1497
+ ? {
1498
+ getStaggering: {
1499
+ value: getStaggering.value.subarray(index, index + 1),
1500
+ size: 1,
1501
+ },
1502
+ }
1503
+ : undefined)),
1504
+ };
1505
+ }
1506
+ exports.getFlowLineAttributesByIndex = getFlowLineAttributesByIndex;
1507
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiRmxvd21hcFNlbGVjdG9ycy5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uL3NyYy9GbG93bWFwU2VsZWN0b3JzLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7QUFBQTs7Ozs7Ozs7Ozs7Ozs7OztHQWdCRzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBRUgsc0RBQTBEO0FBQzFELHFDQUE0RDtBQUM1RCwrQ0FBbUM7QUFDbkMscUNBQTZEO0FBQzdELGtEQUE0QjtBQUM1QixxQ0FLa0I7QUFDbEIseUNBQWdDO0FBQ2hDLDZDQUFtRDtBQUNuRCx1REFLZ0M7QUFDaEMsaURBUWtCO0FBQ2xCLDBGQUFvRTtBQUVwRSwrQkFLZ0I7QUFDaEIsaUNBZWlCO0FBRWpCLElBQU0sc0JBQXNCLEdBQUcsRUFBRSxDQUFDO0FBU2xDO0lBR0UsMEJBQVksU0FBcUM7UUFBakQsaUJBR0M7UUFNRCxvQkFBZSxHQUFHLFVBQUMsS0FBbUIsRUFBRSxLQUF3QjtZQUM5RCxPQUFBLEtBQUssQ0FBQyxLQUFLO1FBQVgsQ0FBVyxDQUFDO1FBQ2Qsd0JBQW1CLEdBQUcsVUFBQyxLQUFtQixFQUFFLEtBQXdCO1lBQ2xFLE9BQUEsS0FBSyxDQUFDLFNBQVM7UUFBZixDQUFlLENBQUM7UUFDbEIsNkJBQXdCLEdBQUcsVUFBQyxLQUFtQixFQUFFLEtBQXdCO1lBQ3ZFLE9BQUEsS0FBSyxDQUFDLGFBQWEsQ0FBQyxxQkFBcUI7UUFBekMsQ0FBeUMsQ0FBQztRQUM1Qyx5QkFBb0IsR0FBRyxVQUFDLEtBQW1CLEVBQUUsS0FBd0I7WUFDbkUsT0FBQSxLQUFLLENBQUMsV0FBVyxDQUFDLGlCQUFpQjtRQUFuQyxDQUFtQyxDQUFDO1FBQ3RDLDBCQUFxQixHQUFHLFVBQUMsS0FBbUIsRUFBRSxLQUF3QjtZQUNwRSxPQUFBLEtBQUssQ0FBQyxXQUFXLENB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QkFDUjthQUNGO1lBQ0gsQ0FBQyxDQUFDLFNBQVMsQ0FBQyxDQUNmO0tBQ0YsQ0FBQztBQUNKLENBQUM7QUE3Q0Qsb0VBNkNDIiwic291cmNlc0NvbnRlbnQiOlsiLypcbiAqIENvcHlyaWdodCAyMDIyIEZsb3dtYXBCbHVlXG4gKiBDb3B5cmlnaHQgMjAxOC0yMDIwIFRlcmFseXRpY3MsIG1vZGlmaWVkIGJ5IEZsb3dtYXBCbHVlXG4gKlxuICogTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlIFwiTGljZW5zZVwiKTtcbiAqIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS5cbiAqIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdFxuICpcbiAqIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMFxuICpcbiAqIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmVcbiAqIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuIFwiQVMgSVNcIiBCQVNJUyxcbiAqIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLlxuICogU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZFxuICogbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuXG4gKlxuICovXG5cbmltcG9ydCB7V2ViTWVyY2F0b3JWaWV3cG9ydH0gZnJvbSAnQG1hdGguZ2wvd2ViLW1lcmNhdG9yJztcbmltcG9ydCB7YXNjZW5kaW5nLCBkZXNjZW5kaW5nLCBleHRlbnQsIG1pbn0gZnJvbSAnZDMtYXJyYXknO1xuaW1wb3J0IHtuZXN0fSBmcm9tICdkMy1jb2xsZWN0aW9uJztcbmltcG9ydCB7U2NhbGVMaW5lYXIsIHNjYWxlTGluZWFyLCBzY2FsZVNxcnR9IGZyb20gJ2QzLXNjYWxlJztcbmltcG9ydCBLREJ1c2ggZnJvbSAna2RidXNoJztcbmltcG9ydCB7XG4gIGNyZWF0ZVNlbGVjdG9yLFxuICBjcmVhdGVTZWxlY3RvckNyZWF0b3IsXG4gIGRlZmF1bHRNZW1vaXplLFxuICBQYXJhbWV0cmljU2VsZWN0b3IsXG59IGZyb20gJ3Jlc2VsZWN0JztcbmltcG9ydCB7YWxlYX0gZnJvbSAnc2VlZHJhbmRvbSc7XG5pbXBvcnQge2NsdXN0ZXJMb2NhdGlvbnN9IGZyb20gJy4vY2x1c3Rlci9jbHVzdGVyJztcbmltcG9ydCB7XG4gIGJ1aWxkSW5kZXgsXG4gIENsdXN0ZXJJbmRleCxcbiAgZmluZEFwcHJvcHJpYXRlWm9vbUxldmVsLFxuICBtYWtlTG9jYXRpb25XZWlnaHRHZXR0ZXIsXG59IGZyb20gJy4vY2x1c3Rlci9DbHVzdGVySW5kZXgnO1xuaW1wb3J0IGdldENvbG9ycywge1xuICBDb2xvcnNSR0JBLFxuICBEaWZmQ29sb3JzUkdCQSxcbiAgZ2V0Q29sb3JzUkdCQSxcbiAgZ2V0RGlmZkNvbG9yc1JHQkEsXG4gIGdldEZsb3dDb2xvclNjYWxlLFxuICBpc0RpZmZDb2xvcnMsXG4gIGlzRGlmZkNvbG9yc1JHQkEsXG59IGZyb20gJy4vY29sb3JzJztcbmltcG9ydCBGbG93bWFwQWdncmVnYXRlQWNjZXNzb3JzIGZyb20gJy4vRmxvd21hcEFnZ3JlZ2F0ZUFjY2Vzc29ycyc7XG5pbXBvcnQge0Zsb3dtYXBTdGF0ZX0gZnJvbSAnLi9GbG93bWFwU3RhdGUnO1xuaW1wb3J0IHtcbiAgZ2V0VGltZUdyYW51bGFyaXR5QnlLZXksXG4gIGdldFRpbWVHcmFudWxhcml0eUJ5T3JkZXIsXG4gIGdldFRpbWVHcmFudWxhcml0eUZvckRhdGUsXG4gIFRpbWVHcmFudWxhcml0eUtleSxcbn0gZnJvbSAnLi90aW1lJztcbmltcG9ydCB7XG4gIEFnZ3JlZ2F0ZUZsb3csXG4gIENsdXN0ZXIsXG4gIENsdXN0ZXJOb2RlLFxuICBDb3VudEJ5VGltZSxcbiAgRmxvd0FjY2Vzc29ycyxcbiAgRmxvd0NpcmNsZXNMYXllckF0dHJpYnV0ZXMsXG4gIEZsb3dMaW5lc0xheWVyQXR0cmlidXRlcyxcbiAgRmxvd21hcERhdGEsXG4gIEZsb3dtYXBEYXRhQWNjZXNzb3JzLFxuICBpc0NsdXN0ZXIsXG4gIGlzTG9jYXRpb25DbHVzdGVyTm9kZSxcbiAgTGF5ZXJzRGF0YSxcbiAgTG9jYXRpb25GaWx0ZXJNb2RlLFxuICBMb2NhdGlvblRvdGFscyxcbn0gZnJvbSAnLi90eXBlcyc7XG5cbmNvbnN0IE1BWF9DTFVTVEVSX1pPT01fTEVWRUwgPSAyMDtcbnR5cGUgS0RCdXNoVHJlZSA9IGFueTtcblxuZXhwb3J0IHR5cGUgU2VsZWN0b3I8TCwgRiwgVD4gPSBQYXJhbWV0cmljU2VsZWN0b3I8XG4gIEZsb3dtYXBTdGF0ZSxcbiAgRmxvd21hcERhdGE8TCwgRj4sXG4gIFRcbj47XG5cbmV4cG9ydCBkZWZhdWx0IGNsYXNzIEZsb3dtYXBTZWxlY3RvcnM8TCwgRj4ge1xuICBhY2Nlc3NvcnM6IEZsb3dtYXBBZ2dyZWdhdGVBY2Nlc3NvcnM8TCwgRj47XG5cbiAgY29uc3RydWN0b3IoYWNjZXNzb3JzOiBGbG93bWFwRGF0YUFjY2Vzc29yczxMLCBGPikge1xuICAgIHRoaXMuYWNjZXNzb3JzID0gbmV3IEZsb3dtYXBBZ2dyZWdhdGVBY2Nlc3NvcnMoYWNjZXNzb3JzKTtcbiAgICB0aGlzLnNldEFjY2Vzc29ycyhhY2Nlc3NvcnMpO1xuICB9XG5cbiAgc2V0QWNjZXNzb3JzKGFjY2Vzc29yczogRmxvd21hcERhdGFBY2Nlc3NvcnM8TCwgRj4pIHtcbiAgICB0aGlzLmFjY2Vzc29ycyA9IG5ldyBGbG93bWFwQWdncmVnYXRlQWNjZXNzb3JzKGFjY2Vzc29ycyk7XG4gIH1cblxuICBnZXRGZXRjaGVkRmxvd3MgPSAoc3RhdGU6IEZsb3dtYXBTdGF0ZSwgcHJvcHM6IEZsb3dtYXBEYXRhPEwsIEY+KSA9PlxuICAgIHByb3BzLmZsb3dzO1xuICBnZXRGZXRjaGVkTG9jYXRpb25zID0gKHN0YXRlOiBGbG93bWFwU3RhdGUsIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPikgPT5cbiAgICBwcm9wcy5sb2NhdGlvbnM7XG4gIGdldE1heFRvcEZsb3dzRGlzcGxheU51bSA9IChzdGF0ZTogRmxvd21hcFN0YXRlLCBwcm9wczogRmxvd21hcERhdGE8TCwgRj4pID0+XG4gICAgc3RhdGUuc2V0dGluZ3NTdGF0ZS5tYXhUb3BGbG93c0Rpc3BsYXlOdW07XG4gIGdldFNlbGVjdGVkTG9jYXRpb25zID0gKHN0YXRlOiBGbG93bWFwU3RhdGUsIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPikgPT5cbiAgICBzdGF0ZS5maWx0ZXJTdGF0ZS5zZWxlY3RlZExvY2F0aW9ucztcbiAgZ2V0TG9jYXRpb25GaWx0ZXJNb2RlID0gKHN0YXRlOiBGbG93bWFwU3RhdGUsIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPikgPT5cbiAgICBzdGF0ZS5maWx0ZXJTdGF0ZS5sb2NhdGlvbkZpbHRlck1vZGU7XG4gIGdldENsdXN0ZXJpbmdFbmFibGVkID0gKHN0YXRlOiBGbG93bWFwU3RhdGUsIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPikgPT5cbiAgICBzdGF0ZS5zZXR0aW5nc1N0YXRlLmNsdXN0ZXJpbmdFbmFibGVkO1xuICBnZXRMb2NhdGlvblRvdGFsc0VuYWJsZWQgPSAoc3RhdGU6IEZsb3dtYXBTdGF0ZSwgcHJvcHM6IEZsb3dtYXBEYXRhPEwsIEY+KSA9PlxuICAgIHN0YXRlLnNldHRpbmdzU3RhdGUubG9jYXRpb25Ub3RhbHNFbmFibGVkO1xuICBnZXRab29tID0gKHN0YXRlOiBGbG93bWFwU3RhdGUsIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPikgPT5cbiAgICBzdGF0ZS52aWV3cG9ydC56b29tO1xuICBnZXRWaWV3cG9ydCA9IChzdGF0ZTogRmxvd21hcFN0YXRlLCBwcm9wczogRmxvd21hcERhdGE8TCwgRj4pID0+XG4gICAgc3RhdGUudmlld3BvcnQ7XG4gIGdldFNlbGVjdGVkVGltZVJhbmdlID0gKHN0YXRlOiBGbG93bWFwU3RhdGUsIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPikgPT5cbiAgICBzdGF0ZS5maWx0ZXJTdGF0ZS5zZWxlY3RlZFRpbWVSYW5nZTtcblxuICBnZXRDb2xvclNjaGVtZTogU2VsZWN0b3I8TCwgRiwgc3RyaW5nIHwgc3RyaW5nW10gfCB1bmRlZmluZWQ+ID0gKFxuICAgIHN0YXRlOiBGbG93bWFwU3RhdGUsXG4gICAgcHJvcHM6IEZsb3dtYXBEYXRhPEwsIEY+LFxuICApID0+IHN0YXRlLnNldHRpbmdzU3RhdGUuY29sb3JTY2hlbWU7XG5cbiAgZ2V0RGFya01vZGU6IFNlbGVjdG9yPEwsIEYsIGJvb2xlYW4+ID0gKFxuICAgIHN0YXRlOiBGbG93bWFwU3RhdGUsXG4gICAgcHJvcHM6IEZsb3dtYXBEYXRhPEwsIEY+LFxuICApID0+IHN0YXRlLnNldHRpbmdzU3RhdGUuZGFya01vZGU7XG5cbiAgZ2V0RmFkZUVuYWJsZWQ6IFNlbGVjdG9yPEwsIEYsIGJvb2xlYW4+ID0gKFxuICAgIHN0YXRlOiBGbG93bWFwU3RhdGUsXG4gICAgcHJvcHM6IEZsb3dtYXBEYXRhPEwsIEY+LFxuICApID0+IHN0YXRlLnNldHRpbmdzU3RhdGUuZmFkZUVuYWJsZWQ7XG5cbiAgZ2V0RmFkZU9wYWNpdHlFbmFibGVkOiBTZWxlY3RvcjxMLCBGLCBib29sZWFuPiA9IChcbiAgICBzdGF0ZTogRmxvd21hcFN0YXRlLFxuICAgIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPixcbiAgKSA9PiBzdGF0ZS5zZXR0aW5nc1N0YXRlLmZhZGVPcGFjaXR5RW5hYmxlZDtcblxuICBnZXRGYWRlQW1vdW50OiBTZWxlY3RvcjxMLCBGLCBudW1iZXI+ID0gKFxuICAgIHN0YXRlOiBGbG93bWFwU3RhdGUsXG4gICAgcHJvcHM6IEZsb3dtYXBEYXRhPEwsIEY+LFxuICApID0+IHN0YXRlLnNldHRpbmdzU3RhdGUuZmFkZUFtb3VudDtcblxuICBnZXRBbmltYXRlOiBTZWxlY3RvcjxMLCBGLCBib29sZWFuPiA9IChcbiAgICBzdGF0ZTogRmxvd21hcFN0YXRlLFxuICAgIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPixcbiAgKSA9PiBzdGF0ZS5zZXR0aW5nc1N0YXRlLmFuaW1hdGlvbkVuYWJsZWQ7XG5cbiAgZ2V0SW52YWxpZExvY2F0aW9uSWRzOiBTZWxlY3RvcjxMLCBGLCBzdHJpbmdbXSB8IHVuZGVmaW5lZD4gPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldEZldGNoZWRMb2NhdGlvbnMsXG4gICAgKGxvY2F0aW9ucykgPT4ge1xuICAgICAgaWYgKCFsb2NhdGlvbnMpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICBjb25zdCBpbnZhbGlkID0gW107XG4gICAgICBmb3IgKGNvbnN0IGxvY2F0aW9uIG9mIGxvY2F0aW9ucykge1xuICAgICAgICBjb25zdCBpZCA9IHRoaXMuYWNjZXNzb3JzLmdldExvY2F0aW9uSWQobG9jYXRpb24pO1xuICAgICAgICBjb25zdCBsb24gPSB0aGlzLmFjY2Vzc29ycy5nZXRMb2NhdGlvbkxvbihsb2NhdGlvbik7XG4gICAgICAgIGNvbnN0IGxhdCA9IHRoaXMuYWNjZXNzb3JzLmdldExvY2F0aW9uTGF0KGxvY2F0aW9uKTtcbiAgICAgICAgaWYgKCEoLTkwIDw9IGxhdCAmJiBsYXQgPD0gOTApIHx8ICEoLTE4MCA8PSBsb24gJiYgbG9uIDw9IDE4MCkpIHtcbiAgICAgICAgICBpbnZhbGlkLnB1c2goaWQpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgICByZXR1cm4gaW52YWxpZC5sZW5ndGggPiAwID8gaW52YWxpZCA6IHVuZGVmaW5lZDtcbiAgICB9LFxuICApO1xuXG4gIGdldExvY2F0aW9uczogU2VsZWN0b3I8TCwgRiwgTFtdIHwgdW5kZWZpbmVkPiA9IGNyZWF0ZVNlbGVjdG9yKFxuICAgIHRoaXMuZ2V0RmV0Y2hlZExvY2F0aW9ucyxcbiAgICB0aGlzLmdldEludmFsaWRMb2NhdGlvbklkcyxcbiAgICAobG9jYXRpb25zLCBpbnZhbGlkSWRzKSA9PiB7XG4gICAgICBpZiAoIWxvY2F0aW9ucykgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIGlmICghaW52YWxpZElkcyB8fCBpbnZhbGlkSWRzLmxlbmd0aCA9PT0gMCkgcmV0dXJuIGxvY2F0aW9ucztcbiAgICAgIGNvbnN0IGludmFsaWQgPSBuZXcgU2V0KGludmFsaWRJZHMpO1xuICAgICAgcmV0dXJuIGxvY2F0aW9ucy5maWx0ZXIoXG4gICAgICAgIChsb2NhdGlvbjogTCkgPT4gIWludmFsaWQuaGFzKHRoaXMuYWNjZXNzb3JzLmdldExvY2F0aW9uSWQobG9jYXRpb24pKSxcbiAgICAgICk7XG4gICAgfSxcbiAgKTtcblxuICBnZXRMb2NhdGlvbklkczogU2VsZWN0b3I8TCwgRiwgU2V0PHN0cmluZz4gfCB1bmRlZmluZWQ+ID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRMb2NhdGlvbnMsXG4gICAgKGxvY2F0aW9ucykgPT5cbiAgICAgIGxvY2F0aW9uc1xuICAgICAgICA/IG5ldyBTZXQobG9jYXRpb25zLm1hcCh0aGlzLmFjY2Vzc29ycy5nZXRMb2NhdGlvbklkKSlcbiAgICAgICAgOiB1bmRlZmluZWQsXG4gICk7XG5cbiAgZ2V0U2VsZWN0ZWRMb2NhdGlvbnNTZXQ6IFNlbGVjdG9yPEwsIEYsIFNldDxzdHJpbmc+IHwgdW5kZWZpbmVkPiA9XG4gICAgY3JlYXRlU2VsZWN0b3IodGhpcy5nZXRTZWxlY3RlZExvY2F0aW9ucywgKGlkcykgPT5cbiAgICAgIGlkcyAmJiBpZHMubGVuZ3RoID4gMCA/IG5ldyBTZXQoaWRzKSA6IHVuZGVmaW5lZCxcbiAgICApO1xuXG4gIGdldFNvcnRlZEZsb3dzRm9yS25vd25Mb2NhdGlvbnM6IFNlbGVjdG9yPEwsIEYsIEZbXSB8IHVuZGVmaW5lZD4gPVxuICAgIGNyZWF0ZVNlbGVjdG9yKHRoaXMuZ2V0RmV0Y2hlZEZsb3dzLCB0aGlzLmdldExvY2F0aW9uSWRzLCAoZmxvd3MsIGlkcykgPT4ge1xuICAgICAgaWYgKCFpZHMgfHwgIWZsb3dzKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgcmV0dXJuIGZsb3dzXG4gICAgICAgIC5maWx0ZXIoXG4gICAgICAgICAgKGZsb3c6IEYpID0+XG4gICAgICAgICAgICBpZHMuaGFzKHRoaXMuYWNjZXNzb3JzLmdldEZsb3dPcmlnaW5JZChmbG93KSkgJiZcbiAgICAgICAgICAgIGlkcy5oYXModGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd0Rlc3RJZChmbG93KSksXG4gICAgICAgIClcbiAgICAgICAgLnNvcnQoKGE6IEYsIGI6IEYpID0+XG4gICAgICAgICAgZGVzY2VuZGluZyhcbiAgICAgICAgICAgIE1hdGguYWJzKHRoaXMuYWNjZXNzb3JzLmdldEZsb3dNYWduaXR1ZGUoYSkpLFxuICAgICAgICAgICAgTWF0aC5hYnModGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd01hZ25pdHVkZShiKSksXG4gICAgICAgICAgKSxcbiAgICAgICAgKTtcbiAgICB9KTtcblxuICBnZXRBY3R1YWxUaW1lRXh0ZW50OiBTZWxlY3RvcjxMLCBGLCBbRGF0ZSwgRGF0ZV0gfCB1bmRlZmluZWQ+ID1cbiAgICBjcmVhdGVTZWxlY3Rvcih0aGlzLmdldFNvcnRlZEZsb3dzRm9yS25vd25Mb2NhdGlvbnMsIChmbG93cykgPT4ge1xuICAgICAgaWYgKCFmbG93cykgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIGxldCBzdGFydCA9IG51bGw7XG4gICAgICBsZXQgZW5kID0gbnVsbDtcbiAgICAgIGZvciAoY29uc3QgZmxvdyBvZiBmbG93cykge1xuICAgICAgICBjb25zdCB0aW1lID0gdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd1RpbWUoZmxvdyk7XG4gICAgICAgIGlmICh0aW1lKSB7XG4gICAgICAgICAgaWYgKHN0YXJ0ID09IG51bGwgfHwgc3RhcnQgPiB0aW1lKSBzdGFydCA9IHRpbWU7XG4gICAgICAgICAgaWYgKGVuZCA9PSBudWxsIHx8IGVuZCA8IHRpbWUpIGVuZCA9IHRpbWU7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICAgIGlmICghc3RhcnQgfHwgIWVuZCkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIHJldHVybiBbc3RhcnQsIGVuZF07XG4gICAgfSk7XG5cbiAgZ2V0VGltZUdyYW51bGFyaXR5S2V5OiBTZWxlY3RvcjxMLCBGLCBUaW1lR3JhbnVsYXJpdHlLZXkgfCB1bmRlZmluZWQ+ID1cbiAgICBjcmVhdGVTZWxlY3RvcihcbiAgICAgIHRoaXMuZ2V0U29ydGVkRmxvd3NGb3JLbm93bkxvY2F0aW9ucyxcbiAgICAgIHRoaXMuZ2V0QWN0dWFsVGltZUV4dGVudCxcbiAgICAgIChmbG93cywgdGltZUV4dGVudCkgPT4ge1xuICAgICAgICBpZiAoIWZsb3dzIHx8ICF0aW1lRXh0ZW50KSByZXR1cm4gdW5kZWZpbmVkO1xuXG4gICAgICAgIGNvbnN0IG1pbk9yZGVyID0gbWluKGZsb3dzLCAoZCkgPT4ge1xuICAgICAgICAgIGNvbnN0IHQgPSB0aGlzLmFjY2Vzc29ycy5nZXRGbG93VGltZShkKTtcbiAgICAgICAgICByZXR1cm4gdCA/IGdldFRpbWVHcmFudWxhcml0eUZvckRhdGUodCkub3JkZXIgOiBudWxsO1xuICAgICAgICB9KTtcbiAgICAgICAgaWYgKG1pbk9yZGVyID09IG51bGwpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICAgIGNvbnN0IHRpbWVHcmFudWxhcml0eSA9IGdldFRpbWVHcmFudWxhcml0eUJ5T3JkZXIobWluT3JkZXIpO1xuICAgICAgICByZXR1cm4gdGltZUdyYW51bGFyaXR5ID8gdGltZUdyYW51bGFyaXR5LmtleSA6IHVuZGVmaW5lZDtcbiAgICAgIH0sXG4gICAgKTtcblxuICBnZXRUaW1lRXh0ZW50OiBTZWxlY3RvcjxMLCBGLCBbRGF0ZSwgRGF0ZV0gfCB1bmRlZmluZWQ+ID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRBY3R1YWxUaW1lRXh0ZW50LFxuICAgIHRoaXMuZ2V0VGltZUdyYW51bGFyaXR5S2V5LFxuICAgICh0aW1lRXh0ZW50LCB0aW1lR3JhbnVsYXJpdHlLZXkpID0+IHtcbiAgICAgIGNvbnN0IHRpbWVHcmFudWxhcml0eSA9IHRpbWVHcmFudWxhcml0eUtleVxuICAgICAgICA/IGdldFRpbWVHcmFudWxhcml0eUJ5S2V5KHRpbWVHcmFudWxhcml0eUtleSlcbiAgICAgICAgOiB1bmRlZmluZWQ7XG4gICAgICBpZiAoIXRpbWVFeHRlbnQgfHwgIXRpbWVHcmFudWxhcml0eT8uaW50ZXJ2YWwpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICBjb25zdCB7aW50ZXJ2YWx9ID0gdGltZUdyYW51bGFyaXR5O1xuICAgICAgcmV0dXJuIFt0aW1lRXh0ZW50WzBdLCBpbnRlcnZhbC5vZmZzZXQoaW50ZXJ2YWwuZmxvb3IodGltZUV4dGVudFsxXSksIDEpXTtcbiAgICB9LFxuICApO1xuXG4gIGdldFNvcnRlZEZsb3dzRm9yS25vd25Mb2NhdGlvbnNGaWx0ZXJlZEJ5VGltZTogU2VsZWN0b3I8XG4gICAgTCxcbiAgICBGLFxuICAgIEZbXSB8IHVuZGVmaW5lZFxuICA+ID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRTb3J0ZWRGbG93c0Zvcktub3duTG9jYXRpb25zLFxuICAgIHRoaXMuZ2V0VGltZUV4dGVudCxcbiAgICB0aGlzLmdldFNlbGVjdGVkVGltZVJhbmdlLFxuICAgIChmbG93cywgdGltZUV4dGVudCwgdGltZVJhbmdlKSA9PiB7XG4gICAgICBpZiAoIWZsb3dzKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgaWYgKFxuICAgICAgICAhdGltZUV4dGVudCB8fFxuICAgICAgICAhdGltZVJhbmdlIHx8XG4gICAgICAgICh0aW1lRXh0ZW50WzBdID09PSB0aW1lUmFuZ2VbMF0gJiYgdGltZUV4dGVudFsxXSA9PT0gdGltZVJhbmdlWzFdKVxuICAgICAgKSB7XG4gICAgICAgIHJldHVybiBmbG93cztcbiAgICAgIH1cbiAgICAgIHJldHVybiBmbG93cy5maWx0ZXIoKGZsb3cpID0+IHtcbiAgICAgICAgY29uc3QgdGltZSA9IHRoaXMuYWNjZXNzb3JzLmdldEZsb3dUaW1lKGZsb3cpO1xuICAgICAgICByZXR1cm4gdGltZSAmJiB0aW1lUmFuZ2VbMF0gPD0gdGltZSAmJiB0aW1lIDwgdGltZVJhbmdlWzFdO1xuICAgICAgfSk7XG4gICAgfSxcbiAgKTtcblxuICBnZXRMb2NhdGlvbnNIYXZpbmdGbG93czogU2VsZWN0b3I8TCwgRiwgTFtdIHwgdW5kZWZpbmVkPiA9IGNyZWF0ZVNlbGVjdG9yKFxuICAgIHRoaXMuZ2V0U29ydGVkRmxvd3NGb3JLbm93bkxvY2F0aW9ucyxcbiAgICB0aGlzLmdldExvY2F0aW9ucyxcbiAgICAoZmxvd3MsIGxvY2F0aW9ucykgPT4ge1xuICAgICAgaWYgKCFsb2NhdGlvbnMgfHwgIWZsb3dzKSByZXR1cm4gbG9jYXRpb25zO1xuICAgICAgY29uc3Qgd2l0aEZsb3dzID0gbmV3IFNldCgpO1xuICAgICAgZm9yIChjb25zdCBmbG93IG9mIGZsb3dzKSB7XG4gICAgICAgIHdpdGhGbG93cy5hZGQodGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd09yaWdpbklkKGZsb3cpKTtcbiAgICAgICAgd2l0aEZsb3dzLmFkZCh0aGlzLmFjY2Vzc29ycy5nZXRGbG93RGVzdElkKGZsb3cpKTtcbiAgICAgIH1cbiAgICAgIHJldHVybiBsb2NhdGlvbnMuZmlsdGVyKChsb2NhdGlvbjogTCkgPT5cbiAgICAgICAgd2l0aEZsb3dzLmhhcyh0aGlzLmFjY2Vzc29ycy5nZXRMb2NhdGlvbklkKGxvY2F0aW9uKSksXG4gICAgICApO1xuICAgIH0sXG4gICk7XG5cbiAgZ2V0TG9jYXRpb25zQnlJZDogU2VsZWN0b3I8TCwgRiwgTWFwPHN0cmluZywgTD4gfCB1bmRlZmluZWQ+ID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRMb2NhdGlvbnNIYXZpbmdGbG93cyxcbiAgICAobG9jYXRpb25zKSA9PiB7XG4gICAgICBpZiAoIWxvY2F0aW9ucykgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIHJldHVybiBuZXN0PEwsIEw+KClcbiAgICAgICAgLmtleSgoZDogTCkgPT4gdGhpcy5hY2Nlc3NvcnMuZ2V0TG9jYXRpb25JZChkKSlcbiAgICAgICAgLnJvbGx1cCgoW2RdKSA9PiBkKVxuICAgICAgICAubWFwKGxvY2F0aW9ucykgYXMgYW55IGFzIE1hcDxzdHJpbmcsIEw+O1xuICAgIH0sXG4gICk7XG5cbiAgZ2V0Q2x1c3RlckluZGV4OiBTZWxlY3RvcjxMLCBGLCBDbHVzdGVySW5kZXg8Rj4gfCB1bmRlZmluZWQ+ID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRMb2NhdGlvbnNIYXZpbmdGbG93cyxcbiAgICB0aGlzLmdldExvY2F0aW9uc0J5SWQsXG4gICAgdGhpcy5nZXRTb3J0ZWRGbG93c0Zvcktub3duTG9jYXRpb25zLFxuICAgIChsb2NhdGlvbnMsIGxvY2F0aW9uc0J5SWQsIGZsb3dzKSA9PiB7XG4gICAgICBpZiAoIWxvY2F0aW9ucyB8fCAhbG9jYXRpb25zQnlJZCB8fCAhZmxvd3MpIHJldHVybiB1bmRlZmluZWQ7XG5cbiAgICAgIGNvbnN0IGdldExvY2F0aW9uV2VpZ2h0ID0gbWFrZUxvY2F0aW9uV2VpZ2h0R2V0dGVyKFxuICAgICAgICBmbG93cyxcbiAgICAgICAgdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd21hcERhdGFBY2Nlc3NvcnMoKSxcbiAgICAgICk7XG4gICAgICBjb25zdCBjbHVzdGVyTGV2ZWxzID0gY2x1c3RlckxvY2F0aW9ucyhcbiAgICAgICAgbG9jYXRpb25zLFxuICAgICAgICB0aGlzLmFjY2Vzc29ycy5nZXRGbG93bWFwRGF0YUFjY2Vzc29ycygpLFxuICAgICAgICBnZXRMb2NhdGlvbldlaWdodCxcbiAgICAgICAge1xuICAgICAgICAgIG1heFpvb206IE1BWF9DTFVTVEVSX1pPT01fTEVWRUwsXG4gICAgICAgIH0sXG4gICAgICApO1xuICAgICAgY29uc3QgY2x1c3RlckluZGV4ID0gYnVpbGRJbmRleDxGPihjbHVzdGVyTGV2ZWxzKTtcbiAgICAgIGNvbnN0IHtnZXRMb2NhdGlvbk5hbWUsIGdldExvY2F0aW9uQ2x1c3Rlck5hbWV9ID1cbiAgICAgICAgdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd21hcERhdGFBY2Nlc3NvcnMoKTtcblxuICAgICAgLy8gQWRkaW5nIG1lYW5pbmdmdWwgbmFtZXNcbiAgICAgIGNvbnN0IGdldE5hbWUgPSAoaWQ6IHN0cmluZykgPT4ge1xuICAgICAgICBjb25zdCBsb2MgPSBsb2NhdGlvbnNCeUlkLmdldChpZCk7XG4gICAgICAgIGlmIChsb2MpIHtcbiAgICAgICAgICByZXR1cm4gZ2V0TG9jYXRpb25OYW1lXG4gICAgICAgICAgICA/IGdldExvY2F0aW9uTmFtZShsb2MpXG4gICAgICAgICAgICA6IHRoaXMuYWNjZXNzb3JzLmdldExvY2F0aW9uSWQobG9jKSB8fCBpZDtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gYFwiJHtpZH1cImA7XG4gICAgICB9O1xuICAgICAgZm9yIChjb25zdCBsZXZlbCBvZiBjbHVzdGVyTGV2ZWxzKSB7XG4gICAgICAgIGZvciAoY29uc3Qgbm9kZSBvZiBsZXZlbC5ub2Rlcykge1xuICAgICAgICAgIC8vIEhlcmUgbXV0YXRpbmcgdGhlIG5vZGVzIChhZGRpbmcgbmFtZXMpXG4gICAgICAgICAgaWYgKGlzQ2x1c3Rlcihub2RlKSkge1xuICAgICAgICAgICAgY29uc3QgbGVhdmVzID0gY2x1c3RlckluZGV4LmV4cGFuZENsdXN0ZXIobm9kZSk7XG5cbiAgICAgICAgICAgIGxlYXZlcy5zb3J0KChhLCBiKSA9PlxuICAgICAgICAgICAgICBkZXNjZW5kaW5nKGdldExvY2F0aW9uV2VpZ2h0KGEpLCBnZXRMb2NhdGlvbldlaWdodChiKSksXG4gICAgICAgICAgICApO1xuXG4gICAgICAgICAgICBpZiAoZ2V0TG9jYXRpb25DbHVzdGVyTmFtZSkge1xuICAgICAgICAgICAgICBub2RlLm5hbWUgPSBnZXRMb2NhdGlvbkNsdXN0ZXJOYW1lKGxlYXZlcyk7XG4gICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICBjb25zdCB0b3BJZCA9IGxlYXZlc1swXTtcbiAgICAgICAgICAgICAgY29uc3Qgb3RoZXJJZCA9IGxlYXZlcy5sZW5ndGggPT09IDIgPyBsZWF2ZXNbMV0gOiB1bmRlZmluZWQ7XG4gICAgICAgICAgICAgIG5vZGUubmFtZSA9IGBcIiR7Z2V0TmFtZSh0b3BJZCl9XCIgYW5kICR7XG4gICAgICAgICAgICAgICAgb3RoZXJJZFxuICAgICAgICAgICAgICAgICAgPyBgXCIke2dldE5hbWUob3RoZXJJZCl9XCJgXG4gICAgICAgICAgICAgICAgICA6IGAke2xlYXZlcy5sZW5ndGggLSAxfSBvdGhlcnNgXG4gICAgICAgICAgICAgIH1gO1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAobm9kZSBhcyBhbnkpLm5hbWUgPSBnZXROYW1lKG5vZGUuaWQpO1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfVxuXG4gICAgICByZXR1cm4gY2x1c3RlckluZGV4O1xuICAgIH0sXG4gICk7XG5cbiAgZ2V0QXZhaWxhYmxlQ2x1c3Rlclpvb21MZXZlbHMgPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldENsdXN0ZXJJbmRleCxcbiAgICB0aGlzLmdldFNlbGVjdGVkTG9jYXRpb25zLFxuICAgIChjbHVzdGVySW5kZXgsIHNlbGVjdGVkTG9jYXRpb25zKTogbnVtYmVyW10gfCB1bmRlZmluZWQgPT4ge1xuICAgICAgaWYgKCFjbHVzdGVySW5kZXgpIHtcbiAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIH1cblxuICAgICAgbGV0IG1heFpvb20gPSBOdW1iZXIuUE9TSVRJVkVfSU5GSU5JVFk7XG4gICAgICBsZXQgbWluWm9vbSA9IE51bWJlci5ORUdBVElWRV9JTkZJTklUWTtcblxuICAgICAgY29uc3QgYWRqdXN0ID0gKHpvbmVJZDogc3RyaW5nKSA9PiB7XG4gICAgICAgIGNvbnN0IGNsdXN0ZXIgPSBjbHVzdGVySW5kZXguZ2V0Q2x1c3RlckJ5SWQoem9uZUlkKTtcbiAgICAgICAgaWYgKGNsdXN0ZXIpIHtcbiAgICAgICAgICBtaW5ab29tID0gTWF0aC5tYXgobWluWm9vbSwgY2x1c3Rlci56b29tKTtcbiAgICAgICAgICBtYXhab29tID0gTWF0aC5taW4obWF4Wm9vbSwgY2x1c3Rlci56b29tKTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICBjb25zdCB6b29tID0gY2x1c3RlckluZGV4LmdldE1pblpvb21Gb3JMb2NhdGlvbih6b25lSWQpO1xuICAgICAgICAgIG1pblpvb20gPSBNYXRoLm1heChtaW5ab29tLCB6b29tKTtcbiAgICAgICAgfVxuICAgICAgfTtcblxuICAgICAgaWYgKHNlbGVjdGVkTG9jYXRpb25zKSB7XG4gICAgICAgIGZvciAoY29uc3QgaWQgb2Ygc2VsZWN0ZWRMb2NhdGlvbnMpIHtcbiAgICAgICAgICBhZGp1c3QoaWQpO1xuICAgICAgICB9XG4gICAgICB9XG5cbiAgICAgIHJldHVybiBjbHVzdGVySW5kZXguYXZhaWxhYmxlWm9vbUxldmVscy5maWx0ZXIoXG4gICAgICAgIChsZXZlbCkgPT4gbWluWm9vbSA8PSBsZXZlbCAmJiBsZXZlbCA8PSBtYXhab29tLFxuICAgICAgKTtcbiAgICB9LFxuICApO1xuXG4gIF9nZXRDbHVzdGVyWm9vbTogU2VsZWN0b3I8TCwgRiwgbnVtYmVyIHwgdW5kZWZpbmVkPiA9IGNyZWF0ZVNlbGVjdG9yKFxuICAgIHRoaXMuZ2V0Q2x1c3RlckluZGV4LFxuICAgIHRoaXMuZ2V0Wm9vbSxcbiAgICB0aGlzLmdldEF2YWlsYWJsZUNsdXN0ZXJab29tTGV2ZWxzLFxuICAgIChjbHVzdGVySW5kZXgsIG1hcFpvb20sIGF2YWlsYWJsZUNsdXN0ZXJab29tTGV2ZWxzKSA9PiB7XG4gICAgICBpZiAoIWNsdXN0ZXJJbmRleCkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIGlmICghYXZhaWxhYmxlQ2x1c3Rlclpvb21MZXZlbHMpIHtcbiAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIH1cblxuICAgICAgY29uc3QgY2x1c3Rlclpvb20gPSBmaW5kQXBwcm9wcmlhdGVab29tTGV2ZWwoXG4gICAgICAgIGF2YWlsYWJsZUNsdXN0ZXJab29tTGV2ZWxzLFxuICAgICAgICBtYXBab29tLFxuICAgICAgKTtcbiAgICAgIHJldHVybiBjbHVzdGVyWm9vbTtcbiAgICB9LFxuICApO1xuXG4gIGdldENsdXN0ZXJab29tID0gKHN0YXRlOiBGbG93bWFwU3RhdGUsIHByb3BzOiBGbG93bWFwRGF0YTxMLCBGPikgPT4ge1xuICAgIGNvbnN0IHtzZXR0aW5nc1N0YXRlfSA9IHN0YXRlO1xuICAgIGlmICghc2V0dGluZ3NTdGF0ZS5jbHVzdGVyaW5nRW5hYmxlZCkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICBpZiAoc2V0dGluZ3NTdGF0ZS5jbHVzdGVyaW5nQXV0byB8fCBzZXR0aW5nc1N0YXRlLmNsdXN0ZXJpbmdMZXZlbCA9PSBudWxsKSB7XG4gICAgICByZXR1cm4gdGhpcy5fZ2V0Q2x1c3Rlclpvb20oc3RhdGUsIHByb3BzKTtcbiAgICB9XG4gICAgcmV0dXJuIHNldHRpbmdzU3RhdGUuY2x1c3RlcmluZ0xldmVsO1xuICB9O1xuXG4gIGdldExvY2F0aW9uc0ZvclNlYXJjaEJveDogU2VsZWN0b3I8TCwgRiwgKEwgfCBDbHVzdGVyKVtdIHwgdW5kZWZpbmVkPiA9XG4gICAgY3JlYXRlU2VsZWN0b3IoXG4gICAgICB0aGlzLmdldENsdXN0ZXJpbmdFbmFibGVkLFxuICAgICAgdGhpcy5nZXRMb2NhdGlvbnNIYXZpbmdGbG93cyxcbiAgICAgIHRoaXMuZ2V0U2VsZWN0ZWRMb2NhdGlvbnMsXG4gICAgICB0aGlzLmdldENsdXN0ZXJab29tLFxuICAgICAgdGhpcy5nZXRDbHVzdGVySW5kZXgsXG4gICAgICAoXG4gICAgICAgIGNsdXN0ZXJpbmdFbmFibGVkLFxuICAgICAgICBsb2NhdGlvbnMsXG4gICAgICAgIHNlbGVjdGVkTG9jYXRpb25zLFxuICAgICAgICBjbHVzdGVyWm9vbSxcbiAgICAgICAgY2x1c3RlckluZGV4LFxuICAgICAgKSA9PiB7XG4gICAgICAgIGlmICghbG9jYXRpb25zKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgICBsZXQgcmVzdWx0OiAoTCB8IENsdXN0ZXIpW10gPSBsb2NhdGlvbnM7XG4gICAgICAgIC8vIGlmIChjbHVzdGVyaW5nRW5hYmxlZCkge1xuICAgICAgICAvLyAgIGlmIChjbHVzdGVySW5kZXgpIHtcbiAgICAgICAgLy8gICAgIGNvbnN0IHpvb21JdGVtcyA9IGNsdXN0ZXJJbmRleC5nZXRDbHVzdGVyTm9kZXNGb3IoY2x1c3Rlclpvb20pO1xuICAgICAgICAvLyAgICAgaWYgKHpvb21JdGVtcykge1xuICAgICAgICAvLyAgICAgICByZXN1bHQgPSByZXN1bHQuY29uY2F0KHpvb21JdGVtcy5maWx0ZXIoaXNDbHVzdGVyKSk7XG4gICAgICAgIC8vICAgICB9XG4gICAgICAgIC8vICAgfVxuICAgICAgICAvLyB9XG5cbiAgICAgICAgaWYgKHJlc3VsdCAmJiBjbHVzdGVySW5kZXggJiYgc2VsZWN0ZWRMb2NhdGlvbnMpIHtcbiAgICAgICAgICBjb25zdCB0b0FwcGVuZCA9IFtdO1xuICAgICAgICAgIGZvciAoY29uc3QgaWQgb2Ygc2VsZWN0ZWRMb2NhdGlvbnMpIHtcbiAgICAgICAgICAgIGNvbnN0IGNsdXN0ZXIgPSBjbHVzdGVySW5kZXguZ2V0Q2x1c3RlckJ5SWQoaWQpO1xuICAgICAgICAgICAgaWYgKFxuICAgICAgICAgICAgICBjbHVzdGVyICYmXG4gICAgICAgICAgICAgICFyZXN1bHQuZmluZChcbiAgICAgICAgICAgICAgICAoZCkgPT5cbiAgICAgICAgICAgICAgICAgIChpc0xvY2F0aW9uQ2x1c3Rlck5vZGUoZClcbiAgICAgICAgICAgICAgICAgICAgPyBkLmlkXG4gICAgICAgICAgICAgICAgICAgIDogdGhpcy5hY2Nlc3NvcnMuZ2V0TG9jYXRpb25JZChkKSkgPT09IGlkLFxuICAgICAgICAgICAgICApXG4gICAgICAgICAgICApIHtcbiAgICAgICAgICAgICAgdG9BcHBlbmQucHVzaChjbHVzdGVyKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgICAgaWYgKHRvQXBwZW5kLmxlbmd0aCA+IDApIHtcbiAgICAgICAgICAgIHJlc3VsdCA9IHJlc3VsdC5jb25jYXQodG9BcHBlbmQpO1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcmVzdWx0O1xuICAgICAgfSxcbiAgICApO1xuXG4gIGdldERpZmZNb2RlOiBTZWxlY3RvcjxMLCBGLCBib29sZWFuPiA9IGNyZWF0ZVNlbGVjdG9yKFxuICAgIHRoaXMuZ2V0RmV0Y2hlZEZsb3dzLFxuICAgIChmbG93cykgPT4ge1xuICAgICAgaWYgKFxuICAgICAgICBmbG93cyAmJlxuICAgICAgICBmbG93cy5maW5kKChmOiBGKSA9PiB0aGlzLmFjY2Vzc29ycy5nZXRGbG93TWFnbml0dWRlKGYpIDwgMClcbiAgICAgICkge1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9LFxuICApO1xuXG4gIF9nZXRGbG93bWFwQ29sb3JzID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXREaWZmTW9kZSxcbiAgICB0aGlzLmdldENvbG9yU2NoZW1lLFxuICAgIHRoaXMuZ2V0RGFya01vZGUsXG4gICAgdGhpcy5nZXRGYWRlRW5hYmxlZCxcbiAgICB0aGlzLmdldEZhZGVPcGFjaXR5RW5hYmxlZCxcbiAgICB0aGlzLmdldEZhZGVBbW91bnQsXG4gICAgdGhpcy5nZXRBbmltYXRlLFxuICAgIGdldENvbG9ycyxcbiAgKTtcblxuICBnZXRGbG93bWFwQ29sb3JzUkdCQSA9IGNyZWF0ZVNlbGVjdG9yKFxuICAgIHRoaXMuX2dldEZsb3dtYXBDb2xvcnMsXG4gICAgKGZsb3dtYXBDb2xvcnMpID0+IHtcbiAgICAgIHJldHVybiBpc0RpZmZDb2xvcnMoZmxvd21hcENvbG9ycylcbiAgICAgICAgPyBnZXREaWZmQ29sb3JzUkdCQShmbG93bWFwQ29sb3JzKVxuICAgICAgICA6IGdldENvbG9yc1JHQkEoZmxvd21hcENvbG9ycyk7XG4gICAgfSxcbiAgKTtcblxuICBnZXRVbmtub3duTG9jYXRpb25zOiBTZWxlY3RvcjxMLCBGLCBTZXQ8c3RyaW5nPiB8IHVuZGVmaW5lZD4gPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldExvY2F0aW9uSWRzLFxuICAgIHRoaXMuZ2V0RmV0Y2hlZEZsb3dzLFxuICAgIHRoaXMuZ2V0U29ydGVkRmxvd3NGb3JLbm93bkxvY2F0aW9ucyxcbiAgICAoaWRzLCBmbG93cywgZmxvd3NGb3JLbm93bkxvY2F0aW9ucykgPT4ge1xuICAgICAgaWYgKCFpZHMgfHwgIWZsb3dzKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgaWYgKFxuICAgICAgICBmbG93c0Zvcktub3duTG9jYXRpb25zICYmXG4gICAgICAgIGZsb3dzLmxlbmd0aCA9PT0gZmxvd3NGb3JLbm93bkxvY2F0aW9ucy5sZW5ndGhcbiAgICAgIClcbiAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIGNvbnN0IG1pc3NpbmcgPSBuZXcgU2V0PHN0cmluZz4oKTtcbiAgICAgIGZvciAoY29uc3QgZmxvdyBvZiBmbG93cykge1xuICAgICAgICBpZiAoIWlkcy5oYXModGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd09yaWdpbklkKGZsb3cpKSlcbiAgICAgICAgICBtaXNzaW5nLmFkZCh0aGlzLmFjY2Vzc29ycy5nZXRGbG93T3JpZ2luSWQoZmxvdykpO1xuICAgICAgICBpZiAoIWlkcy5oYXModGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd0Rlc3RJZChmbG93KSkpXG4gICAgICAgICAgbWlzc2luZy5hZGQodGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd0Rlc3RJZChmbG93KSk7XG4gICAgICB9XG4gICAgICByZXR1cm4gbWlzc2luZztcbiAgICB9LFxuICApO1xuXG4gIGdldFNvcnRlZEFnZ3JlZ2F0ZWRGaWx0ZXJlZEZsb3dzOiBTZWxlY3RvcjxcbiAgICBMLFxuICAgIEYsXG4gICAgKEYgfCBBZ2dyZWdhdGVGbG93KVtdIHwgdW5kZWZpbmVkXG4gID4gPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldENsdXN0ZXJJbmRleCxcbiAgICB0aGlzLmdldENsdXN0ZXJpbmdFbmFibGVkLFxuICAgIHRoaXMuZ2V0U29ydGVkRmxvd3NGb3JLbm93bkxvY2F0aW9uc0ZpbHRlcmVkQnlUaW1lLFxuICAgIHRoaXMuZ2V0Q2x1c3Rlclpvb20sXG4gICAgdGhpcy5nZXRUaW1lRXh0ZW50LFxuICAgIChjbHVzdGVyVHJlZSwgaXNDbHVzdGVyaW5nRW5hYmxlZCwgZmxvd3MsIGNsdXN0ZXJab29tLCB0aW1lRXh0ZW50KSA9PiB7XG4gICAgICBpZiAoIWZsb3dzKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgbGV0IGFnZ3JlZ2F0ZWQ6IChGIHwgQWdncmVnYXRlRmxvdylbXTtcbiAgICAgIGlmIChpc0NsdXN0ZXJpbmdFbmFibGVkICYmIGNsdXN0ZXJUcmVlICYmIGNsdXN0ZXJab29tICE9IG51bGwpIHtcbiAgICAgICAgYWdncmVnYXRlZCA9IGNsdXN0ZXJUcmVlLmFnZ3JlZ2F0ZUZsb3dzKFxuICAgICAgICAgIC8vIFRPRE86IGFnZ3JlZ2F0ZSBhY3Jvc3MgdGltZVxuICAgICAgICAgIC8vIHRpbWVFeHRlbnQgIT0gbnVsbFxuICAgICAgICAgIC8vICAgPyBhZ2dyZWdhdGVGbG93cyhmbG93cykgLy8gY2x1c3RlclRyZWUuYWdncmVnYXRlRmxvd3Mgd29uJ3QgYWdncmVnYXRlIHVuY2x1c3RlcmVkIGFjcm9zcyB0aW1lXG4gICAgICAgICAgLy8gICA6IGZsb3dzLFxuICAgICAgICAgIGZsb3dzLFxuICAgICAgICAgIGNsdXN0ZXJab29tLFxuICAgICAgICAgIHRoaXMuYWNjZXNzb3JzLmdldEZsb3dtYXBEYXRhQWNjZXNzb3JzKCksXG4gICAgICAgICk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBhZ2dyZWdhdGVkID0gYWdncmVnYXRlRmxvd3MoXG4gICAgICAgICAgZmxvd3MsXG4gICAgICAgICAgdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd21hcERhdGFBY2Nlc3NvcnMoKSxcbiAgICAgICAgKTtcbiAgICAgIH1cbiAgICAgIGFnZ3JlZ2F0ZWQuc29ydCgoYSwgYikgPT5cbiAgICAgICAgZGVzY2VuZGluZyhcbiAgICAgICAgICBNYXRoLmFicyh0aGlzLmFjY2Vzc29ycy5nZXRGbG93TWFnbml0dWRlKGEpKSxcbiAgICAgICAgICBNYXRoLmFicyh0aGlzLmFjY2Vzc29ycy5nZXRGbG93TWFnbml0dWRlKGIpKSxcbiAgICAgICAgKSxcbiAgICAgICk7XG4gICAgICByZXR1cm4gYWdncmVnYXRlZDtcbiAgICB9LFxuICApO1xuXG4gIGdldEV4cGFuZGVkU2VsZWN0ZWRMb2NhdGlvbnNTZXQ6IFNlbGVjdG9yPEwsIEYsIFNldDxzdHJpbmc+IHwgdW5kZWZpbmVkPiA9XG4gICAgY3JlYXRlU2VsZWN0b3IoXG4gICAgICB0aGlzLmdldENsdXN0ZXJpbmdFbmFibGVkLFxuICAgICAgdGhpcy5nZXRTZWxlY3RlZExvY2F0aW9uc1NldCxcbiAgICAgIHRoaXMuZ2V0Q2x1c3RlckluZGV4LFxuICAgICAgKGNsdXN0ZXJpbmdFbmFibGVkLCBzZWxlY3RlZExvY2F0aW9ucywgY2x1c3RlckluZGV4KSA9PiB7XG4gICAgICAgIGlmICghc2VsZWN0ZWRMb2NhdGlvbnMgfHwgIWNsdXN0ZXJJbmRleCkge1xuICAgICAgICAgIHJldHVybiBzZWxlY3RlZExvY2F0aW9ucztcbiAgICAgICAgfVxuXG4gICAgICAgIGNvbnN0IHJlc3VsdCA9IG5ldyBTZXQ8c3RyaW5nPigpO1xuICAgICAgICBmb3IgKGNvbnN0IGxvY2F0aW9uSWQgb2Ygc2VsZWN0ZWRMb2NhdGlvbnMpIHtcbiAgICAgICAgICBjb25zdCBjbHVzdGVyID0gY2x1c3RlckluZGV4LmdldENsdXN0ZXJCeUlkKGxvY2F0aW9uSWQpO1xuICAgICAgICAgIGlmIChjbHVzdGVyKSB7XG4gICAgICAgICAgICBjb25zdCBleHBhbmRlZCA9IGNsdXN0ZXJJbmRleC5leHBhbmRDbHVzdGVyKGNsdXN0ZXIpO1xuICAgICAgICAgICAgZm9yIChjb25zdCBpZCBvZiBleHBhbmRlZCkge1xuICAgICAgICAgICAgICByZXN1bHQuYWRkKGlkKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgcmVzdWx0LmFkZChsb2NhdGlvbklkKTtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHJlc3VsdDtcbiAgICAgIH0sXG4gICAgKTtcblxuICBnZXRUb3RhbENvdW50c0J5VGltZTogU2VsZWN0b3I8TCwgRiwgQ291bnRCeVRpbWVbXSB8IHVuZGVmaW5lZD4gPVxuICAgIGNyZWF0ZVNlbGVjdG9yKFxuICAgICAgdGhpcy5nZXRTb3J0ZWRGbG93c0Zvcktub3duTG9jYXRpb25zLFxuICAgICAgdGhpcy5nZXRUaW1lR3JhbnVsYXJpdHlLZXksXG4gICAgICB0aGlzLmdldFRpbWVFeHRlbnQsXG4gICAgICB0aGlzLmdldEV4cGFuZGVkU2VsZWN0ZWRMb2NhdGlvbnNTZXQsXG4gICAgICB0aGlzLmdldExvY2F0aW9uRmlsdGVyTW9kZSxcbiAgICAgIChcbiAgICAgICAgZmxvd3MsXG4gICAgICAgIHRpbWVHcmFudWxhcml0eUtleSxcbiAgICAgICAgdGltZUV4dGVudCxcbiAgICAgICAgc2VsZWN0ZWRMb2NhdGlvblNldCxcbiAgICAgICAgbG9jYXRpb25GaWx0ZXJNb2RlLFxuICAgICAgKSA9PiB7XG4gICAgICAgIGNvbnN0IHRpbWVHcmFudWxhcml0eSA9IHRpbWVHcmFudWxhcml0eUtleVxuICAgICAgICAgID8gZ2V0VGltZUdyYW51bGFyaXR5QnlLZXkodGltZUdyYW51bGFyaXR5S2V5KVxuICAgICAgICAgIDogdW5kZWZpbmVkO1xuICAgICAgICBpZiAoIWZsb3dzIHx8ICF0aW1lR3JhbnVsYXJpdHkgfHwgIXRpbWVFeHRlbnQpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICAgIGNvbnN0IGJ5VGltZSA9IGZsb3dzLnJlZHVjZSgobSwgZmxvdykgPT4ge1xuICAgICAgICAgIGlmIChcbiAgICAgICAgICAgIHRoaXMuaXNGbG93SW5TZWxlY3Rpb24oXG4gICAgICAgICAgICAgIGZsb3csXG4gICAgICAgICAgICAgIHNlbGVjdGVkTG9jYXRpb25TZXQsXG4gICAgICAgICAgICAgIGxvY2F0aW9uRmlsdGVyTW9kZSxcbiAgICAgICAgICAgIClcbiAgICAgICAgICApIHtcbiAgICAgICAgICAgIGNvbnN0IGtleSA9IHRpbWVHcmFudWxhcml0eVxuICAgICAgICAgICAgICAuaW50ZXJ2YWwodGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd1RpbWUoZmxvdykpXG4gICAgICAgICAgICAgIC5nZXRUaW1lKCk7XG4gICAgICAgICAgICBtLnNldChcbiAgICAgICAgICAgICAga2V5LFxuICAgICAgICAgICAgICAobS5nZXQoa2V5KSA/PyAwKSArIHRoaXMuYWNjZXNzb3JzLmdldEZsb3dNYWduaXR1ZGUoZmxvdyksXG4gICAgICAgICAgICApO1xuICAgICAgICAgIH1cbiAgICAgICAgICByZXR1cm4gbTtcbiAgICAgICAgfSwgbmV3IE1hcDxudW1iZXIsIG51bWJlcj4oKSk7XG5cbiAgICAgICAgcmV0dXJuIEFycmF5LmZyb20oYnlUaW1lLmVudHJpZXMoKSkubWFwKChbbWlsbGlzLCBjb3VudF0pID0+ICh7XG4gICAgICAgICAgdGltZTogbmV3IERhdGUobWlsbGlzKSxcbiAgICAgICAgICBjb3VudCxcbiAgICAgICAgfSkpO1xuICAgICAgfSxcbiAgICApO1xuXG4gIGdldE1heExvY2F0aW9uQ2lyY2xlU2l6ZTogU2VsZWN0b3I8TCwgRiwgbnVtYmVyPiA9IGNyZWF0ZVNlbGVjdG9yKFxuICAgIHRoaXMuZ2V0TG9jYXRpb25Ub3RhbHNFbmFibGVkLFxuICAgIChsb2NhdGlvblRvdGFsc0VuYWJsZWQpID0+IChsb2NhdGlvblRvdGFsc0VuYWJsZWQgPyAxNyA6IDEpLFxuICApO1xuXG4gIGdldFZpZXdwb3J0Qm91bmRpbmdCb3g6IFNlbGVjdG9yPEwsIEYsIFtudW1iZXIsIG51bWJlciwgbnVtYmVyLCBudW1iZXJdPiA9XG4gICAgY3JlYXRlU2VsZWN0b3IoXG4gICAgICB0aGlzLmdldFZpZXdwb3J0LFxuICAgICAgdGhpcy5nZXRNYXhMb2NhdGlvbkNpcmNsZVNpemUsXG4gICAgICAodmlld3BvcnQsIG1heExvY2F0aW9uQ2lyY2xlU2l6ZSkgPT4ge1xuICAgICAgICBjb25zdCBwYWQgPSBtYXhMb2NhdGlvbkNpcmNsZVNpemU7XG4gICAgICAgIGNvbnN0IGJvdW5kcyA9IG5ldyBXZWJNZXJjYXRvclZpZXdwb3J0KHtcbiAgICAgICAgICAuLi52aWV3cG9ydCxcbiAgICAgICAgICB3aWR0aDogdmlld3BvcnQud2lkdGggKyBwYWQgKiAyLFxuICAgICAgICAgIGhlaWdodDogdmlld3BvcnQuaGVpZ2h0ICsgcGFkICogMixcbiAgICAgICAgfSkuZ2V0Qm91bmRzKCk7XG4gICAgICAgIHJldHVybiBbYm91bmRzWzBdWzBdLCBib3VuZHNbMF1bMV0sIGJvdW5kc1sxXVswXSwgYm91bmRzWzFdWzFdXTtcbiAgICAgIH0sXG4gICAgKTtcblxuICBnZXRMb2NhdGlvbnNGb3Jab29tOiBTZWxlY3RvcjxMLCBGLCBMW10gfCBDbHVzdGVyTm9kZVtdIHwgdW5kZWZpbmVkPiA9XG4gICAgY3JlYXRlU2VsZWN0b3IoXG4gICAgICB0aGlzLmdldENsdXN0ZXJpbmdFbmFibGVkLFxuICAgICAgdGhpcy5nZXRMb2NhdGlvbnNIYXZpbmdGbG93cyxcbiAgICAgIHRoaXMuZ2V0Q2x1c3RlckluZGV4LFxuICAgICAgdGhpcy5nZXRDbHVzdGVyWm9vbSxcbiAgICAgIChjbHVzdGVyaW5nRW5hYmxlZCwgbG9jYXRpb25zSGF2aW5nRmxvd3MsIGNsdXN0ZXJJbmRleCwgY2x1c3Rlclpvb20pID0+IHtcbiAgICAgICAgaWYgKGNsdXN0ZXJpbmdFbmFibGVkICYmIGNsdXN0ZXJJbmRleCkge1xuICAgICAgICAgIHJldHVybiBjbHVzdGVySW5kZXguZ2V0Q2x1c3Rlck5vZGVzRm9yKGNsdXN0ZXJab29tKTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICByZXR1cm4gbG9jYXRpb25zSGF2aW5nRmxvd3M7XG4gICAgICAgIH1cbiAgICAgIH0sXG4gICAgKTtcblxuICBnZXRMb2NhdGlvblRvdGFsczogU2VsZWN0b3I8TCwgRiwgTWFwPHN0cmluZywgTG9jYXRpb25Ub3RhbHM+IHwgdW5kZWZpbmVkPiA9XG4gICAgY3JlYXRlU2VsZWN0b3IoXG4gICAgICB0aGlzLmdldExvY2F0aW9uc0Zvclpvb20sXG4gICAgICB0aGlzLmdldFNvcnRlZEFnZ3JlZ2F0ZWRGaWx0ZXJlZEZsb3dzLFxuICAgICAgdGhpcy5nZXRTZWxlY3RlZExvY2F0aW9uc1NldCxcbiAgICAgIHRoaXMuZ2V0TG9jYXRpb25GaWx0ZXJNb2RlLFxuICAgICAgKGxvY2F0aW9ucywgZmxvd3MsIHNlbGVjdGVkTG9jYXRpb25zU2V0LCBsb2NhdGlvbkZpbHRlck1vZGUpID0+IHtcbiAgICAgICAgaWYgKCFmbG93cykgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgICAgY29uc3QgdG90YWxzID0gbmV3IE1hcDxzdHJpbmcsIExvY2F0aW9uVG90YWxzPigpO1xuICAgICAgICBjb25zdCBhZGQgPSAoXG4gICAgICAgICAgaWQ6IHN0cmluZyxcbiAgICAgICAgICBkOiBQYXJ0aWFsPExvY2F0aW9uVG90YWxzPixcbiAgICAgICAgKTogTG9jYXRpb25Ub3RhbHMgPT4ge1xuICAgICAgICAgIGNvbnN0IHJ2ID0gdG90YWxzLmdldChpZCkgPz8ge1xuICAgICAgICAgICAgaW5jb21pbmdDb3VudDogMCxcbiAgICAgICAgICAgIG91dGdvaW5nQ291bnQ6IDAsXG4gICAgICAgICAgICBpbnRlcm5hbENvdW50OiAwLFxuICAgICAgICAgIH07XG4gICAgICAgICAgaWYgKGQuaW5jb21pbmdDb3VudCAhPSBudWxsKSBydi5pbmNvbWluZ0NvdW50ICs9IGQuaW5jb21pbmdDb3VudDtcbiAgICAgICAgICBpZiAoZC5vdXRnb2luZ0NvdW50ICE9IG51bGwpIHJ2Lm91dGdvaW5nQ291bnQgKz0gZC5vdXRnb2luZ0NvdW50O1xuICAgICAgICAgIGlmIChkLmludGVybmFsQ291bnQgIT0gbnVsbCkgcnYuaW50ZXJuYWxDb3VudCArPSBkLmludGVybmFsQ291bnQ7XG4gICAgICAgICAgcmV0dXJuIHJ2O1xuICAgICAgICB9O1xuICAgICAgICBmb3IgKGNvbnN0IGYgb2YgZmxvd3MpIHtcbiAgICAgICAgICBpZiAoXG4gICAgICAgICAgICB0aGlzLmlzRmxvd0luU2VsZWN0aW9uKGYsIHNlbGVjdGVkTG9jYXRpb25zU2V0LCBsb2NhdGlvbkZpbHRlck1vZGUpXG4gICAgICAgICAgKSB7XG4gICAgICAgICAgICBjb25zdCBvcmlnaW5JZCA9IHRoaXMuYWNjZXNzb3JzLmdldEZsb3dPcmlnaW5JZChmKTtcbiAgICAgICAgICAgIGNvbnN0IGRlc3RJZCA9IHRoaXMuYWNjZXNzb3JzLmdldEZsb3dEZXN0SWQoZik7XG4gICAgICAgICAgICBjb25zdCBjb3VudCA9IHRoaXMuYWNjZXNzb3JzLmdldEZsb3dNYWduaXR1ZGUoZik7XG4gICAgICAgICAgICBpZiAob3JpZ2luSWQgPT09IGRlc3RJZCkge1xuICAgICAgICAgICAgICB0b3RhbHMuc2V0KG9yaWdpbklkLCBhZGQob3JpZ2luSWQsIHtpbnRlcm5hbENvdW50OiBjb3VudH0pKTtcbiAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgIHRvdGFscy5zZXQob3JpZ2luSWQsIGFkZChvcmlnaW5JZCwge291dGdvaW5nQ291bnQ6IGNvdW50fSkpO1xuICAgICAgICAgICAgICB0b3RhbHMuc2V0KGRlc3RJZCwgYWRkKGRlc3RJZCwge2luY29taW5nQ291bnQ6IGNvdW50fSkpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gdG90YWxzO1xuICAgICAgfSxcbiAgICApO1xuXG4gIGdldExvY2F0aW9uc1RyZWU6IFNlbGVjdG9yPEwsIEYsIEtEQnVzaFRyZWU+ID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRMb2NhdGlvbnNGb3Jab29tLFxuICAgIChsb2NhdGlvbnMpID0+IHtcbiAgICAgIGlmICghbG9jYXRpb25zKSB7XG4gICAgICAgIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICB9XG4gICAgICByZXR1cm4gbmV3IEtEQnVzaChcbiAgICAgICAgLy8gQHRzLWlnbm9yZVxuICAgICAgICBsb2NhdGlvbnMsXG4gICAgICAgIChsb2NhdGlvbjogTCB8IENsdXN0ZXJOb2RlKSA9PlxuICAgICAgICAgIGxuZ1godGhpcy5hY2Nlc3NvcnMuZ2V0TG9jYXRpb25Mb24obG9jYXRpb24pKSxcbiAgICAgICAgKGxvY2F0aW9uOiBMIHwgQ2x1c3Rlck5vZGUpID0+XG4gICAgICAgICAgbGF0WSh0aGlzLmFjY2Vzc29ycy5nZXRMb2NhdGlvbkxhdChsb2NhdGlvbikpLFxuICAgICAgKTtcbiAgICB9LFxuICApO1xuXG4gIF9nZXRMb2NhdGlvbklkc0luVmlld3BvcnQ6IFNlbGVjdG9yPEwsIEYsIFNldDxzdHJpbmc+IHwgdW5kZWZpbmVkPiA9XG4gICAgY3JlYXRlU2VsZWN0b3IoXG4gICAgICB0aGlzLmdldExvY2F0aW9uc1RyZWUsXG4gICAgICB0aGlzLmdldFZpZXdwb3J0Qm91bmRpbmdCb3gsXG4gICAgICAodHJlZTogS0RCdXNoVHJlZSwgYmJveDogW251bWJlciwgbnVtYmVyLCBudW1iZXIsIG51bWJlcl0pID0+IHtcbiAgICAgICAgY29uc3QgaWRzID0gdGhpcy5fZ2V0TG9jYXRpb25zSW5CYm94SW5kaWNlcyh0cmVlLCBiYm94KTtcbiAgICAgICAgaWYgKGlkcykge1xuICAgICAgICAgIHJldHVybiBuZXcgU2V0KFxuICAgICAgICAgICAgaWRzLm1hcCgoaWR4OiBudW1iZXIpID0+IHRyZWUucG9pbnRzW2lkeF0uaWQpIGFzIEFycmF5PHN0cmluZz4sXG4gICAgICAgICAgKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgfSxcbiAgICApO1xuXG4gIGdldExvY2F0aW9uSWRzSW5WaWV3cG9ydDogU2VsZWN0b3I8TCwgRiwgU2V0PHN0cmluZz4gfCB1bmRlZmluZWQ+ID1cbiAgICBjcmVhdGVTZWxlY3RvckNyZWF0b3IoXG4gICAgICBkZWZhdWx0TWVtb2l6ZSxcbiAgICAgIC8vIEB0cy1pZ25vcmVcbiAgICAgIChcbiAgICAgICAgczE6IFNldDxzdHJpbmc+IHwgdW5kZWZpbmVkLFxuICAgICAgICBzMjogU2V0PHN0cmluZz4gfCB1bmRlZmluZWQsXG4gICAgICAgIGluZGV4OiBudW1iZXIsXG4gICAgICApID0+IHtcbiAgICAgICAgaWYgKHMxID09PSBzMikgcmV0dXJuIHRydWU7XG4gICAgICAgIGlmIChzMSA9PSBudWxsIHx8IHMyID09IG51bGwpIHJldHVybiBmYWxzZTtcbiAgICAgICAgaWYgKHMxLnNpemUgIT09IHMyLnNpemUpIHJldHVybiBmYWxzZTtcbiAgICAgICAgZm9yIChjb25zdCBpdGVtIG9mIHMxKSBpZiAoIXMyLmhhcyhpdGVtKSkgcmV0dXJuIGZhbHNlO1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH0sXG4gICAgKShcbiAgICAgIHRoaXMuX2dldExvY2F0aW9uSWRzSW5WaWV3cG9ydCxcbiAgICAgIChsb2NhdGlvbklkczogU2V0PHN0cmluZz4gfCB1bmRlZmluZWQpID0+IHtcbiAgICAgICAgaWYgKCFsb2NhdGlvbklkcykgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgICAgcmV0dXJuIGxvY2F0aW9uSWRzO1xuICAgICAgfSxcbiAgICApO1xuXG4gIGdldFRvdGFsVW5maWx0ZXJlZENvdW50OiBTZWxlY3RvcjxMLCBGLCBudW1iZXIgfCB1bmRlZmluZWQ+ID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRTb3J0ZWRGbG93c0Zvcktub3duTG9jYXRpb25zLFxuICAgIChmbG93cykgPT4ge1xuICAgICAgaWYgKCFmbG93cykgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIHJldHVybiBmbG93cy5yZWR1Y2UoXG4gICAgICAgIChtLCBmbG93KSA9PiBtICsgdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd01hZ25pdHVkZShmbG93KSxcbiAgICAgICAgMCxcbiAgICAgICk7XG4gICAgfSxcbiAgKTtcblxuICBnZXRUb3RhbEZpbHRlcmVkQ291bnQ6IFNlbGVjdG9yPEwsIEYsIG51bWJlciB8IHVuZGVmaW5lZD4gPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldFNvcnRlZEFnZ3JlZ2F0ZWRGaWx0ZXJlZEZsb3dzLFxuICAgIHRoaXMuZ2V0U2VsZWN0ZWRMb2NhdGlvbnNTZXQsXG4gICAgdGhpcy5nZXRMb2NhdGlvbkZpbHRlck1vZGUsXG4gICAgKGZsb3dzLCBzZWxlY3RlZExvY2F0aW9uU2V0LCBsb2NhdGlvbkZpbHRlck1vZGUpID0+IHtcbiAgICAgIGlmICghZmxvd3MpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICBjb25zdCBjb3VudCA9IGZsb3dzLnJlZHVjZSgobSwgZmxvdykgPT4ge1xuICAgICAgICBpZiAoXG4gICAgICAgICAgdGhpcy5pc0Zsb3dJblNlbGVjdGlvbihmbG93LCBzZWxlY3RlZExvY2F0aW9uU2V0LCBsb2NhdGlvbkZpbHRlck1vZGUpXG4gICAgICAgICkge1xuICAgICAgICAgIHJldHVybiBtICsgdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd01hZ25pdHVkZShmbG93KTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gbTtcbiAgICAgIH0sIDApO1xuICAgICAgcmV0dXJuIGNvdW50O1xuICAgIH0sXG4gICk7XG5cbiAgX2dldExvY2F0aW9uVG90YWxzRXh0ZW50OiBTZWxlY3RvcjxMLCBGLCBbbnVtYmVyLCBudW1iZXJdIHwgdW5kZWZpbmVkPiA9XG4gICAgY3JlYXRlU2VsZWN0b3IodGhpcy5nZXRMb2NhdGlvblRvdGFscywgKGxvY2F0aW9uVG90YWxzKSA9PlxuICAgICAgY2FsY0xvY2F0aW9uVG90YWxzRXh0ZW50KGxvY2F0aW9uVG90YWxzLCB1bmRlZmluZWQpLFxuICAgICk7XG5cbiAgX2dldExvY2F0aW9uVG90YWxzRm9yVmlld3BvcnRFeHRlbnQ6IFNlbGVjdG9yPFxuICAgIEwsXG4gICAgRixcbiAgICBbbnVtYmVyLCBudW1iZXJdIHwgdW5kZWZpbmVkXG4gID4gPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldExvY2F0aW9uVG90YWxzLFxuICAgIHRoaXMuZ2V0TG9jYXRpb25JZHNJblZpZXdwb3J0LFxuICAgIChsb2NhdGlvblRvdGFscywgbG9jYXRpb25zSW5WaWV3cG9ydCkgPT5cbiAgICAgIGNhbGNMb2NhdGlvblRvdGFsc0V4dGVudChsb2NhdGlvblRvdGFscywgbG9jYXRpb25zSW5WaWV3cG9ydCksXG4gICk7XG5cbiAgZ2V0TG9jYXRpb25Ub3RhbHNFeHRlbnQgPSAoXG4gICAgc3RhdGU6IEZsb3dtYXBTdGF0ZSxcbiAgICBwcm9wczogRmxvd21hcERhdGE8TCwgRj4sXG4gICk6IFtudW1iZXIsIG51bWJlcl0gfCB1bmRlZmluZWQgPT4ge1xuICAgIGlmIChzdGF0ZS5zZXR0aW5nc1N0YXRlLmFkYXB0aXZlU2NhbGVzRW5hYmxlZCkge1xuICAgICAgcmV0dXJuIHRoaXMuX2dldExvY2F0aW9uVG90YWxzRm9yVmlld3BvcnRFeHRlbnQoc3RhdGUsIHByb3BzKTtcbiAgICB9IGVsc2Uge1xuICAgICAgcmV0dXJuIHRoaXMuX2dldExvY2F0aW9uVG90YWxzRXh0ZW50KHN0YXRlLCBwcm9wcyk7XG4gICAgfVxuICB9O1xuXG4gIGdldEZsb3dzRm9yRmxvd21hcExheWVyOiBTZWxlY3RvcjxMLCBGLCAoRiB8IEFnZ3JlZ2F0ZUZsb3cpW10gfCB1bmRlZmluZWQ+ID1cbiAgICBjcmVhdGVTZWxlY3RvcihcbiAgICAgIHRoaXMuZ2V0U29ydGVkQWdncmVnYXRlZEZpbHRlcmVkRmxvd3MsXG4gICAgICB0aGlzLmdldExvY2F0aW9uSWRzSW5WaWV3cG9ydCxcbiAgICAgIHRoaXMuZ2V0U2VsZWN0ZWRMb2NhdGlvbnNTZXQsXG4gICAgICB0aGlzLmdldExvY2F0aW9uRmlsdGVyTW9kZSxcbiAgICAgIHRoaXMuZ2V0TWF4VG9wRmxvd3NEaXNwbGF5TnVtLFxuICAgICAgKFxuICAgICAgICBmbG93cyxcbiAgICAgICAgbG9jYXRpb25JZHNJblZpZXdwb3J0LFxuICAgICAgICBzZWxlY3RlZExvY2F0aW9uc1NldCxcbiAgICAgICAgbG9jYXRpb25GaWx0ZXJNb2RlLFxuICAgICAgICBtYXhUb3BGbG93c0Rpc3BsYXlOdW0sXG4gICAgICApID0+IHtcbiAgICAgICAgaWYgKCFmbG93cyB8fCAhbG9jYXRpb25JZHNJblZpZXdwb3J0KSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgICBjb25zdCBwaWNrZWQ6IChGIHwgQWdncmVnYXRlRmxvdylbXSA9IFtdO1xuICAgICAgICBsZXQgcGlja2VkQ291bnQgPSAwO1xuICAgICAgICBmb3IgKGNvbnN0IGZsb3cgb2YgZmxvd3MpIHtcbiAgICAgICAgICBjb25zdCBvcmlnaW4gPSB0aGlzLmFjY2Vzc29ycy5nZXRGbG93T3JpZ2luSWQoZmxvdyk7XG4gICAgICAgICAgY29uc3QgZGVzdCA9IHRoaXMuYWNjZXNzb3JzLmdldEZsb3dEZXN0SWQoZmxvdyk7XG4gICAgICAgICAgaWYgKFxuICAgICAgICAgICAgbG9jYXRpb25JZHNJblZpZXdwb3J0LmhhcyhvcmlnaW4pIHx8XG4gICAgICAgICAgICBsb2NhdGlvbklkc0luVmlld3BvcnQuaGFzKGRlc3QpXG4gICAgICAgICAgKSB7XG4gICAgICAgICAgICBpZiAoXG4gICAgICAgICAgICAgIHRoaXMuaXNGbG93SW5TZWxlY3Rpb24oXG4gICAgICAgICAgICAgICAgZmxvdyxcbiAgICAgICAgICAgICAgICBzZWxlY3RlZExvY2F0aW9uc1NldCxcbiAgICAgICAgICAgICAgICBsb2NhdGlvbkZpbHRlck1vZGUsXG4gICAgICAgICAgICAgIClcbiAgICAgICAgICAgICkge1xuICAgICAgICAgICAgICBpZiAob3JpZ2luICE9PSBkZXN0KSB7XG4gICAgICAgICAgICAgICAgLy8gZXhjbHVkZSBzZWxmLWxvb3BzXG4gICAgICAgICAgICAgICAgcGlja2VkLnB1c2goZmxvdyk7XG4gICAgICAgICAgICAgICAgcGlja2VkQ291bnQrKztcbiAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cbiAgICAgICAgICAvLyBPbmx5IGtlZXAgdG9wXG4gICAgICAgICAgaWYgKHBpY2tlZENvdW50ID4gbWF4VG9wRmxvd3NEaXNwbGF5TnVtKSBicmVhaztcbiAgICAgICAgfVxuICAgICAgICAvLyBhc3N1bWluZyB0aGV5IGFyZSBzb3J0ZWQgaW4gZGVzY2VuZGluZyBvcmRlcixcbiAgICAgICAgLy8gd2UgbmVlZCBhc2NlbmRpbmcgZm9yIHJlbmRlcmluZ1xuICAgICAgICByZXR1cm4gcGlja2VkLnJldmVyc2UoKTtcbiAgICAgIH0sXG4gICAgKTtcblxuICBfZ2V0Rmxvd01hZ25pdHVkZUV4dGVudDogU2VsZWN0b3I8TCwgRiwgW251bWJlciwgbnVtYmVyXSB8IHVuZGVmaW5lZD4gPVxuICAgIGNyZWF0ZVNlbGVjdG9yKFxuICAgICAgdGhpcy5nZXRTb3J0ZWRBZ2dyZWdhdGVkRmlsdGVyZWRGbG93cyxcbiAgICAgIHRoaXMuZ2V0U2VsZWN0ZWRMb2NhdGlvbnNTZXQsXG4gICAgICB0aGlzLmdldExvY2F0aW9uRmlsdGVyTW9kZSxcbiAgICAgIChmbG93cywgc2VsZWN0ZWRMb2NhdGlvbnNTZXQsIGxvY2F0aW9uRmlsdGVyTW9kZSkgPT4ge1xuICAgICAgICBpZiAoIWZsb3dzKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgICBsZXQgcnY6IFtudW1iZXIsIG51bWJlcl0gfCB1bmRlZmluZWQgPSB1bmRlZmluZWQ7XG4gICAgICAgIGZvciAoY29uc3QgZiBvZiBmbG93cykge1xuICAgICAgICAgIGlmIChcbiAgICAgICAgICAgIHRoaXMuYWNjZXNzb3JzLmdldEZsb3dPcmlnaW5JZChmKSAhPT1cbiAgICAgICAgICAgICAgdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd0Rlc3RJZChmKSAmJlxuICAgICAgICAgICAgdGhpcy5pc0Zsb3dJblNlbGVjdGlvbihmLCBzZWxlY3RlZExvY2F0aW9uc1NldCwgbG9jYXRpb25GaWx0ZXJNb2RlKVxuICAgICAgICAgICkge1xuICAgICAgICAgICAgY29uc3QgY291bnQgPSB0aGlzLmFjY2Vzc29ycy5nZXRGbG93TWFnbml0dWRlKGYpO1xuICAgICAgICAgICAgaWYgKHJ2ID09IG51bGwpIHtcbiAgICAgICAgICAgICAgcnYgPSBbY291bnQsIGNvdW50XTtcbiAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgIGlmIChjb3VudCA8IHJ2WzBdKSBydlswXSA9IGNvdW50O1xuICAgICAgICAgICAgICBpZiAoY291bnQgPiBydlsxXSkgcnZbMV0gPSBjb3VudDtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHJ2O1xuICAgICAgfSxcbiAgICApO1xuXG4gIF9nZXRBZGFwdGl2ZUZsb3dNYWduaXR1ZGVFeHRlbnQ6IFNlbGVjdG9yPFxuICAgIEwsXG4gICAgRixcbiAgICBbbnVtYmVyLCBudW1iZXJdIHwgdW5kZWZpbmVkXG4gID4gPSBjcmVhdGVTZWxlY3Rvcih0aGlzLmdldEZsb3dzRm9yRmxvd21hcExheWVyLCAoZmxvd3MpID0+IHtcbiAgICBpZiAoIWZsb3dzKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgIGNvbnN0IHJ2ID0gZXh0ZW50KGZsb3dzLCB0aGlzLmFjY2Vzc29ycy5nZXRGbG93TWFnbml0dWRlKTtcbiAgICByZXR1cm4gcnZbMF0gIT09IHVuZGVmaW5lZCAmJiBydlsxXSAhPT0gdW5kZWZpbmVkID8gcnYgOiB1bmRlZmluZWQ7XG4gIH0pO1xuXG4gIGdldEZsb3dNYWduaXR1ZGVFeHRlbnQgPSAoXG4gICAgc3RhdGU6IEZsb3dtYXBTdGF0ZSxcbiAgICBwcm9wczogRmxvd21hcERhdGE8TCwgRj4sXG4gICk6IFtudW1iZXIsIG51bWJlcl0gfCB1bmRlZmluZWQgPT4ge1xuICAgIGlmIChzdGF0ZS5zZXR0aW5nc1N0YXRlLmFkYXB0aXZlU2NhbGVzRW5hYmxlZCkge1xuICAgICAgcmV0dXJuIHRoaXMuX2dldEFkYXB0aXZlRmxvd01hZ25pdHVkZUV4dGVudChzdGF0ZSwgcHJvcHMpO1xuICAgIH0gZWxzZSB7XG4gICAgICByZXR1cm4gdGhpcy5fZ2V0Rmxvd01hZ25pdHVkZUV4dGVudChzdGF0ZSwgcHJvcHMpO1xuICAgIH1cbiAgfTtcblxuICBnZXRMb2NhdGlvbk1heEFic1RvdGFsR2V0dGVyID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRMb2NhdGlvblRvdGFscyxcbiAgICAobG9jYXRpb25Ub3RhbHMpID0+IHtcbiAgICAgIHJldHVybiAobG9jYXRpb25JZDogc3RyaW5nKSA9PiB7XG4gICAgICAgIGNvbnN0IHRvdGFsID0gbG9jYXRpb25Ub3RhbHM/LmdldChsb2NhdGlvbklkKTtcbiAgICAgICAgaWYgKCF0b3RhbCkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgICAgcmV0dXJuIE1hdGgubWF4KFxuICAgICAgICAgIE1hdGguYWJzKHRvdGFsLmluY29taW5nQ291bnQgKyB0b3RhbC5pbnRlcm5hbENvdW50KSxcbiAgICAgICAgICBNYXRoLmFicyh0b3RhbC5vdXRnb2luZ0NvdW50ICsgdG90YWwuaW50ZXJuYWxDb3VudCksXG4gICAgICAgICk7XG4gICAgICB9O1xuICAgIH0sXG4gICk7XG5cbiAgZ2V0Rmxvd1RoaWNrbmVzc1NjYWxlID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgdGhpcy5nZXRGbG93TWFnbml0dWRlRXh0ZW50LFxuICAgIChtYWduaXR1ZGVFeHRlbnQpID0+IHtcbiAgICAgIGlmICghbWFnbml0dWRlRXh0ZW50KSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgcmV0dXJuIHNjYWxlTGluZWFyKClcbiAgICAgICAgLnJhbmdlKFswLjAyNSwgMC41XSlcbiAgICAgICAgLmRvbWFpbihbXG4gICAgICAgICAgMCxcbiAgICAgICAgICAvLyBzaG91bGQgc3VwcG9ydCBkaWZmIG1vZGUgdG9vXG4gICAgICAgICAgTWF0aC5tYXguYXBwbHkoXG4gICAgICAgICAgICBudWxsLFxuICAgICAgICAgICAgbWFnbml0dWRlRXh0ZW50Lm1hcCgoeDogbnVtYmVyIHwgdW5kZWZpbmVkKSA9PiBNYXRoLmFicyh4IHx8IDApKSxcbiAgICAgICAgICApLFxuICAgICAgICBdKTtcbiAgICB9LFxuICApO1xuXG4gIGdldENpcmNsZVNpemVTY2FsZSA9IGNyZWF0ZVNlbGVjdG9yKFxuICAgIHRoaXMuZ2V0TWF4TG9jYXRpb25DaXJjbGVTaXplLFxuICAgIHRoaXMuZ2V0TG9jYXRpb25Ub3RhbHNFbmFibGVkLFxuICAgIHRoaXMuZ2V0TG9jYXRpb25Ub3RhbHNFeHRlbnQsXG4gICAgKG1heExvY2F0aW9uQ2lyY2xlU2l6ZSwgbG9jYXRpb25Ub3RhbHNFbmFibGVkLCBsb2NhdGlvblRvdGFsc0V4dGVudCkgPT4ge1xuICAgICAgaWYgKCFsb2NhdGlvblRvdGFsc0VuYWJsZWQpIHtcbiAgICAgICAgcmV0dXJuICgpID0+IG1heExvY2F0aW9uQ2lyY2xlU2l6ZTtcbiAgICAgIH1cbiAgICAgIGlmICghbG9jYXRpb25Ub3RhbHNFeHRlbnQpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgICByZXR1cm4gc2NhbGVTcXJ0KClcbiAgICAgICAgLnJhbmdlKFswLCBtYXhMb2NhdGlvbkNpcmNsZVNpemVdKVxuICAgICAgICAuZG9tYWluKFtcbiAgICAgICAgICAwLFxuICAgICAgICAgIC8vIHNob3VsZCBzdXBwb3J0IGRpZmYgbW9kZSB0b29cbiAgICAgICAgICBNYXRoLm1heC5hcHBseShcbiAgICAgICAgICAgIG51bGwsXG4gICAgICAgICAgICBsb2NhdGlvblRvdGFsc0V4dGVudC5tYXAoKHg6IG51bWJlciB8IHVuZGVmaW5lZCkgPT5cbiAgICAgICAgICAgICAgTWF0aC5hYnMoeCB8fCAwKSxcbiAgICAgICAgICAgICksXG4gICAgICAgICAgKSxcbiAgICAgICAgXSk7XG4gICAgfSxcbiAgKTtcblxuICBnZXRJbkNpcmNsZVNpemVHZXR0ZXIgPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldENpcmNsZVNpemVTY2FsZSxcbiAgICB0aGlzLmdldExvY2F0aW9uVG90YWxzLFxuICAgIChjaXJjbGVTaXplU2NhbGUsIGxvY2F0aW9uVG90YWxzKSA9PiB7XG4gICAgICByZXR1cm4gKGxvY2F0aW9uSWQ6IHN0cmluZykgPT4ge1xuICAgICAgICBjb25zdCB0b3RhbCA9IGxvY2F0aW9uVG90YWxzPy5nZXQobG9jYXRpb25JZCk7XG4gICAgICAgIGlmICh0b3RhbCAmJiBjaXJjbGVTaXplU2NhbGUpIHtcbiAgICAgICAgICByZXR1cm4gKFxuICAgICAgICAgICAgY2lyY2xlU2l6ZVNjYWxlKFxuICAgICAgICAgICAgICBNYXRoLmFicyh0b3RhbC5pbmNvbWluZ0NvdW50ICsgdG90YWwuaW50ZXJuYWxDb3VudCksXG4gICAgICAgICAgICApIHx8IDBcbiAgICAgICAgICApO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiAwO1xuICAgICAgfTtcbiAgICB9LFxuICApO1xuXG4gIGdldE91dENpcmNsZVNpemVHZXR0ZXIgPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldENpcmNsZVNpemVTY2FsZSxcbiAgICB0aGlzLmdldExvY2F0aW9uVG90YWxzLFxuICAgIChjaXJjbGVTaXplU2NhbGUsIGxvY2F0aW9uVG90YWxzKSA9PiB7XG4gICAgICByZXR1cm4gKGxvY2F0aW9uSWQ6IHN0cmluZykgPT4ge1xuICAgICAgICBjb25zdCB0b3RhbCA9IGxvY2F0aW9uVG90YWxzPy5nZXQobG9jYXRpb25JZCk7XG4gICAgICAgIGlmICh0b3RhbCAmJiBjaXJjbGVTaXplU2NhbGUpIHtcbiAgICAgICAgICByZXR1cm4gKFxuICAgICAgICAgICAgY2lyY2xlU2l6ZVNjYWxlKFxuICAgICAgICAgICAgICBNYXRoLmFicyh0b3RhbC5vdXRnb2luZ0NvdW50ICsgdG90YWwuaW50ZXJuYWxDb3VudCksXG4gICAgICAgICAgICApIHx8IDBcbiAgICAgICAgICApO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiAwO1xuICAgICAgfTtcbiAgICB9LFxuICApO1xuXG4gIGdldFNvcnRlZExvY2F0aW9uc0Zvclpvb206IFNlbGVjdG9yPEwsIEYsIExbXSB8IENsdXN0ZXJOb2RlW10gfCB1bmRlZmluZWQ+ID1cbiAgICBjcmVhdGVTZWxlY3RvcihcbiAgICAgIHRoaXMuZ2V0TG9jYXRpb25zRm9yWm9vbSxcbiAgICAgIHRoaXMuZ2V0SW5DaXJjbGVTaXplR2V0dGVyLFxuICAgICAgdGhpcy5nZXRPdXRDaXJjbGVTaXplR2V0dGVyLFxuICAgICAgKGxvY2F0aW9ucywgZ2V0SW5DaXJjbGVTaXplLCBnZXRPdXRDaXJjbGVTaXplKSA9PiB7XG4gICAgICAgIGlmICghbG9jYXRpb25zKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgICAgICBjb25zdCBuZXh0TG9jYXRpb25zID0gWy4uLmxvY2F0aW9uc10gYXMgTFtdIHwgQ2x1c3Rlck5vZGVbXTtcbiAgICAgICAgcmV0dXJuIG5leHRMb2NhdGlvbnMuc29ydCgoYSwgYikgPT4ge1xuICAgICAgICAgIGNvbnN0IGlkQSA9IHRoaXMuYWNjZXNzb3JzLmdldExvY2F0aW9uSWQoYSk7XG4gICAgICAgICAgY29uc3QgaWRCID0gdGhpcy5hY2Nlc3NvcnMuZ2V0TG9jYXRpb25JZChiKTtcbiAgICAgICAgICByZXR1cm4gYXNjZW5kaW5nKFxuICAgICAgICAgICAgTWF0aC5tYXgoZ2V0SW5DaXJjbGVTaXplKGlkQSksIGdldE91dENpcmNsZVNpemUoaWRBKSksXG4gICAgICAgICAgICBNYXRoLm1heChnZXRJbkNpcmNsZVNpemUoaWRCKSwgZ2V0T3V0Q2lyY2xlU2l6ZShpZEIpKSxcbiAgICAgICAgICApO1xuICAgICAgICB9KTtcbiAgICAgIH0sXG4gICAgKTtcblxuICBnZXRMb2NhdGlvbnNGb3JGbG93bWFwTGF5ZXI6IFNlbGVjdG9yPFxuICAgIEwsXG4gICAgRixcbiAgICBBcnJheTxMIHwgQ2x1c3Rlck5vZGU+IHwgdW5kZWZpbmVkXG4gID4gPSBjcmVhdGVTZWxlY3RvcihcbiAgICB0aGlzLmdldFNvcnRlZExvY2F0aW9uc0Zvclpvb20sXG4gICAgLy8gdGhpcy5nZXRMb2NhdGlvbklkc0luVmlld3BvcnQsXG4gICAgKFxuICAgICAgbG9jYXRpb25zLFxuICAgICAgLy8gbG9jYXRpb25JZHNJblZpZXdwb3J0XG4gICAgKSA9PiB7XG4gICAgICAvLyBpZiAoIWxvY2F0aW9ucykgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICAgIC8vIGlmICghbG9jYXRpb25JZHNJblZpZXdwb3J0KSByZXR1cm4gbG9jYXRpb25zO1xuICAgICAgLy8gaWYgKGxvY2F0aW9uSWRzSW5WaWV3cG9ydC5zaXplID09PSBsb2NhdGlvbnMubGVuZ3RoKSByZXR1cm4gbG9jYXRpb25zO1xuICAgICAgLy8gY29uc3QgZmlsdGVyZWQgPSBbXTtcbiAgICAgIC8vIGZvciAoY29uc3QgbG9jIG9mIGxvY2F0aW9ucykge1xuICAgICAgLy8gICBpZiAobG9jYXRpb25JZHNJblZpZXdwb3J0Lmhhcyhsb2MuaWQpKSB7XG4gICAgICAvLyAgICAgZmlsdGVyZWQucHVzaChsb2MpO1xuICAgICAgLy8gICB9XG4gICAgICAvLyB9XG4gICAgICAvLyByZXR1cm4gZmlsdGVyZWQ7XG4gICAgICAvLyBAdHMtaWdub3JlXG4gICAgICAvLyByZXR1cm4gbG9jYXRpb25zLmZpbHRlcihcbiAgICAgIC8vICAgKGxvYzogTCB8IENsdXN0ZXJOb2RlKSA9PiBsb2NhdGlvbklkc0luVmlld3BvcnQhLmhhcyhsb2MuaWQpXG4gICAgICAvLyApO1xuICAgICAgLy8gVE9ETzogcmV0dXJuIGxvY2F0aW9uIGluIHZpZXdwb3J0ICsgXCJjb25uZWN0ZWRcIiBvbmVzXG4gICAgICByZXR1cm4gbG9jYXRpb25zO1xuICAgIH0sXG4gICk7XG5cbiAgZ2V0TG9jYXRpb25zRm9yRmxvd21hcExheWVyQnlJZDogU2VsZWN0b3I8XG4gICAgTCxcbiAgICBGLFxuICAgIE1hcDxzdHJpbmcsIEwgfCBDbHVzdGVyTm9kZT4gfCB1bmRlZmluZWRcbiAgPiA9IGNyZWF0ZVNlbGVjdG9yKHRoaXMuZ2V0TG9jYXRpb25zRm9yRmxvd21hcExheWVyLCAobG9jYXRpb25zKSA9PiB7XG4gICAgaWYgKCFsb2NhdGlvbnMpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgcmV0dXJuIGxvY2F0aW9ucy5yZWR1Y2UoXG4gICAgICAobSwgZCkgPT4gKG0uc2V0KHRoaXMuYWNjZXNzb3JzLmdldExvY2F0aW9uSWQoZCksIGQpLCBtKSxcbiAgICAgIG5ldyBNYXAoKSxcbiAgICApO1xuICB9KTtcblxuICBnZXRMYXllcnNEYXRhOiBTZWxlY3RvcjxMLCBGLCBMYXllcnNEYXRhPiA9IGNyZWF0ZVNlbGVjdG9yKFxuICAgIHRoaXMuZ2V0TG9jYXRpb25zRm9yRmxvd21hcExheWVyLFxuICAgIHRoaXMuZ2V0Rmxvd3NGb3JGbG93bWFwTGF5ZXIsXG4gICAgdGhpcy5nZXRGbG93bWFwQ29sb3JzUkdCQSxcbiAgICB0aGlzLmdldExvY2F0aW9uc0ZvckZsb3dtYXBMYXllckJ5SWQsXG4gICAgdGhpcy5nZXRMb2NhdGlvbklkc0luVmlld3BvcnQsXG4gICAgdGhpcy5nZXRJbkNpcmNsZVNpemVHZXR0ZXIsXG4gICAgdGhpcy5nZXRPdXRDaXJjbGVTaXplR2V0dGVyLFxuICAgIHRoaXMuZ2V0Rmxvd1RoaWNrbmVzc1NjYWxlLFxuICAgIHRoaXMuZ2V0QW5pbWF0ZSxcbiAgICAoXG4gICAgICBsb2NhdGlvbnMsXG4gICAgICBmbG93cyxcbiAgICAgIGZsb3dtYXBDb2xvcnMsXG4gICAgICBsb2NhdGlvbnNCeUlkLFxuICAgICAgbG9jYXRpb25JZHNJblZpZXdwb3J0LFxuICAgICAgZ2V0SW5DaXJjbGVTaXplLFxuICAgICAgZ2V0T3V0Q2lyY2xlU2l6ZSxcbiAgICAgIGZsb3dUaGlja25lc3NTY2FsZSxcbiAgICAgIGFuaW1hdGlvbkVuYWJsZWQsXG4gICAgKSA9PiB7XG4gICAgICByZXR1cm4gdGhpcy5fcHJlcGFyZUxheWVyc0RhdGEoXG4gICAgICAgIGxvY2F0aW9ucyxcbiAgICAgICAgZmxvd3MsXG4gICAgICAgIGZsb3dtYXBDb2xvcnMsXG4gICAgICAgIGxvY2F0aW9uc0J5SWQsXG4gICAgICAgIGxvY2F0aW9uSWRzSW5WaWV3cG9ydCxcbiAgICAgICAgZ2V0SW5DaXJjbGVTaXplLFxuICAgICAgICBnZXRPdXRDaXJjbGVTaXplLFxuICAgICAgICBmbG93VGhpY2tuZXNzU2NhbGUsXG4gICAgICAgIGFuaW1hdGlvbkVuYWJsZWQsXG4gICAgICApO1xuICAgIH0sXG4gICk7XG5cbiAgcHJlcGFyZUxheWVyc0RhdGEoc3RhdGU6IEZsb3dtYXBTdGF0ZSwgcHJvcHM6IEZsb3dtYXBEYXRhPEwsIEY+KTogTGF5ZXJzRGF0YSB7XG4gICAgY29uc3QgbG9jYXRpb25zID0gdGhpcy5nZXRMb2NhdGlvbnNGb3JGbG93bWFwTGF5ZXIoc3RhdGUsIHByb3BzKSB8fCBbXTtcbiAgICBjb25zdCBmbG93cyA9IHRoaXMuZ2V0Rmxvd3NGb3JGbG93bWFwTGF5ZXIoc3RhdGUsIHByb3BzKSB8fCBbXTtcbiAgICBjb25zdCBmbG93bWFwQ29sb3JzID0gdGhpcy5nZXRGbG93bWFwQ29sb3JzUkdCQShzdGF0ZSwgcHJvcHMpO1xuICAgIGNvbnN0IGxvY2F0aW9uc0J5SWQgPSB0aGlzLmdldExvY2F0aW9uc0ZvckZsb3dtYXBMYXllckJ5SWQoc3RhdGUsIHByb3BzKTtcbiAgICBjb25zdCBsb2NhdGlvbklkc0luVmlld3BvcnQgPSB0aGlzLmdldExvY2F0aW9uSWRzSW5WaWV3cG9ydChzdGF0ZSwgcHJvcHMpO1xuICAgIGNvbnN0IGdldEluQ2lyY2xlU2l6ZSA9IHRoaXMuZ2V0SW5DaXJjbGVTaXplR2V0dGVyKHN0YXRlLCBwcm9wcyk7XG4gICAgY29uc3QgZ2V0T3V0Q2lyY2xlU2l6ZSA9IHRoaXMuZ2V0T3V0Q2lyY2xlU2l6ZUdldHRlcihzdGF0ZSwgcHJvcHMpO1xuICAgIGNvbnN0IGZsb3dUaGlja25lc3NTY2FsZSA9IHRoaXMuZ2V0Rmxvd1RoaWNrbmVzc1NjYWxlKHN0YXRlLCBwcm9wcyk7XG4gICAgcmV0dXJuIHRoaXMuX3ByZXBhcmVMYXllcnNEYXRhKFxuICAgICAgbG9jYXRpb25zLFxuICAgICAgZmxvd3MsXG4gICAgICBmbG93bWFwQ29sb3JzLFxuICAgICAgbG9jYXRpb25zQnlJZCxcbiAgICAgIGxvY2F0aW9uSWRzSW5WaWV3cG9ydCxcbiAgICAgIGdldEluQ2lyY2xlU2l6ZSxcbiAgICAgIGdldE91dENpcmNsZVNpemUsXG4gICAgICBmbG93VGhpY2tuZXNzU2NhbGUsXG4gICAgICBzdGF0ZS5zZXR0aW5nc1N0YXRlLmFuaW1hdGlvbkVuYWJsZWQsXG4gICAgKTtcbiAgfVxuXG4gIF9wcmVwYXJlTGF5ZXJzRGF0YShcbiAgICBsb2NhdGlvbnM6IChMIHwgQ2x1c3Rlck5vZGUpW10gfCB1bmRlZmluZWQsXG4gICAgZmxvd3M6IChGIHwgQWdncmVnYXRlRmxvdylbXSB8IHVuZGVmaW5lZCxcbiAgICBmbG93bWFwQ29sb3JzOiBEaWZmQ29sb3JzUkdCQSB8IENvbG9yc1JHQkEsXG4gICAgbG9jYXRpb25zQnlJZDogTWFwPHN0cmluZywgTCB8IENsdXN0ZXJOb2RlPiB8IHVuZGVmaW5lZCxcbiAgICBsb2NhdGlvbklkc0luVmlld3BvcnQ6IFNldDxzdHJpbmc+IHwgdW5kZWZpbmVkLFxuICAgIGdldEluQ2lyY2xlU2l6ZTogKGxvY2F0aW9uSWQ6IHN0cmluZykgPT4gbnVtYmVyLFxuICAgIGdldE91dENpcmNsZVNpemU6IChsb2NhdGlvbklkOiBzdHJpbmcpID0+IG51bWJlcixcbiAgICBmbG93VGhpY2tuZXNzU2NhbGU6IFNjYWxlTGluZWFyPG51bWJlciwgbnVtYmVyLCBuZXZlcj4gfCB1bmRlZmluZWQsXG4gICAgYW5pbWF0aW9uRW5hYmxlZDogYm9vbGVhbixcbiAgKTogTGF5ZXJzRGF0YSB7XG4gICAgaWYgKCFsb2NhdGlvbnMpIGxvY2F0aW9ucyA9IFtdO1xuICAgIGlmICghZmxvd3MpIGZsb3dzID0gW107XG4gICAgY29uc3Qge1xuICAgICAgZ2V0Rmxvd09yaWdpbklkLFxuICAgICAgZ2V0Rmxvd0Rlc3RJZCxcbiAgICAgIGdldEZsb3dNYWduaXR1ZGUsXG4gICAgICBnZXRMb2NhdGlvbklkLFxuICAgICAgZ2V0TG9jYXRpb25Mb24sXG4gICAgICBnZXRMb2NhdGlvbkxhdCxcbiAgICB9ID0gdGhpcy5hY2Nlc3NvcnM7XG5cbiAgICBjb25zdCBmbG93TWFnbml0dWRlRXh0ZW50ID0gZXh0ZW50KGZsb3dzLCAoZikgPT4gZ2V0Rmxvd01hZ25pdHVkZShmKSkgYXMgW1xuICAgICAgbnVtYmVyLFxuICAgICAgbnVtYmVyLFxuICAgIF07XG4gICAgY29uc3QgZmxvd0NvbG9yU2NhbGUgPSBnZXRGbG93Q29sb3JTY2FsZShcbiAgICAgIGZsb3dtYXBDb2xvcnMsXG4gICAgICBmbG93TWFnbml0dWRlRXh0ZW50LFxuICAgICAgZmFsc2UsXG4gICAgKTtcblxuICAgIC8vIFVzaW5nIGEgZ2VuZXJhdG9yIGhlcmUgaGVscHMgdG8gYXZvaWQgY3JlYXRpbmcgaW50ZXJtZWRpYXJ5IGFycmF5c1xuICAgIGNvbnN0IGNpcmNsZVBvc2l0aW9ucyA9IEZsb2F0MzJBcnJheS5mcm9tKFxuICAgICAgKGZ1bmN0aW9uKiAoKSB7XG4gICAgICAgIGZvciAoY29uc3QgbG9jYXRpb24gb2YgbG9jYXRpb25zKSB7XG4gICAgICAgICAgeWllbGQgZ2V0TG9jYXRpb25Mb24obG9jYXRpb24pO1xuICAgICAgICAgIHlpZWxkIGdldExvY2F0aW9uTGF0KGxvY2F0aW9uKTtcbiAgICAgICAgfVxuICAgICAgfSkoKSxcbiAgICApO1xuXG4gICAgLy8gVE9ETzogZGlmZiBtb2RlXG4gICAgY29uc3QgY2lyY2xlQ29sb3IgPSBpc0RpZmZDb2xvcnNSR0JBKGZsb3dtYXBDb2xvcnMpXG4gICAgICA/IGZsb3dtYXBDb2xvcnMucG9zaXRpdmUubG9jYXRpb25DaXJjbGVzLmlubmVyXG4gICAgICA6IGZsb3dtYXBDb2xvcnMubG9jYXRpb25DaXJjbGVzLmlubmVyO1xuXG4gICAgY29uc3QgY2lyY2xlQ29sb3JzID0gVWludDhBcnJheS5mcm9tKFxuICAgICAgKGZ1bmN0aW9uKiAoKSB7XG4gICAgICAgIGZvciAoY29uc3QgbG9jYXRpb24gb2YgbG9jYXRpb25zKSB7XG4gICAgICAgICAgeWllbGQqIGNpcmNsZUNvbG9yO1xuICAgICAgICB9XG4gICAgICB9KSgpLFxuICAgICk7XG5cbiAgICBjb25zdCBpbkNpcmNsZVJhZGlpID0gRmxvYXQzMkFycmF5LmZyb20oXG4gICAgICAoZnVuY3Rpb24qICgpIHtcbiAgICAgICAgZm9yIChjb25zdCBsb2NhdGlvbiBvZiBsb2NhdGlvbnMpIHtcbiAgICAgICAgICBjb25zdCBpZCA9IGdldExvY2F0aW9uSWQobG9jYXRpb24pO1xuICAgICAgICAgIHlpZWxkIGxvY2F0aW9uSWRzSW5WaWV3cG9ydD8uaGFzKGlkKSA/IGdldEluQ2lyY2xlU2l6ZShpZCkgOiAxLjA7XG4gICAgICAgIH1cbiAgICAgIH0pKCksXG4gICAgKTtcbiAgICBjb25zdCBvdXRDaXJjbGVSYWRpaSA9IEZsb2F0MzJBcnJheS5mcm9tKFxuICAgICAgKGZ1bmN0aW9uKiAoKSB7XG4gICAgICAgIGZvciAoY29uc3QgbG9jYXRpb24gb2YgbG9jYXRpb25zKSB7XG4gICAgICAgICAgY29uc3QgaWQgPSBnZXRMb2NhdGlvbklkKGxvY2F0aW9uKTtcbiAgICAgICAgICB5aWVsZCBsb2NhdGlvbklkc0luVmlld3BvcnQ/LmhhcyhpZCkgPyBnZXRPdXRDaXJjbGVTaXplKGlkKSA6IDEuMDtcbiAgICAgICAgfVxuICAgICAgfSkoKSxcbiAgICApO1xuXG4gICAgY29uc3Qgc291cmNlUG9zaXRpb25zID0gRmxvYXQzMkFycmF5LmZyb20oXG4gICAgICAoZnVuY3Rpb24qICgpIHtcbiAgICAgICAgZm9yIChjb25zdCBmbG93IG9mIGZsb3dzKSB7XG4gICAgICAgICAgY29uc3QgbG9jID0gbG9jYXRpb25zQnlJZD8uZ2V0KGdldEZsb3dPcmlnaW5JZChmbG93KSk7XG4gICAgICAgICAgeWllbGQgbG9jID8gZ2V0TG9jYXRpb25Mb24obG9jKSA6IDA7XG4gICAgICAgICAgeWllbGQgbG9jID8gZ2V0TG9jYXRpb25MYXQobG9jKSA6IDA7XG4gICAgICAgIH1cbiAgICAgIH0pKCksXG4gICAgKTtcbiAgICBjb25zdCB0YXJnZXRQb3NpdGlvbnMgPSBGbG9hdDMyQXJyYXkuZnJvbShcbiAgICAgIChmdW5jdGlvbiogKCkge1xuICAgICAgICBmb3IgKGNvbnN0IGZsb3cgb2YgZmxvd3MpIHtcbiAgICAgICAgICBjb25zdCBsb2MgPSBsb2NhdGlvbnNCeUlkPy5nZXQoZ2V0Rmxvd0Rlc3RJZChmbG93KSk7XG4gICAgICAgICAgeWllbGQgbG9jID8gZ2V0TG9jYXRpb25Mb24obG9jKSA6IDA7XG4gICAgICAgICAgeWllbGQgbG9jID8gZ2V0TG9jYXRpb25MYXQobG9jKSA6IDA7XG4gICAgICAgIH1cbiAgICAgIH0pKCksXG4gICAgKTtcbiAgICBjb25zdCB0aGlja25lc3NlcyA9IEZsb2F0MzJBcnJheS5mcm9tKFxuICAgICAgKGZ1bmN0aW9uKiAoKSB7XG4gICAgICAgIGZvciAoY29uc3QgZmxvdyBvZiBmbG93cykge1xuICAgICAgICAgIHlpZWxkIGZsb3dUaGlja25lc3NTY2FsZVxuICAgICAgICAgICAgPyBmbG93VGhpY2tuZXNzU2NhbGUoZ2V0Rmxvd01hZ25pdHVkZShmbG93KSkgfHwgMFxuICAgICAgICAgICAgOiAwO1xuICAgICAgICB9XG4gICAgICB9KSgpLFxuICAgICk7XG4gICAgY29uc3QgZW5kcG9pbnRPZmZzZXRzID0gRmxvYXQzMkFycmF5LmZyb20oXG4gICAgICAoZnVuY3Rpb24qICgpIHtcbiAgICAgICAgZm9yIChjb25zdCBmbG93IG9mIGZsb3dzKSB7XG4gICAgICAgICAgY29uc3Qgb3JpZ2luSWQgPSBnZXRGbG93T3JpZ2luSWQoZmxvdyk7XG4gICAgICAgICAgY29uc3QgZGVzdElkID0gZ2V0Rmxvd0Rlc3RJZChmbG93KTtcbiAgICAgICAgICB5aWVsZCBNYXRoLm1heChnZXRJbkNpcmNsZVNpemUob3JpZ2luSWQpLCBnZXRPdXRDaXJjbGVTaXplKG9yaWdpbklkKSk7XG4gICAgICAgICAgeWllbGQgTWF0aC5tYXgoZ2V0SW5DaXJjbGVTaXplKGRlc3RJZCksIGdldE91dENpcmNsZVNpemUoZGVzdElkKSk7XG4gICAgICAgIH1cbiAgICAgIH0pKCksXG4gICAgKTtcbiAgICBjb25zdCBmbG93TGluZUNvbG9ycyA9IFVpbnQ4QXJyYXkuZnJvbShcbiAgICAgIChmdW5jdGlvbiogKCkge1xuICAgICAgICBmb3IgKGNvbnN0IGZsb3cgb2YgZmxvd3MpIHtcbiAgICAgICAgICB5aWVsZCogZmxvd0NvbG9yU2NhbGUoZ2V0Rmxvd01hZ25pdHVkZShmbG93KSk7XG4gICAgICAgIH1cbiAgICAgIH0pKCksXG4gICAgKTtcblxuICAgIGNvbnN0IHN0YWdnZXJpbmdWYWx1ZXMgPSBhbmltYXRpb25FbmFibGVkXG4gICAgICA/IEZsb2F0MzJBcnJheS5mcm9tKFxuICAgICAgICAgIChmdW5jdGlvbiogKCkge1xuICAgICAgICAgICAgZm9yIChjb25zdCBmIG9mIGZsb3dzKSB7XG4gICAgICAgICAgICAgIC8vIEB0cy1pZ25vcmVcbiAgICAgICAgICAgICAgeWllbGQgbmV3IGFsZWEoYCR7Z2V0Rmxvd09yaWdpbklkKGYpfS0ke2dldEZsb3dEZXN0SWQoZil9YCkoKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9KSgpLFxuICAgICAgICApXG4gICAgICA6IHVuZGVmaW5lZDtcblxuICAgIHJldHVybiB7XG4gICAgICBjaXJjbGVBdHRyaWJ1dGVzOiB7XG4gICAgICAgIGxlbmd0aDogbG9jYXRpb25zLmxlbmd0aCxcbiAgICAgICAgYXR0cmlidXRlczoge1xuICAgICAgICAgIGdldFBvc2l0aW9uOiB7dmFsdWU6IGNpcmNsZVBvc2l0aW9ucywgc2l6ZTogMn0sXG4gICAgICAgICAgZ2V0Q29sb3I6IHt2YWx1ZTogY2lyY2xlQ29sb3JzLCBzaXplOiA0fSxcbiAgICAgICAgICBnZXRJblJhZGl1czoge3ZhbHVlOiBpbkNpcmNsZVJhZGlpLCBzaXplOiAxfSxcbiAgICAgICAgICBnZXRPdXRSYWRpdXM6IHt2YWx1ZTogb3V0Q2lyY2xlUmFkaWksIHNpemU6IDF9LFxuICAgICAgICB9LFxuICAgICAgfSxcbiAgICAgIGxpbmVBdHRyaWJ1dGVzOiB7XG4gICAgICAgIGxlbmd0aDogZmxvd3MubGVuZ3RoLFxuICAgICAgICBhdHRyaWJ1dGVzOiB7XG4gICAgICAgICAgZ2V0U291cmNlUG9zaXRpb246IHt2YWx1ZTogc291cmNlUG9zaXRpb25zLCBzaXplOiAyfSxcbiAgICAgICAgICBnZXRUYXJnZXRQb3NpdGlvbjoge3ZhbHVlOiB0YXJnZXRQb3NpdGlvbnMsIHNpemU6IDJ9LFxuICAgICAgICAgIGdldFRoaWNrbmVzczoge3ZhbHVlOiB0aGlja25lc3Nlcywgc2l6ZTogMX0sXG4gICAgICAgICAgZ2V0Q29sb3I6IHt2YWx1ZTogZmxvd0xpbmVDb2xvcnMsIHNpemU6IDR9LFxuICAgICAgICAgIGdldEVuZHBvaW50T2Zmc2V0czoge3ZhbHVlOiBlbmRwb2ludE9mZnNldHMsIHNpemU6IDJ9LFxuICAgICAgICAgIC4uLihzdGFnZ2VyaW5nVmFsdWVzXG4gICAgICAgICAgICA/IHtnZXRTdGFnZ2VyaW5nOiB7dmFsdWU6IHN0YWdnZXJpbmdWYWx1ZXMsIHNpemU6IDF9fVxuICAgICAgICAgICAgOiB7fSksXG4gICAgICAgIH0sXG4gICAgICB9LFxuICAgIH07XG4gIH1cblxuICBnZXRMb2NhdGlvbnNJbkJib3goXG4gICAgdHJlZTogS0RCdXNoVHJlZSxcbiAgICBiYm94OiBbbnVtYmVyLCBudW1iZXIsIG51bWJlciwgbnVtYmVyXSxcbiAgKTogQXJyYXk8TD4gfCB1bmRlZmluZWQge1xuICAgIGlmICghdHJlZSkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICByZXR1cm4gdGhpcy5fZ2V0TG9jYXRpb25zSW5CYm94SW5kaWNlcyh0cmVlLCBiYm94KS5tYXAoXG4gICAgICAoaWR4OiBudW1iZXIpID0+IHRyZWUucG9pbnRzW2lkeF0sXG4gICAgKSBhcyBBcnJheTxMPjtcbiAgfVxuXG4gIF9nZXRMb2NhdGlvbnNJbkJib3hJbmRpY2VzKFxuICAgIHRyZWU6IEtEQnVzaFRyZWUsXG4gICAgYmJveDogW251bWJlciwgbnVtYmVyLCBudW1iZXIsIG51bWJlcl0sXG4gICkge1xuICAgIGlmICghdHJlZSkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICBjb25zdCBbbG9uMSwgbGF0MSwgbG9uMiwgbGF0Ml0gPSBiYm94O1xuICAgIGNvbnN0IFt4MSwgeTEsIHgyLCB5Ml0gPSBbbG5nWChsb24xKSwgbGF0WShsYXQxKSwgbG5nWChsb24yKSwgbGF0WShsYXQyKV07XG4gICAgcmV0dXJuIHRyZWUucmFuZ2UoXG4gICAgICBNYXRoLm1pbih4MSwgeDIpLFxuICAgICAgTWF0aC5taW4oeTEsIHkyKSxcbiAgICAgIE1hdGgubWF4KHgxLCB4MiksXG4gICAgICBNYXRoLm1heCh5MSwgeTIpLFxuICAgICk7XG4gIH1cblxuICBpc0Zsb3dJblNlbGVjdGlvbihcbiAgICBmbG93OiBGIHwgQWdncmVnYXRlRmxvdyxcbiAgICBzZWxlY3RlZExvY2F0aW9uc1NldDogU2V0PHN0cmluZz4gfCB1bmRlZmluZWQsXG4gICAgbG9jYXRpb25GaWx0ZXJNb2RlOiBMb2NhdGlvbkZpbHRlck1vZGUsXG4gICkge1xuICAgIGNvbnN0IG9yaWdpbiA9IHRoaXMuYWNjZXNzb3JzLmdldEZsb3dPcmlnaW5JZChmbG93KTtcbiAgICBjb25zdCBkZXN0ID0gdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd0Rlc3RJZChmbG93KTtcbiAgICBpZiAoc2VsZWN0ZWRMb2NhdGlvbnNTZXQpIHtcbiAgICAgIHN3aXRjaCAobG9jYXRpb25GaWx0ZXJNb2RlKSB7XG4gICAgICAgIGNhc2UgTG9jYXRpb25GaWx0ZXJNb2RlLkFMTDpcbiAgICAgICAgICByZXR1cm4gKFxuICAgICAgICAgICAgc2VsZWN0ZWRMb2NhdGlvbnNTZXQuaGFzKG9yaWdpbikgfHwgc2VsZWN0ZWRMb2NhdGlvbnNTZXQuaGFzKGRlc3QpXG4gICAgICAgICAgKTtcbiAgICAgICAgY2FzZSBMb2NhdGlvbkZpbHRlck1vZGUuQkVUV0VFTjpcbiAgICAgICAgICByZXR1cm4gKFxuICAgICAgICAgICAgc2VsZWN0ZWRMb2NhdGlvbnNTZXQuaGFzKG9yaWdpbikgJiYgc2VsZWN0ZWRMb2NhdGlvbnNTZXQuaGFzKGRlc3QpXG4gICAgICAgICAgKTtcbiAgICAgICAgY2FzZSBMb2NhdGlvbkZpbHRlck1vZGUuSU5DT01JTkc6XG4gICAgICAgICAgcmV0dXJuIHNlbGVjdGVkTG9jYXRpb25zU2V0LmhhcyhkZXN0KTtcbiAgICAgICAgY2FzZSBMb2NhdGlvbkZpbHRlck1vZGUuT1VUR09JTkc6XG4gICAgICAgICAgcmV0dXJuIHNlbGVjdGVkTG9jYXRpb25zU2V0LmhhcyhvcmlnaW4pO1xuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gdHJ1ZTtcbiAgfVxuXG4gIC8vIGNhbGNMb2NhdGlvblRvdGFscyhcbiAgLy8gICBsb2NhdGlvbnM6IChMIHwgQ2x1c3Rlck5vZGUpW10sXG4gIC8vICAgZmxvd3M6IEZbXSxcbiAgLy8gKTogTG9jYXRpb25zVG90YWxzIHtcbiAgLy8gICByZXR1cm4gZmxvd3MucmVkdWNlKFxuICAvLyAgICAgKGFjYzogTG9jYXRpb25zVG90YWxzLCBjdXJyKSA9PiB7XG4gIC8vICAgICAgIGNvbnN0IG9yaWdpbklkID0gdGhpcy5hY2Nlc3NvcnMuZ2V0Rmxvd09yaWdpbklkKGN1cnIpO1xuICAvLyAgICAgICBjb25zdCBkZXN0SWQgPSB0aGlzLmFjY2Vzc29ycy5nZXRGbG93RGVzdElkKGN1cnIpO1xuICAvLyAgICAgICBjb25zdCBtYWduaXR1ZGUgPSB0aGlzLmFjY2Vzc29ycy5nZXRGbG93TWFnbml0dWRlKGN1cnIpO1xuICAvLyAgICAgICBpZiAob3JpZ2luSWQgPT09IGRlc3RJZCkge1xuICAvLyAgICAgICAgIGFjYy5pbnRlcm5hbFtvcmlnaW5JZF0gPSAoYWNjLmludGVybmFsW29yaWdpbklkXSB8fCAwKSArIG1hZ25pdHVkZTtcbiAgLy8gICAgICAgfSBlbHNlIHtcbiAgLy8gICAgICAgICBhY2Mub3V0Z29pbmdbb3JpZ2luSWRdID0gKGFjYy5vdXRnb2luZ1tvcmlnaW5JZF0gfHwgMCkgKyBtYWduaXR1ZGU7XG4gIC8vICAgICAgICAgYWNjLmluY29taW5nW2Rlc3RJZF0gPSAoYWNjLmluY29taW5nW2Rlc3RJZF0gfHwgMCkgKyBtYWduaXR1ZGU7XG4gIC8vICAgICAgIH1cbiAgLy8gICAgICAgcmV0dXJuIGFjYztcbiAgLy8gICAgIH0sXG4gIC8vICAgICB7aW5jb21pbmc6IHt9LCBvdXRnb2luZzoge30sIGludGVybmFsOiB7fX0sXG4gIC8vICAgKTtcbiAgLy8gfVxufVxuXG5mdW5jdGlvbiBjYWxjTG9jYXRpb25Ub3RhbHNFeHRlbnQoXG4gIGxvY2F0aW9uVG90YWxzOiBNYXA8c3RyaW5nLCBMb2NhdGlvblRvdGFscz4gfCB1bmRlZmluZWQsXG4gIGxvY2F0aW9uSWRzSW5WaWV3cG9ydDogU2V0PHN0cmluZz4gfCB1bmRlZmluZWQsXG4pIHtcbiAgaWYgKCFsb2NhdGlvblRvdGFscykgcmV0dXJuIHVuZGVmaW5lZDtcbiAgbGV0IHJ2OiBbbnVtYmVyLCBudW1iZXJdIHwgdW5kZWZpbmVkID0gdW5kZWZpbmVkO1xuICBmb3IgKGNvbnN0IFtcbiAgICBpZCxcbiAgICB7aW5jb21pbmdDb3VudCwgb3V0Z29pbmdDb3VudCwgaW50ZXJuYWxDb3VudH0sXG4gIF0gb2YgbG9jYXRpb25Ub3RhbHMuZW50cmllcygpKSB7XG4gICAgaWYgKGxvY2F0aW9uSWRzSW5WaWV3cG9ydCA9PSBudWxsIHx8IGxvY2F0aW9uSWRzSW5WaWV3cG9ydC5oYXMoaWQpKSB7XG4gICAgICBjb25zdCBsbyA9IE1hdGgubWluKFxuICAgICAgICBpbmNvbWluZ0NvdW50ICsgaW50ZXJuYWxDb3VudCxcbiAgICAgICAgb3V0Z29pbmdDb3VudCArIGludGVybmFsQ291bnQsXG4gICAgICAgIGludGVybmFsQ291bnQsXG4gICAgICApO1xuICAgICAgY29uc3QgaGkgPSBNYXRoLm1heChcbiAgICAgICAgaW5jb21pbmdDb3VudCArIGludGVybmFsQ291bnQsXG4gICAgICAgIG91dGdvaW5nQ291bnQgKyBpbnRlcm5hbENvdW50LFxuICAgICAgICBpbnRlcm5hbENvdW50LFxuICAgICAgKTtcbiAgICAgIGlmICghcnYpIHtcbiAgICAgICAgcnYgPSBbbG8sIGhpXTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGlmIChsbyA8IHJ2WzBdKSBydlswXSA9IGxvO1xuICAgICAgICBpZiAoaGkgPiBydlsxXSkgcnZbMV0gPSBoaTtcbiAgICAgIH1cbiAgICB9XG4gIH1cbiAgcmV0dXJuIHJ2O1xufVxuXG4vLyBsb25naXR1ZGUvbGF0aXR1ZGUgdG8gc3BoZXJpY2FsIG1lcmNhdG9yIGluIFswLi4xXSByYW5nZVxuZnVuY3Rpb24gbG5nWChsbmc6IG51bWJlcikge1xuICByZXR1cm4gbG5nIC8gMzYwICsgMC41O1xufVxuXG5mdW5jdGlvbiBsYXRZKGxhdDogbnVtYmVyKSB7XG4gIGNvbnN0IHNpbiA9IE1hdGguc2luKChsYXQgKiBNYXRoLlBJKSAvIDE4MCk7XG4gIGNvbnN0IHkgPSAwLjUgLSAoMC4yNSAqIE1hdGgubG9nKCgxICsgc2luKSAvICgxIC0gc2luKSkpIC8gTWF0aC5QSTtcbiAgcmV0dXJuIHkgPCAwID8gMCA6IHkgPiAxID8gMSA6IHk7XG59XG5cbmZ1bmN0aW9uIGFnZ3JlZ2F0ZUZsb3dzPEY+KFxuICBmbG93czogRltdLFxuICBmbG93QWNjZXNzb3JzOiBGbG93QWNjZXNzb3JzPEY+LFxuKTogQWdncmVnYXRlRmxvd1tdIHtcbiAgLy8gU3VtIHVwIGZsb3dzIHdpdGggc2FtZSBvcmlnaW4sIGRlc3RcbiAgY29uc3QgYnlPcmlnaW5EZXN0ID0gbmVzdDxGLCBBZ2dyZWdhdGVGbG93PigpXG4gICAgLmtleShmbG93QWNjZXNzb3JzLmdldEZsb3dPcmlnaW5JZClcbiAgICAua2V5KGZsb3dBY2Nlc3NvcnMuZ2V0Rmxvd0Rlc3RJZClcbiAgICAucm9sbHVwKChmZjogRltdKSA9PiB7XG4gICAgICBjb25zdCBvcmlnaW4gPSBmbG93QWNjZXNzb3JzLmdldEZsb3dPcmlnaW5JZChmZlswXSk7XG4gICAgICBjb25zdCBkZXN0ID0gZmxvd0FjY2Vzc29ycy5nZXRGbG93RGVzdElkKGZmWzBdKTtcbiAgICAgIC8vIGNvbnN0IGNvbG9yID0gZmZbMF0uY29sb3I7XG4gICAgICBjb25zdCBydjogQWdncmVnYXRlRmxvdyA9IHtcbiAgICAgICAgYWdncmVnYXRlOiB0cnVlLFxuICAgICAgICBvcmlnaW4sXG4gICAgICAgIGRlc3QsXG4gICAgICAgIGNvdW50OiBmZi5yZWR1Y2UoKG0sIGYpID0+IHtcbiAgICAgICAgICBjb25zdCBjb3VudCA9IGZsb3dBY2Nlc3NvcnMuZ2V0Rmxvd01hZ25pdHVkZShmKTtcbiAgICAgICAgICBpZiAoY291bnQpIHtcbiAgICAgICAgICAgIGlmICghaXNOYU4oY291bnQpICYmIGlzRmluaXRlKGNvdW50KSkgcmV0dXJuIG0gKyBjb3VudDtcbiAgICAgICAgICB9XG4gICAgICAgICAgcmV0dXJuIG07XG4gICAgICAgIH0sIDApLFxuICAgICAgICAvLyB0aW1lOiB1bmRlZmluZWQsXG4gICAgICB9O1xuICAgICAgLy8gaWYgKGNvbG9yKSBydi5jb2xvciA9IGNvbG9yO1xuICAgICAgcmV0dXJuIHJ2O1xuICAgIH0pXG4gICAgLmVudHJpZXMoZmxvd3MpO1xuICBjb25zdCBydjogQWdncmVnYXRlRmxvd1tdID0gW107XG4gIGZvciAoY29uc3Qge3ZhbHVlc30gb2YgYnlPcmlnaW5EZXN0KSB7XG4gICAgZm9yIChjb25zdCB7dmFsdWV9IG9mIHZhbHVlcykge1xuICAgICAgcnYucHVzaCh2YWx1ZSk7XG4gICAgfVxuICB9XG4gIHJldHVybiBydjtcbn1cblxuLyoqXG4gKiBUaGlzIGlzIHVzZWQgdG8gYXVnbWVudCBob3ZlciBwaWNraW5nIGluZm8gc28gdGhhdCB3ZSBjYW4gZGlzcGxhY2UgbG9jYXRpb24gdG9vbHRpcFxuICogQHBhcmFtIGNpcmNsZUF0dHJpYnV0ZXNcbiAqIEBwYXJhbSBpbmRleFxuICovXG5leHBvcnQgZnVuY3Rpb24gZ2V0T3V0ZXJDaXJjbGVSYWRpdXNCeUluZGV4KFxuICBjaXJjbGVBdHRyaWJ1dGVzOiBGbG93Q2lyY2xlc0xheWVyQXR0cmlidXRlcyxcbiAgaW5kZXg6IG51bWJlcixcbik6IG51bWJlciB7XG4gIGNvbnN0IHtnZXRJblJhZGl1cywgZ2V0T3V0UmFkaXVzfSA9IGNpcmNsZUF0dHJpYnV0ZXMuYXR0cmlidXRlcztcbiAgcmV0dXJuIE1hdGgubWF4KGdldEluUmFkaXVzLnZhbHVlW2luZGV4XSwgZ2V0T3V0UmFkaXVzLnZhbHVlW2luZGV4XSk7XG59XG5cbmV4cG9ydCBmdW5jdGlvbiBnZXRMb2NhdGlvbkNvb3Jkc0J5SW5kZXgoXG4gIGNpcmNsZUF0dHJpYnV0ZXM6IEZsb3dDaXJjbGVzTGF5ZXJBdHRyaWJ1dGVzLFxuICBpbmRleDogbnVtYmVyLFxuKTogW251bWJlciwgbnVtYmVyXSB7XG4gIGNvbnN0IHtnZXRQb3NpdGlvbn0gPSBjaXJjbGVBdHRyaWJ1dGVzLmF0dHJpYnV0ZXM7XG4gIHJldHVybiBbZ2V0UG9zaXRpb24udmFsdWVbaW5kZXggKiAyXSwgZ2V0UG9zaXRpb24udmFsdWVbaW5kZXggKiAyICsgMV1dO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gZ2V0Rmxvd0xpbmVBdHRyaWJ1dGVzQnlJbmRleChcbiAgbGluZUF0dHJpYnV0ZXM6IEZsb3dMaW5lc0xheWVyQXR0cmlidXRlcyxcbiAgaW5kZXg6IG51bWJlcixcbik6IEZsb3dMaW5lc0xheWVyQXR0cmlidXRlcyB7XG4gIGNvbnN0IHtcbiAgICBnZXRDb2xvcixcbiAgICBnZXRFbmRwb2ludE9mZnNldHMsXG4gICAgZ2V0U291cmNlUG9zaXRpb24sXG4gICAgZ2V0VGFyZ2V0UG9zaXRpb24sXG4gICAgZ2V0VGhpY2tuZXNzLFxuICAgIGdldFN0YWdnZXJpbmcsXG4gIH0gPSBsaW5lQXR0cmlidXRlcy5hdHRyaWJ1dGVzO1xuICByZXR1cm4ge1xuICAgIGxlbmd0aDogMSxcbiAgICBhdHRyaWJ1dGVzOiB7XG4gICAgICBnZXRDb2xvcjoge1xuICAgICAgICB2YWx1ZTogZ2V0Q29sb3IudmFsdWUuc3ViYXJyYXkoaW5kZXggKiA0LCAoaW5kZXggKyAxKSAqIDQpLFxuICAgICAgICBzaXplOiA0LFxuICAgICAgfSxcbiAgICAgIGdldEVuZHBvaW50T2Zmc2V0czoge1xuICAgICAgICB2YWx1ZTogZ2V0RW5kcG9pbnRPZmZzZXRzLnZhbHVlLnN1YmFycmF5KGluZGV4ICogMiwgKGluZGV4ICsgMSkgKiAyKSxcbiAgICAgICAgc2l6ZTogMixcbiAgICAgIH0sXG4gICAgICBnZXRTb3VyY2VQb3NpdGlvbjoge1xuICAgICAgICB2YWx1ZTogZ2V0U291cmNlUG9zaXRpb24udmFsdWUuc3ViYXJyYXkoaW5kZXggKiAyLCAoaW5kZXggKyAxKSAqIDIpLFxuICAgICAgICBzaXplOiAyLFxuICAgICAgfSxcbiAgICAgIGdldFRhcmdldFBvc2l0aW9uOiB7XG4gICAgICAgIHZhbHVlOiBnZXRUYXJnZXRQb3NpdGlvbi52YWx1ZS5zdWJhcnJheShpbmRleCAqIDIsIChpbmRleCArIDEpICogMiksXG4gICAgICAgIHNpemU6IDIsXG4gICAgICB9LFxuICAgICAgZ2V0VGhpY2tuZXNzOiB7XG4gICAgICAgIHZhbHVlOiBnZXRUaGlja25lc3MudmFsdWUuc3ViYXJyYXkoaW5kZXgsIGluZGV4ICsgMSksXG4gICAgICAgIHNpemU6IDEsXG4gICAgICB9LFxuICAgICAgLi4uKGdldFN0YWdnZXJpbmdcbiAgICAgICAgPyB7XG4gICAgICAgICAgICBnZXRTdGFnZ2VyaW5nOiB7XG4gICAgICAgICAgICAgIHZhbHVlOiBnZXRTdGFnZ2VyaW5nLnZhbHVlLnN1YmFycmF5KGluZGV4LCBpbmRleCArIDEpLFxuICAgICAgICAgICAgICBzaXplOiAxLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICB9XG4gICAgICAgIDogdW5kZWZpbmVkKSxcbiAgICB9LFxuICB9O1xufVxuIl19