Subversion Repositories eFlore/Applications.cel

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
3205 delphine 1
(window["webpackJsonp"] = window["webpackJsonp"] || []).push([["main"],{
2
 
3
/***/ "./dist/tb-geoloc-lib/fesm5/tb-geoloc-lib.js":
4
/*!***************************************************!*\
5
  !*** ./dist/tb-geoloc-lib/fesm5/tb-geoloc-lib.js ***!
6
  \***************************************************/
7
/*! exports provided: TbGeolocLibModule, TbGeolocLibComponent, MapComponent, GeocodingService, ElevationService, ɵa */
8
/***/ (function(module, __webpack_exports__, __webpack_require__) {
9
 
10
"use strict";
11
__webpack_require__.r(__webpack_exports__);
12
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "TbGeolocLibModule", function() { return TbGeolocLibModule; });
13
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "TbGeolocLibComponent", function() { return TbGeolocLibComponent; });
14
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "MapComponent", function() { return MapComponent; });
15
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "GeocodingService", function() { return GeocodingService; });
16
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "ElevationService", function() { return ElevationService; });
17
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "ɵa", function() { return OsmPlaceReadableAddressPipe; });
18
/* harmony import */ var _angular_core__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @angular/core */ "./node_modules/@angular/core/fesm5/core.js");
19
/* harmony import */ var leaflet__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! leaflet */ "./node_modules/leaflet/dist/leaflet-src.js");
20
/* harmony import */ var leaflet__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(leaflet__WEBPACK_IMPORTED_MODULE_1__);
21
/* harmony import */ var _angular_common_http__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! @angular/common/http */ "./node_modules/@angular/common/fesm5/http.js");
22
/* harmony import */ var rxjs__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! rxjs */ "./node_modules/rxjs/_esm5/index.js");
23
/* harmony import */ var rxjs_operators__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! rxjs/operators */ "./node_modules/rxjs/_esm5/operators/index.js");
24
/* harmony import */ var _angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! @angular/compiler/src/util */ "./node_modules/@angular/compiler/src/util.js");
25
/* harmony import */ var _angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5___default = /*#__PURE__*/__webpack_require__.n(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__);
26
/* harmony import */ var _angular_forms__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! @angular/forms */ "./node_modules/@angular/forms/fesm5/forms.js");
27
/* harmony import */ var leaflet_draw__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! leaflet-draw */ "./node_modules/leaflet-draw/dist/leaflet.draw.js");
28
/* harmony import */ var leaflet_draw__WEBPACK_IMPORTED_MODULE_7___default = /*#__PURE__*/__webpack_require__.n(leaflet_draw__WEBPACK_IMPORTED_MODULE_7__);
29
/* harmony import */ var _angular_common__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! @angular/common */ "./node_modules/@angular/common/fesm5/common.js");
30
/* harmony import */ var _angular_platform_browser_animations__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! @angular/platform-browser/animations */ "./node_modules/@angular/platform-browser/fesm5/animations.js");
31
/* harmony import */ var _angular_platform_browser__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__(/*! @angular/platform-browser */ "./node_modules/@angular/platform-browser/fesm5/platform-browser.js");
32
/* harmony import */ var _angular_material__WEBPACK_IMPORTED_MODULE_11__ = __webpack_require__(/*! @angular/material */ "./node_modules/@angular/material/esm5/material.es5.js");
33
/* harmony import */ var _asymmetrik_ngx_leaflet__WEBPACK_IMPORTED_MODULE_12__ = __webpack_require__(/*! @asymmetrik/ngx-leaflet */ "./node_modules/@asymmetrik/ngx-leaflet/dist/index.js");
34
/* harmony import */ var _asymmetrik_ngx_leaflet_draw__WEBPACK_IMPORTED_MODULE_13__ = __webpack_require__(/*! @asymmetrik/ngx-leaflet-draw */ "./node_modules/@asymmetrik/ngx-leaflet-draw/dist/index.js");
35
 
36
 
37
 
38
 
39
 
40
 
41
 
42
 
43
 
44
 
45
 
46
 
47
 
48
 
49
 
50
/**
51
 * @fileoverview added by tsickle
52
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
53
 */
54
var TbGeolocLibComponent = /** @class */ (function () {
55
    function TbGeolocLibComponent() {
56
    }
57
    /**
58
     * @return {?}
59
     */
60
    TbGeolocLibComponent.prototype.ngOnInit = /**
61
     * @return {?}
62
     */
63
    function () {
64
    };
65
    TbGeolocLibComponent.decorators = [
66
        { type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Component"], args: [{
67
                    selector: 'tb-geoloc-tb-geoloc-lib',
68
                    template: "",
69
                    styles: []
70
                },] },
71
    ];
72
    /** @nocollapse */
73
    TbGeolocLibComponent.ctorParameters = function () { return []; };
74
    return TbGeolocLibComponent;
75
}());
76
 
77
/**
78
 * @fileoverview added by tsickle
79
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
80
 */
81
/**
82
 * GeoPoint
83
 *
84
 * https://github.com/perfectline/geopoint
85
 *
86
 * Authors :
87
 * Tanel Suurhans (http://twitter.com/tanelsuurhans)
88
 * Tarmo Lehtpuu (http://twitter.com/tarmolehtpuu)
89
 *
90
 * License :
91
 * Copyright 2011 by PerfectLine LLC (http://www.perfectline.ee) and is released under the MIT license.
92
 */
93
/** @type {?} */
94
var GeoPoint = function (lon, lat) {
95
    switch (typeof (lon)) {
96
        case 'number':
97
            this.lonDeg = this.dec2deg(lon, this.MAX_LON);
98
            this.lonDec = lon;
99
            break;
100
        case 'string':
101
            if (this.decode(lon)) {
102
                this.lonDeg = lon;
103
            }
104
            this.lonDec = this.deg2dec(lon, this.MAX_LON);
105
            break;
106
    }
107
    switch (typeof (lat)) {
108
        case 'number':
109
            this.latDeg = this.dec2deg(lat, this.MAX_LAT);
110
            this.latDec = lat;
111
            break;
112
        case 'string':
113
            if (this.decode(lat)) {
114
                this.latDeg = lat;
115
            }
116
            this.latDec = this.deg2dec(lat, this.MAX_LAT);
117
            break;
118
    }
119
};
120
GeoPoint.prototype = {
121
    CHAR_DEG: '\u00B0',
122
    CHAR_MIN: '\u0027',
123
    CHAR_SEC: '\u0022',
124
    CHAR_SEP: '\u0020',
125
    MAX_LON: 180,
126
    MAX_LAT: 90,
127
    // decimal
128
    lonDec: NaN,
129
    latDec: NaN,
130
    // degrees
131
    lonDeg: NaN,
132
    latDeg: NaN,
133
    dec2deg: function (value, max) {
134
        /** @type {?} */
135
        var sign = value < 0 ? -1 : 1;
136
        /** @type {?} */
137
        var abs = Math.abs(Math.round(value * 1000000));
138
        if (abs > (max * 1000000)) {
139
            return NaN;
140
        }
141
        /** @type {?} */
142
        var dec = abs % 1000000 / 1000000;
143
        /** @type {?} */
144
        var deg = Math.floor(abs / 1000000) * sign;
145
        /** @type {?} */
146
        var min = Math.floor(dec * 60);
147
        /** @type {?} */
148
        var sec = (dec - min / 60) * 3600;
149
        /** @type {?} */
150
        var result = '';
151
        result += deg;
152
        result += this.CHAR_DEG;
153
        result += this.CHAR_SEP;
154
        result += min;
155
        result += this.CHAR_MIN;
156
        result += this.CHAR_SEP;
157
        result += sec.toFixed(2);
158
        result += this.CHAR_SEC;
159
        return result;
160
    },
161
    deg2dec: function (value) {
162
        /** @type {?} */
163
        var matches = this.decode(value);
164
        if (!matches) {
165
            return NaN;
166
        }
167
        /** @type {?} */
168
        var deg = parseFloat(matches[1]);
169
        /** @type {?} */
170
        var min = parseFloat(matches[2]);
171
        /** @type {?} */
172
        var sec = parseFloat(matches[3]);
173
        if (isNaN(deg) || isNaN(min) || isNaN(sec)) {
174
            return NaN;
175
        }
176
        return deg + (min / 60.0) + (sec / 3600);
177
    },
178
    decode: function (value) {
179
        /** @type {?} */
180
        var pattern = '';
181
        // deg
182
        pattern += '(-?\\d+)';
183
        pattern += this.CHAR_DEG;
184
        pattern += '\\s*';
185
        // min
186
        pattern += '(\\d+)';
187
        pattern += this.CHAR_MIN;
188
        pattern += '\\s*';
189
        // sec
190
        pattern += '(\\d+(?:\\.\\d+)?)';
191
        pattern += this.CHAR_SEC;
192
        return value.match(new RegExp(pattern));
193
    },
194
    getLonDec: function () {
195
        return this.lonDec;
196
    },
197
    getLatDec: function () {
198
        return this.latDec;
199
    },
200
    getLonDeg: function () {
201
        return this.lonDeg;
202
    },
203
    getLatDeg: function () {
204
        return this.latDeg;
205
    }
206
};
207
 
208
/**
209
 * @fileoverview added by tsickle
210
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
211
 */
212
/** *
213
 *
214
 * \@param lat
215
 * \@param lng
216
 * \@param dragend callback
217
  @type {?} */
218
var draggableMarker = function (lat, lng, dragend) {
219
    /** @type {?} */
220
    var simpleIcon = simpleIconMarker();
221
    /** @type {?} */
222
    var marker$$1 = Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["marker"])([lat, lng], { icon: simpleIcon, draggable: true });
223
    marker$$1.on('dragend', function (event) { return dragend(event); });
224
    return marker$$1;
225
};
226
/** *
227
 *
228
  @type {?} */
229
var simpleIconMarker = function () {
230
    return Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["icon"])({
231
        iconUrl: './assets/img/map/marker-icon.png',
232
        shadowUrl: './assets/img/map/marker-shadow.png',
233
        iconAnchor: [13, 40]
234
    });
235
};
236
/** *
237
 *
238
  @type {?} */
239
var drawControlPanel = new leaflet__WEBPACK_IMPORTED_MODULE_1__["Control"].Draw({
240
    position: 'topleft',
241
    draw: {
242
        marker: { icon: simpleIconMarker() },
243
        polyline: {},
244
        polygon: { showArea: true, metric: false },
245
        rectangle: false,
246
        circle: false,
247
        circlemarker: false
248
    }
249
});
250
/**
251
 *
252
 * @param {?} editedLayer
253
 * @return {?}
254
 */
255
function drawControlEditPanel(editedLayer) {
256
    return new leaflet__WEBPACK_IMPORTED_MODULE_1__["Control"].Draw({
257
        position: 'topleft',
258
        draw: {
259
            marker: false,
260
            polyline: false,
261
            polygon: false,
262
            rectangle: false,
263
            circle: false,
264
            circlemarker: false
265
        },
266
        edit: {
267
            featureGroup: editedLayer,
268
            // this panel id editing editedLayer
269
            edit: {},
270
            remove: {}
271
        }
272
    });
273
}
274
/** *
275
 *
276
  @type {?} */
277
var circleMarkerStyle = {
278
    radius: 6,
279
    fillColor: '#ff7800',
280
    color: '#000',
281
    weight: 1,
282
    opacity: 1,
283
    fillOpacity: 0.8
284
};
285
/** *
286
 *
287
  @type {?} */
288
var cityStyle = {
289
    color: '#ff7800',
290
    weight: 5,
291
    opacity: 0.65
292
};
293
/** *
294
 *
295
  @type {?} */
296
var gpsPhotoMarkerIcon = function () {
297
    return Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["icon"])({
298
        iconUrl: './assets/img/map/photo-marker-icon.png',
299
        shadowUrl: './assets/img/map/marker-shadow.png',
300
        iconSize: [33, 41],
301
        // size of the icon
302
        // shadowSize:   [50, 64], // size of the shadow
303
        iconAnchor: [13, 40],
304
        // point of the icon which will correspond to marker's location
305
        // shadowAnchor: [4, 62],  // the same for the shadow
306
        popupAnchor: [5, -41] // point from which the popup should open relative to the iconAnchor
307
    });
308
};
309
 
310
/**
311
 * @fileoverview added by tsickle
312
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
313
 */
314
/**
315
 * Auto format a DMS coordinates
316
 * eg. user can enter 43 0 14.77
317
 * and the formatter returns 43° 0' 14.77"
318
 * + avoid enter non numeric (or . ,) characters
319
 * + force entire numbers for degrees and minutes
320
 * @param {?} dmsStr
321
 * @return {?}
322
 */
323
function dmsFormatter(dmsStr) {
324
    try {
325
        // replace multiples spaces
326
        dmsStr = dmsStr.replace(/\s\s+/g, ' ');
327
        // replace space at first position
328
        if (dmsStr.charAt(0) === ' ') {
329
            dmsStr = dmsStr.slice(1, dmsStr.length - 1);
330
        }
331
        // replace , by .
332
        dmsStr = dmsStr.replace(',', '.');
333
        // delete all non numeric characters
334
        dmsStr = dmsStr.replace(/[^0-9\-.,°\'"\s]/g, '');
335
        /** @type {?} */
336
        var nbSpaces = void 0;
337
        /** @type {?} */
338
        var degChr = '';
339
        /** @type {?} */
340
        var minChr = '';
341
        /** @type {?} */
342
        var secChr = '';
343
        /** @type {?} */
344
        var v = dmsStr.split(' ');
345
        // remove last space od input string
346
        if (dmsStr.charAt(dmsStr.length - 1) === ' ') {
347
            v = v.slice(0, v.length - 1);
348
        }
349
        // remove last item of v array if it's empty
350
        if (v[v.length - 1] === '') {
351
            v = v.slice(0, v.length - 1);
352
        }
353
        if (v.length === 1) {
354
            degChr = v[0];
355
            // degChr must be an entire number
356
            if (degChr.indexOf('.') !== -1) {
357
                degChr = degChr.slice(0, degChr.indexOf('.'));
358
            }
359
            // between -90 & +90
360
            if (Number(degChr) < -90) {
361
                degChr = '-90';
362
            }
363
            if (Number(degChr) > 90) {
364
                degChr = '90';
365
            }
366
        }
367
        if (v.length === 2) {
368
            degChr = v[0];
369
            minChr = v[1];
370
            if (degChr.indexOf('.') !== -1) {
371
                degChr = degChr.slice(0, degChr.indexOf('.'));
372
            }
373
            if (minChr.indexOf('.') !== -1) {
374
                minChr = minChr.slice(0, degChr.indexOf('.'));
375
            }
376
            if (Number(degChr) < -90) {
377
                degChr = '-90';
378
            }
379
            if (Number(degChr) > 90) {
380
                degChr = '90';
381
            }
382
            if (Number(minChr) < -90) {
383
                minChr = '-90';
384
            }
385
            if (Number(minChr) > 90) {
386
                minChr = '90';
387
            }
388
        }
389
        if (v.length === 3) {
390
            degChr = v[0];
391
            minChr = v[1];
392
            secChr = v[2];
393
            if (degChr.indexOf('.') !== -1) {
394
                degChr = degChr.slice(0, degChr.indexOf('.'));
395
            }
396
            if (minChr.indexOf('.') !== -1) {
397
                minChr = minChr.slice(0, degChr.indexOf('.'));
398
            }
399
            if (Number(degChr) < -90) {
400
                degChr = '-90';
401
            }
402
            if (Number(degChr) > 90) {
403
                degChr = '90';
404
            }
405
            if (Number(minChr) < -90) {
406
                minChr = '-90';
407
            }
408
            if (Number(minChr) > 90) {
409
                minChr = '90';
410
            }
411
        }
412
        if (v.length >= 4) {
413
            v = v.slice(0, 2);
414
            if (degChr.indexOf('.') !== -1) {
415
                degChr = degChr.slice(0, degChr.indexOf('.'));
416
            }
417
            if (minChr.indexOf('.') !== -1) {
418
                minChr = minChr.slice(0, degChr.indexOf('.'));
419
            }
420
            if (Number(degChr) < -90) {
421
                degChr = '-90';
422
            }
423
            if (Number(degChr) > 90) {
424
                degChr = '90';
425
            }
426
            if (Number(minChr) < -90) {
427
                minChr = '-90';
428
            }
429
            if (Number(minChr) > 90) {
430
                minChr = '90';
431
            }
432
        }
433
        try {
434
            nbSpaces = dmsStr.match(/\s/g).length;
435
        }
436
        catch (e) {
437
            nbSpaces = 0;
438
        }
439
        if (nbSpaces === 0 && v.length === 1) ;
440
        else if (nbSpaces === 1 && v.length >= 1) {
441
            degChr = degChr.replace(' ', '');
442
            if (degChr.slice(degChr.length - 1, degChr.length) !== '°') {
443
                degChr += '° ';
444
            }
445
            else {
446
                degChr += ' ';
447
            }
448
        }
449
        else if (nbSpaces === 2 && v.length >= 2) {
450
            degChr = degChr.replace(' ', '');
451
            minChr = minChr.replace(' ', '');
452
            if (degChr.slice(degChr.length - 1, degChr.length) !== '°') {
453
                degChr += '° ';
454
            }
455
            else {
456
                degChr += ' ';
457
            }
458
            if (minChr.slice(minChr.length - 1, minChr.length) !== '\'') {
459
                minChr += '\' ';
460
            }
461
            else {
462
                minChr += ' ';
463
            }
464
        }
465
        else if (nbSpaces === 3 && v.length >= 3) {
466
            degChr = degChr.replace(' ', '');
467
            minChr = minChr.replace(' ', '');
468
            secChr = secChr.replace(' ', '');
469
            if (degChr.slice(degChr.length - 1, degChr.length) !== '°') {
470
                degChr += '° ';
471
            }
472
            else {
473
                degChr += ' ';
474
            }
475
            if (minChr.slice(minChr.length - 1, minChr.length) !== '\'') {
476
                minChr += '\' ';
477
            }
478
            else {
479
                minChr += ' ';
480
            }
481
            if (secChr.slice(secChr.length - 1, secChr.length) !== '"') {
482
                secChr += '"';
483
            }
484
        }
485
        else {
486
            throw { error: 'Can\'t manage input string.' };
487
        }
488
        return degChr + minChr + secChr;
489
    }
490
    catch (e) {
491
        return dmsStr;
492
    }
493
}
494
 
495
/**
496
 * @fileoverview added by tsickle
497
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
498
 */
499
var GeocodingService = /** @class */ (function () {
500
    function GeocodingService(http) {
501
        this.http = http;
502
    }
503
    /**
504
     * @param {?} address
505
     * @return {?}
506
     */
507
    GeocodingService.prototype.geocode = /**
508
     * @param {?} address
509
     * @return {?}
510
     */
511
    function (address) {
512
        if (address === null) {
513
            return Object(rxjs__WEBPACK_IMPORTED_MODULE_3__["empty"])();
514
        }
515
        /** @type {?} */
516
        var url = "https://nominatim.openstreetmap.org/?format=json&addressdetails=1&q=" + address + "&format=json&limit=10&polygon_geojson=1";
517
        return this.http.get(url).pipe(Object(rxjs_operators__WEBPACK_IMPORTED_MODULE_4__["map"])(function (obj) { return obj; }));
518
    };
519
    /**
520
     * @param {?} lat
521
     * @param {?} lng
522
     * @return {?}
523
     */
524
    GeocodingService.prototype.reverse = /**
525
     * @param {?} lat
526
     * @param {?} lng
527
     * @return {?}
528
     */
529
    function (lat, lng) {
530
        /** @type {?} */
531
        var url = "https://nominatim.openstreetmap.org/reverse?format=json&lat=" + lat + "&lon=" + lng + "&polygon_geojson=1";
532
        return this.http.get(url).pipe(Object(rxjs_operators__WEBPACK_IMPORTED_MODULE_4__["map"])(function (obj) { return obj; }));
533
    };
534
    /**
535
     * @param {?} osmPlaceResult
536
     * @return {?}
537
     */
538
    GeocodingService.prototype.getReadbleAddress = /**
539
     * @param {?} osmPlaceResult
540
     * @return {?}
541
     */
542
    function (osmPlaceResult) {
543
        /** @type {?} */
544
        var locality = null;
545
        /** @type {?} */
546
        var subLocality = null;
547
        /** @type {?} */
548
        var road = null;
549
        /** @type {?} */
550
        var neighbourhood = null;
551
        // Get "city" information (I mean city or something similar like village)
552
        if (Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.city)) {
553
            locality = osmPlaceResult.address.city;
554
        }
555
        else if (Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.town)) {
556
            locality = osmPlaceResult.address.town;
557
        }
558
        else if (Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.village)) {
559
            locality = osmPlaceResult.address.village;
560
        }
561
        else if (Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.hamlet)) {
562
            locality = osmPlaceResult.address.hamlet;
563
        }
564
        // Get suburbr & if not defined : postcode
565
        if (Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.suburb) && Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.postcode) && locality !== null) {
566
            subLocality = osmPlaceResult.address.suburb + ', ' + osmPlaceResult.address.postcode;
567
        }
568
        else if (!Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.suburb) && Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.postcode) && locality !== null) {
569
            subLocality = osmPlaceResult.address.postcode;
570
        }
571
        // Get "road"
572
        if (Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.road)) {
573
            road = osmPlaceResult.address.road;
574
        }
575
        else if (Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.pedestrian)) {
576
            road = osmPlaceResult.address.pedestrian;
577
        }
578
        // Get neighbourhood
579
        if (Object(_angular_compiler_src_util__WEBPACK_IMPORTED_MODULE_5__["isDefined"])(osmPlaceResult.address.neighbourhood)) {
580
            neighbourhood = osmPlaceResult.address.neighbourhood;
581
        }
582
        // Return
583
        if (road && neighbourhood && subLocality && locality) {
584
            return road + ' (' + neighbourhood + ') ' + subLocality + ' ' + locality;
585
        }
586
        else if (road && !neighbourhood && subLocality && locality) {
587
            return road + ' ' + subLocality + ' ' + locality;
588
        }
589
        else if (!road && neighbourhood && subLocality && locality) {
590
            return neighbourhood + ' ' + subLocality + ' ' + locality;
591
        }
592
        else if (!road && !neighbourhood && subLocality && locality) {
593
            return subLocality + ' ' + locality;
594
        }
595
        else if (!road && !neighbourhood && !subLocality && locality) {
596
            return locality;
597
        }
598
        else {
599
            return osmPlaceResult.display_name;
600
        }
601
    };
602
    /**
603
     * @param {?} osmClassFilter
604
     * @param {?} osmResults
605
     * @return {?}
606
     */
607
    GeocodingService.prototype.osmClassFilter = /**
608
     * @param {?} osmClassFilter
609
     * @param {?} osmResults
610
     * @return {?}
611
     */
612
    function (osmClassFilter, osmResults) {
613
        /** @type {?} */
614
        var osmFilteredResults = [];
615
        if (osmClassFilter.length > 0 && osmResults.length > 0) {
616
            osmResults.forEach(function (osmItem) {
617
                /** @type {?} */
618
                var filterMatchOccurence = 0;
619
                /** @type {?} */
620
                var removeOccurence = false;
621
                osmClassFilter.forEach(function (osmFilterItem) {
622
                    /** @type {?} */
623
                    var _class = osmFilterItem.split(':')[0];
624
                    /** @type {?} */
625
                    var _type = osmFilterItem.split(':')[1];
626
                    if (_type === '*') {
627
                        if (osmItem.class === _class) {
628
                            filterMatchOccurence++;
629
                        }
630
                    }
631
                    else {
632
                        // if !, remove
633
                        if (_type.substr(0, 1) === '!') {
634
                            if (osmItem.class === _class && '!' + osmItem.type === _type) {
635
                                removeOccurence = true;
636
                            }
637
                        }
638
                        else {
639
                            if (osmItem.class === _class && osmItem.type === _type) {
640
                                filterMatchOccurence++;
641
                            }
642
                        }
643
                    }
644
                });
645
                if (filterMatchOccurence > 0 && !removeOccurence) {
646
                    osmFilteredResults.push(osmItem);
647
                }
648
            });
649
            return Object(rxjs__WEBPACK_IMPORTED_MODULE_3__["of"])(osmFilteredResults);
650
        }
651
        else {
652
            return Object(rxjs__WEBPACK_IMPORTED_MODULE_3__["of"])(osmResults);
653
        }
654
    };
655
    /**
656
     * @param {?} coordinatesArray
657
     * @return {?}
658
     */
659
    GeocodingService.prototype.reverseCorrdinatesArray = /**
660
     * @param {?} coordinatesArray
661
     * @return {?}
662
     */
663
    function (coordinatesArray) {
664
        if (coordinatesArray.length > 0) {
665
            coordinatesArray.forEach(function (item) {
666
                item.reverse();
667
            });
668
            return coordinatesArray;
669
        }
670
    };
671
    /**
672
     * @param {?} coordinatesArray
673
     * @return {?}
674
     */
675
    GeocodingService.prototype.simplifyPolyline = /**
676
     * @param {?} coordinatesArray
677
     * @return {?}
678
     */
679
    function (coordinatesArray) {
680
        if (coordinatesArray.length > 1) {
681
            /** @type {?} */
682
            var firstCoordinate = coordinatesArray[0];
683
            /** @type {?} */
684
            var lastCoordinate = coordinatesArray[coordinatesArray.length - 1];
685
            return [firstCoordinate, lastCoordinate];
686
        }
687
        else {
688
            return coordinatesArray;
689
        }
690
    };
691
    GeocodingService.decorators = [
692
        { type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Injectable"], args: [{
693
                    providedIn: 'root'
694
                },] },
695
    ];
696
    /** @nocollapse */
697
    GeocodingService.ctorParameters = function () { return [
698
        { type: _angular_common_http__WEBPACK_IMPORTED_MODULE_2__["HttpClient"] }
699
    ]; };
700
    /** @nocollapse */ GeocodingService.ngInjectableDef = Object(_angular_core__WEBPACK_IMPORTED_MODULE_0__["defineInjectable"])({ factory: function GeocodingService_Factory() { return new GeocodingService(Object(_angular_core__WEBPACK_IMPORTED_MODULE_0__["inject"])(_angular_common_http__WEBPACK_IMPORTED_MODULE_2__["HttpClient"])); }, token: GeocodingService, providedIn: "root" });
701
    return GeocodingService;
702
}());
703
 
704
/**
705
 * @fileoverview added by tsickle
706
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
707
 */
708
var ElevationService = /** @class */ (function () {
709
    function ElevationService(http) {
710
        this.http = http;
711
    }
712
    /**
713
     * @param {?} lat
714
     * @param {?} lng
715
     * @return {?}
716
     */
717
    ElevationService.prototype.getElevation = /**
718
     * @param {?} lat
719
     * @param {?} lng
720
     * @return {?}
721
     */
722
    function (lat, lng) {
723
        /** @type {?} */
724
        var apiUrl = "https://api.open-elevation.com/api/v1/lookup?locations=" + lat + "," + lng;
725
        return this.http.get(apiUrl).pipe(Object(rxjs_operators__WEBPACK_IMPORTED_MODULE_4__["map"])(function (obj) { return obj.results[0].elevation; }));
726
    };
727
    ElevationService.decorators = [
728
        { type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Injectable"], args: [{
729
                    providedIn: 'root'
730
                },] },
731
    ];
732
    /** @nocollapse */
733
    ElevationService.ctorParameters = function () { return [
734
        { type: _angular_common_http__WEBPACK_IMPORTED_MODULE_2__["HttpClient"] }
735
    ]; };
736
    /** @nocollapse */ ElevationService.ngInjectableDef = Object(_angular_core__WEBPACK_IMPORTED_MODULE_0__["defineInjectable"])({ factory: function ElevationService_Factory() { return new ElevationService(Object(_angular_core__WEBPACK_IMPORTED_MODULE_0__["inject"])(_angular_common_http__WEBPACK_IMPORTED_MODULE_2__["HttpClient"])); }, token: ElevationService, providedIn: "root" });
737
    return ElevationService;
738
}());
739
 
740
/**
741
 * @fileoverview added by tsickle
742
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
743
 */
744
var MapComponent = /** @class */ (function () {
745
    // ----
746
    // CODE
747
    // ----
748
    function MapComponent(fb, geocodeService, elevationService) {
749
        this.fb = fb;
750
        this.geocodeService = geocodeService;
751
        this.elevationService = elevationService;
752
        // --------------
753
        // INPUT / OUTPUT
754
        // --------------
755
        this.layersToAdd = ['osm'];
756
        this.osmClassFilter = [];
757
        this.location = new _angular_core__WEBPACK_IMPORTED_MODULE_0__["EventEmitter"]();
758
        this.coordFormat = 'dms';
759
        // ---------
760
        // VARIABLES
761
        // ---------
762
        this._location = /** @type {?} */ ({});
763
        this.geolocatedPhotoLatLngData = [];
764
        this.geolocatedPhotoLatLngDisplayedColumnsTable = ['select', 'photoName', 'lat', 'lng', 'altitude'];
765
        this.isLoadingAddress = false;
766
        this.isLoadingLatitude = false;
767
        this.isLoadingLongitude = false;
768
        this.isLoadingElevation = false;
769
        // -------------
770
        // SUBSCRIPTIONS
771
        // -------------
772
        this.geoSearchSubscription = new rxjs__WEBPACK_IMPORTED_MODULE_3__["Subscription"];
773
        this.latDmsInputSubscription = new rxjs__WEBPACK_IMPORTED_MODULE_3__["Subscription"];
774
        this.lngDmsInputSubscription = new rxjs__WEBPACK_IMPORTED_MODULE_3__["Subscription"];
775
        this.mapLat = 0;
776
        this.mapLng = 0;
777
        this.osmLayer = Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["tileLayer"])('http://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', { maxZoom: 18, attribution: 'Open Street map' });
778
        this.googleSatelliteLayer = Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["tileLayer"])('http://{s}.google.com/vt/lyrs=s&x={x}&y={y}&z={z}', { maxZoom: 20, subdomains: ['mt0', 'mt1', 'mt2', 'mt3'], attribution: 'Google maps' });
779
        this.googleHybridLayer = Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["tileLayer"])('http://{s}.google.com/vt/lyrs=s,h&x={x}&y={y}&z={z}', { maxZoom: 20, subdomains: ['mt0', 'mt1', 'mt2', 'mt3'], attribution: 'Google maps' });
780
        this.brgmLayer = leaflet__WEBPACK_IMPORTED_MODULE_1__["tileLayer"].wms('http://geoservices.brgm.fr/geologie', { version: '1.3.0', layers: 'Geologie' });
781
        this.mapLayers = {
782
            'Google': this.googleHybridLayer,
783
            'OSM': this.osmLayer,
784
            'BRGM': this.brgmLayer
785
        };
786
        this.geoResultsLayer = Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["geoJSON"])(null, { style: function () { return { color: '#ff7800', weight: 5, opacity: 0.65 }; } });
787
        this.geolocatedPhotoLatLngLayer = Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["geoJSON"])();
788
        // map options
789
        this.options = {
790
            layers: [this.osmLayer],
791
            zoom: 4,
792
            center: Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["latLng"])({ lat: 46.55886030311719, lng: 2.9882812500000004 })
793
        };
794
        // Leaflet map configuration
795
        this.drawnItems = new leaflet__WEBPACK_IMPORTED_MODULE_1__["FeatureGroup"]();
796
        this.drawControlFull = drawControlPanel;
797
        this.drawControlEdit = drawControlEditPanel(this.drawnItems);
798
        this.circleMarkerOpt = circleMarkerStyle;
799
        this.geoResultsOpt = cityStyle;
800
    }
801
    /**
802
     * - Create the forms
803
     * - Set up subscriptions (geo search, geolocated photos, lat / lng inputs)
804
     */
805
    /**
806
     * - Create the forms
807
     * - Set up subscriptions (geo search, geolocated photos, lat / lng inputs)
808
     * @return {?}
809
     */
810
    MapComponent.prototype.ngOnInit = /**
811
     * - Create the forms
812
     * - Set up subscriptions (geo search, geolocated photos, lat / lng inputs)
813
     * @return {?}
814
     */
815
    function () {
816
        var _this = this;
817
        // Create forms
818
        this.latlngFormGroup = this.fb.group({
819
            latInput: this.fb.control('', [_angular_forms__WEBPACK_IMPORTED_MODULE_6__["Validators"].required, this.latLngDecValidator]),
820
            lngInput: this.fb.control('', [_angular_forms__WEBPACK_IMPORTED_MODULE_6__["Validators"].required, this.latLngDecValidator]),
821
            dmsLatInput: this.fb.control('', [_angular_forms__WEBPACK_IMPORTED_MODULE_6__["Validators"].required, this.latLngDmsValidator]),
822
            dmsLngInput: this.fb.control('', [_angular_forms__WEBPACK_IMPORTED_MODULE_6__["Validators"].required, this.latLngDmsValidator])
823
        });
824
        this.elevationFormGroup = this.fb.group({
825
            elevationInput: this.fb.control('', null)
826
        });
827
        this.geoSearchFormGroup = this.fb.group({
828
            placeInput: this.fb.control('', null)
829
        });
830
        // Watch placeInput changes
831
        this.geoSearchSubscription = this.geoSearchFormGroup.controls["placeInput"].valueChanges
832
            .pipe(Object(rxjs_operators__WEBPACK_IMPORTED_MODULE_4__["debounceTime"])(400), Object(rxjs_operators__WEBPACK_IMPORTED_MODULE_4__["distinctUntilChanged"])(), Object(rxjs_operators__WEBPACK_IMPORTED_MODULE_4__["switchMap"])(function (value) {
833
            _this.isLoadingAddress = true;
834
            return _this.geocodeService.geocode(value);
835
        })).subscribe(function (results) {
836
            _this.isLoadingAddress = false;
837
            // filter results if needed
838
            if (_this.osmClassFilter.length > 0) {
839
                _this.geocodeService.osmClassFilter(_this.osmClassFilter, results).subscribe(function (filteredResults) {
840
                    _this.geoSearchResults = filteredResults;
841
                });
842
            }
843
            else {
844
                _this.geoSearchResults = results;
845
            }
846
        }, function (error) {
847
            // @toto manage error
848
            // @toto manage error
849
            _this.isLoadingAddress = false;
850
        });
851
        // Watch geolocated photo input changes
852
        this.geolocatedPhotoLatLng.subscribe(function (photoLatLng) {
853
            // @todo clear this.geolocatedPhotoLatLngLayer
854
            // @todo clear this.geolocatedPhotoLatLngLayer
855
            _this.geolocatedPhotoLatLngData = photoLatLng;
856
            // For each geolocated photo, add marker and bind mouse event on thoses markers
857
            // For each geolocated photo, add marker and bind mouse event on thoses markers
858
            _this.geolocatedPhotoLatLngData.forEach(function (data) {
859
                /** @type {?} */
860
                var _latDms = data.lat.deg + '° ' + data.lat.min + '\'' + data.lat.sec + '"';
861
                /** @type {?} */
862
                var _lngDms = data.lng.deg + '° ' + data.lng.min + '\'' + data.lng.sec + '"';
863
                /** @type {?} */
864
                var g = new GeoPoint(_lngDms, _latDms);
865
                data.latDec = g.latDec;
866
                data.lngDec = g.lonDec;
867
                /** @type {?} */
868
                var latLng$$1 = Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["latLng"])(data.latDec, data.lngDec);
869
                /** @type {?} */
870
                var gpsPhotoMarker = new leaflet__WEBPACK_IMPORTED_MODULE_1__["Marker"](latLng$$1, { icon: gpsPhotoMarkerIcon() });
871
                /** @type {?} */
872
                var html = "\n          <b>Fichier \"" + data.photoName + "\"</b><br>\n          Lat. : " + g.latDeg + "<br />\n          Lng. : " + g.lonDeg + "<br />\n          Alt. : " + data.altitude + " m<br /><br />\n          <b>Cliquez sur le point pour utiliser ces coordonn\u00E9es</b>";
873
                gpsPhotoMarker.bindPopup(html).openPopup();
874
                // Marker mouse events
875
                gpsPhotoMarker.on('click', (function (event) { _this.gpsMarkerSetValues(data.latDec, data.lngDec, data.altitude); }));
876
                gpsPhotoMarker.on('mouseover', function (event) { gpsPhotoMarker.openPopup(); });
877
                gpsPhotoMarker.on('mouseout', (function (event) { gpsPhotoMarker.closePopup(); }));
878
                // Add the marker to the map
879
                gpsPhotoMarker.addTo(_this.geolocatedPhotoLatLngLayer);
880
            });
881
            // Fit map to geolocated photos markers
882
            // Fit map to geolocated photos markers
883
            _this.flyToGeolocatedPhotoItems();
884
        });
885
        // Watch lat & lng DMS inputs changes and set up the DMS formatter
886
        // The DMS formatter restricts the keyboard input of the user : only number, comma, dot and '-', deg and min must be between -90 and +90
887
        // The formatter auto fill the ° ' and " characters to help the user input
888
        this.latDmsInputSubscription = this.latlngFormGroup.controls["dmsLatInput"].valueChanges.subscribe(function (value) {
889
            _this.latlngFormGroup.controls["dmsLatInput"].setValue(dmsFormatter(value), { emitEvent: false });
890
        });
891
        this.lngDmsInputSubscription = this.latlngFormGroup.controls["dmsLngInput"].valueChanges.subscribe(function (value) {
892
            _this.latlngFormGroup.controls["dmsLngInput"].setValue(dmsFormatter(value), { emitEvent: false });
893
        });
894
    };
895
    /**
896
     * Unsubscribe
897
     */
898
    /**
899
     * Unsubscribe
900
     * @return {?}
901
     */
902
    MapComponent.prototype.ngOnDestroy = /**
903
     * Unsubscribe
904
     * @return {?}
905
     */
906
    function () {
907
        this.geoSearchSubscription.unsubscribe();
908
        this.latDmsInputSubscription.unsubscribe();
909
        this.lngDmsInputSubscription.unsubscribe();
910
    };
911
    /**
912
     * Add layers and events listeners
913
     */
914
    /**
915
     * Add layers and events listeners
916
     * @param {?} map
917
     * @return {?}
918
     */
919
    MapComponent.prototype.onMapReady = /**
920
     * Add layers and events listeners
921
     * @param {?} map
922
     * @return {?}
923
     */
924
    function (map$$1) {
925
        var _this = this;
926
        this.map = map$$1;
927
        this.map.addControl(leaflet__WEBPACK_IMPORTED_MODULE_1__["control"].layers(null, this.mapLayers, { position: 'topright' }));
928
        this.map.addLayer(this.drawnItems);
929
        this.map.addLayer(this.geoResultsLayer);
930
        this.map.addLayer(this.geolocatedPhotoLatLngLayer);
931
        this.map.addControl(this.drawControlFull);
932
        this.map.on('draw:created', function (e) {
933
            _this.drawnItem = e['layer'];
934
            _this.drawType = e['layerType'];
935
            // If it's a marker, it must be draggable. By default, leaflet.draw module does not provide a draggable marker
936
            // So, we don't do a this.drawnItems.addLayer(layer);
937
            // We just draw a new draggableMarker instead
938
            if (_this.drawType === 'marker') {
939
                /** @type {?} */
940
                var latlng = _this.drawnItem._latlng;
941
                draggableMarker(latlng.lat, latlng.lng, function (dragEnd) { _this.callGeolocElevationApisUsingLatLngInputsValues(); }).addTo(_this.drawnItems);
942
            }
943
            else {
944
                _this.drawnItems.addLayer(_this.drawnItem);
945
            }
946
            // Show / hide control panels
947
            // if ONE item is drawn, set place and elevation inputs (call API)
948
            if (_this.drawnItems.getLayers().length > 0) {
949
                _this.setMapEditMode();
950
            }
951
            if (_this.drawnItems.getLayers().length === 1) {
952
                _this.callGeolocElevationApisUsingLatLngInputsValues();
953
            }
954
            _this.flyToDrawnItems();
955
        });
956
        this.map.on('draw:edited', function (e) {
957
            _this.drawnItem = e['layer'];
958
            _this.drawType = e['layerType'];
959
            //      this.drawnItems.addLayer(this.drawnItem);
960
            if (_this.drawnItems.getLayers().length === 1) {
961
                _this.callGeolocElevationApisUsingLatLngInputsValues();
962
            }
963
            _this.flyToDrawnItems();
964
        });
965
        this.map.on('draw:deleted', function (e) {
966
            _this.clearGeoResultsLayer();
967
            _this.clearDrawnItemsLayer();
968
            _this.setMapDrawMode();
969
            _this.clearForm();
970
        });
971
        this.redrawMap(100);
972
    };
973
    /**
974
     * When the map parent's div size change (eg. panel width), have to redraw the map
975
     * Sometimes (when opening / closing a tab), size change is detected too earlier, need to set a delay (about 10-100ms seems to be convenient)
976
     */
977
    /**
978
     * When the map parent's div size change (eg. panel width), have to redraw the map
979
     * Sometimes (when opening / closing a tab), size change is detected too earlier, need to set a delay (about 10-100ms seems to be convenient)
980
     * @param {?=} delay
981
     * @return {?}
982
     */
983
    MapComponent.prototype.redrawMap = /**
984
     * When the map parent's div size change (eg. panel width), have to redraw the map
985
     * Sometimes (when opening / closing a tab), size change is detected too earlier, need to set a delay (about 10-100ms seems to be convenient)
986
     * @param {?=} delay
987
     * @return {?}
988
     */
989
    function (delay) {
990
        var _this = this;
991
        if (delay) {
992
            window.setTimeout(function () { return _this.map.invalidateSize(); }, delay);
993
        }
994
        else {
995
            this.map.invalidateSize();
996
        }
997
    };
998
    /**
999
     * Show the "edit" toolbar inside map
1000
     */
1001
    /**
1002
     * Show the "edit" toolbar inside map
1003
     * @return {?}
1004
     */
1005
    MapComponent.prototype.setMapEditMode = /**
1006
     * Show the "edit" toolbar inside map
1007
     * @return {?}
1008
     */
1009
    function () {
1010
        this.map.removeControl(this.drawControlFull);
1011
        this.map.addControl(this.drawControlEdit);
1012
    };
1013
    /**
1014
     * Show the "draw" toolbar inside map
1015
     */
1016
    /**
1017
     * Show the "draw" toolbar inside map
1018
     * @return {?}
1019
     */
1020
    MapComponent.prototype.setMapDrawMode = /**
1021
     * Show the "draw" toolbar inside map
1022
     * @return {?}
1023
     */
1024
    function () {
1025
        this.map.removeControl(this.drawControlEdit);
1026
        this.map.addControl(this.drawControlFull);
1027
    };
1028
    /**
1029
     * Set map bounds to drawn items
1030
     */
1031
    /**
1032
     * Set map bounds to drawn items
1033
     * @param {?=} _maxZoom
1034
     * @return {?}
1035
     */
1036
    MapComponent.prototype.flyToDrawnItems = /**
1037
     * Set map bounds to drawn items
1038
     * @param {?=} _maxZoom
1039
     * @return {?}
1040
     */
1041
    function (_maxZoom) {
1042
        if (_maxZoom === void 0) { _maxZoom = 14; }
1043
        /** @type {?} */
1044
        var b = this.drawnItems.getBounds();
1045
        this.map.flyToBounds(b, { maxZoom: _maxZoom, animate: false });
1046
    };
1047
    /**
1048
     * Set map bounds to geo reults items
1049
     */
1050
    /**
1051
     * Set map bounds to geo reults items
1052
     * @return {?}
1053
     */
1054
    MapComponent.prototype.flyToGeoResultsItems = /**
1055
     * Set map bounds to geo reults items
1056
     * @return {?}
1057
     */
1058
    function () {
1059
        /** @type {?} */
1060
        var b = this.geoResultsLayer.getBounds();
1061
        this.map.flyToBounds(b, { maxZoom: 14, animate: false });
1062
    };
1063
    /**
1064
     * Set map bounds to geolocated photos items
1065
     */
1066
    /**
1067
     * Set map bounds to geolocated photos items
1068
     * @return {?}
1069
     */
1070
    MapComponent.prototype.flyToGeolocatedPhotoItems = /**
1071
     * Set map bounds to geolocated photos items
1072
     * @return {?}
1073
     */
1074
    function () {
1075
        /** @type {?} */
1076
        var b = this.geolocatedPhotoLatLngLayer.getBounds();
1077
        this.map.flyToBounds(b, { maxZoom: 14, animate: false });
1078
    };
1079
    /**
1080
     * Draw a marker on drawItems featureGroup with DMS input values
1081
     */
1082
    /**
1083
     * Draw a marker on drawItems featureGroup with DMS input values
1084
     * @return {?}
1085
     */
1086
    MapComponent.prototype.addMarkerFromDmsCoord = /**
1087
     * Draw a marker on drawItems featureGroup with DMS input values
1088
     * @return {?}
1089
     */
1090
    function () {
1091
        // clear drawn items layer
1092
        this.clearDrawnItemsLayer();
1093
        // update map toolbar
1094
        this.setMapEditMode();
1095
        /** @type {?} */
1096
        var geopoint = new GeoPoint(this.latlngFormGroup.controls["dmsLngInput"].value, this.latlngFormGroup.controls["dmsLatInput"].value);
1097
        draggableMarker(geopoint.getLatDec(), geopoint.getLonDec(), function (e) {
1098
            /* dragend callback fn */
1099
        }).addTo(this.drawnItems);
1100
        // Set (decimal) latLng inputs
1101
        this.latlngFormGroup.controls["latInput"].setValue(geopoint.getLatDec(), { emitEvent: false });
1102
        this.latlngFormGroup.controls["lngInput"].setValue(geopoint.getLatDec(), { emitEvent: false });
1103
        // Fly
1104
        this.flyToDrawnItems();
1105
    };
1106
    /**
1107
     * Draw a marker on drawItems featureGroup with decimal input values
1108
     */
1109
    /**
1110
     * Draw a marker on drawItems featureGroup with decimal input values
1111
     * @return {?}
1112
     */
1113
    MapComponent.prototype.addMarkerFromLatLngCoord = /**
1114
     * Draw a marker on drawItems featureGroup with decimal input values
1115
     * @return {?}
1116
     */
1117
    function () {
1118
        // clear drawn items layer
1119
        this.clearDrawnItemsLayer();
1120
        // update map toolbar
1121
        this.setMapEditMode();
1122
        /** @type {?} */
1123
        var geopoint = new GeoPoint(Number(this.latlngFormGroup.controls["lngInput"].value), Number(this.latlngFormGroup.controls["latInput"].value));
1124
        draggableMarker(geopoint.getLatDec(), geopoint.getLonDec(), function (dragEnd) {
1125
            /* dragend callback fn */
1126
        }).addTo(this.drawnItems);
1127
        // Set dmsLatLng inputs
1128
        this.latlngFormGroup.controls["dmsLatInput"].setValue(geopoint.getLatDeg(), { emitEvent: false });
1129
        this.latlngFormGroup.controls["dmsLngInput"].setValue(geopoint.getLonDeg(), { emitEvent: false });
1130
        // Fly
1131
        this.flyToDrawnItems();
1132
    };
1133
    /**
1134
    *
1135
    */
1136
    /**
1137
     *
1138
     * @param {?} coordinates
1139
     * @return {?}
1140
     */
1141
    MapComponent.prototype.addPolyline = /**
1142
     *
1143
     * @param {?} coordinates
1144
     * @return {?}
1145
     */
1146
    function (coordinates) {
1147
        // clear drawn items layer
1148
        this.clearDrawnItemsLayer();
1149
        // update map toolbar
1150
        this.setMapEditMode();
1151
        /** @type {?} */
1152
        var polyline$$1 = Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["polyline"])(coordinates);
1153
        polyline$$1.addTo(this.drawnItems);
1154
        // fly with max zoom
1155
        this.flyToDrawnItems(18);
1156
    };
1157
    /**
1158
     * Take latitude and longitude input values and call geocoding and elevation API
1159
     * Sometimes you may want to force the elevation value and avoid calling elevation API (eg. elevation come from gps photo metadata)
1160
     * then, you cas use the avoidCallingElevationApi option
1161
     *
1162
     * What is done inside this function :
1163
     * - create an observable that zip all required observables
1164
     * - do a switchmap on the main observable so that if one one the sub-observable change, old data are ignored
1165
     * - when the main observable is finished, can send new location Output
1166
     *
1167
     * Several if / else avoidCallingElevationApi are used because when
1168
     * avoidCallingElevationApi === false, httpTasks returns a single value (osmPlace)
1169
     * whereas if avoidCallingElevationApi === true, httpTasks returns an array of 2 values [elevation, osmPlace]
1170
     */
1171
    /**
1172
     * Take latitude and longitude input values and call geocoding and elevation API
1173
     * Sometimes you may want to force the elevation value and avoid calling elevation API (eg. elevation come from gps photo metadata)
1174
     * then, you cas use the avoidCallingElevationApi option
1175
     *
1176
     * What is done inside this function :
1177
     * - create an observable that zip all required observables
1178
     * - do a switchmap on the main observable so that if one one the sub-observable change, old data are ignored
1179
     * - when the main observable is finished, can send new location Output
1180
     *
1181
     * Several if / else avoidCallingElevationApi are used because when
1182
     * avoidCallingElevationApi === false, httpTasks returns a single value (osmPlace)
1183
     * whereas if avoidCallingElevationApi === true, httpTasks returns an array of 2 values [elevation, osmPlace]
1184
     * @param {?=} avoidCallingElevationApi
1185
     * @param {?=} avoidCallingGeolocApi
1186
     * @return {?}
1187
     */
1188
    MapComponent.prototype.callGeolocElevationApisUsingLatLngInputsValues = /**
1189
     * Take latitude and longitude input values and call geocoding and elevation API
1190
     * Sometimes you may want to force the elevation value and avoid calling elevation API (eg. elevation come from gps photo metadata)
1191
     * then, you cas use the avoidCallingElevationApi option
1192
     *
1193
     * What is done inside this function :
1194
     * - create an observable that zip all required observables
1195
     * - do a switchmap on the main observable so that if one one the sub-observable change, old data are ignored
1196
     * - when the main observable is finished, can send new location Output
1197
     *
1198
     * Several if / else avoidCallingElevationApi are used because when
1199
     * avoidCallingElevationApi === false, httpTasks returns a single value (osmPlace)
1200
     * whereas if avoidCallingElevationApi === true, httpTasks returns an array of 2 values [elevation, osmPlace]
1201
     * @param {?=} avoidCallingElevationApi
1202
     * @param {?=} avoidCallingGeolocApi
1203
     * @return {?}
1204
     */
1205
    function (avoidCallingElevationApi, avoidCallingGeolocApi) {
1206
        var _this = this;
1207
        if (avoidCallingElevationApi === void 0) { avoidCallingElevationApi = false; }
1208
        if (avoidCallingGeolocApi === void 0) { avoidCallingGeolocApi = false; }
1209
        this.setLatLngInputFromDrawnItems();
1210
        this.setLatLngDmsInputFromDrawnItems();
1211
        /** @type {?} */
1212
        var httpTasks;
1213
        /** @type {?} */
1214
        var elevation;
1215
        /** @type {?} */
1216
        var osmPlace;
1217
        if (avoidCallingElevationApi && !avoidCallingGeolocApi) {
1218
            httpTasks = this.reverseGeocodingFromInputValue();
1219
        }
1220
        else if (avoidCallingGeolocApi && !avoidCallingElevationApi) {
1221
            httpTasks = this.getElevationFromInputValue();
1222
        }
1223
        else if (!avoidCallingElevationApi && !avoidCallingGeolocApi) {
1224
            httpTasks = Object(rxjs__WEBPACK_IMPORTED_MODULE_3__["zip"])(this.getElevationFromInputValue(), this.reverseGeocodingFromInputValue());
1225
        }
1226
        else if (avoidCallingElevationApi && avoidCallingGeolocApi) {
1227
            // nothing to do ; throw or log an error ?
1228
            return;
1229
        }
1230
        // spinnners on
1231
        this.isLoadingAddress = !avoidCallingGeolocApi;
1232
        this.isLoadingElevation = !avoidCallingElevationApi;
1233
        httpTasks.subscribe(function (result) {
1234
            _this.isLoadingElevation = false;
1235
            _this.isLoadingAddress = false;
1236
            if (avoidCallingElevationApi && !avoidCallingGeolocApi) {
1237
                elevation = null;
1238
                osmPlace = result;
1239
            }
1240
            else if (avoidCallingGeolocApi && !avoidCallingElevationApi) {
1241
                elevation = result;
1242
                osmPlace = null;
1243
                elevation = result;
1244
            }
1245
            else if (!avoidCallingGeolocApi && !avoidCallingGeolocApi) {
1246
                elevation = result[0];
1247
                osmPlace = result[1];
1248
            }
1249
            // Set elevation input
1250
            if (!avoidCallingElevationApi) {
1251
                _this.elevationFormGroup.controls["elevationInput"].setValue(elevation);
1252
            }
1253
            // Patch place input value
1254
            if (!avoidCallingGeolocApi) {
1255
                _this.geoSearchFormGroup.controls["placeInput"].patchValue(_this.geocodeService.getReadbleAddress(osmPlace), { emitEvent: false });
1256
            }
1257
            // bind _location & emit location
1258
            if (avoidCallingElevationApi) {
1259
                _this.bindLocationOutput([_this.elevationFormGroup.controls["elevationInput"].value, osmPlace]);
1260
            }
1261
            else {
1262
                _this.bindLocationOutput(result);
1263
            }
1264
        }, function (error) {
1265
            // Manage error
1266
            // spinnners off
1267
            // Manage error
1268
            // spinnners off
1269
            _this.isLoadingAddress = false;
1270
            _this.isLoadingElevation = false;
1271
        });
1272
    };
1273
    /**
1274
     * Should be improved for complex polygons / polylines ?
1275
     * Could use turf.js
1276
     */
1277
    /**
1278
     * Should be improved for complex polygons / polylines ?
1279
     * Could use turf.js
1280
     * @return {?}
1281
     */
1282
    MapComponent.prototype.setLatLngInputFromDrawnItems = /**
1283
     * Should be improved for complex polygons / polylines ?
1284
     * Could use turf.js
1285
     * @return {?}
1286
     */
1287
    function () {
1288
        /** @type {?} */
1289
        var centroid = this.drawnItems.getBounds().getCenter();
1290
        this.latlngFormGroup.controls["latInput"].setValue(centroid.lat);
1291
        this.latlngFormGroup.controls["lngInput"].setValue(centroid.lng);
1292
    };
1293
    /**
1294
     *
1295
     */
1296
    /**
1297
     *
1298
     * @return {?}
1299
     */
1300
    MapComponent.prototype.setLatLngDmsInputFromDrawnItems = /**
1301
     *
1302
     * @return {?}
1303
     */
1304
    function () {
1305
        /** @type {?} */
1306
        var centroid = this.drawnItems.getBounds().getCenter();
1307
        /** @type {?} */
1308
        var geopoint = new GeoPoint(centroid.lng, centroid.lat);
1309
        this.latlngFormGroup.controls["dmsLatInput"].patchValue(geopoint.getLatDeg());
1310
        this.latlngFormGroup.controls["dmsLngInput"].patchValue(geopoint.getLonDeg());
1311
    };
1312
    /**
1313
     *
1314
     */
1315
    /**
1316
     *
1317
     * @return {?}
1318
     */
1319
    MapComponent.prototype.getElevationFromInputValue = /**
1320
     *
1321
     * @return {?}
1322
     */
1323
    function () {
1324
        return this.elevationService.getElevation(this.latlngFormGroup.controls["latInput"].value, this.latlngFormGroup.controls["lngInput"].value);
1325
    };
1326
    /**
1327
     * Reverse geocoding from lat / lng inputs values
1328
     */
1329
    /**
1330
     * Reverse geocoding from lat / lng inputs values
1331
     * @return {?}
1332
     */
1333
    MapComponent.prototype.reverseGeocodingFromInputValue = /**
1334
     * Reverse geocoding from lat / lng inputs values
1335
     * @return {?}
1336
     */
1337
    function () {
1338
        return this.geocodeService.reverse(this.latlngFormGroup.controls["latInput"].value, this.latlngFormGroup.controls["lngInput"].value);
1339
    };
1340
    /**
1341
     * Latitude / longitude DMS form Validator
1342
     */
1343
    /**
1344
     * Latitude / longitude DMS form Validator
1345
     * @param {?} control
1346
     * @return {?}
1347
     */
1348
    MapComponent.prototype.latLngDmsValidator = /**
1349
     * Latitude / longitude DMS form Validator
1350
     * @param {?} control
1351
     * @return {?}
1352
     */
1353
    function (control$$1) {
1354
        /** @type {?} */
1355
        var regexp = new RegExp('^(\\-)?[0-9]{1,2}\\° [0-9]{1,2}\\\' [0-9]{1,2}\\.[0-9]{1,12}\\"');
1356
        return regexp.test(control$$1.value) ? null : { malformedLatLngDmsFormat: true };
1357
    };
1358
    /**
1359
     * Latitude / longitude decimal form validator
1360
     */
1361
    /**
1362
     * Latitude / longitude decimal form validator
1363
     * @param {?} control
1364
     * @return {?}
1365
     */
1366
    MapComponent.prototype.latLngDecValidator = /**
1367
     * Latitude / longitude decimal form validator
1368
     * @param {?} control
1369
     * @return {?}
1370
     */
1371
    function (control$$1) {
1372
        /** @type {?} */
1373
        var regexp = new RegExp('^(\\-)?[0-9]{1,2}\\.[0-9]{1,20}');
1374
        return regexp.test(control$$1.value) ? null : { malformedLatLngDecFormat: true };
1375
    };
1376
    /**
1377
     * When user select an address within the autocomplete results list
1378
     *
1379
     * Call the geoloc API 2 times :
1380
     *  - first call is for reverse geocoding
1381
     *  - second call is for geoconding, so the address input (placeInput) is updated
1382
     */
1383
    /**
1384
     * When user select an address within the autocomplete results list
1385
     *
1386
     * Call the geoloc API 2 times :
1387
     *  - first call is for reverse geocoding
1388
     *  - second call is for geoconding, so the address input (placeInput) is updated
1389
     * @param {?} event
1390
     * @return {?}
1391
     */
1392
    MapComponent.prototype.addressSelectedChanged = /**
1393
     * When user select an address within the autocomplete results list
1394
     *
1395
     * Call the geoloc API 2 times :
1396
     *  - first call is for reverse geocoding
1397
     *  - second call is for geoconding, so the address input (placeInput) is updated
1398
     * @param {?} event
1399
     * @return {?}
1400
     */
1401
    function (event) {
1402
        /** @type {?} */
1403
        var osmPlace = event.option.value;
1404
        /** @type {?} */
1405
        var southWest = new leaflet__WEBPACK_IMPORTED_MODULE_1__["LatLng"](osmPlace.boundingbox[0], osmPlace.boundingbox[2]);
1406
        /** @type {?} */
1407
        var northEast = new leaflet__WEBPACK_IMPORTED_MODULE_1__["LatLng"](osmPlace.boundingbox[1], osmPlace.boundingbox[3]);
1408
        this.map.fitBounds(Object(leaflet__WEBPACK_IMPORTED_MODULE_1__["latLngBounds"])(southWest, northEast));
1409
        // Add geojson to the map (if user enter a city, draw the administrative shape on the map)
1410
        this.clearGeoResultsLayer();
1411
        this.geoResultsLayer.addData(osmPlace.geojson);
1412
        // Fly
1413
        this.flyToGeoResultsItems();
1414
        // Patch input value
1415
        this.geoSearchFormGroup.controls["placeInput"].patchValue(this.geocodeService.getReadbleAddress(osmPlace), { emitEvent: false });
1416
        /** @type {?} */
1417
        var g = new GeoPoint(Number(osmPlace.lon), Number(osmPlace.lat));
1418
        this.latlngFormGroup.controls["latInput"].setValue(osmPlace.lat, { emitEvent: false });
1419
        this.latlngFormGroup.controls["lngInput"].setValue(osmPlace.lon, { emitEvent: false });
1420
        this.latlngFormGroup.controls["dmsLatInput"].setValue(g.getLatDeg(), { emitEvent: false });
1421
        this.latlngFormGroup.controls["dmsLngInput"].setValue(g.getLonDeg(), { emitEvent: false });
1422
        this.elevationFormGroup.controls["elevationInput"].setValue(osmPlace.elevation, { emitEvent: false });
1423
        // Draw a polyline or place a marker at the center of a polygon
1424
        if (osmPlace.geojson.type === 'LineString') {
1425
            // osm geojson coordinates is like [[long, lat], [long, lat], ...]
1426
            // but leaflet needs [[lat, long], [lat, long], ...] format !
1427
            this.geocodeService.simplifyPolyline(osmPlace.geojson.coordinates);
1428
            this.addPolyline(/** @type {?} */ (this.geocodeService.reverseCorrdinatesArray(this.geocodeService.simplifyPolyline(osmPlace.geojson.coordinates))));
1429
            this.clearGeoResultsLayer();
1430
        }
1431
        else {
1432
            this.addMarkerFromLatLngCoord();
1433
        }
1434
        // Call geoloc and elevation APIs
1435
        this.callGeolocElevationApisUsingLatLngInputsValues(false, false);
1436
    };
1437
    /**
1438
     * Clear the form when nedded : 'draw:deleted', etc.
1439
     */
1440
    /**
1441
     * Clear the form when nedded : 'draw:deleted', etc.
1442
     * @return {?}
1443
     */
1444
    MapComponent.prototype.clearForm = /**
1445
     * Clear the form when nedded : 'draw:deleted', etc.
1446
     * @return {?}
1447
     */
1448
    function () {
1449
        this.latlngFormGroup.controls["latInput"].setValue('', { emitEvent: false });
1450
        this.latlngFormGroup.controls["lngInput"].setValue('', { emitEvent: false });
1451
        this.latlngFormGroup.controls["dmsLatInput"].setValue('', { emitEvent: false });
1452
        this.latlngFormGroup.controls["dmsLngInput"].setValue('', { emitEvent: false });
1453
        this.latlngFormGroup.reset();
1454
        this.elevationFormGroup.controls["elevationInput"].setValue('', { emitEvent: false });
1455
        this.elevationFormGroup.reset();
1456
        this.geoSearchFormGroup.controls["placeInput"].setValue('', { emitEvent: false });
1457
    };
1458
    /**
1459
     * Clear geoResults layer (eg this layer contains administrative polygons -- "commune")
1460
     */
1461
    /**
1462
     * Clear geoResults layer (eg this layer contains administrative polygons -- "commune")
1463
     * @return {?}
1464
     */
1465
    MapComponent.prototype.clearGeoResultsLayer = /**
1466
     * Clear geoResults layer (eg this layer contains administrative polygons -- "commune")
1467
     * @return {?}
1468
     */
1469
    function () {
1470
        this.geoResultsLayer.clearLayers();
1471
    };
1472
    /**
1473
     *
1474
     */
1475
    /**
1476
     *
1477
     * @return {?}
1478
     */
1479
    MapComponent.prototype.clearDrawnItemsLayer = /**
1480
     *
1481
     * @return {?}
1482
     */
1483
    function () {
1484
        this.drawnItems.clearLayers();
1485
    };
1486
    /**
1487
     *
1488
     */
1489
    /**
1490
     *
1491
     * @return {?}
1492
     */
1493
    MapComponent.prototype.resetLocation = /**
1494
     *
1495
     * @return {?}
1496
     */
1497
    function () {
1498
        this.location = null;
1499
    };
1500
    /**
1501
     * Bind data from elevation and OSM http results to this._location
1502
     * Perform some verifications to ensure data integrity
1503
     * @param data data[0] = elevation, data[1] = osm data | data = osm data
1504
     */
1505
    /**
1506
     * Bind data from elevation and OSM http results to this._location
1507
     * Perform some verifications to ensure data integrity
1508
     * @param {?} data data[0] = elevation, data[1] = osm data | data = osm data
1509
     * @return {?}
1510
     */
1511
    MapComponent.prototype.bindLocationOutput = /**
1512
     * Bind data from elevation and OSM http results to this._location
1513
     * Perform some verifications to ensure data integrity
1514
     * @param {?} data data[0] = elevation, data[1] = osm data | data = osm data
1515
     * @return {?}
1516
     */
1517
    function (data) {
1518
        /** @type {?} */
1519
        var elevation;
1520
        /** @type {?} */
1521
        var osmPlace;
1522
        if (Array.isArray(data)) {
1523
            elevation = data[0];
1524
            osmPlace = data[1];
1525
        }
1526
        else {
1527
            elevation = this.elevationFormGroup.controls["elevationInput"].value;
1528
            osmPlace = data;
1529
        }
1530
        this._location.geometry = this.drawnItems.toGeoJSON();
1531
        // geodatum
1532
        this._location.elevation = elevation;
1533
        this._location.localityConsistency = this._location.localityConsistency ? true : null; // perform : Cohérence entre les coordonnées et la localité
1534
        this._location.locationAccuracy = this._location.locationAccuracy ? 0 : null; // perform : Précision (ou incertitude) de la localisation, en mètres --> voir le nombre de décimales pour decLatInput ou decLngInput si point, sinon, demi-longeur de la bounding-box
1535
        // published_location : Précision géographique à laquelle est publiée l'obs, permet de gérer le floutage - Précise, Localité, Maille 10x10km
1536
        this._location.osmCountry = osmPlace.address.country;
1537
        this._location.osmCountryCode = osmPlace.address.country_code;
1538
        this._location.osmCounty = osmPlace.address.county;
1539
        this._location.osmPostcode = osmPlace.address.postcode;
1540
        if (osmPlace.address.city) {
1541
            this._location.locality = osmPlace.address.city;
1542
        }
1543
        if (osmPlace.address.town) {
1544
            this._location.locality = osmPlace.address.town;
1545
        }
1546
        if (osmPlace.address.village) {
1547
            this._location.locality = osmPlace.address.village;
1548
        }
1549
        this._location.sublocality = osmPlace.hamlet;
1550
        this._location.osmRoad = osmPlace.address.road;
1551
        this._location.osmState = osmPlace.address.state;
1552
        this._location.osmSuburb = osmPlace.address.suburb;
1553
        this._location.osmId = osmPlace.osm_id;
1554
        this._location.osmNeighbourhood = null; // not provided by nominatim
1555
        this._location.osmPlaceId = osmPlace.place_id;
1556
        this._location.publishedLocation = null; // perform
1557
        this._location.station = null; // perform
1558
        // Verifications
1559
        // @todo
1560
        // Emit
1561
        this.location.next(this._location);
1562
    };
1563
    /**
1564
     * Change the form coordinates format : 'decimal' or 'dms'
1565
     */
1566
    /**
1567
     * Change the form coordinates format : 'decimal' or 'dms'
1568
     * @param {?} format
1569
     * @return {?}
1570
     */
1571
    MapComponent.prototype.setLatLngInputFormat = /**
1572
     * Change the form coordinates format : 'decimal' or 'dms'
1573
     * @param {?} format
1574
     * @return {?}
1575
     */
1576
    function (format) {
1577
        if (format !== 'decimal' && format !== 'dms') {
1578
            return;
1579
        }
1580
        this.coordFormat = format;
1581
    };
1582
    /**
1583
     * Set inputs values, add a marker and call API for a geolocated photo
1584
     */
1585
    /**
1586
     * Set inputs values, add a marker and call API for a geolocated photo
1587
     * @param {?} latDec
1588
     * @param {?} lngDec
1589
     * @param {?} elevation
1590
     * @return {?}
1591
     */
1592
    MapComponent.prototype.gpsMarkerSetValues = /**
1593
     * Set inputs values, add a marker and call API for a geolocated photo
1594
     * @param {?} latDec
1595
     * @param {?} lngDec
1596
     * @param {?} elevation
1597
     * @return {?}
1598
     */
1599
    function (latDec, lngDec, elevation) {
1600
        // set inputs values
1601
        this.latlngFormGroup.controls["latInput"].setValue(latDec);
1602
        this.latlngFormGroup.controls["lngInput"].setValue(lngDec);
1603
        this.elevationFormGroup.controls["elevationInput"].setValue(elevation);
1604
        // add marker
1605
        this.addMarkerFromLatLngCoord();
1606
        // call APIs
1607
        this.callGeolocElevationApisUsingLatLngInputsValues(true, false);
1608
        // clear geolocated photos layer
1609
        this.geolocatedPhotoLatLngLayer.clearLayers();
1610
    };
1611
    /**
1612
     * @param {?} value
1613
     * @return {?}
1614
     */
1615
    MapComponent.prototype.latLngDmsAutoFormatter = /**
1616
     * @param {?} value
1617
     * @return {?}
1618
     */
1619
    function (value) {
1620
        return '';
1621
    };
1622
    MapComponent.decorators = [
1623
        { type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Component"], args: [{
1624
                    selector: 'tb-geoloc-map',
1625
                    template: "<h1>O\u00F9 ?</h1>\n  \n<div id=\"geoloc-map\">\n  <div id=\"geoloc-map-meta\">\n    <!-- geosearch autocomplete -->\n    <mat-form-field style=\"width: 100%;\">\n      <input matInput [formControl]=\"geoSearchFormGroup.controls.placeInput\" placeholder=\"Trouver un lieu\" aria-label=\"Trouver un lieu\" [matAutocomplete]=\"auto\">\n      <mat-spinner *ngIf=\"isLoadingAddress\" diameter=\"20\" matSuffix></mat-spinner>\n      <mat-autocomplete #auto=\"matAutocomplete\" (optionSelected)=\"addressSelectedChanged($event)\">\n        <mat-option *ngFor=\"let address of geoSearchResults\" [value]=\"address\">\n          <span>{{ address | osmPlaceReadableAddress }}</span>\n        </mat-option>\n      </mat-autocomplete>\n    </mat-form-field>\n    \n    <div class=\"geolocationInputs\">\n      <div [formGroup]=\"latlngFormGroup\">\n        <div class=\"latLngMenuInputs\">\n          <!-- latitude / longitude decimal format -->\n          <div *ngIf=\"coordFormat=='decimal'\">\n            <!-- latitude / longitude format selection -->  \n            <button mat-icon-button [matMenuTriggerFor]=\"menu\">\n              <mat-icon>more_vert</mat-icon>\n            </button>\n\n            <mat-form-field>\n              <input matInput formControlName=\"latInput\" placeholder=\"latitude\">\n              <mat-spinner *ngIf=\"isLoadingLatitude\" diameter=\"20\" matSuffix></mat-spinner>\n              <mat-error *ngIf=\"latlngFormGroup.controls.latInput.dirty && latlngFormGroup.controls.latInput.hasError('malformedLatLngDecFormat')\">Format non valide</mat-error>\n            </mat-form-field>\n            <mat-form-field>\n              <input matInput formControlName=\"lngInput\" placeholder=\"longitude\">\n              <mat-spinner *ngIf=\"isLoadingLongitude\" diameter=\"20\" matSuffix></mat-spinner>\n              <mat-error *ngIf=\"latlngFormGroup.controls.latInput.dirty && latlngFormGroup.controls.latInput.hasError('malformedLatLngDecFormat')\">Format non valide</mat-error>\n            </mat-form-field>\n            \n            <button mat-icon-button (click)=\"addMarkerFromLatLngCoord(); callGeolocElevationApisUsingLatLngInputsValues();\" [disabled]=\"!latlngFormGroup.controls.latInput.valid || !latlngFormGroup.controls.lngInput.valid\" color=\"primary\">\n              <mat-icon matTooltip=\"Utiliser ces coordonn\u00E9es\">where_to_vote</mat-icon>\n            </button>\n          </div>\n        </div>\n\n        <!-- menu format decimal / dms-->\n        <mat-menu #menu=\"matMenu\">\n          <button mat-menu-item (click)=\"setLatLngInputFormat('dms')\">Degr\u00E9s minutes secondes</button>\n          <button mat-menu-item (click)=\"setLatLngInputFormat('decimal')\">D\u00E9cimal</button>\n        </mat-menu>\n\n        <!-- latitude / longitude DMS format -->\n        <div *ngIf=\"coordFormat=='dms'\">\n          <!-- latitude / longitude format selection -->  \n          <button mat-icon-button [matMenuTriggerFor]=\"menu\">\n            <mat-icon>more_vert</mat-icon>\n          </button>\n\n          <mat-form-field>\n            <input matInput formControlName=\"dmsLatInput\" placeholder=\"(deg)\u00B0  (min)'  (sec)&quot;\">\n            <span matPrefix>N&nbsp;</span>\n            <mat-spinner *ngIf=\"isLoadingLatitude\" diameter=\"20\" matSuffix></mat-spinner>\n            <mat-error *ngIf=\"latlngFormGroup.controls.dmsLatInput.dirty && latlngFormGroup.controls.dmsLatInput.hasError('malformedLatLngDmsFormat')\">Format non valide</mat-error>\n          </mat-form-field>\n\n          <mat-form-field>\n            <input matInput formControlName=\"dmsLngInput\" placeholder=\"(deg)\u00B0  (min)'  (sec)&quot;\">\n            <span matPrefix>E&nbsp;</span>\n            <mat-spinner *ngIf=\"isLoadingLongitude\" diameter=\"20\" matSuffix></mat-spinner>\n            <mat-error *ngIf=\"latlngFormGroup.controls.dmsLatInput.dirty && latlngFormGroup.controls.dmsLatInput.hasError('malformedLatLngDmsFormat')\">Format non valide</mat-error>\n          </mat-form-field>\n\n          <button mat-icon-button (click)=\"addMarkerFromDmsCoord(); callGeolocElevationApisUsingLatLngInputsValues();\" [disabled]=\"!latlngFormGroup.controls.dmsLatInput.valid || !latlngFormGroup.controls.dmsLngInput.valid\" color=\"primary\">\n            <mat-icon matTooltip=\"Utiliser ces coordonn\u00E9es\">where_to_vote</mat-icon>\n          </button>\n        </div>\n      </div>\n    \n      <!-- elevation -->\n      <div [formGroup]=\"elevationFormGroup\">\n        <mat-form-field style=\"width: 100px;\">\n          <input matInput formControlName=\"elevationInput\" placeholder=\"altitude\">\n          <mat-spinner *ngIf=\"isLoadingElevation\" diameter=\"20\" matSuffix></mat-spinner>\n          <span *ngIf=\"!isLoadingElevation\" matSuffix>m</span>\n        </mat-form-field>\n      </div>\n    </div>\n  </div>\n\n  <div id=\"geoloc-map-draw\" style=\"height: 400px;\"\n      leaflet \n      [leafletOptions]=\"options\"\n      (leafletMapReady)=\"onMapReady($event)\">\n  </div>\n</div>",
1626
                    styles: ["[hidden]{display:none!important}#geoloc-map{display:flex;flex-direction:column;min-height:200px}#geoloc-map #geoloc-map-meta{flex:1;padding:15px}#geoloc-map #geoloc-map-meta .geolocationInputs{display:flex;flex-direction:row;justify-content:space-between}#geoloc-map #geoloc-map-draw{position:relative;flex:3}#geoloc-map #httpTasksRunningSpinner{flex:1}button .mini{min-width:0;line-height:30px}.geolocatedPhotoMetadataTable{width:100%}"]
1627
                },] },
1628
    ];
1629
    /** @nocollapse */
1630
    MapComponent.ctorParameters = function () { return [
1631
        { type: _angular_forms__WEBPACK_IMPORTED_MODULE_6__["FormBuilder"] },
1632
        { type: GeocodingService },
1633
        { type: ElevationService }
1634
    ]; };
1635
    MapComponent.propDecorators = {
1636
        layersToAdd: [{ type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Input"] }],
1637
        geolocatedPhotoLatLng: [{ type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Input"] }],
1638
        osmClassFilter: [{ type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Input"] }],
1639
        location: [{ type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Output"] }]
1640
    };
1641
    return MapComponent;
1642
}());
1643
 
1644
/**
1645
 * @fileoverview added by tsickle
1646
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
1647
 */
1648
/**
1649
 * To show an address to the user, we could use the display_name attribute returned by nominatim
1650
 * This attribute is far complicated to read (road, neighbourhood, suburb, town, city, postcode, county, country, etc.)
1651
 * This pipe use the getReadbleAddress() function of geocode service to show minimal information about the address returned by nominatim API
1652
 */
1653
var OsmPlaceReadableAddressPipe = /** @class */ (function () {
1654
    function OsmPlaceReadableAddressPipe(geocodeService) {
1655
        this.geocodeService = geocodeService;
1656
    }
1657
    /**
1658
     * @param {?} value
1659
     * @param {?=} args
1660
     * @return {?}
1661
     */
1662
    OsmPlaceReadableAddressPipe.prototype.transform = /**
1663
     * @param {?} value
1664
     * @param {?=} args
1665
     * @return {?}
1666
     */
1667
    function (value, args) {
1668
        return this.geocodeService.getReadbleAddress(value);
1669
    };
1670
    OsmPlaceReadableAddressPipe.decorators = [
1671
        { type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["Pipe"], args: [{
1672
                    name: 'osmPlaceReadableAddress'
1673
                },] },
1674
    ];
1675
    /** @nocollapse */
1676
    OsmPlaceReadableAddressPipe.ctorParameters = function () { return [
1677
        { type: GeocodingService }
1678
    ]; };
1679
    return OsmPlaceReadableAddressPipe;
1680
}());
1681
 
1682
/**
1683
 * @fileoverview added by tsickle
1684
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
1685
 */
1686
var TbGeolocLibModule = /** @class */ (function () {
1687
    function TbGeolocLibModule() {
1688
    }
1689
    TbGeolocLibModule.decorators = [
1690
        { type: _angular_core__WEBPACK_IMPORTED_MODULE_0__["NgModule"], args: [{
1691
                    imports: [
1692
                        _angular_common__WEBPACK_IMPORTED_MODULE_8__["CommonModule"],
1693
                        _angular_platform_browser_animations__WEBPACK_IMPORTED_MODULE_9__["BrowserAnimationsModule"],
1694
                        _angular_platform_browser__WEBPACK_IMPORTED_MODULE_10__["BrowserModule"],
1695
                        _angular_common_http__WEBPACK_IMPORTED_MODULE_2__["HttpClientModule"],
1696
                        _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatSelectModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatInputModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatAutocompleteModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatProgressSpinnerModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatTooltipModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatChipsModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatIconModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatButtonModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatRadioModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatProgressBarModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatMenuModule"], _angular_material__WEBPACK_IMPORTED_MODULE_11__["MatTableModule"],
1697
                        _asymmetrik_ngx_leaflet__WEBPACK_IMPORTED_MODULE_12__["LeafletModule"].forRoot(), _asymmetrik_ngx_leaflet_draw__WEBPACK_IMPORTED_MODULE_13__["LeafletDrawModule"].forRoot(),
1698
                        _angular_forms__WEBPACK_IMPORTED_MODULE_6__["FormsModule"],
1699
                        _angular_forms__WEBPACK_IMPORTED_MODULE_6__["ReactiveFormsModule"]
1700
                    ],
1701
                    declarations: [TbGeolocLibComponent, MapComponent, OsmPlaceReadableAddressPipe],
1702
                    exports: [TbGeolocLibComponent, MapComponent]
1703
                },] },
1704
    ];
1705
    return TbGeolocLibModule;
1706
}());
1707
 
1708
/**
1709
 * @fileoverview added by tsickle
1710
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
1711
 */
1712
 
1713
/**
1714
 * @fileoverview added by tsickle
1715
 * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc
1716
 */
1717
 
1718
 
1719
 
1720
//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidGItZ2VvbG9jLWxpYi5qcy5tYXAiLCJzb3VyY2VzIjpbIm5nOi8vdGItZ2VvbG9jLWxpYi9saWIvdGItZ2VvbG9jLWxpYi5jb21wb25lbnQudHMiLCJuZzovL3RiLWdlb2xvYy1saWIvbGliL19oZWxwZXJzL2dlb0NvbnZlcnQudHMiLCJuZzovL3RiLWdlb2xvYy1saWIvbGliL19oZWxwZXJzL2xlYWZsZXRPYmplY3RzLnRzIiwibmc6Ly90Yi1nZW9sb2MtbGliL2xpYi9faGVscGVycy9kbXNUb29scy50cyIsIm5nOi8vdGItZ2VvbG9jLWxpYi9saWIvX3NlcnZpY2VzL2dlb2NvZGluZy5zZXJ2aWNlLnRzIiwibmc6Ly90Yi1nZW9sb2MtbGliL2xpYi9fc2VydmljZXMvZWxldmF0aW9uLnNlcnZpY2UudHMiLCJuZzovL3RiLWdlb2xvYy1saWIvbGliL21hcC9tYXAuY29tcG9uZW50LnRzIiwibmc6Ly90Yi1nZW9sb2MtbGliL2xpYi9fcGlwZXMvb3NtLXBsYWNlLXJlYWRhYmxlLWFkZHJlc3MucGlwZS50cyIsIm5nOi8vdGItZ2VvbG9jLWxpYi9saWIvdGItZ2VvbG9jLWxpYi5tb2R1bGUudHMiXSwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgQ29tcG9uZW50LCBPbkluaXQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcblxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAndGItZ2VvbG9jLXRiLWdlb2xvYy1saWInLFxuICB0ZW1wbGF0ZTogYGAsXG4gIHN0eWxlczogW11cbn0pXG5leHBvcnQgY2xhc3MgVGJHZW9sb2NMaWJDb21wb25lbnQgaW1wbGVtZW50cyBPbkluaXQge1xuXG4gIGNvbnN0cnVjdG9yKCkgeyB9XG5cbiAgbmdPbkluaXQoKSB7XG4gIH1cblxufVxuIiwiLyoqXG4gKiBHZW9Qb2ludFxuICpcbiAqIGh0dHBzOi8vZ2l0aHViLmNvbS9wZXJmZWN0bGluZS9nZW9wb2ludFxuICpcbiAqIEF1dGhvcnMgOlxuICogVGFuZWwgU3V1cmhhbnMgKGh0dHA6Ly90d2l0dGVyLmNvbS90YW5lbHN1dXJoYW5zKVxuICogVGFybW8gTGVodHB1dSAoaHR0cDovL3R3aXR0ZXIuY29tL3Rhcm1vbGVodHB1dSlcbiAqXG4gKiBMaWNlbnNlIDpcbiAqIENvcHlyaWdodCAyMDExIGJ5IFBlcmZlY3RMaW5lIExMQyAoaHR0cDovL3d3dy5wZXJmZWN0bGluZS5lZSkgYW5kIGlzIHJlbGVhc2VkIHVuZGVyIHRoZSBNSVQgbGljZW5zZS5cbiAqL1xuXG5leHBvcnQgY29uc3QgR2VvUG9pbnQgPSBmdW5jdGlvbihsb24sIGxhdCkge1xuXG5cbiAgc3dpdGNoICh0eXBlb2YobG9uKSkge1xuXG4gICAgICBjYXNlICdudW1iZXInOlxuXG4gICAgICAgICAgdGhpcy5sb25EZWcgPSB0aGlzLmRlYzJkZWcobG9uLCB0aGlzLk1BWF9MT04pO1xuICAgICAgICAgIHRoaXMubG9uRGVjID0gbG9uO1xuXG4gICAgICAgICAgYnJlYWs7XG5cbiAgICAgIGNhc2UgJ3N0cmluZyc6XG5cbiAgICAgICAgICBpZiAodGhpcy5kZWNvZGUobG9uKSkge1xuICAgICAgICAgICAgICB0aGlzLmxvbkRlZyA9IGxvbjtcbiAgICAgICAgICB9XG5cbiAgICAgICAgICB0aGlzLmxvbkRlYyA9IHRoaXMuZGVnMmRlYyhsb24sIHRoaXMuTUFYX0xPTik7XG5cbiAgICAgICAgICBicmVhaztcbiAgfVxuXG4gIHN3aXRjaCAodHlwZW9mKGxhdCkpIHtcblxuICAgICAgY2FzZSAnbnVtYmVyJzpcblxuICAgICAgICAgIHRoaXMubGF0RGVnID0gdGhpcy5kZWMyZGVnKGxhdCwgdGhpcy5NQVhfTEFUKTtcbiAgICAgICAgICB0aGlzLmxhdERlYyA9IGxhdDtcblxuICAgICAgICAgIGJyZWFrO1xuXG4gICAgICBjYXNlICdzdHJpbmcnOlxuXG4gICAgICAgICAgaWYgKHRoaXMuZGVjb2RlKGxhdCkpIHtcbiAgICAgICAgICAgICAgdGhpcy5sYXREZWcgPSBsYXQ7XG4gICAgICAgICAgfVxuXG4gICAgICAgICAgdGhpcy5sYXREZWMgPSB0aGlzLmRlZzJkZWMobGF0LCB0aGlzLk1BWF9MQVQpO1xuXG4gICAgICAgICAgYnJlYWs7XG5cbiAgfVxufTtcblxuR2VvUG9pbnQucHJvdG90eXBlID0ge1xuXG4gIENIQVJfREVHIDogJ1xcdTAwQjAnLFxuICBDSEFSX01JTiA6ICdcXHUwMDI3JyxcbiAgQ0hBUl9TRUMgOiAnXFx1MDAyMicsXG4gIENIQVJfU0VQIDogJ1xcdTAwMjAnLFxuXG4gIE1BWF9MT046IDE4MCxcbiAgTUFYX0xBVDogOTAsXG5cbiAgLy8gZGVjaW1hbFxuICBsb25EZWM6IE5hTixcbiAgbGF0RGVjOiBOYU4sXG5cbiAgLy8gZGVncmVlc1xuICBsb25EZWc6IE5hTixcbiAgbGF0RGVnOiBOYU4sXG5cbiAgZGVjMmRlZzogZnVuY3Rpb24odmFsdWUsIG1heCkge1xuXG4gICAgICBjb25zdCBzaWduID0gdmFsdWUgPCAwID8gLTEgOiAxO1xuXG4gICAgICBjb25zdCBhYnMgPSBNYXRoLmFicyhNYXRoLnJvdW5kKHZhbHVlICogMTAwMDAwMCkpO1xuXG4gICAgICBpZiAoYWJzID4gKG1heCAqIDEwMDAwMDApKSB7XG4gICAgICAgICAgcmV0dXJuIE5hTjtcbiAgICAgIH1cblxuICAgICAgY29uc3QgZGVjID0gYWJzICUgMTAwMDAwMCAvIDEwMDAwMDA7XG4gICAgICBjb25zdCBkZWcgPSBNYXRoLmZsb29yKGFicyAvIDEwMDAwMDApICogc2lnbjtcbiAgICAgIGNvbnN0IG1pbiA9IE1hdGguZmxvb3IoZGVjICogNjApO1xuICAgICAgY29uc3Qgc2VjID0gKGRlYyAtIG1pbiAvIDYwKSAqIDM2MDA7XG5cbiAgICAgIGxldCByZXN1bHQgPSAnJztcblxuICAgICAgcmVzdWx0ICs9IGRlZztcbiAgICAgIHJlc3VsdCArPSB0aGlzLkNIQVJfREVHO1xuICAgICAgcmVzdWx0ICs9IHRoaXMuQ0hBUl9TRVA7XG4gICAgICByZXN1bHQgKz0gbWluO1xuICAgICAgcmVzdWx0ICs9IHRoaXMuQ0hBUl9NSU47XG4gICAgICByZXN1bHQgKz0gdGhpcy5DSEFSX1NFUDtcbiAgICAgIHJlc3VsdCArPSBzZWMudG9GaXhlZCgyKTtcbiAgICAgIHJlc3VsdCArPSB0aGlzLkNIQVJfU0VDO1xuXG4gICAgICByZXR1cm4gcmVzdWx0O1xuXG4gIH0sXG5cbiAgZGVnMmRlYzogZnVuY3Rpb24odmFsdWUpIHtcblxuICAgICAgY29uc3QgbWF0Y2hlcyA9IHRoaXMuZGVjb2RlKHZhbHVlKTtcblxuICAgICAgaWYgKCFtYXRjaGVzKSB7XG4gICAgICAgICAgcmV0dXJuIE5hTjtcbiAgICAgIH1cblxuICAgICAgY29uc3QgZGVnID0gcGFyc2VGbG9hdChtYXRjaGVzWzFdKTtcbiAgICAgIGNvbnN0IG1pbiA9IHBhcnNlRmxvYXQobWF0Y2hlc1syXSk7XG4gICAgICBjb25zdCBzZWMgPSBwYXJzZUZsb2F0KG1hdGNoZXNbM10pO1xuXG4gICAgICBpZiAoaXNOYU4oZGVnKSB8fCBpc05hTihtaW4pIHx8IGlzTmFOKHNlYykpIHtcbiAgICAgICAgICByZXR1cm4gTmFOO1xuICAgICAgfVxuXG4gICAgICByZXR1cm4gZGVnICsgKG1pbiAvIDYwLjApICsgKHNlYyAvIDM2MDApO1xuICB9LFxuXG4gIGRlY29kZTogZnVuY3Rpb24odmFsdWUpIHtcbiAgICAgIGxldCBwYXR0ZXJuID0gJyc7XG5cbiAgICAgIC8vIGRlZ1xuICAgICAgcGF0dGVybiArPSAnKC0/XFxcXGQrKSc7XG4gICAgICBwYXR0ZXJuICs9IHRoaXMuQ0hBUl9ERUc7XG4gICAgICBwYXR0ZXJuICs9ICdcXFxccyonO1xuXG4gICAgICAvLyBtaW5cbiAgICAgIHBhdHRlcm4gKz0gJyhcXFxcZCspJztcbiAgICAgIHBhdHRlcm4gKz0gdGhpcy5DSEFSX01JTjtcbiAgICAgIHBhdHRlcm4gKz0gJ1xcXFxzKic7XG5cbiAgICAgIC8vIHNlY1xuICAgICAgcGF0dGVybiArPSAnKFxcXFxkKyg/OlxcXFwuXFxcXGQrKT8pJztcbiAgICAgIHBhdHRlcm4gKz0gdGhpcy5DSEFSX1NFQztcblxuICAgICAgcmV0dXJuIHZhbHVlLm1hdGNoKG5ldyBSZWdFeHAocGF0dGVybikpO1xuICB9LFxuXG4gIGdldExvbkRlYzogZnVuY3Rpb24oKSB7XG4gICAgICByZXR1cm4gdGhpcy5sb25EZWM7XG4gIH0sXG5cbiAgZ2V0TGF0RGVjOiBmdW5jdGlvbigpIHtcbiAgICAgIHJldHVybiB0aGlzLmxhdERlYztcbiAgfSxcblxuICBnZXRMb25EZWc6IGZ1bmN0aW9uKCkge1xuICAgICAgcmV0dXJuIHRoaXMubG9uRGVnO1xuICB9LFxuXG4gIGdldExhdERlZzogZnVuY3Rpb24oKSB7XG4gICAgICByZXR1cm4gdGhpcy5sYXREZWc7XG4gIH1cblxufTtcbiIsIi8qKlxuICpcbiAqL1xuXG5pbXBvcnQgKiBhcyBMIGZyb20gJ2xlYWZsZXQnO1xuXG4vKipcbiAqXG4gKiBAcGFyYW0gbGF0XG4gKiBAcGFyYW0gbG5nXG4gKiBAcGFyYW0gZHJhZ2VuZCBjYWxsYmFja1xuICovXG5leHBvcnQgY29uc3QgZHJhZ2dhYmxlTWFya2VyID0gZnVuY3Rpb24obGF0OiBudW1iZXIsIGxuZzogbnVtYmVyLCBkcmFnZW5kOiBGdW5jdGlvbik6IEwuTWFya2VyIHtcbiAgY29uc3Qgc2ltcGxlSWNvbiA9IHNpbXBsZUljb25NYXJrZXIoKTtcbiAgY29uc3QgbWFya2VyID0gTC5tYXJrZXIoW2xhdCwgbG5nXSwge2ljb246IHNpbXBsZUljb24sIGRyYWdnYWJsZTogdHJ1ZX0pO1xuICBtYXJrZXIub24oJ2RyYWdlbmQnLCBmdW5jdGlvbihldmVudCkgeyByZXR1cm4gZHJhZ2VuZChldmVudCk7IH0pO1xuICByZXR1cm4gbWFya2VyO1xufTtcblxuLyoqXG4gKlxuICovXG5leHBvcnQgY29uc3Qgc2ltcGxlSWNvbk1hcmtlciA9IGZ1bmN0aW9uKCk6IEwuSWNvbiB7XG4gIHJldHVybiBMLmljb24oe1xuICAgIGljb25Vcmw6ICcuL2Fzc2V0cy9pbWcvbWFwL21hcmtlci1pY29uLnBuZycsXG4gICAgc2hhZG93VXJsOiAnLi9hc3NldHMvaW1nL21hcC9tYXJrZXItc2hhZG93LnBuZycsXG4gICAgaWNvbkFuY2hvcjogWzEzLCA0MF1cbiAgfSk7XG59O1xuXG4vKipcbiAqXG4gKi9cbmV4cG9ydCBjb25zdCBkcmF3Q29udHJvbFBhbmVsID0gbmV3IEwuQ29udHJvbC5EcmF3KHtcbiAgcG9zaXRpb246ICd0b3BsZWZ0JyxcbiAgZHJhdzoge1xuICAgIG1hcmtlcjogeyBpY29uOiBzaW1wbGVJY29uTWFya2VyKCkgfSxcbiAgICBwb2x5bGluZToge30sXG4gICAgcG9seWdvbjogeyBzaG93QXJlYTogdHJ1ZSwgbWV0cmljOiBmYWxzZSB9LFxuICAgIHJlY3RhbmdsZTogZmFsc2UsXG4gICAgY2lyY2xlOiBmYWxzZSxcbiAgICBjaXJjbGVtYXJrZXI6IGZhbHNlXG4gIH1cbn0pO1xuXG4vKipcbiAqXG4gKiBAcGFyYW0gZWRpdGVkTGF5ZXJcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGRyYXdDb250cm9sRWRpdFBhbmVsKGVkaXRlZExheWVyKSB7XG4gIHJldHVybiBuZXcgTC5Db250cm9sLkRyYXcoe1xuICAgIHBvc2l0aW9uOiAndG9wbGVmdCcsXG4gICAgZHJhdzoge1xuICAgICAgbWFya2VyOiBmYWxzZSxcbiAgICAgIHBvbHlsaW5lOiBmYWxzZSxcbiAgICAgIHBvbHlnb246IGZhbHNlLFxuICAgICAgcmVjdGFuZ2xlOiBmYWxzZSxcbiAgICAgIGNpcmNsZTogZmFsc2UsXG4gICAgICBjaXJjbGVtYXJrZXI6IGZhbHNlXG4gICAgfSxcbiAgICBlZGl0OiB7XG4gICAgICBmZWF0dXJlR3JvdXA6IGVkaXRlZExheWVyLCAvLyB0aGlzIHBhbmVsIGlkIGVkaXRpbmcgZWRpdGVkTGF5ZXJcbiAgICAgIGVkaXQ6IHt9LFxuICAgICAgcmVtb3ZlOiB7fVxuICAgIH1cbiAgfSk7XG59XG5cbi8qKlxuICpcbiAqL1xuZXhwb3J0IGNvbnN0IGNpcmNsZU1hcmtlclN0eWxlID0ge1xuICByYWRpdXM6IDYsXG4gIGZpbGxDb2xvcjogJyNmZjc4MDAnLFxuICBjb2xvcjogJyMwMDAnLFxuICB3ZWlnaHQ6IDEsXG4gIG9wYWNpdHk6IDEsXG4gIGZpbGxPcGFjaXR5OiAwLjhcbn07XG5cbi8qKlxuICpcbiAqL1xuZXhwb3J0IGNvbnN0IGNpdHlTdHlsZSA9IHtcbiAgY29sb3I6ICcjZmY3ODAwJyxcbiAgICB3ZWlnaHQ6IDUsXG4gICAgb3BhY2l0eTogMC42NVxufTtcblxuLyoqXG4gKlxuICovXG5leHBvcnQgY29uc3QgZ3BzUGhvdG9NYXJrZXJJY29uID0gKCk6IEwuSWNvbiA9PiB7XG4gIHJldHVybiBMLmljb24oe1xuICAgIGljb25Vcmw6ICcuL2Fzc2V0cy9pbWcvbWFwL3Bob3RvLW1hcmtlci1pY29uLnBuZycsXG4gICAgc2hhZG93VXJsOiAnLi9hc3NldHMvaW1nL21hcC9tYXJrZXItc2hhZG93LnBuZycsXG5cbiAgICBpY29uU2l6ZTogICAgIFszMywgNDFdLCAvLyBzaXplIG9mIHRoZSBpY29uXG4gICAgLy8gc2hhZG93U2l6ZTogICBbNTAsIDY0XSwgLy8gc2l6ZSBvZiB0aGUgc2hhZG93XG4gICAgaWNvbkFuY2hvcjogICBbMTMsIDQwXSwgLy8gcG9pbnQgb2YgdGhlIGljb24gd2hpY2ggd2lsbCBjb3JyZXNwb25kIHRvIG1hcmtlcidzIGxvY2F0aW9uXG4gICAgLy8gc2hhZG93QW5jaG9yOiBbNCwgNjJdLCAgLy8gdGhlIHNhbWUgZm9yIHRoZSBzaGFkb3dcbiAgICBwb3B1cEFuY2hvcjogIFs1LCAtNDFdIC8vIHBvaW50IGZyb20gd2hpY2ggdGhlIHBvcHVwIHNob3VsZCBvcGVuIHJlbGF0aXZlIHRvIHRoZSBpY29uQW5jaG9yXG4gIH0pO1xufTtcblxuLyoqXG4gKlxuICovXG5leHBvcnQgY29uc3QgZ3BzUGhvdG9NYXJrZXJJY29uSGlnaGxpZ2h0ID0gKCk6IEwuSWNvbiA9PiB7XG4gIHJldHVybiBMLmljb24oe1xuICAgIGljb25Vcmw6ICcuL2Fzc2V0cy9pbWcvbWFwL3Bob3RvLW1hcmtlci1pY29uLnBuZycsXG4gICAgc2hhZG93VXJsOiAnLi9hc3NldHMvaW1nL21hcC9tYXJrZXItc2hhZG93LnBuZycsXG5cbiAgICBpY29uU2l6ZTogICAgIFs0MywgNTRdLCAvLyBzaXplIG9mIHRoZSBpY29uXG4gICAgLy8gc2hhZG93U2l6ZTogICBbNTAsIDY0XSwgLy8gc2l6ZSBvZiB0aGUgc2hhZG93XG4gICAgaWNvbkFuY2hvcjogICBbMTMsIDQwXSwgLy8gcG9pbnQgb2YgdGhlIGljb24gd2hpY2ggd2lsbCBjb3JyZXNwb25kIHRvIG1hcmtlcidzIGxvY2F0aW9uXG4gICAgLy8gc2hhZG93QW5jaG9yOiBbNCwgNjJdLCAgLy8gdGhlIHNhbWUgZm9yIHRoZSBzaGFkb3dcbiAgICBwb3B1cEFuY2hvcjogIFswLCAtNzZdIC8vIHBvaW50IGZyb20gd2hpY2ggdGhlIHBvcHVwIHNob3VsZCBvcGVuIHJlbGF0aXZlIHRvIHRoZSBpY29uQW5jaG9yXG4gIH0pO1xufTtcbiIsIi8qKlxuICogQXV0byBmb3JtYXQgYSBETVMgY29vcmRpbmF0ZXNcbiAqIGVnLiB1c2VyIGNhbiBlbnRlciA0MyAwIDE0Ljc3XG4gKiBhbmQgdGhlIGZvcm1hdHRlciByZXR1cm5zIDQzw4LCsCAwJyAxNC43N1wiXG4gKiArIGF2b2lkIGVudGVyIG5vbiBudW1lcmljIChvciAuICwpIGNoYXJhY3RlcnNcbiAqICsgZm9yY2UgZW50aXJlIG51bWJlcnMgZm9yIGRlZ3JlZXMgYW5kIG1pbnV0ZXNcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGRtc0Zvcm1hdHRlcihkbXNTdHI6IHN0cmluZyk6IHN0cmluZyB7XG4gIHRyeSB7XG4gICAgLy8gcmVwbGFjZSBtdWx0aXBsZXMgc3BhY2VzXG4gICAgZG1zU3RyID0gZG1zU3RyLnJlcGxhY2UoL1xcc1xccysvZywgJyAnKTtcbiAgICAvLyByZXBsYWNlIHNwYWNlIGF0IGZpcnN0IHBvc2l0aW9uXG4gICAgaWYgKGRtc1N0ci5jaGFyQXQoMCkgPT09ICcgJykgeyBkbXNTdHIgPSBkbXNTdHIuc2xpY2UoMSwgZG1zU3RyLmxlbmd0aCAtIDEpOyB9XG4gICAgLy8gcmVwbGFjZSAsIGJ5IC5cbiAgICBkbXNTdHIgPSBkbXNTdHIucmVwbGFjZSgnLCcsICcuJyk7XG4gICAgLy8gZGVsZXRlIGFsbCBub24gbnVtZXJpYyBjaGFyYWN0ZXJzXG4gICAgZG1zU3RyID0gZG1zU3RyLnJlcGxhY2UoL1teMC05XFwtLizDgsKwXFwnXCJcXHNdL2csICcnKTtcblxuICAgIGxldCBuYlNwYWNlczogbnVtYmVyO1xuICAgIGxldCBkZWdDaHIgPSAnJztcbiAgICBsZXQgbWluQ2hyID0gJyc7XG4gICAgbGV0IHNlY0NociA9ICcnO1xuXG4gICAgbGV0IHYgPSBkbXNTdHIuc3BsaXQoJyAnKTtcbiAgICAvLyByZW1vdmUgbGFzdCBzcGFjZSBvZCBpbnB1dCBzdHJpbmdcbiAgICBpZiAoZG1zU3RyLmNoYXJBdChkbXNTdHIubGVuZ3RoIC0gMSkgPT09ICcgJykge1xuICAgICAgdiA9IHYuc2xpY2UoMCAsIHYubGVuZ3RoIC0gMSk7XG4gICAgfVxuICAgIC8vIHJlbW92ZSBsYXN0IGl0ZW0gb2YgdiBhcnJheSBpZiBpdCdzIGVtcHR5XG4gICAgaWYgKHZbdi5sZW5ndGggLSAxXSA9PT0gJycpIHtcbiAgICAgIHYgPSB2LnNsaWNlKDAgLCB2Lmxlbmd0aCAtIDEpO1xuICAgIH1cbiAgICBpZiAodi5sZW5ndGggPT09IDEpIHtcbiAgICAgIGRlZ0NociA9IHZbMF07XG4gICAgICAvLyBkZWdDaHIgbXVzdCBiZSBhbiBlbnRpcmUgbnVtYmVyXG4gICAgICBpZiAoZGVnQ2hyLmluZGV4T2YoJy4nKSAhPT0gLTEpIHsgZGVnQ2hyID0gZGVnQ2hyLnNsaWNlKDAsIGRlZ0Noci5pbmRleE9mKCcuJykpOyB9XG4gICAgICAvLyBiZXR3ZWVuIC05MCAmICs5MFxuICAgICAgaWYgKE51bWJlcihkZWdDaHIpIDwgLTkwKSB7IGRlZ0NociA9ICctOTAnOyB9XG4gICAgICBpZiAoTnVtYmVyKGRlZ0NocikgPiA5MCkgeyBkZWdDaHIgPSAnOTAnOyB9XG4gICAgfVxuICAgIGlmICh2Lmxlbmd0aCA9PT0gMikge1xuICAgICAgZGVnQ2hyID0gdlswXTsgbWluQ2hyID0gdlsxXTtcbiAgICAgIGlmIChkZWdDaHIuaW5kZXhPZignLicpICE9PSAtMSkgeyBkZWdDaHIgPSBkZWdDaHIuc2xpY2UoMCwgZGVnQ2hyLmluZGV4T2YoJy4nKSk7IH1cbiAgICAgIGlmIChtaW5DaHIuaW5kZXhPZignLicpICE9PSAtMSkgeyBtaW5DaHIgPSBtaW5DaHIuc2xpY2UoMCwgZGVnQ2hyLmluZGV4T2YoJy4nKSk7IH1cbiAgICAgIGlmIChOdW1iZXIoZGVnQ2hyKSA8IC05MCkgeyBkZWdDaHIgPSAnLTkwJzsgfVxuICAgICAgaWYgKE51bWJlcihkZWdDaHIpID4gOTApIHsgZGVnQ2hyID0gJzkwJzsgfVxuICAgICAgaWYgKE51bWJlcihtaW5DaHIpIDwgLTkwKSB7IG1pbkNociA9ICctOTAnOyB9XG4gICAgICBpZiAoTnVtYmVyKG1pbkNocikgPiA5MCkgeyBtaW5DaHIgPSAnOTAnOyB9XG4gICAgICB9XG4gICAgaWYgKHYubGVuZ3RoID09PSAzKSB7XG4gICAgICBkZWdDaHIgPSB2WzBdOyBtaW5DaHIgPSB2WzFdOyBzZWNDaHIgPSB2WzJdO1xuICAgICAgaWYgKGRlZ0Noci5pbmRleE9mKCcuJykgIT09IC0xKSB7IGRlZ0NociA9IGRlZ0Noci5zbGljZSgwLCBkZWdDaHIuaW5kZXhPZignLicpKTsgfVxuICAgICAgaWYgKG1pbkNoci5pbmRleE9mKCcuJykgIT09IC0xKSB7IG1pbkNociA9IG1pbkNoci5zbGljZSgwLCBkZWdDaHIuaW5kZXhPZignLicpKTsgfVxuICAgICAgaWYgKE51bWJlcihkZWdDaHIpIDwgLTkwKSB7IGRlZ0NociA9ICctOTAnOyB9XG4gICAgICBpZiAoTnVtYmVyKGRlZ0NocikgPiA5MCkgeyBkZWdDaHIgPSAnOTAnOyB9XG4gICAgICBpZiAoTnVtYmVyKG1pbkNocikgPCAtOTApIHsgbWluQ2hyID0gJy05MCc7IH1cbiAgICAgIGlmIChOdW1iZXIobWluQ2hyKSA+IDkwKSB7IG1pbkNociA9ICc5MCc7IH1cbiAgICAgIH1cbiAgICBpZiAodi5sZW5ndGggPj0gNCkge1xuICAgICAgdiA9IHYuc2xpY2UoMCwgMik7XG4gICAgICBpZiAoZGVnQ2hyLmluZGV4T2YoJy4nKSAhPT0gLTEpIHsgZGVnQ2hyID0gZGVnQ2hyLnNsaWNlKDAsIGRlZ0Noci5pbmRleE9mKCcuJykpOyB9XG4gICAgICBpZiAobWluQ2hyLmluZGV4T2YoJy4nKSAhPT0gLTEpIHsgbWluQ2hyID0gbWluQ2hyLnNsaWNlKDAsIGRlZ0Noci5pbmRleE9mKCcuJykpOyB9XG4gICAgICBpZiAoTnVtYmVyKGRlZ0NocikgPCAtOTApIHsgZGVnQ2hyID0gJy05MCc7IH1cbiAgICAgIGlmIChOdW1iZXIoZGVnQ2hyKSA+IDkwKSB7IGRlZ0NociA9ICc5MCc7IH1cbiAgICAgIGlmIChOdW1iZXIobWluQ2hyKSA8IC05MCkgeyBtaW5DaHIgPSAnLTkwJzsgfVxuICAgICAgaWYgKE51bWJlcihtaW5DaHIpID4gOTApIHsgbWluQ2hyID0gJzkwJzsgfVxuICAgIH1cblxuICAgIHRyeSB7XG4gICAgICBuYlNwYWNlcyA9IGRtc1N0ci5tYXRjaCgvXFxzL2cpLmxlbmd0aDtcbiAgICB9IGNhdGNoIChlKSB7XG4gICAgICBuYlNwYWNlcyA9IDA7XG4gICAgfVxuICAgIGlmIChuYlNwYWNlcyA9PT0gMCAmJiB2Lmxlbmd0aCA9PT0gMSnDgsKge1xuICAgICAgLy8gZG8gbm90aGluZ1xuICAgIH0gZWxzZSBpZiAobmJTcGFjZXMgPT09IDEgJiYgdi5sZW5ndGggPj0gMSkge1xuICAgICAgZGVnQ2hyID0gZGVnQ2hyLnJlcGxhY2UoJyAnLCAnJyk7XG4gICAgICBpZiAoZGVnQ2hyLnNsaWNlKGRlZ0Noci5sZW5ndGggLSAxLCBkZWdDaHIubGVuZ3RoKSAhPT0gJ8OCwrAnKSB7IGRlZ0NociArPSAnw4LCsCAnOyB9IGVsc2UgeyBkZWdDaHIgKz0gJyAnOyB9XG4gICAgfSBlbHNlIGlmIChuYlNwYWNlcyA9PT0gMiAmJiB2Lmxlbmd0aCA+PSAyKSB7XG4gICAgICBkZWdDaHIgPSBkZWdDaHIucmVwbGFjZSgnICcsICcnKTtcbiAgICAgIG1pbkNociA9IG1pbkNoci5yZXBsYWNlKCcgJywgJycpO1xuICAgICAgaWYgKGRlZ0Noci5zbGljZShkZWdDaHIubGVuZ3RoIC0gMSwgZGVnQ2hyLmxlbmd0aCkgIT09ICfDgsKwJykgeyBkZWdDaHIgKz0gJ8OCwrAgJzsgfSBlbHNlIHsgZGVnQ2hyICs9ICcgJzsgfVxuICAgICAgaWYgKG1pbkNoci5zbGljZShtaW5DaHIubGVuZ3RoIC0gMSwgbWluQ2hyLmxlbmd0aCkgIT09ICdcXCcnKSB7IG1pbkNociArPSAnXFwnICc7IH0gZWxzZSB7IG1pbkNociArPSAnICc7IH1cbiAgICB9IGVsc2UgaWYgKG5iU3BhY2VzID09PSAzICYmIHYubGVuZ3RoID49IDMpIHtcbiAgICAgIGRlZ0NociA9IGRlZ0Noci5yZXBsYWNlKCcgJywgJycpO1xuICAgICAgbWluQ2hyID0gbWluQ2hyLnJlcGxhY2UoJyAnLCAnJyk7XG4gICAgICBzZWNDaHIgPSBzZWNDaHIucmVwbGFjZSgnICcsICcnKTtcbiAgICAgIGlmIChkZWdDaHIuc2xpY2UoZGVnQ2hyLmxlbmd0aCAtIDEsIGRlZ0Noci5sZW5ndGgpICE9PSAnw4LCsCcpIHsgZGVnQ2hyICs9ICfDgsKwICc7IH0gZWxzZSB7IGRlZ0NociArPSAnICc7IH1cbiAgICAgIGlmIChtaW5DaHIuc2xpY2UobWluQ2hyLmxlbmd0aCAtIDEsIG1pbkNoci5sZW5ndGgpICE9PSAnXFwnJykgeyBtaW5DaHIgKz0gJ1xcJyAnOyB9IGVsc2UgeyBtaW5DaHIgKz0gJyAnOyB9XG4gICAgICBpZiAoc2VjQ2hyLnNsaWNlKHNlY0Noci5sZW5ndGggLSAxLCBzZWNDaHIubGVuZ3RoKSAhPT0gJ1wiJykgeyBzZWNDaHIgKz0gJ1wiJzsgfVxuICAgIH0gZWxzZSB7XG4gICAgICB0aHJvdyB7IGVycm9yOiAnQ2FuXFwndCBtYW5hZ2UgaW5wdXQgc3RyaW5nLicgfTtcbiAgICB9XG5cbiAgICByZXR1cm4gZGVnQ2hyICsgbWluQ2hyICsgc2VjQ2hyO1xuXG4gIH0gY2F0Y2ggKGUpIHtcbiAgICByZXR1cm4gZG1zU3RyO1xuICB9XG59XG4iLCJpbXBvcnQgeyBJbmplY3RhYmxlIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBIdHRwQ2xpZW50IH0gZnJvbSAnQGFuZ3VsYXIvY29tbW9uL2h0dHAnO1xuaW1wb3J0IHsgT2JzZXJ2YWJsZSwgZW1wdHksIG9mIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBtYXAgfSBmcm9tICdyeGpzL29wZXJhdG9ycyc7XG5pbXBvcnQgeyBOb21pbmF0aW1PYmplY3QgfSBmcm9tICcuLi9fbW9kZWxzL25vbWluYXRpbU9iai5tb2RlbCc7XG5pbXBvcnQgeyBPc21QbGFjZU1vZGVsIH0gZnJvbSAnLi4vX21vZGVscy9vc21QbGFjZS5tb2RlbCc7XG5pbXBvcnQgeyBpc0RlZmluZWQgfSBmcm9tICdAYW5ndWxhci9jb21waWxlci9zcmMvdXRpbCc7XG5cbkBJbmplY3RhYmxlKHtcbiAgcHJvdmlkZWRJbjogJ3Jvb3QnXG59KVxuZXhwb3J0IGNsYXNzIEdlb2NvZGluZ1NlcnZpY2Uge1xuXG4gIGNvbnN0cnVjdG9yKHByaXZhdGUgaHR0cDogSHR0cENsaWVudCkgeyB9XG5cbiAgZ2VvY29kZShhZGRyZXNzOiBzdHJpbmcpOiBPYnNlcnZhYmxlPGFueT4ge1xuICAgIGlmIChhZGRyZXNzID09PSBudWxsKSB7IHJldHVybiBlbXB0eSgpOyB9IC8vIEF2b2lkIHNlbmRpbmcgcmVxdWVzdCBvbiBmb3JtIHJlc2V0XG4gICAgY29uc3QgdXJsID0gYGh0dHBzOi8vbm9taW5hdGltLm9wZW5zdHJlZXRtYXAub3JnLz9mb3JtYXQ9anNvbiZhZGRyZXNzZGV0YWlscz0xJnE9JHthZGRyZXNzfSZmb3JtYXQ9anNvbiZsaW1pdD0xMCZwb2x5Z29uX2dlb2pzb249MWA7XG4gICAgcmV0dXJuIHRoaXMuaHR0cC5nZXQodXJsKS5waXBlKFxuICAgICAgbWFwKChvYmo6IE5vbWluYXRpbU9iamVjdCkgPT4gb2JqKVxuICAgICk7XG4gIH1cblxuICByZXZlcnNlKGxhdDogbnVtYmVyLCBsbmc6IG51bWJlcik6IE9ic2VydmFibGU8YW55PiB7XG4gICAgY29uc3QgdXJsID0gYGh0dHBzOi8vbm9taW5hdGltLm9wZW5zdHJlZXRtYXAub3JnL3JldmVyc2U/Zm9ybWF0PWpzb24mbGF0PSR7bGF0fSZsb249JHtsbmd9JnBvbHlnb25fZ2VvanNvbj0xYDtcbiAgICByZXR1cm4gdGhpcy5odHRwLmdldCh1cmwpLnBpcGUoXG4gICAgICBtYXAoKG9iajogTm9taW5hdGltT2JqZWN0KSA9PiBvYmopXG4gICAgKTtcbiAgfVxuXG4gIGdldFJlYWRibGVBZGRyZXNzKG9zbVBsYWNlUmVzdWx0OiBPc21QbGFjZU1vZGVsKTogc3RyaW5nIHtcbiAgICBsZXQgbG9jYWxpdHk6IHN0cmluZyA9IG51bGw7ICAgIC8vIGNpdHkgb3IgdmlsbGFnZSBvciAuLi5cbiAgICBsZXQgc3ViTG9jYWxpdHk6IHN0cmluZyA9IG51bGw7IC8vIGRpc3RyaWN0IG9yXG4gICAgbGV0IHJvYWQ6IHN0cmluZyA9IG51bGw7XG4gICAgbGV0IG5laWdoYm91cmhvb2Q6IHN0cmluZyA9IG51bGw7XG5cbiAgICAvLyBHZXQgXCJjaXR5XCIgaW5mb3JtYXRpb24gKEkgbWVhbiBjaXR5IG9yIHNvbWV0aGluZyBzaW1pbGFyIGxpa2UgdmlsbGFnZSlcbiAgICBpZiAoaXNEZWZpbmVkKG9zbVBsYWNlUmVzdWx0LmFkZHJlc3MuY2l0eSkpIHsgbG9jYWxpdHkgPSBvc21QbGFjZVJlc3VsdC5hZGRyZXNzLmNpdHk7XG4gICAgfSBlbHNlIGlmIChpc0RlZmluZWQob3NtUGxhY2VSZXN1bHQuYWRkcmVzcy50b3duKSkgeyBsb2NhbGl0eSA9IG9zbVBsYWNlUmVzdWx0LmFkZHJlc3MudG93bjtcbiAgICB9IGVsc2UgaWYgKGlzRGVmaW5lZChvc21QbGFjZVJlc3VsdC5hZGRyZXNzLnZpbGxhZ2UpKSB7IGxvY2FsaXR5ID0gb3NtUGxhY2VSZXN1bHQuYWRkcmVzcy52aWxsYWdlO1xuICAgIH0gZWxzZSBpZiAoaXNEZWZpbmVkKG9zbVBsYWNlUmVzdWx0LmFkZHJlc3MuaGFtbGV0KSkgeyBsb2NhbGl0eSA9IG9zbVBsYWNlUmVzdWx0LmFkZHJlc3MuaGFtbGV0OyB9XG5cbiAgICAvLyBHZXQgc3VidXJiciAmIGlmIG5vdCBkZWZpbmVkIDogcG9zdGNvZGVcbiAgICBpZiAoaXNEZWZpbmVkKG9zbVBsYWNlUmVzdWx0LmFkZHJlc3Muc3VidXJiKSAmJiBpc0RlZmluZWQob3NtUGxhY2VSZXN1bHQuYWRkcmVzcy5wb3N0Y29kZSkgJiYgbG9jYWxpdHkgIT09IG51bGwpIHtcbiAgICAgIHN1YkxvY2FsaXR5ID0gb3NtUGxhY2VSZXN1bHQuYWRkcmVzcy5zdWJ1cmIgKyAnLCAnICsgb3NtUGxhY2VSZXN1bHQuYWRkcmVzcy5wb3N0Y29kZTtcbiAgICB9IGVsc2UgaWYgKCFpc0RlZmluZWQob3NtUGxhY2VSZXN1bHQuYWRkcmVzcy5zdWJ1cmIpICYmIGlzRGVmaW5lZChvc21QbGFjZVJlc3VsdC5hZGRyZXNzLnBvc3Rjb2RlKSAmJiBsb2NhbGl0eSAhPT0gbnVsbCkge1xuICAgICAgc3ViTG9jYWxpdHkgPSBvc21QbGFjZVJlc3VsdC5hZGRyZXNzLnBvc3Rjb2RlO1xuICAgIH1cblxuICAgIC8vIEdldCBcInJvYWRcIlxuICAgIGlmIChpc0RlZmluZWQob3NtUGxhY2VSZXN1bHQuYWRkcmVzcy5yb2FkKSkge1xuICAgICAgcm9hZCA9IG9zbVBsYWNlUmVzdWx0LmFkZHJlc3Mucm9hZDtcbiAgICB9IGVsc2UgaWYgKGlzRGVmaW5lZChvc21QbGFjZVJlc3VsdC5hZGRyZXNzLnBlZGVzdHJpYW4pKSB7XG4gICAgICByb2FkID0gb3NtUGxhY2VSZXN1bHQuYWRkcmVzcy5wZWRlc3RyaWFuO1xuICAgIH1cblxuICAgIC8vIEdldCBuZWlnaGJvdXJob29kXG4gICAgaWYgKGlzRGVmaW5lZChvc21QbGFjZVJlc3VsdC5hZGRyZXNzLm5laWdoYm91cmhvb2QpKSB7XG4gICAgICBuZWlnaGJvdXJob29kID0gb3NtUGxhY2VSZXN1bHQuYWRkcmVzcy5uZWlnaGJvdXJob29kO1xuICAgIH1cblxuICAgIC8vIFJldHVyblxuICAgIGlmIChyb2FkICYmIG5laWdoYm91cmhvb2QgJiYgc3ViTG9jYWxpdHkgJiYgbG9jYWxpdHkpIHtcbiAgICAgIHJldHVybiByb2FkICsgJyAoJyArIG5laWdoYm91cmhvb2QgKyAnKSAnICsgc3ViTG9jYWxpdHkgKyAnICcgKyBsb2NhbGl0eTtcbiAgICB9IGVsc2UgaWYgKHJvYWQgJiYgIW5laWdoYm91cmhvb2QgJiYgc3ViTG9jYWxpdHkgJiYgbG9jYWxpdHkpIHtcbiAgICAgIHJldHVybiByb2FkICsgJyAnICsgc3ViTG9jYWxpdHkgKyAnICcgKyBsb2NhbGl0eTtcbiAgICB9IGVsc2UgaWYgKCFyb2FkICYmIG5laWdoYm91cmhvb2QgJiYgc3ViTG9jYWxpdHkgJiYgbG9jYWxpdHkpIHtcbiAgICAgIHJldHVybiBuZWlnaGJvdXJob29kICsgJyAnICsgc3ViTG9jYWxpdHkgKyAnICcgKyBsb2NhbGl0eTtcbiAgICB9IGVsc2UgaWYgKCFyb2FkICYmICFuZWlnaGJvdXJob29kICYmIHN1YkxvY2FsaXR5ICYmIGxvY2FsaXR5KSB7XG4gICAgICByZXR1cm4gc3ViTG9jYWxpdHkgKyAnICcgKyBsb2NhbGl0eTtcbiAgICB9IGVsc2UgaWYgKCFyb2FkICYmICFuZWlnaGJvdXJob29kICYmICFzdWJMb2NhbGl0eSAmJiBsb2NhbGl0eSkge1xuICAgICAgcmV0dXJuIGxvY2FsaXR5O1xuICAgIH0gZWxzZSB7XG4gICAgICByZXR1cm4gb3NtUGxhY2VSZXN1bHQuZGlzcGxheV9uYW1lO1xuICAgIH1cblxuICB9XG5cbiAgb3NtQ2xhc3NGaWx0ZXIob3NtQ2xhc3NGaWx0ZXI6IEFycmF5PHN0cmluZz4sIG9zbVJlc3VsdHM6IEFycmF5PE5vbWluYXRpbU9iamVjdD4pIHtcbiAgICBjb25zdCBvc21GaWx0ZXJlZFJlc3VsdHM6IEFycmF5PE5vbWluYXRpbU9iamVjdD4gPSBbXTtcbiAgICBpZiAob3NtQ2xhc3NGaWx0ZXIubGVuZ3RoID4gMCAmJiBvc21SZXN1bHRzLmxlbmd0aCA+IDApIHtcbiAgICAgIG9zbVJlc3VsdHMuZm9yRWFjaChvc21JdGVtID0+IHtcbiAgICAgICAgbGV0IGZpbHRlck1hdGNoT2NjdXJlbmNlID0gMDtcbiAgICAgICAgbGV0IHJlbW92ZU9jY3VyZW5jZSAgID0gZmFsc2U7XG4gICAgICAgIG9zbUNsYXNzRmlsdGVyLmZvckVhY2gob3NtRmlsdGVySXRlbSA9PiB7XG4gICAgICAgICAgY29uc3QgX2NsYXNzID0gb3NtRmlsdGVySXRlbS5zcGxpdCgnOicpWzBdO1xuICAgICAgICAgIGNvbnN0IF90eXBlID0gb3NtRmlsdGVySXRlbS5zcGxpdCgnOicpWzFdO1xuICAgICAgICAgIGlmIChfdHlwZSA9PT0gJyonKSB7XG4gICAgICAgICAgICBpZiAob3NtSXRlbS5jbGFzcyA9PT0gX2NsYXNzKSB7IGZpbHRlck1hdGNoT2NjdXJlbmNlKys7IH1cbiAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgLy8gaWYgISwgcmVtb3ZlXG4gICAgICAgICAgICBpZiAoX3R5cGUuc3Vic3RyKDAsIDEpID09PSAnIScpIHtcbiAgICAgICAgICAgICAgaWYgKG9zbUl0ZW0uY2xhc3MgPT09IF9jbGFzcyAmJiAnIScgKyBvc21JdGVtLnR5cGUgPT09IF90eXBlKSB7IHJlbW92ZU9jY3VyZW5jZSA9IHRydWU7IH1cbiAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgIGlmIChvc21JdGVtLmNsYXNzID09PSBfY2xhc3MgJiYgb3NtSXRlbS50eXBlID09PSBfdHlwZSkgeyBmaWx0ZXJNYXRjaE9jY3VyZW5jZSsrOyB9XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICAgICAgaWYgKGZpbHRlck1hdGNoT2NjdXJlbmNlID4gMCAmJiAhcmVtb3ZlT2NjdXJlbmNlKSB7XG4gICAgICAgICAgb3NtRmlsdGVyZWRSZXN1bHRzLnB1c2gob3NtSXRlbSk7XG4gICAgICAgIH1cbiAgICAgIH0pO1xuICAgICAgcmV0dXJuIG9mKG9zbUZpbHRlcmVkUmVzdWx0cyk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHJldHVybiBvZihvc21SZXN1bHRzKTtcbiAgICB9XG4gIH1cblxuICByZXZlcnNlQ29ycmRpbmF0ZXNBcnJheShjb29yZGluYXRlc0FycmF5OiBBcnJheTxbbnVtYmVyLCBudW1iZXJdPikge1xuICAgIGlmIChjb29yZGluYXRlc0FycmF5Lmxlbmd0aCA+IDApIHtcbiAgICAgIGNvb3JkaW5hdGVzQXJyYXkuZm9yRWFjaChpdGVtID0+IHtcbiAgICAgICAgaXRlbS5yZXZlcnNlKCk7XG4gICAgICB9KTtcbiAgICAgIHJldHVybiBjb29yZGluYXRlc0FycmF5O1xuICAgIH1cbiAgfVxuXG4gIHNpbXBsaWZ5UG9seWxpbmUoY29vcmRpbmF0ZXNBcnJheTogQXJyYXk8W251bWJlciwgbnVtYmVyXT4pOiBBcnJheTxbbnVtYmVyLCBudW1iZXJdPiB7XG4gICAgaWYgKGNvb3JkaW5hdGVzQXJyYXkubGVuZ3RoID4gMSkge1xuICAgICAgY29uc3QgZmlyc3RDb29yZGluYXRlID0gY29vcmRpbmF0ZXNBcnJheVswXTtcbiAgICAgIGNvbnN0IGxhc3RDb29yZGluYXRlID0gY29vcmRpbmF0ZXNBcnJheVtjb29yZGluYXRlc0FycmF5Lmxlbmd0aCAtIDFdO1xuICAgICAgcmV0dXJuIFtmaXJzdENvb3JkaW5hdGUsIGxhc3RDb29yZGluYXRlXTtcbiAgICB9IGVsc2Uge1xuICAgICAgcmV0dXJuIGNvb3JkaW5hdGVzQXJyYXk7XG4gICAgfVxuICB9XG59XG5cblxuXG5cbiIsImltcG9ydCB7IEluamVjdGFibGUgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IEh0dHBDbGllbnQgfSBmcm9tICdAYW5ndWxhci9jb21tb24vaHR0cCc7XG5pbXBvcnQgeyBPYnNlcnZhYmxlIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBtYXAgfSBmcm9tICdyeGpzL29wZXJhdG9ycyc7XG5cbkBJbmplY3RhYmxlKHtcbiAgcHJvdmlkZWRJbjogJ3Jvb3QnXG59KVxuZXhwb3J0IGNsYXNzIEVsZXZhdGlvblNlcnZpY2Uge1xuXG4gIGNvbnN0cnVjdG9yKHByaXZhdGUgaHR0cDogSHR0cENsaWVudCkgeyB9XG5cbiAgZ2V0RWxldmF0aW9uKGxhdDogbnVtYmVyLCBsbmc6IG51bWJlcik6IE9ic2VydmFibGU8bnVtYmVyPiB7XG4gICAgY29uc3QgYXBpVXJsID0gYGh0dHBzOi8vYXBpLm9wZW4tZWxldmF0aW9uLmNvbS9hcGkvdjEvbG9va3VwP2xvY2F0aW9ucz0ke2xhdH0sJHtsbmd9YDtcbiAgICByZXR1cm4gdGhpcy5odHRwLmdldChhcGlVcmwpLnBpcGUoXG4gICAgICBtYXAoKG9iajogT3BlbkVsZXZhdGlvbkFwaU9iamVjdCkgPT4gb2JqLnJlc3VsdHNbMF0uZWxldmF0aW9uKVxuICAgICk7XG4gIH1cbn1cblxuaW50ZXJmYWNlIE9wZW5FbGV2YXRpb25BcGlPYmplY3Qge1xuICByZXN1bHRzOiBBcnJheTx7XG4gICAgZWxldmF0aW9uOiBudW1iZXIsXG4gICAgbGF0aXR1ZGU6IG51bWJlcixcbiAgICBsb25naXR1ZGU6IG51bWJlclxuICB9Pjtcbn1cbiIsIi8qKlxuICogQHRvZG8gbGltaXQgcG9seWdvbiBhcmVhIC8gcG9seWxpbmUgbGVuZ2h0XG4gKiBAdG9kbyBmaXggZm9ybSBpbnB1dCBub3QgdXBkYXRlZCBhZnRlciAuc2V0VmFsdWUgKGV4Y2VwdCBmb3IgdGhlIGdwc01hcmtlclNldFZhbHVlcyBtZXRob2QpXG4gKiBzZWUgOiBodHRwczovL2dpdGh1Yi5jb20vYW5ndWxhci9tYXRlcmlhbDIvaXNzdWVzLzc2MDEjaXNzdWVjb21tZW50LTMzNDk0NzI4MCxcbiAqICAgICAgIGh0dHBzOi8vZ2l0aHViLmNvbS9hbmd1bGFyL21hdGVyaWFsMi9pc3N1ZXMvMjQzNCxcbiAqICAgICAgIGh0dHBzOi8vZ2l0aHViLmNvbS9hbmd1bGFyL21hdGVyaWFsMi9pc3N1ZXMvMjM2MyxcbiAqICAgICAgIGh0dHBzOi8vZ2l0aHViLmNvbS9hbmd1bGFyL21hdGVyaWFsMi9wdWxsLzI0NTUsXG4gKiAgICAgICBodHRwczovL2dpdGh1Yi5jb20vYW5ndWxhci9tYXRlcmlhbDIvaXNzdWVzLzI4MzcjaXNzdWVjb21tZW50LTI3NjUzODYxNixcbiAqICAgICAgIGh0dHBzOi8vZ2l0aHViLmNvbS9hbmd1bGFyL21hdGVyaWFsMi9pc3N1ZXMvNzYwMSxcbiAqICAgICAgIGh0dHBzOi8vZ2l0aHViLmNvbS9hbmd1bGFyL21hdGVyaWFsMi9pc3N1ZXMvMjQ0MVxuICovXG5pbXBvcnQgeyBDb21wb25lbnQsIE9uSW5pdCwgT25EZXN0cm95LCBFdmVudEVtaXR0ZXIsIElucHV0LCBPdXRwdXQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IEZvcm1CdWlsZGVyLCBGb3JtQ29udHJvbCwgRm9ybUdyb3VwLCBWYWxpZGF0b3JzIH0gZnJvbSAnQGFuZ3VsYXIvZm9ybXMnO1xuaW1wb3J0IHsgTWF0QXV0b2NvbXBsZXRlU2VsZWN0ZWRFdmVudCB9IGZyb20gJ0Bhbmd1bGFyL21hdGVyaWFsJztcbmltcG9ydCB7IFN1YnNjcmlwdGlvbiwgT2JzZXJ2YWJsZSwgemlwIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBkZWJvdW5jZVRpbWUsIGRpc3RpbmN0VW50aWxDaGFuZ2VkLCBzd2l0Y2hNYXAgfSBmcm9tICdyeGpzL29wZXJhdG9ycyc7XG5pbXBvcnQgKiBhcyBMIGZyb20gJ2xlYWZsZXQnO1xuaW1wb3J0ICdsZWFmbGV0LWRyYXcnO1xuaW1wb3J0IHsgTGF0TG5nRXhwcmVzc2lvbiB9IGZyb20gJ2xlYWZsZXQnO1xuXG5pbXBvcnQgeyBHZW9Qb2ludCB9IGZyb20gJy4uL19oZWxwZXJzL2dlb0NvbnZlcnQnO1xuaW1wb3J0ICogYXMgbGVhZmxldE9iamVjdHMgZnJvbSAnLi4vX2hlbHBlcnMvbGVhZmxldE9iamVjdHMnO1xuaW1wb3J0IHsgZG1zRm9ybWF0dGVyIH0gZnJvbSAnLi4vX2hlbHBlcnMvZG1zVG9vbHMnO1xuXG5pbXBvcnQgeyBHZW9jb2RpbmdTZXJ2aWNlIH0gZnJvbSAnLi4vX3NlcnZpY2VzL2dlb2NvZGluZy5zZXJ2aWNlJztcbmltcG9ydCB7IEVsZXZhdGlvblNlcnZpY2UgfSBmcm9tICcuLi9fc2VydmljZXMvZWxldmF0aW9uLnNlcnZpY2UnO1xuXG5pbXBvcnQgeyBMb2NhdGlvbk1vZGVsIH0gZnJvbSAnLi4vX21vZGVscy9sb2NhdGlvbi5tb2RlbCc7XG5pbXBvcnQgeyBOb21pbmF0aW1PYmplY3QgfSBmcm9tICcuLi9fbW9kZWxzL25vbWluYXRpbU9iai5tb2RlbCc7XG5pbXBvcnQgeyBMYXRMbmdETVNBbHRpdHVkZVBob3RvTmFtZSB9IGZyb20gJy4uL19tb2RlbHMvZ3BzTGF0TG5nJztcblxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAndGItZ2VvbG9jLW1hcCcsXG4gIHRlbXBsYXRlOiBgPGgxPk/Dg8K5ID88L2gxPlxuICBcbjxkaXYgaWQ9XCJnZW9sb2MtbWFwXCI+XG4gIDxkaXYgaWQ9XCJnZW9sb2MtbWFwLW1ldGFcIj5cbiAgICA8IS0tIGdlb3NlYXJjaCBhdXRvY29tcGxldGUgLS0+XG4gICAgPG1hdC1mb3JtLWZpZWxkIHN0eWxlPVwid2lkdGg6IDEwMCU7XCI+XG4gICAgICA8aW5wdXQgbWF0SW5wdXQgW2Zvcm1Db250cm9sXT1cImdlb1NlYXJjaEZvcm1Hcm91cC5jb250cm9scy5wbGFjZUlucHV0XCIgcGxhY2Vob2xkZXI9XCJUcm91dmVyIHVuIGxpZXVcIiBhcmlhLWxhYmVsPVwiVHJvdXZlciB1biBsaWV1XCIgW21hdEF1dG9jb21wbGV0ZV09XCJhdXRvXCI+XG4gICAgICA8bWF0LXNwaW5uZXIgKm5nSWY9XCJpc0xvYWRpbmdBZGRyZXNzXCIgZGlhbWV0ZXI9XCIyMFwiIG1hdFN1ZmZpeD48L21hdC1zcGlubmVyPlxuICAgICAgPG1hdC1hdXRvY29tcGxldGUgI2F1dG89XCJtYXRBdXRvY29tcGxldGVcIiAob3B0aW9uU2VsZWN0ZWQpPVwiYWRkcmVzc1NlbGVjdGVkQ2hhbmdlZCgkZXZlbnQpXCI+XG4gICAgICAgIDxtYXQtb3B0aW9uICpuZ0Zvcj1cImxldCBhZGRyZXNzIG9mIGdlb1NlYXJjaFJlc3VsdHNcIiBbdmFsdWVdPVwiYWRkcmVzc1wiPlxuICAgICAgICAgIDxzcGFuPnt7IGFkZHJlc3MgfCBvc21QbGFjZVJlYWRhYmxlQWRkcmVzcyB9fTwvc3Bhbj5cbiAgICAgICAgPC9tYXQtb3B0aW9uPlxuICAgICAgPC9tYXQtYXV0b2NvbXBsZXRlPlxuICAgIDwvbWF0LWZvcm0tZmllbGQ+XG4gICAgXG4gICAgPGRpdiBjbGFzcz1cImdlb2xvY2F0aW9uSW5wdXRzXCI+XG4gICAgICA8ZGl2IFtmb3JtR3JvdXBdPVwibGF0bG5nRm9ybUdyb3VwXCI+XG4gICAgICAgIDxkaXYgY2xhc3M9XCJsYXRMbmdNZW51SW5wdXRzXCI+XG4gICAgICAgICAgPCEtLSBsYXRpdHVkZSAvIGxvbmdpdHVkZSBkZWNpbWFsIGZvcm1hdCAtLT5cbiAgICAgICAgICA8ZGl2ICpuZ0lmPVwiY29vcmRGb3JtYXQ9PSdkZWNpbWFsJ1wiPlxuICAgICAgICAgICAgPCEtLSBsYXRpdHVkZSAvIGxvbmdpdHVkZSBmb3JtYXQgc2VsZWN0aW9uIC0tPiAgXG4gICAgICAgICAgICA8YnV0dG9uIG1hdC1pY29uLWJ1dHRvbiBbbWF0TWVudVRyaWdnZXJGb3JdPVwibWVudVwiPlxuICAgICAgICAgICAgICA8bWF0LWljb24+bW9yZV92ZXJ0PC9tYXQtaWNvbj5cbiAgICAgICAgICAgIDwvYnV0dG9uPlxuXG4gICAgICAgICAgICA8bWF0LWZvcm0tZmllbGQ+XG4gICAgICAgICAgICAgIDxpbnB1dCBtYXRJbnB1dCBmb3JtQ29udHJvbE5hbWU9XCJsYXRJbnB1dFwiIHBsYWNlaG9sZGVyPVwibGF0aXR1ZGVcIj5cbiAgICAgICAgICAgICAgPG1hdC1zcGlubmVyICpuZ0lmPVwiaXNMb2FkaW5nTGF0aXR1ZGVcIiBkaWFtZXRlcj1cIjIwXCIgbWF0U3VmZml4PjwvbWF0LXNwaW5uZXI+XG4gICAgICAgICAgICAgIDxtYXQtZXJyb3IgKm5nSWY9XCJsYXRsbmdGb3JtR3JvdXAuY29udHJvbHMubGF0SW5wdXQuZGlydHkgJiYgbGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmxhdElucHV0Lmhhc0Vycm9yKCdtYWxmb3JtZWRMYXRMbmdEZWNGb3JtYXQnKVwiPkZvcm1hdCBub24gdmFsaWRlPC9tYXQtZXJyb3I+XG4gICAgICAgICAgICA8L21hdC1mb3JtLWZpZWxkPlxuICAgICAgICAgICAgPG1hdC1mb3JtLWZpZWxkPlxuICAgICAgICAgICAgICA8aW5wdXQgbWF0SW5wdXQgZm9ybUNvbnRyb2xOYW1lPVwibG5nSW5wdXRcIiBwbGFjZWhvbGRlcj1cImxvbmdpdHVkZVwiPlxuICAgICAgICAgICAgICA8bWF0LXNwaW5uZXIgKm5nSWY9XCJpc0xvYWRpbmdMb25naXR1ZGVcIiBkaWFtZXRlcj1cIjIwXCIgbWF0U3VmZml4PjwvbWF0LXNwaW5uZXI+XG4gICAgICAgICAgICAgIDxtYXQtZXJyb3IgKm5nSWY9XCJsYXRsbmdGb3JtR3JvdXAuY29udHJvbHMubGF0SW5wdXQuZGlydHkgJiYgbGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmxhdElucHV0Lmhhc0Vycm9yKCdtYWxmb3JtZWRMYXRMbmdEZWNGb3JtYXQnKVwiPkZvcm1hdCBub24gdmFsaWRlPC9tYXQtZXJyb3I+XG4gICAgICAgICAgICA8L21hdC1mb3JtLWZpZWxkPlxuICAgICAgICAgICAgXG4gICAgICAgICAgICA8YnV0dG9uIG1hdC1pY29uLWJ1dHRvbiAoY2xpY2spPVwiYWRkTWFya2VyRnJvbUxhdExuZ0Nvb3JkKCk7IGNhbGxHZW9sb2NFbGV2YXRpb25BcGlzVXNpbmdMYXRMbmdJbnB1dHNWYWx1ZXMoKTtcIiBbZGlzYWJsZWRdPVwiIWxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5sYXRJbnB1dC52YWxpZCB8fCAhbGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmxuZ0lucHV0LnZhbGlkXCIgY29sb3I9XCJwcmltYXJ5XCI+XG4gICAgICAgICAgICAgIDxtYXQtaWNvbiBtYXRUb29sdGlwPVwiVXRpbGlzZXIgY2VzIGNvb3Jkb25uw4PCqWVzXCI+d2hlcmVfdG9fdm90ZTwvbWF0LWljb24+XG4gICAgICAgICAgICA8L2J1dHRvbj5cbiAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgPC9kaXY+XG5cbiAgICAgICAgPCEtLSBtZW51IGZvcm1hdCBkZWNpbWFsIC8gZG1zLS0+XG4gICAgICAgIDxtYXQtbWVudSAjbWVudT1cIm1hdE1lbnVcIj5cbiAgICAgICAgICA8YnV0dG9uIG1hdC1tZW51LWl0ZW0gKGNsaWNrKT1cInNldExhdExuZ0lucHV0Rm9ybWF0KCdkbXMnKVwiPkRlZ3LDg8KpcyBtaW51dGVzIHNlY29uZGVzPC9idXR0b24+XG4gICAgICAgICAgPGJ1dHRvbiBtYXQtbWVudS1pdGVtIChjbGljayk9XCJzZXRMYXRMbmdJbnB1dEZvcm1hdCgnZGVjaW1hbCcpXCI+RMODwqljaW1hbDwvYnV0dG9uPlxuICAgICAgICA8L21hdC1tZW51PlxuXG4gICAgICAgIDwhLS0gbGF0aXR1ZGUgLyBsb25naXR1ZGUgRE1TIGZvcm1hdCAtLT5cbiAgICAgICAgPGRpdiAqbmdJZj1cImNvb3JkRm9ybWF0PT0nZG1zJ1wiPlxuICAgICAgICAgIDwhLS0gbGF0aXR1ZGUgLyBsb25naXR1ZGUgZm9ybWF0IHNlbGVjdGlvbiAtLT4gIFxuICAgICAgICAgIDxidXR0b24gbWF0LWljb24tYnV0dG9uIFttYXRNZW51VHJpZ2dlckZvcl09XCJtZW51XCI+XG4gICAgICAgICAgICA8bWF0LWljb24+bW9yZV92ZXJ0PC9tYXQtaWNvbj5cbiAgICAgICAgICA8L2J1dHRvbj5cblxuICAgICAgICAgIDxtYXQtZm9ybS1maWVsZD5cbiAgICAgICAgICAgIDxpbnB1dCBtYXRJbnB1dCBmb3JtQ29udHJvbE5hbWU9XCJkbXNMYXRJbnB1dFwiIHBsYWNlaG9sZGVyPVwiKGRlZynDgsKwICAobWluKScgIChzZWMpJnF1b3Q7XCI+XG4gICAgICAgICAgICA8c3BhbiBtYXRQcmVmaXg+TiZuYnNwOzwvc3Bhbj5cbiAgICAgICAgICAgIDxtYXQtc3Bpbm5lciAqbmdJZj1cImlzTG9hZGluZ0xhdGl0dWRlXCIgZGlhbWV0ZXI9XCIyMFwiIG1hdFN1ZmZpeD48L21hdC1zcGlubmVyPlxuICAgICAgICAgICAgPG1hdC1lcnJvciAqbmdJZj1cImxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMYXRJbnB1dC5kaXJ0eSAmJiBsYXRsbmdGb3JtR3JvdXAuY29udHJvbHMuZG1zTGF0SW5wdXQuaGFzRXJyb3IoJ21hbGZvcm1lZExhdExuZ0Rtc0Zvcm1hdCcpXCI+Rm9ybWF0IG5vbiB2YWxpZGU8L21hdC1lcnJvcj5cbiAgICAgICAgICA8L21hdC1mb3JtLWZpZWxkPlxuXG4gICAgICAgICAgPG1hdC1mb3JtLWZpZWxkPlxuICAgICAgICAgICAgPGlucHV0IG1hdElucHV0IGZvcm1Db250cm9sTmFtZT1cImRtc0xuZ0lucHV0XCIgcGxhY2Vob2xkZXI9XCIoZGVnKcOCwrAgIChtaW4pJyAgKHNlYykmcXVvdDtcIj5cbiAgICAgICAgICAgIDxzcGFuIG1hdFByZWZpeD5FJm5ic3A7PC9zcGFuPlxuICAgICAgICAgICAgPG1hdC1zcGlubmVyICpuZ0lmPVwiaXNMb2FkaW5nTG9uZ2l0dWRlXCIgZGlhbWV0ZXI9XCIyMFwiIG1hdFN1ZmZpeD48L21hdC1zcGlubmVyPlxuICAgICAgICAgICAgPG1hdC1lcnJvciAqbmdJZj1cImxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMYXRJbnB1dC5kaXJ0eSAmJiBsYXRsbmdGb3JtR3JvdXAuY29udHJvbHMuZG1zTGF0SW5wdXQuaGFzRXJyb3IoJ21hbGZvcm1lZExhdExuZ0Rtc0Zvcm1hdCcpXCI+Rm9ybWF0IG5vbiB2YWxpZGU8L21hdC1lcnJvcj5cbiAgICAgICAgICA8L21hdC1mb3JtLWZpZWxkPlxuXG4gICAgICAgICAgPGJ1dHRvbiBtYXQtaWNvbi1idXR0b24gKGNsaWNrKT1cImFkZE1hcmtlckZyb21EbXNDb29yZCgpOyBjYWxsR2VvbG9jRWxldmF0aW9uQXBpc1VzaW5nTGF0TG5nSW5wdXRzVmFsdWVzKCk7XCIgW2Rpc2FibGVkXT1cIiFsYXRsbmdGb3JtR3JvdXAuY29udHJvbHMuZG1zTGF0SW5wdXQudmFsaWQgfHwgIWxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMbmdJbnB1dC52YWxpZFwiIGNvbG9yPVwicHJpbWFyeVwiPlxuICAgICAgICAgICAgPG1hdC1pY29uIG1hdFRvb2x0aXA9XCJVdGlsaXNlciBjZXMgY29vcmRvbm7Dg8KpZXNcIj53aGVyZV90b192b3RlPC9tYXQtaWNvbj5cbiAgICAgICAgICA8L2J1dHRvbj5cbiAgICAgICAgPC9kaXY+XG4gICAgICA8L2Rpdj5cbiAgICBcbiAgICAgIDwhLS0gZWxldmF0aW9uIC0tPlxuICAgICAgPGRpdiBbZm9ybUdyb3VwXT1cImVsZXZhdGlvbkZvcm1Hcm91cFwiPlxuICAgICAgICA8bWF0LWZvcm0tZmllbGQgc3R5bGU9XCJ3aWR0aDogMTAwcHg7XCI+XG4gICAgICAgICAgPGlucHV0IG1hdElucHV0IGZvcm1Db250cm9sTmFtZT1cImVsZXZhdGlvbklucHV0XCIgcGxhY2Vob2xkZXI9XCJhbHRpdHVkZVwiPlxuICAgICAgICAgIDxtYXQtc3Bpbm5lciAqbmdJZj1cImlzTG9hZGluZ0VsZXZhdGlvblwiIGRpYW1ldGVyPVwiMjBcIiBtYXRTdWZmaXg+PC9tYXQtc3Bpbm5lcj5cbiAgICAgICAgICA8c3BhbiAqbmdJZj1cIiFpc0xvYWRpbmdFbGV2YXRpb25cIiBtYXRTdWZmaXg+bTwvc3Bhbj5cbiAgICAgICAgPC9tYXQtZm9ybS1maWVsZD5cbiAgICAgIDwvZGl2PlxuICAgIDwvZGl2PlxuICA8L2Rpdj5cblxuICA8ZGl2IGlkPVwiZ2VvbG9jLW1hcC1kcmF3XCIgc3R5bGU9XCJoZWlnaHQ6IDQwMHB4O1wiXG4gICAgICBsZWFmbGV0IFxuICAgICAgW2xlYWZsZXRPcHRpb25zXT1cIm9wdGlvbnNcIlxuICAgICAgKGxlYWZsZXRNYXBSZWFkeSk9XCJvbk1hcFJlYWR5KCRldmVudClcIj5cbiAgPC9kaXY+XG48L2Rpdj5gLFxuICBzdHlsZXM6IFtgW2hpZGRlbl17ZGlzcGxheTpub25lIWltcG9ydGFudH0jZ2VvbG9jLW1hcHtkaXNwbGF5OmZsZXg7ZmxleC1kaXJlY3Rpb246Y29sdW1uO21pbi1oZWlnaHQ6MjAwcHh9I2dlb2xvYy1tYXAgI2dlb2xvYy1tYXAtbWV0YXtmbGV4OjE7cGFkZGluZzoxNXB4fSNnZW9sb2MtbWFwICNnZW9sb2MtbWFwLW1ldGEgLmdlb2xvY2F0aW9uSW5wdXRze2Rpc3BsYXk6ZmxleDtmbGV4LWRpcmVjdGlvbjpyb3c7anVzdGlmeS1jb250ZW50OnNwYWNlLWJldHdlZW59I2dlb2xvYy1tYXAgI2dlb2xvYy1tYXAtZHJhd3twb3NpdGlvbjpyZWxhdGl2ZTtmbGV4OjN9I2dlb2xvYy1tYXAgI2h0dHBUYXNrc1J1bm5pbmdTcGlubmVye2ZsZXg6MX1idXR0b24gLm1pbml7bWluLXdpZHRoOjA7bGluZS1oZWlnaHQ6MzBweH0uZ2VvbG9jYXRlZFBob3RvTWV0YWRhdGFUYWJsZXt3aWR0aDoxMDAlfWBdXG59KVxuZXhwb3J0IGNsYXNzIE1hcENvbXBvbmVudCBpbXBsZW1lbnRzIE9uSW5pdCwgT25EZXN0cm95IHtcblxuICAvLyAtLS0tLS0tLS0tLS0tLVxuICAvLyBJTlBVVCAvIE9VVFBVVFxuICAvLyAtLS0tLS0tLS0tLS0tLVxuICBASW5wdXQoKSBsYXllcnNUb0FkZDogQXJyYXk8c3RyaW5nPiA9IFsnb3NtJ107XG4gIEBJbnB1dCgpIGdlb2xvY2F0ZWRQaG90b0xhdExuZzogT2JzZXJ2YWJsZTxBcnJheTxMYXRMbmdETVNBbHRpdHVkZVBob3RvTmFtZT4+O1xuICBASW5wdXQoKSBvc21DbGFzc0ZpbHRlcjogQXJyYXk8c3RyaW5nPiA9IFtdO1xuXG4gIEBPdXRwdXQoKSBsb2NhdGlvbiA9IG5ldyBFdmVudEVtaXR0ZXI8TG9jYXRpb25Nb2RlbD4oKTsgLy8gb2JqZWN0IHRvIHJldHVyblxuXG4gIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbiAgLy8gRk9STVMgJiBSRUxBVEVEIFZBUklBQkxFU1xuICAvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4gIGxhdGxuZ0Zvcm1Hcm91cDogRm9ybUdyb3VwO1xuICBlbGV2YXRpb25Gb3JtR3JvdXA6IEZvcm1Hcm91cDtcbiAgZ2VvU2VhcmNoRm9ybUdyb3VwOiBGb3JtR3JvdXA7XG4gIGdlb1NlYXJjaFJlc3VsdHM6IEFycmF5PE5vbWluYXRpbU9iamVjdD47XG4gIGNvb3JkRm9ybWF0ID0gJ2Rtcyc7ICAgICAgICAgICAgLy8gJ2RlY2ltYWwnIHwgJ2RtcydcblxuICAvLyAtLS0tLS0tLS1cbiAgLy8gVkFSSUFCTEVTXG4gIC8vIC0tLS0tLS0tLVxuICBfbG9jYXRpb24gPSA8TG9jYXRpb25Nb2RlbD57fTtcbiAgZ2VvbG9jYXRlZFBob3RvTGF0TG5nRGF0YTogQXJyYXk8TGF0TG5nRE1TQWx0aXR1ZGVQaG90b05hbWU+ID0gW107XG4gIGdlb2xvY2F0ZWRQaG90b0xhdExuZ0Rpc3BsYXllZENvbHVtbnNUYWJsZTogQXJyYXk8c3RyaW5nPiA9IFsnc2VsZWN0JywgJ3Bob3RvTmFtZScsICdsYXQnLCAnbG5nJywgJ2FsdGl0dWRlJ107XG4gIGlzTG9hZGluZ0FkZHJlc3MgPSBmYWxzZTtcbiAgaXNMb2FkaW5nTGF0aXR1ZGUgPSBmYWxzZTtcbiAgaXNMb2FkaW5nTG9uZ2l0dWRlID0gZmFsc2U7XG4gIGlzTG9hZGluZ0VsZXZhdGlvbiA9IGZhbHNlO1xuXG4gIC8vIC0tLS0tLS0tLS0tLS1cbiAgLy8gU1VCU0NSSVBUSU9OU1xuICAvLyAtLS0tLS0tLS0tLS0tXG4gIGdlb1NlYXJjaFN1YnNjcmlwdGlvbiA9IG5ldyBTdWJzY3JpcHRpb247XG4gIGxhdERtc0lucHV0U3Vic2NyaXB0aW9uID0gbmV3IFN1YnNjcmlwdGlvbjtcbiAgbG5nRG1zSW5wdXRTdWJzY3JpcHRpb24gPSBuZXcgU3Vic2NyaXB0aW9uO1xuXG4gIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbiAgLy8gTEVBRkxFVCBWQVJJQUJMRVMsIExBWUVSUyBBTkQgTUFQIENPTkZJR1xuICAvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4gIHByaXZhdGUgbWFwOiBMLk1hcDtcbiAgcHVibGljIG1hcExhdCA9IDA7XG4gIHB1YmxpYyBtYXBMbmcgPSAwO1xuICBwcml2YXRlIGRyYXdUeXBlOiBzdHJpbmc7XG4gIHByaXZhdGUgZHJhd25JdGVtOiBhbnk7XG5cbiAgcHJpdmF0ZSBvc21MYXllciA9IEwudGlsZUxheWVyKCdodHRwOi8ve3N9LnRpbGUub3BlbnN0cmVldG1hcC5vcmcve3p9L3t4fS97eX0ucG5nJywgeyBtYXhab29tOiAxOCwgYXR0cmlidXRpb246ICdPcGVuIFN0cmVldCBtYXAnIH0pO1xuICBwcml2YXRlIGdvb2dsZVNhdGVsbGl0ZUxheWVyID0gTC50aWxlTGF5ZXIoJ2h0dHA6Ly97c30uZ29vZ2xlLmNvbS92dC9seXJzPXMmeD17eH0meT17eX0mej17en0nLCB7IG1heFpvb206IDIwLCBzdWJkb21haW5zOiBbJ210MCcsICdtdDEnLCAnbXQyJywgJ210MyddLCBhdHRyaWJ1dGlvbjogJ0dvb2dsZSBtYXBzJyB9KTtcbiAgcHJpdmF0ZSBnb29nbGVIeWJyaWRMYXllciA9IEwudGlsZUxheWVyKCdodHRwOi8ve3N9Lmdvb2dsZS5jb20vdnQvbHlycz1zLGgmeD17eH0meT17eX0mej17en0nLCB7IG1heFpvb206IDIwLCBzdWJkb21haW5zOiBbJ210MCcsICdtdDEnLCAnbXQyJywgJ210MyddLCBhdHRyaWJ1dGlvbjogJ0dvb2dsZSBtYXBzJyB9KTtcbiAgcHJpdmF0ZSBicmdtTGF5ZXIgPSBMLnRpbGVMYXllci53bXMoJ2h0dHA6Ly9nZW9zZXJ2aWNlcy5icmdtLmZyL2dlb2xvZ2llJywgeyB2ZXJzaW9uOiAnMS4zLjAnLCBsYXllcnM6ICdHZW9sb2dpZSd9KTtcbiAgcHJpdmF0ZSBtYXBMYXllcnMgPSB7XG4gICAgJ0dvb2dsZSc6IHRoaXMuZ29vZ2xlSHlicmlkTGF5ZXIsXG4gICAgJ09TTSc6IHRoaXMub3NtTGF5ZXIsXG4gICAgJ0JSR00nOiB0aGlzLmJyZ21MYXllclxuICB9O1xuICBwcml2YXRlIGdlb1Jlc3VsdHNMYXllciA9IEwuZ2VvSlNPTihudWxsLCB7c3R5bGU6IGZ1bmN0aW9uKCkgeyByZXR1cm4geyBjb2xvcjogJyNmZjc4MDAnLCB3ZWlnaHQ6IDUsIG9wYWNpdHk6IDAuNjUgfTsgfX0pO1xuICBwcml2YXRlIGdlb2xvY2F0ZWRQaG90b0xhdExuZ0xheWVyID0gTC5nZW9KU09OKCk7XG5cbiAgLy8gbWFwIG9wdGlvbnNcbiAgb3B0aW9ucyA9IHtcbiAgICBsYXllcnM6IFsgdGhpcy5vc21MYXllciBdLFxuICAgIHpvb206IDQsXG4gICAgY2VudGVyOiBMLmxhdExuZyh7IGxhdDogNDYuNTU4ODYwMzAzMTE3MTksIGxuZzogMi45ODgyODEyNTAwMDAwMDA0IH0pXG4gIH07XG5cbiAgLy8gTGVhZmxldCBtYXAgY29uZmlndXJhdGlvblxuICBkcmF3bkl0ZW1zID0gbmV3IEwuRmVhdHVyZUdyb3VwKCk7ICAvLyBhbGwgZHJhd24gaXRlbXNcbiAgZHJhd0NvbnRyb2xGdWxsID0gbGVhZmxldE9iamVjdHMuZHJhd0NvbnRyb2xQYW5lbDsgICAgICAvLyBkcmF3IHBhbmVsXG4gIGRyYXdDb250cm9sRWRpdCA9IGxlYWZsZXRPYmplY3RzLmRyYXdDb250cm9sRWRpdFBhbmVsKHRoaXMuZHJhd25JdGVtcyk7ICAvLyBlZGl0IHBhbmVsXG4gIGNpcmNsZU1hcmtlck9wdCA9IGxlYWZsZXRPYmplY3RzLmNpcmNsZU1hcmtlclN0eWxlOyAgICAgLy8gbWFya2VyIG9wdGlvbnNcbiAgZ2VvUmVzdWx0c09wdCA9IGxlYWZsZXRPYmplY3RzLmNpdHlTdHlsZTtcblxuXG5cbiAgLy8gLS0tLVxuICAvLyBDT0RFXG4gIC8vIC0tLS1cblxuICBjb25zdHJ1Y3RvcihcbiAgICBwcml2YXRlIGZiOiBGb3JtQnVpbGRlcixcbiAgICBwcml2YXRlIGdlb2NvZGVTZXJ2aWNlOiBHZW9jb2RpbmdTZXJ2aWNlLFxuICAgIHByaXZhdGUgZWxldmF0aW9uU2VydmljZTogRWxldmF0aW9uU2VydmljZSkgeyB9XG5cbiAgLyoqXG4gICAqIC0gQ3JlYXRlIHRoZSBmb3Jtc1xuICAgKiAtIFNldCB1cCBzdWJzY3JpcHRpb25zIChnZW8gc2VhcmNoLCBnZW9sb2NhdGVkIHBob3RvcywgbGF0IC8gbG5nIGlucHV0cylcbiAgICovXG4gIG5nT25Jbml0KCkge1xuICAgIC8vIENyZWF0ZSBmb3Jtc1xuICAgIHRoaXMubGF0bG5nRm9ybUdyb3VwID0gdGhpcy5mYi5ncm91cCh7XG4gICAgICBsYXRJbnB1dDogdGhpcy5mYi5jb250cm9sKCcnLCBbVmFsaWRhdG9ycy5yZXF1aXJlZCwgdGhpcy5sYXRMbmdEZWNWYWxpZGF0b3JdKSxcbiAgICAgIGxuZ0lucHV0OiB0aGlzLmZiLmNvbnRyb2woJycsIFtWYWxpZGF0b3JzLnJlcXVpcmVkLCB0aGlzLmxhdExuZ0RlY1ZhbGlkYXRvcl0pLFxuICAgICAgZG1zTGF0SW5wdXQ6IHRoaXMuZmIuY29udHJvbCgnJywgW1ZhbGlkYXRvcnMucmVxdWlyZWQsIHRoaXMubGF0TG5nRG1zVmFsaWRhdG9yXSksXG4gICAgICBkbXNMbmdJbnB1dDogdGhpcy5mYi5jb250cm9sKCcnLCBbVmFsaWRhdG9ycy5yZXF1aXJlZCwgdGhpcy5sYXRMbmdEbXNWYWxpZGF0b3JdKVxuICAgIH0pO1xuXG4gICAgdGhpcy5lbGV2YXRpb25Gb3JtR3JvdXAgPSB0aGlzLmZiLmdyb3VwKHtcbiAgICAgIGVsZXZhdGlvbklucHV0OiB0aGlzLmZiLmNvbnRyb2woJycsIG51bGwpXG4gICAgfSk7XG5cbiAgICB0aGlzLmdlb1NlYXJjaEZvcm1Hcm91cCA9IHRoaXMuZmIuZ3JvdXAoe1xuICAgICAgcGxhY2VJbnB1dDogdGhpcy5mYi5jb250cm9sKCcnLCBudWxsKVxuICAgIH0pO1xuXG4gICAgLy8gV2F0Y2ggcGxhY2VJbnB1dCBjaGFuZ2VzXG4gICAgdGhpcy5nZW9TZWFyY2hTdWJzY3JpcHRpb24gPSB0aGlzLmdlb1NlYXJjaEZvcm1Hcm91cC5jb250cm9scy5wbGFjZUlucHV0LnZhbHVlQ2hhbmdlc1xuICAgIC5waXBlKFxuICAgICAgZGVib3VuY2VUaW1lKDQwMCksXG4gICAgICBkaXN0aW5jdFVudGlsQ2hhbmdlZCgpLFxuICAgICAgc3dpdGNoTWFwKHZhbHVlID0+IHtcbiAgICAgICAgdGhpcy5pc0xvYWRpbmdBZGRyZXNzID0gdHJ1ZTtcbiAgICAgICAgcmV0dXJuIHRoaXMuZ2VvY29kZVNlcnZpY2UuZ2VvY29kZSh2YWx1ZSk7XG4gICAgICB9KVxuICAgICkuc3Vic2NyaWJlKHJlc3VsdHMgPT4ge1xuICAgICAgdGhpcy5pc0xvYWRpbmdBZGRyZXNzID0gZmFsc2U7XG4gICAgICAvLyBmaWx0ZXIgcmVzdWx0cyBpZiBuZWVkZWRcbiAgICAgIGlmICh0aGlzLm9zbUNsYXNzRmlsdGVyLmxlbmd0aCA+IDApIHtcbiAgICAgICAgdGhpcy5nZW9jb2RlU2VydmljZS5vc21DbGFzc0ZpbHRlcih0aGlzLm9zbUNsYXNzRmlsdGVyLCByZXN1bHRzKS5zdWJzY3JpYmUoZmlsdGVyZWRSZXN1bHRzID0+IHtcbiAgICAgICAgICB0aGlzLmdlb1NlYXJjaFJlc3VsdHMgPSBmaWx0ZXJlZFJlc3VsdHM7XG4gICAgICAgIH0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5nZW9TZWFyY2hSZXN1bHRzID0gcmVzdWx0cztcbiAgICAgIH1cbiAgICB9LCAoZXJyb3IpID0+IHtcbiAgICAgIC8vIEB0b3RvIG1hbmFnZSBlcnJvclxuICAgICAgdGhpcy5pc0xvYWRpbmdBZGRyZXNzID0gZmFsc2U7XG4gICAgfSk7XG5cbiAgICAvLyBXYXRjaCBnZW9sb2NhdGVkIHBob3RvIGlucHV0IGNoYW5nZXNcbiAgICB0aGlzLmdlb2xvY2F0ZWRQaG90b0xhdExuZy5zdWJzY3JpYmUocGhvdG9MYXRMbmcgPT4ge1xuICAgICAgLy8gQHRvZG8gY2xlYXIgdGhpcy5nZW9sb2NhdGVkUGhvdG9MYXRMbmdMYXllclxuXG4gICAgICB0aGlzLmdlb2xvY2F0ZWRQaG90b0xhdExuZ0RhdGEgPSBwaG90b0xhdExuZztcblxuICAgICAgLy8gRm9yIGVhY2ggZ2VvbG9jYXRlZCBwaG90bywgYWRkIG1hcmtlciBhbmQgYmluZCBtb3VzZSBldmVudCBvbiB0aG9zZXMgbWFya2Vyc1xuICAgICAgdGhpcy5nZW9sb2NhdGVkUGhvdG9MYXRMbmdEYXRhLmZvckVhY2goZGF0YSA9PiB7XG4gICAgICAgIC8vIEdldCBsYXRpdHVkZSBhbmQgbG9uZ2l0dWRlIChnZW9sb2NhdGVkIGRhdGEgYXJlIGluIERNUyBmb3JtYXQpXG4gICAgICAgIGNvbnN0IF9sYXREbXMgPSBkYXRhLmxhdC5kZWcgKyAnw4LCsCAnICsgZGF0YS5sYXQubWluICsgJ1xcJycgKyBkYXRhLmxhdC5zZWMgKyAnXCInO1xuICAgICAgICBjb25zdCBfbG5nRG1zID0gZGF0YS5sbmcuZGVnICsgJ8OCwrAgJyArIGRhdGEubG5nLm1pbiArICdcXCcnICsgZGF0YS5sbmcuc2VjICsgJ1wiJztcbiAgICAgICAgY29uc3QgZyA9IG5ldyBHZW9Qb2ludChfbG5nRG1zLCBfbGF0RG1zKTtcbiAgICAgICAgZGF0YS5sYXREZWMgPSBnLmxhdERlYztcbiAgICAgICAgZGF0YS5sbmdEZWMgPSBnLmxvbkRlYztcblxuICAgICAgICAvLyBDcmVhdGUgdGhlIG1hcmtlclxuICAgICAgICBjb25zdCBsYXRMbmcgPSBMLmxhdExuZyhkYXRhLmxhdERlYywgZGF0YS5sbmdEZWMpO1xuICAgICAgICBjb25zdCBncHNQaG90b01hcmtlciA9IG5ldyBMLk1hcmtlcihsYXRMbmcsIHsgaWNvbjogbGVhZmxldE9iamVjdHMuZ3BzUGhvdG9NYXJrZXJJY29uKCkgfSk7XG4gICAgICAgIC8vIE1hcmtlciBwb3B1cFxuICAgICAgICBjb25zdCBodG1sID0gYFxuICAgICAgICAgIDxiPkZpY2hpZXIgXCIke2RhdGEucGhvdG9OYW1lfVwiPC9iPjxicj5cbiAgICAgICAgICBMYXQuIDogJHtnLmxhdERlZ308YnIgLz5cbiAgICAgICAgICBMbmcuIDogJHtnLmxvbkRlZ308YnIgLz5cbiAgICAgICAgICBBbHQuIDogJHtkYXRhLmFsdGl0dWRlfSBtPGJyIC8+PGJyIC8+XG4gICAgICAgICAgPGI+Q2xpcXVleiBzdXIgbGUgcG9pbnQgcG91ciB1dGlsaXNlciBjZXMgY29vcmRvbm7Dg8KpZXM8L2I+YDtcbiAgICAgICAgZ3BzUGhvdG9NYXJrZXIuYmluZFBvcHVwKGh0bWwpLm9wZW5Qb3B1cCgpO1xuICAgICAgICAvLyBNYXJrZXIgbW91c2UgZXZlbnRzXG4gICAgICAgIGdwc1Bob3RvTWFya2VyLm9uKCdjbGljaycsIChldmVudCA9PiB7IHRoaXMuZ3BzTWFya2VyU2V0VmFsdWVzKGRhdGEubGF0RGVjLCBkYXRhLmxuZ0RlYywgZGF0YS5hbHRpdHVkZSk7IH0pKTtcbiAgICAgICAgZ3BzUGhvdG9NYXJrZXIub24oJ21vdXNlb3ZlcicsIChldmVudCkgPT4geyBncHNQaG90b01hcmtlci5vcGVuUG9wdXAoKTsgfSk7XG4gICAgICAgIGdwc1Bob3RvTWFya2VyLm9uKCdtb3VzZW91dCcsIChldmVudCA9PiB7IGdwc1Bob3RvTWFya2VyLmNsb3NlUG9wdXAoKTsgfSkpO1xuICAgICAgICAvLyBBZGQgdGhlIG1hcmtlciB0byB0aGUgbWFwXG4gICAgICAgIGdwc1Bob3RvTWFya2VyLmFkZFRvKHRoaXMuZ2VvbG9jYXRlZFBob3RvTGF0TG5nTGF5ZXIpO1xuICAgICAgfSk7XG5cbiAgICAgIC8vIEZpdCBtYXAgdG8gZ2VvbG9jYXRlZCBwaG90b3MgbWFya2Vyc1xuICAgICAgdGhpcy5mbHlUb0dlb2xvY2F0ZWRQaG90b0l0ZW1zKCk7XG4gICAgfSk7XG5cbiAgICAvLyBXYXRjaCBsYXQgJiBsbmcgRE1TIGlucHV0cyBjaGFuZ2VzIGFuZCBzZXQgdXAgdGhlIERNUyBmb3JtYXR0ZXJcbiAgICAvLyBUaGUgRE1TIGZvcm1hdHRlciByZXN0cmljdHMgdGhlIGtleWJvYXJkIGlucHV0IG9mIHRoZSB1c2VyIDogb25seSBudW1iZXIsIGNvbW1hLCBkb3QgYW5kICctJywgZGVnIGFuZCBtaW4gbXVzdCBiZSBiZXR3ZWVuIC05MCBhbmQgKzkwXG4gICAgLy8gVGhlIGZvcm1hdHRlciBhdXRvIGZpbGwgdGhlIMOCwrAgJyBhbmQgXCIgY2hhcmFjdGVycyB0byBoZWxwIHRoZSB1c2VyIGlucHV0XG4gICAgdGhpcy5sYXREbXNJbnB1dFN1YnNjcmlwdGlvbiA9IHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmRtc0xhdElucHV0LnZhbHVlQ2hhbmdlcy5zdWJzY3JpYmUodmFsdWUgPT4ge1xuICAgICAgdGhpcy5sYXRsbmdGb3JtR3JvdXAuY29udHJvbHMuZG1zTGF0SW5wdXQuc2V0VmFsdWUoZG1zRm9ybWF0dGVyKHZhbHVlKSwgeyBlbWl0RXZlbnQ6IGZhbHNlfSk7XG4gICAgfSk7XG4gICAgdGhpcy5sbmdEbXNJbnB1dFN1YnNjcmlwdGlvbiA9IHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmRtc0xuZ0lucHV0LnZhbHVlQ2hhbmdlcy5zdWJzY3JpYmUodmFsdWUgPT4ge1xuICAgICAgdGhpcy5sYXRsbmdGb3JtR3JvdXAuY29udHJvbHMuZG1zTG5nSW5wdXQuc2V0VmFsdWUoZG1zRm9ybWF0dGVyKHZhbHVlKSwgeyBlbWl0RXZlbnQ6IGZhbHNlfSk7XG4gICAgfSk7XG4gIH1cblxuICAvKipcbiAgICogVW5zdWJzY3JpYmVcbiAgICovXG4gIG5nT25EZXN0cm95KCkge1xuICAgIHRoaXMuZ2VvU2VhcmNoU3Vic2NyaXB0aW9uLnVuc3Vic2NyaWJlKCk7XG4gICAgdGhpcy5sYXREbXNJbnB1dFN1YnNjcmlwdGlvbi51bnN1YnNjcmliZSgpO1xuICAgIHRoaXMubG5nRG1zSW5wdXRTdWJzY3JpcHRpb24udW5zdWJzY3JpYmUoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBBZGQgbGF5ZXJzIGFuZCBldmVudHMgbGlzdGVuZXJzXG4gICAqL1xuICBvbk1hcFJlYWR5KG1hcDogTC5NYXApIHtcbiAgICB0aGlzLm1hcCA9IG1hcDtcbiAgICB0aGlzLm1hcC5hZGRDb250cm9sKEwuY29udHJvbC5sYXllcnMobnVsbCwgdGhpcy5tYXBMYXllcnMsIHsgcG9zaXRpb246ICd0b3ByaWdodCd9KSk7XG4gICAgdGhpcy5tYXAuYWRkTGF5ZXIodGhpcy5kcmF3bkl0ZW1zKTtcbiAgICB0aGlzLm1hcC5hZGRMYXllcih0aGlzLmdlb1Jlc3VsdHNMYXllcik7XG4gICAgdGhpcy5tYXAuYWRkTGF5ZXIodGhpcy5nZW9sb2NhdGVkUGhvdG9MYXRMbmdMYXllcik7XG4gICAgdGhpcy5tYXAuYWRkQ29udHJvbCh0aGlzLmRyYXdDb250cm9sRnVsbCk7XG4gICAgdGhpcy5tYXAub24oJ2RyYXc6Y3JlYXRlZCcsIChlKSA9PiB7XG4gICAgICB0aGlzLmRyYXduSXRlbSA9IGVbJ2xheWVyJ107XG4gICAgICB0aGlzLmRyYXdUeXBlID0gZVsnbGF5ZXJUeXBlJ107XG4gICAgICAvLyBJZiBpdCdzIGEgbWFya2VyLCBpdCBtdXN0IGJlIGRyYWdnYWJsZS4gQnkgZGVmYXVsdCwgbGVhZmxldC5kcmF3IG1vZHVsZSBkb2VzIG5vdCBwcm92aWRlIGEgZHJhZ2dhYmxlIG1hcmtlclxuICAgICAgLy8gU28sIHdlIGRvbid0IGRvIGEgdGhpcy5kcmF3bkl0ZW1zLmFkZExheWVyKGxheWVyKTtcbiAgICAgIC8vIFdlIGp1c3QgZHJhdyBhIG5ldyBkcmFnZ2FibGVNYXJrZXIgaW5zdGVhZFxuICAgICAgaWYgKHRoaXMuZHJhd1R5cGUgPT09ICdtYXJrZXInKSB7XG4gICAgICAgIGNvbnN0IGxhdGxuZyA9IHRoaXMuZHJhd25JdGVtLl9sYXRsbmc7XG4gICAgICAgIGxlYWZsZXRPYmplY3RzLmRyYWdnYWJsZU1hcmtlcihsYXRsbmcubGF0LCBsYXRsbmcubG5nLCAoZHJhZ0VuZCkgPT4geyB0aGlzLmNhbGxHZW9sb2NFbGV2YXRpb25BcGlzVXNpbmdMYXRMbmdJbnB1dHNWYWx1ZXMoKTsgfSkuYWRkVG8odGhpcy5kcmF3bkl0ZW1zKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRoaXMuZHJhd25JdGVtcy5hZGRMYXllcih0aGlzLmRyYXduSXRlbSk7XG4gICAgICB9XG5cbiAgICAgIC8vIFNob3cgLyBoaWRlIGNvbnRyb2wgcGFuZWxzXG4gICAgICAvLyBpZiBPTkUgaXRlbSBpcyBkcmF3biwgc2V0IHBsYWNlIGFuZCBlbGV2YXRpb24gaW5wdXRzIChjYWxsIEFQSSlcbiAgICAgIGlmICh0aGlzLmRyYXduSXRlbXMuZ2V0TGF5ZXJzKCkubGVuZ3RoID4gMCkge1xuICAgICAgICB0aGlzLnNldE1hcEVkaXRNb2RlKCk7XG4gICAgICB9XG4gICAgICBpZiAodGhpcy5kcmF3bkl0ZW1zLmdldExheWVycygpLmxlbmd0aCA9PT0gMSkge1xuICAgICAgICB0aGlzLmNhbGxHZW9sb2NFbGV2YXRpb25BcGlzVXNpbmdMYXRMbmdJbnB1dHNWYWx1ZXMoKTtcbiAgICAgIH1cblxuICAgICAgdGhpcy5mbHlUb0RyYXduSXRlbXMoKTtcbiAgICB9KTtcblxuICAgIHRoaXMubWFwLm9uKCdkcmF3OmVkaXRlZCcsIChlKSA9PiB7XG4gICAgICB0aGlzLmRyYXduSXRlbSA9IGVbJ2xheWVyJ107XG4gICAgICB0aGlzLmRyYXdUeXBlID0gZVsnbGF5ZXJUeXBlJ107XG5cbi8vICAgICAgdGhpcy5kcmF3bkl0ZW1zLmFkZExheWVyKHRoaXMuZHJhd25JdGVtKTtcblxuICAgICAgaWYgKHRoaXMuZHJhd25JdGVtcy5nZXRMYXllcnMoKS5sZW5ndGggPT09IDEpIHtcbiAgICAgICAgdGhpcy5jYWxsR2VvbG9jRWxldmF0aW9uQXBpc1VzaW5nTGF0TG5nSW5wdXRzVmFsdWVzKCk7XG4gICAgICB9XG5cbiAgICAgIHRoaXMuZmx5VG9EcmF3bkl0ZW1zKCk7XG4gICAgfSk7XG5cbiAgICB0aGlzLm1hcC5vbignZHJhdzpkZWxldGVkJywgKGUpID0+IHtcbiAgICAgIHRoaXMuY2xlYXJHZW9SZXN1bHRzTGF5ZXIoKTtcbiAgICAgIHRoaXMuY2xlYXJEcmF3bkl0ZW1zTGF5ZXIoKTtcbiAgICAgIHRoaXMuc2V0TWFwRHJhd01vZGUoKTtcbiAgICAgIHRoaXMuY2xlYXJGb3JtKCk7XG4gICAgfSk7XG5cbiAgICB0aGlzLnJlZHJhd01hcCgxMDApO1xuICB9XG5cbiAgLyoqXG4gICAqIFdoZW4gdGhlIG1hcCBwYXJlbnQncyBkaXYgc2l6ZSBjaGFuZ2UgKGVnLiBwYW5lbCB3aWR0aCksIGhhdmUgdG8gcmVkcmF3IHRoZSBtYXBcbiAgICogU29tZXRpbWVzICh3aGVuIG9wZW5pbmcgLyBjbG9zaW5nIGEgdGFiKSwgc2l6ZSBjaGFuZ2UgaXMgZGV0ZWN0ZWQgdG9vIGVhcmxpZXIsIG5lZWQgdG8gc2V0IGEgZGVsYXkgKGFib3V0IDEwLTEwMG1zIHNlZW1zIHRvIGJlIGNvbnZlbmllbnQpXG4gICAqL1xuICByZWRyYXdNYXAoZGVsYXk/OiBudW1iZXIpIHtcbiAgICBpZiAoZGVsYXkpIHtcbiAgICAgIHdpbmRvdy5zZXRUaW1lb3V0KCgpID0+IHRoaXMubWFwLmludmFsaWRhdGVTaXplKCksIGRlbGF5KTtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhpcy5tYXAuaW52YWxpZGF0ZVNpemUoKTtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogU2hvdyB0aGUgXCJlZGl0XCIgdG9vbGJhciBpbnNpZGUgbWFwXG4gICAqL1xuICBzZXRNYXBFZGl0TW9kZSgpIHtcbiAgICB0aGlzLm1hcC5yZW1vdmVDb250cm9sKHRoaXMuZHJhd0NvbnRyb2xGdWxsKTtcbiAgICB0aGlzLm1hcC5hZGRDb250cm9sKHRoaXMuZHJhd0NvbnRyb2xFZGl0KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBTaG93IHRoZSBcImRyYXdcIiB0b29sYmFyIGluc2lkZSBtYXBcbiAgICovXG4gIHNldE1hcERyYXdNb2RlKCkge1xuICAgIHRoaXMubWFwLnJlbW92ZUNvbnRyb2wodGhpcy5kcmF3Q29udHJvbEVkaXQpO1xuICAgIHRoaXMubWFwLmFkZENvbnRyb2wodGhpcy5kcmF3Q29udHJvbEZ1bGwpO1xuICB9XG5cbiAgLyoqXG4gICAqIFNldCBtYXAgYm91bmRzIHRvIGRyYXduIGl0ZW1zXG4gICAqL1xuICBmbHlUb0RyYXduSXRlbXMoX21heFpvb20gPSAxNCkge1xuICAgIGNvbnN0IGIgPSB0aGlzLmRyYXduSXRlbXMuZ2V0Qm91bmRzKCk7XG4gICAgdGhpcy5tYXAuZmx5VG9Cb3VuZHMoYiwgeyBtYXhab29tOiBfbWF4Wm9vbSwgYW5pbWF0ZTogZmFsc2UgfSk7XG4gIH1cblxuICAvKipcbiAgICogU2V0IG1hcCBib3VuZHMgdG8gZ2VvIHJldWx0cyBpdGVtc1xuICAgKi9cbiAgZmx5VG9HZW9SZXN1bHRzSXRlbXMoKSB7XG4gICAgY29uc3QgYiA9IHRoaXMuZ2VvUmVzdWx0c0xheWVyLmdldEJvdW5kcygpO1xuICAgIHRoaXMubWFwLmZseVRvQm91bmRzKGIsIHsgbWF4Wm9vbTogMTQsIGFuaW1hdGU6IGZhbHNlIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIFNldCBtYXAgYm91bmRzIHRvIGdlb2xvY2F0ZWQgcGhvdG9zIGl0ZW1zXG4gICAqL1xuICBmbHlUb0dlb2xvY2F0ZWRQaG90b0l0ZW1zKCkge1xuICAgIGNvbnN0IGIgPSB0aGlzLmdlb2xvY2F0ZWRQaG90b0xhdExuZ0xheWVyLmdldEJvdW5kcygpO1xuICAgIHRoaXMubWFwLmZseVRvQm91bmRzKGIsIHsgbWF4Wm9vbTogMTQsIGFuaW1hdGU6IGZhbHNlIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIERyYXcgYSBtYXJrZXIgb24gZHJhd0l0ZW1zIGZlYXR1cmVHcm91cCB3aXRoIERNUyBpbnB1dCB2YWx1ZXNcbiAgICovXG4gIGFkZE1hcmtlckZyb21EbXNDb29yZCgpIHtcbiAgICAvLyBjbGVhciBkcmF3biBpdGVtcyBsYXllclxuICAgIHRoaXMuY2xlYXJEcmF3bkl0ZW1zTGF5ZXIoKTtcblxuICAgIC8vIHVwZGF0ZSBtYXAgdG9vbGJhclxuICAgIHRoaXMuc2V0TWFwRWRpdE1vZGUoKTtcbiAgICAvLyBAVE9ETyBjaGVjayBsYXRpdHVkZSBhbmQgbG9uZ2l0dWRlIHZhbHVlcyAoZm9ybWF0ICsgbGltaXRzKVxuICAgIGNvbnN0IGdlb3BvaW50ID0gbmV3IEdlb1BvaW50KHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmRtc0xuZ0lucHV0LnZhbHVlLCB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMYXRJbnB1dC52YWx1ZSk7XG4gICAgbGVhZmxldE9iamVjdHMuZHJhZ2dhYmxlTWFya2VyKGdlb3BvaW50LmdldExhdERlYygpLCBnZW9wb2ludC5nZXRMb25EZWMoKSwgKGUpID0+IHsgLyogZHJhZ2VuZCBjYWxsYmFjayBmbiAqLyB9KS5hZGRUbyh0aGlzLmRyYXduSXRlbXMpO1xuXG4gICAgLy8gU2V0IChkZWNpbWFsKSBsYXRMbmcgaW5wdXRzXG4gICAgdGhpcy5sYXRsbmdGb3JtR3JvdXAuY29udHJvbHMubGF0SW5wdXQuc2V0VmFsdWUoZ2VvcG9pbnQuZ2V0TGF0RGVjKCksIHsgZW1pdEV2ZW50OiBmYWxzZSB9KTtcbiAgICB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5sbmdJbnB1dC5zZXRWYWx1ZShnZW9wb2ludC5nZXRMYXREZWMoKSwgeyBlbWl0RXZlbnQ6IGZhbHNlIH0pO1xuXG4gICAgLy8gRmx5XG4gICAgdGhpcy5mbHlUb0RyYXduSXRlbXMoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBEcmF3IGEgbWFya2VyIG9uIGRyYXdJdGVtcyBmZWF0dXJlR3JvdXAgd2l0aCBkZWNpbWFsIGlucHV0IHZhbHVlc1xuICAgKi9cbiAgYWRkTWFya2VyRnJvbUxhdExuZ0Nvb3JkKCkge1xuICAgIC8vIGNsZWFyIGRyYXduIGl0ZW1zIGxheWVyXG4gICAgdGhpcy5jbGVhckRyYXduSXRlbXNMYXllcigpO1xuXG4gICAgLy8gdXBkYXRlIG1hcCB0b29sYmFyXG4gICAgdGhpcy5zZXRNYXBFZGl0TW9kZSgpO1xuXG4gICAgLy8gVE9ETyBjaGVjayBsYXRpdHVkZSBhbmQgbG9uZ2l0dWRlIHZhbHVlcyAoZm9ybWF0ICsgbGltaXRzKVxuICAgIGNvbnN0IGdlb3BvaW50ID0gbmV3IEdlb1BvaW50KE51bWJlcih0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5sbmdJbnB1dC52YWx1ZSksIE51bWJlcih0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5sYXRJbnB1dC52YWx1ZSkpO1xuICAgIGxlYWZsZXRPYmplY3RzLmRyYWdnYWJsZU1hcmtlcihnZW9wb2ludC5nZXRMYXREZWMoKSwgZ2VvcG9pbnQuZ2V0TG9uRGVjKCksIChkcmFnRW5kKSA9PiB7IC8qIGRyYWdlbmQgY2FsbGJhY2sgZm4gKi8gfSkuYWRkVG8odGhpcy5kcmF3bkl0ZW1zKTtcblxuICAgIC8vIFNldCBkbXNMYXRMbmcgaW5wdXRzXG4gICAgdGhpcy5sYXRsbmdGb3JtR3JvdXAuY29udHJvbHMuZG1zTGF0SW5wdXQuc2V0VmFsdWUoZ2VvcG9pbnQuZ2V0TGF0RGVnKCksIHsgZW1pdEV2ZW50OiBmYWxzZSB9KTtcbiAgICB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMbmdJbnB1dC5zZXRWYWx1ZShnZW9wb2ludC5nZXRMb25EZWcoKSwgeyBlbWl0RXZlbnQ6IGZhbHNlIH0pO1xuXG4gICAgLy8gRmx5XG4gICAgdGhpcy5mbHlUb0RyYXduSXRlbXMoKTtcbiAgfVxuXG4gIC8qKlxuICAqXG4gICovXG4gIGFkZFBvbHlsaW5lKGNvb3JkaW5hdGVzOiBMYXRMbmdFeHByZXNzaW9uW10pIHtcbiAgICAvLyBjbGVhciBkcmF3biBpdGVtcyBsYXllclxuICAgIHRoaXMuY2xlYXJEcmF3bkl0ZW1zTGF5ZXIoKTtcblxuICAgIC8vIHVwZGF0ZSBtYXAgdG9vbGJhclxuICAgIHRoaXMuc2V0TWFwRWRpdE1vZGUoKTtcblxuICAgIC8vIGRyYXdcbiAgICBjb25zdCBwb2x5bGluZSA9IEwucG9seWxpbmUoY29vcmRpbmF0ZXMpO1xuICAgIHBvbHlsaW5lLmFkZFRvKHRoaXMuZHJhd25JdGVtcyk7XG5cbiAgICAvLyBmbHkgd2l0aCBtYXggem9vbVxuICAgIHRoaXMuZmx5VG9EcmF3bkl0ZW1zKDE4KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBUYWtlIGxhdGl0dWRlIGFuZCBsb25naXR1ZGUgaW5wdXQgdmFsdWVzIGFuZCBjYWxsIGdlb2NvZGluZyBhbmQgZWxldmF0aW9uIEFQSVxuICAgKiBTb21ldGltZXMgeW91IG1heSB3YW50IHRvIGZvcmNlIHRoZSBlbGV2YXRpb24gdmFsdWUgYW5kIGF2b2lkIGNhbGxpbmcgZWxldmF0aW9uIEFQSSAoZWcuIGVsZXZhdGlvbiBjb21lIGZyb20gZ3BzIHBob3RvIG1ldGFkYXRhKVxuICAgKiB0aGVuLCB5b3UgY2FzIHVzZSB0aGUgYXZvaWRDYWxsaW5nRWxldmF0aW9uQXBpIG9wdGlvblxuICAgKlxuICAgKiBXaGF0IGlzIGRvbmUgaW5zaWRlIHRoaXMgZnVuY3Rpb24gOlxuICAgKiAtIGNyZWF0ZSBhbiBvYnNlcnZhYmxlIHRoYXQgemlwIGFsbCByZXF1aXJlZCBvYnNlcnZhYmxlc1xuICAgKiAtIGRvIGEgc3dpdGNobWFwIG9uIHRoZSBtYWluIG9ic2VydmFibGUgc28gdGhhdCBpZiBvbmUgb25lIHRoZSBzdWItb2JzZXJ2YWJsZSBjaGFuZ2UsIG9sZCBkYXRhIGFyZSBpZ25vcmVkXG4gICAqIC0gd2hlbiB0aGUgbWFpbiBvYnNlcnZhYmxlIGlzIGZpbmlzaGVkLCBjYW4gc2VuZCBuZXcgbG9jYXRpb24gT3V0cHV0XG4gICAqXG4gICAqIFNldmVyYWwgaWYgLyBlbHNlIGF2b2lkQ2FsbGluZ0VsZXZhdGlvbkFwaSBhcmUgdXNlZCBiZWNhdXNlIHdoZW5cbiAgICogYXZvaWRDYWxsaW5nRWxldmF0aW9uQXBpID09PSBmYWxzZSwgaHR0cFRhc2tzIHJldHVybnMgYSBzaW5nbGUgdmFsdWUgKG9zbVBsYWNlKVxuICAgKiB3aGVyZWFzIGlmIGF2b2lkQ2FsbGluZ0VsZXZhdGlvbkFwaSA9PT0gdHJ1ZSwgaHR0cFRhc2tzIHJldHVybnMgYW4gYXJyYXkgb2YgMiB2YWx1ZXMgW2VsZXZhdGlvbiwgb3NtUGxhY2VdXG4gICAqL1xuICBjYWxsR2VvbG9jRWxldmF0aW9uQXBpc1VzaW5nTGF0TG5nSW5wdXRzVmFsdWVzKGF2b2lkQ2FsbGluZ0VsZXZhdGlvbkFwaSA9IGZhbHNlLCBhdm9pZENhbGxpbmdHZW9sb2NBcGkgPSBmYWxzZSk6IHZvaWQge1xuXG4gICAgdGhpcy5zZXRMYXRMbmdJbnB1dEZyb21EcmF3bkl0ZW1zKCk7XG4gICAgdGhpcy5zZXRMYXRMbmdEbXNJbnB1dEZyb21EcmF3bkl0ZW1zKCk7XG4gICAgbGV0IGh0dHBUYXNrczogT2JzZXJ2YWJsZTxhbnk+O1xuICAgIGxldCBlbGV2YXRpb246IGFueTtcbiAgICBsZXQgb3NtUGxhY2U6IGFueTtcblxuICAgIGlmIChhdm9pZENhbGxpbmdFbGV2YXRpb25BcGkgJiYgIWF2b2lkQ2FsbGluZ0dlb2xvY0FwaSkge1xuICAgICAgaHR0cFRhc2tzID0gdGhpcy5yZXZlcnNlR2VvY29kaW5nRnJvbUlucHV0VmFsdWUoKTtcbiAgICB9IGVsc2UgaWYgKGF2b2lkQ2FsbGluZ0dlb2xvY0FwaSAmJiAhYXZvaWRDYWxsaW5nRWxldmF0aW9uQXBpKSB7XG4gICAgICBodHRwVGFza3MgPSB0aGlzLmdldEVsZXZhdGlvbkZyb21JbnB1dFZhbHVlKCk7XG4gICAgfSBlbHNlIGlmICghYXZvaWRDYWxsaW5nRWxldmF0aW9uQXBpICYmICFhdm9pZENhbGxpbmdHZW9sb2NBcGkpIHtcbiAgICAgIGh0dHBUYXNrcyA9IHppcChcbiAgICAgICAgdGhpcy5nZXRFbGV2YXRpb25Gcm9tSW5wdXRWYWx1ZSgpLFxuICAgICAgICB0aGlzLnJldmVyc2VHZW9jb2RpbmdGcm9tSW5wdXRWYWx1ZSgpXG4gICAgICApO1xuICAgIH0gZWxzZSBpZiAoYXZvaWRDYWxsaW5nRWxldmF0aW9uQXBpICYmIGF2b2lkQ2FsbGluZ0dlb2xvY0FwaSkge1xuICAgICAgLy8gbm90aGluZyB0byBkbyA7IHRocm93IG9yIGxvZyBhbiBlcnJvciA/XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgLy8gc3Bpbm5uZXJzIG9uXG4gICAgdGhpcy5pc0xvYWRpbmdBZGRyZXNzID0gIWF2b2lkQ2FsbGluZ0dlb2xvY0FwaTtcbiAgICB0aGlzLmlzTG9hZGluZ0VsZXZhdGlvbiA9ICFhdm9pZENhbGxpbmdFbGV2YXRpb25BcGk7XG5cbiAgICBodHRwVGFza3Muc3Vic2NyaWJlKHJlc3VsdCA9PiB7XG4gICAgICB0aGlzLmlzTG9hZGluZ0VsZXZhdGlvbiA9IGZhbHNlO1xuICAgICAgdGhpcy5pc0xvYWRpbmdBZGRyZXNzID0gZmFsc2U7XG4gICAgICBpZiAoYXZvaWRDYWxsaW5nRWxldmF0aW9uQXBpICYmICFhdm9pZENhbGxpbmdHZW9sb2NBcGkpIHtcbiAgICAgICAgZWxldmF0aW9uID0gbnVsbDtcbiAgICAgICAgb3NtUGxhY2UgPSByZXN1bHQ7XG4gICAgICB9IGVsc2UgaWYgKGF2b2lkQ2FsbGluZ0dlb2xvY0FwaSAmJiAhYXZvaWRDYWxsaW5nRWxldmF0aW9uQXBpKSB7XG4gICAgICAgIGVsZXZhdGlvbiA9IHJlc3VsdDtcbiAgICAgICAgb3NtUGxhY2UgPSBudWxsO1xuICAgICAgICBlbGV2YXRpb24gPSByZXN1bHQ7XG4gICAgICB9IGVsc2UgaWYgKCFhdm9pZENhbGxpbmdHZW9sb2NBcGkgJiYgIWF2b2lkQ2FsbGluZ0dlb2xvY0FwaSkge1xuICAgICAgICBlbGV2YXRpb24gPSByZXN1bHRbMF07XG4gICAgICAgIG9zbVBsYWNlID0gcmVzdWx0WzFdO1xuICAgICAgfVxuXG4gICAgICAvLyBTZXQgZWxldmF0aW9uIGlucHV0XG4gICAgICBpZiAoIWF2b2lkQ2FsbGluZ0VsZXZhdGlvbkFwaSkgeyB0aGlzLmVsZXZhdGlvbkZvcm1Hcm91cC5jb250cm9scy5lbGV2YXRpb25JbnB1dC5zZXRWYWx1ZShlbGV2YXRpb24pOyB9XG5cbiAgICAgIC8vIFBhdGNoIHBsYWNlIGlucHV0IHZhbHVlXG4gICAgICBpZiAoIWF2b2lkQ2FsbGluZ0dlb2xvY0FwaSkge1xuICAgICAgICB0aGlzLmdlb1NlYXJjaEZvcm1Hcm91cC5jb250cm9scy5wbGFjZUlucHV0LnBhdGNoVmFsdWUodGhpcy5nZW9jb2RlU2VydmljZS5nZXRSZWFkYmxlQWRkcmVzcyhvc21QbGFjZSksIHtlbWl0RXZlbnQ6IGZhbHNlfSk7XG4gICAgICB9XG5cbiAgICAgIC8vIGJpbmQgX2xvY2F0aW9uICYgZW1pdCBsb2NhdGlvblxuICAgICAgaWYgKGF2b2lkQ2FsbGluZ0VsZXZhdGlvbkFwaSkge1xuICAgICAgICB0aGlzLmJpbmRMb2NhdGlvbk91dHB1dChbdGhpcy5lbGV2YXRpb25Gb3JtR3JvdXAuY29udHJvbHMuZWxldmF0aW9uSW5wdXQudmFsdWUsIG9zbVBsYWNlXSk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB0aGlzLmJpbmRMb2NhdGlvbk91dHB1dChyZXN1bHQpO1xuICAgICAgfVxuXG4gICAgfSwgZXJyb3IgPT4ge1xuICAgICAgLy8gTWFuYWdlIGVycm9yXG4gICAgICAvLyBzcGlubm5lcnMgb2ZmXG4gICAgICB0aGlzLmlzTG9hZGluZ0FkZHJlc3MgPSBmYWxzZTtcbiAgICAgIHRoaXMuaXNMb2FkaW5nRWxldmF0aW9uID0gZmFsc2U7XG4gICAgfSk7XG4gIH1cblxuICAvKipcbiAgICogU2hvdWxkIGJlIGltcHJvdmVkIGZvciBjb21wbGV4IHBvbHlnb25zIC8gcG9seWxpbmVzID9cbiAgICogQ291bGQgdXNlIHR1cmYuanNcbiAgICovXG4gIHNldExhdExuZ0lucHV0RnJvbURyYXduSXRlbXMoKTogdm9pZCB7XG4gICAgY29uc3QgY2VudHJvaWQgPSB0aGlzLmRyYXduSXRlbXMuZ2V0Qm91bmRzKCkuZ2V0Q2VudGVyKCk7XG4gICAgdGhpcy5sYXRsbmdGb3JtR3JvdXAuY29udHJvbHMubGF0SW5wdXQuc2V0VmFsdWUoY2VudHJvaWQubGF0KTtcbiAgICB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5sbmdJbnB1dC5zZXRWYWx1ZShjZW50cm9pZC5sbmcpO1xuICB9XG5cbiAgLyoqXG4gICAqXG4gICAqL1xuICBzZXRMYXRMbmdEbXNJbnB1dEZyb21EcmF3bkl0ZW1zKCk6IHZvaWQge1xuICAgIGNvbnN0IGNlbnRyb2lkID0gdGhpcy5kcmF3bkl0ZW1zLmdldEJvdW5kcygpLmdldENlbnRlcigpO1xuICAgIGNvbnN0IGdlb3BvaW50ID0gbmV3IEdlb1BvaW50KGNlbnRyb2lkLmxuZywgY2VudHJvaWQubGF0KTtcbiAgICB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMYXRJbnB1dC5wYXRjaFZhbHVlKGdlb3BvaW50LmdldExhdERlZygpKTtcbiAgICB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMbmdJbnB1dC5wYXRjaFZhbHVlKGdlb3BvaW50LmdldExvbkRlZygpKTtcbiAgfVxuXG4gIC8qKlxuICAgKlxuICAgKi9cbiAgZ2V0RWxldmF0aW9uRnJvbUlucHV0VmFsdWUoKTogT2JzZXJ2YWJsZTxudW1iZXI+IHtcbiAgICByZXR1cm4gdGhpcy5lbGV2YXRpb25TZXJ2aWNlLmdldEVsZXZhdGlvbih0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5sYXRJbnB1dC52YWx1ZSwgdGhpcy5sYXRsbmdGb3JtR3JvdXAuY29udHJvbHMubG5nSW5wdXQudmFsdWUpO1xuICB9XG5cbiAgLyoqXG4gICAqIFJldmVyc2UgZ2VvY29kaW5nIGZyb20gbGF0IC8gbG5nIGlucHV0cyB2YWx1ZXNcbiAgICovXG4gIHJldmVyc2VHZW9jb2RpbmdGcm9tSW5wdXRWYWx1ZSgpOiBPYnNlcnZhYmxlPGFueT4ge1xuICAgIHJldHVybiB0aGlzLmdlb2NvZGVTZXJ2aWNlLnJldmVyc2UodGhpcy5sYXRsbmdGb3JtR3JvdXAuY29udHJvbHMubGF0SW5wdXQudmFsdWUsIHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmxuZ0lucHV0LnZhbHVlKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBMYXRpdHVkZSAvIGxvbmdpdHVkZSBETVMgZm9ybSBWYWxpZGF0b3JcbiAgICovXG4gIGxhdExuZ0Rtc1ZhbGlkYXRvcihjb250cm9sOiBGb3JtQ29udHJvbCkge1xuICAgIGNvbnN0IHJlZ2V4cCA9IG5ldyBSZWdFeHAoJ14oXFxcXC0pP1swLTldezEsMn1cXFxcw4LCsCBbMC05XXsxLDJ9XFxcXFxcJyBbMC05XXsxLDJ9XFxcXC5bMC05XXsxLDEyfVxcXFxcIicpO1xuICAgIHJldHVybiByZWdleHAudGVzdChjb250cm9sLnZhbHVlKSA/IG51bGwgOiB7IG1hbGZvcm1lZExhdExuZ0Rtc0Zvcm1hdDogdHJ1ZSB9O1xuICB9XG5cbiAgLyoqXG4gICAqIExhdGl0dWRlIC8gbG9uZ2l0dWRlIGRlY2ltYWwgZm9ybSB2YWxpZGF0b3JcbiAgICovXG4gIGxhdExuZ0RlY1ZhbGlkYXRvcihjb250cm9sOiBGb3JtQ29udHJvbCkge1xuICAgIGNvbnN0IHJlZ2V4cCA9IG5ldyBSZWdFeHAoJ14oXFxcXC0pP1swLTldezEsMn1cXFxcLlswLTldezEsMjB9Jyk7XG4gICAgcmV0dXJuIHJlZ2V4cC50ZXN0KGNvbnRyb2wudmFsdWUpID8gbnVsbCA6IHsgbWFsZm9ybWVkTGF0TG5nRGVjRm9ybWF0OiB0cnVlIH07XG4gIH1cblxuICAvKipcbiAgICogV2hlbiB1c2VyIHNlbGVjdCBhbiBhZGRyZXNzIHdpdGhpbiB0aGUgYXV0b2NvbXBsZXRlIHJlc3VsdHMgbGlzdFxuICAgKlxuICAgKiBDYWxsIHRoZSBnZW9sb2MgQVBJIDIgdGltZXMgOlxuICAgKiAgLSBmaXJzdCBjYWxsIGlzIGZvciByZXZlcnNlIGdlb2NvZGluZ1xuICAgKiAgLSBzZWNvbmQgY2FsbCBpcyBmb3IgZ2VvY29uZGluZywgc28gdGhlIGFkZHJlc3MgaW5wdXQgKHBsYWNlSW5wdXQpIGlzIHVwZGF0ZWRcbiAgICovXG4gIGFkZHJlc3NTZWxlY3RlZENoYW5nZWQoZXZlbnQ6IE1hdEF1dG9jb21wbGV0ZVNlbGVjdGVkRXZlbnQpIHtcbiAgICBjb25zdCBvc21QbGFjZSA9IGV2ZW50Lm9wdGlvbi52YWx1ZTtcbiAgICAvLyBGaXQgbWFwIGJvdW5kc1xuICAgIGNvbnN0IHNvdXRoV2VzdCA9IG5ldyBMLkxhdExuZyhvc21QbGFjZS5ib3VuZGluZ2JveFswXSwgb3NtUGxhY2UuYm91bmRpbmdib3hbMl0pO1xuICAgIGNvbnN0IG5vcnRoRWFzdCA9IG5ldyBMLkxhdExuZyhvc21QbGFjZS5ib3VuZGluZ2JveFsxXSwgb3NtUGxhY2UuYm91bmRpbmdib3hbM10pO1xuICAgIHRoaXMubWFwLmZpdEJvdW5kcyhMLmxhdExuZ0JvdW5kcyhzb3V0aFdlc3QsIG5vcnRoRWFzdCkpO1xuXG4gICAgLy8gQWRkIGdlb2pzb24gdG8gdGhlIG1hcCAoaWYgdXNlciBlbnRlciBhIGNpdHksIGRyYXcgdGhlIGFkbWluaXN0cmF0aXZlIHNoYXBlIG9uIHRoZSBtYXApXG4gICAgdGhpcy5jbGVhckdlb1Jlc3VsdHNMYXllcigpO1xuICAgIHRoaXMuZ2VvUmVzdWx0c0xheWVyLmFkZERhdGEob3NtUGxhY2UuZ2VvanNvbik7XG5cbiAgICAvLyBGbHlcbiAgICB0aGlzLmZseVRvR2VvUmVzdWx0c0l0ZW1zKCk7XG5cbiAgICAvLyBQYXRjaCBpbnB1dCB2YWx1ZVxuICAgIHRoaXMuZ2VvU2VhcmNoRm9ybUdyb3VwLmNvbnRyb2xzLnBsYWNlSW5wdXQucGF0Y2hWYWx1ZSh0aGlzLmdlb2NvZGVTZXJ2aWNlLmdldFJlYWRibGVBZGRyZXNzKG9zbVBsYWNlKSwge2VtaXRFdmVudDogZmFsc2V9KTtcbiAgICAvLyBGaWxsIGxhdGl0dWRlLCBsb25naXR1ZGUgJiBhbHRpdHVkZSBpbnB1dHNcbiAgICBjb25zdCBnID0gbmV3IEdlb1BvaW50KE51bWJlcihvc21QbGFjZS5sb24pLCBOdW1iZXIob3NtUGxhY2UubGF0KSk7XG4gICAgdGhpcy5sYXRsbmdGb3JtR3JvdXAuY29udHJvbHMubGF0SW5wdXQuc2V0VmFsdWUob3NtUGxhY2UubGF0LCB7ZW1pdEV2ZW50OiBmYWxzZX0pO1xuICAgIHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmxuZ0lucHV0LnNldFZhbHVlKG9zbVBsYWNlLmxvbiwge2VtaXRFdmVudDogZmFsc2V9KTtcbiAgICB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMYXRJbnB1dC5zZXRWYWx1ZShnLmdldExhdERlZygpICwge2VtaXRFdmVudDogZmFsc2V9KTtcbiAgICB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5kbXNMbmdJbnB1dC5zZXRWYWx1ZShnLmdldExvbkRlZygpLCB7ZW1pdEV2ZW50OiBmYWxzZX0pO1xuICAgIHRoaXMuZWxldmF0aW9uRm9ybUdyb3VwLmNvbnRyb2xzLmVsZXZhdGlvbklucHV0LnNldFZhbHVlKG9zbVBsYWNlLmVsZXZhdGlvbiwge2VtaXRFdmVudDogZmFsc2V9KTtcblxuICAgIC8vIERyYXcgYSBwb2x5bGluZSBvciBwbGFjZSBhIG1hcmtlciBhdCB0aGUgY2VudGVyIG9mIGEgcG9seWdvblxuICAgIGlmIChvc21QbGFjZS5nZW9qc29uLnR5cGUgPT09ICdMaW5lU3RyaW5nJykge1xuICAgICAgLy8gb3NtIGdlb2pzb24gY29vcmRpbmF0ZXMgaXMgbGlrZSBbW2xvbmcsIGxhdF0sIFtsb25nLCBsYXRdLCAuLi5dXG4gICAgICAvLyBidXQgbGVhZmxldCBuZWVkcyBbW2xhdCwgbG9uZ10sIFtsYXQsIGxvbmddLCAuLi5dIGZvcm1hdCAhXG4gICAgICB0aGlzLmdlb2NvZGVTZXJ2aWNlLnNpbXBsaWZ5UG9seWxpbmUob3NtUGxhY2UuZ2VvanNvbi5jb29yZGluYXRlcyk7XG4gICAgICB0aGlzLmFkZFBvbHlsaW5lKHRoaXMuZ2VvY29kZVNlcnZpY2UucmV2ZXJzZUNvcnJkaW5hdGVzQXJyYXkoXG4gICAgICAgIHRoaXMuZ2VvY29kZVNlcnZpY2Uuc2ltcGxpZnlQb2x5bGluZShvc21QbGFjZS5nZW9qc29uLmNvb3JkaW5hdGVzKSkgYXMgTGF0TG5nRXhwcmVzc2lvbltdXG4gICAgICApO1xuICAgICAgdGhpcy5jbGVhckdlb1Jlc3VsdHNMYXllcigpO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmFkZE1hcmtlckZyb21MYXRMbmdDb29yZCgpO1xuICAgIH1cblxuICAgIC8vIENhbGwgZ2VvbG9jIGFuZCBlbGV2YXRpb24gQVBJc1xuICAgIHRoaXMuY2FsbEdlb2xvY0VsZXZhdGlvbkFwaXNVc2luZ0xhdExuZ0lucHV0c1ZhbHVlcyhmYWxzZSwgZmFsc2UpO1xuXG4gIH1cblxuICAvKipcbiAgICogQ2xlYXIgdGhlIGZvcm0gd2hlbiBuZWRkZWQgOiAnZHJhdzpkZWxldGVkJywgZXRjLlxuICAgKi9cbiAgY2xlYXJGb3JtKCk6IHZvaWQge1xuICAgIHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmxhdElucHV0LnNldFZhbHVlKCcnLCB7ZW1pdEV2ZW50OiBmYWxzZX0pO1xuICAgIHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmxuZ0lucHV0LnNldFZhbHVlKCcnLCB7ZW1pdEV2ZW50OiBmYWxzZX0pO1xuICAgIHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmRtc0xhdElucHV0LnNldFZhbHVlKCcnLCB7ZW1pdEV2ZW50OiBmYWxzZX0pO1xuICAgIHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmRtc0xuZ0lucHV0LnNldFZhbHVlKCcnLCB7ZW1pdEV2ZW50OiBmYWxzZX0pO1xuICAgIHRoaXMubGF0bG5nRm9ybUdyb3VwLnJlc2V0KCk7XG5cbiAgICB0aGlzLmVsZXZhdGlvbkZvcm1Hcm91cC5jb250cm9scy5lbGV2YXRpb25JbnB1dC5zZXRWYWx1ZSgnJywge2VtaXRFdmVudDogZmFsc2V9KTtcbiAgICB0aGlzLmVsZXZhdGlvbkZvcm1Hcm91cC5yZXNldCgpO1xuXG4gICAgdGhpcy5nZW9TZWFyY2hGb3JtR3JvdXAuY29udHJvbHMucGxhY2VJbnB1dC5zZXRWYWx1ZSgnJywge2VtaXRFdmVudDogZmFsc2V9KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDbGVhciBnZW9SZXN1bHRzIGxheWVyIChlZyB0aGlzIGxheWVyIGNvbnRhaW5zIGFkbWluaXN0cmF0aXZlIHBvbHlnb25zIC0tIFwiY29tbXVuZVwiKVxuICAgKi9cbiAgY2xlYXJHZW9SZXN1bHRzTGF5ZXIoKSB7XG4gICAgdGhpcy5nZW9SZXN1bHRzTGF5ZXIuY2xlYXJMYXllcnMoKTtcbiAgfVxuXG4gIC8qKlxuICAgKlxuICAgKi9cbiAgY2xlYXJEcmF3bkl0ZW1zTGF5ZXIoKTogdm9pZCB7XG4gICAgdGhpcy5kcmF3bkl0ZW1zLmNsZWFyTGF5ZXJzKCk7XG4gIH1cblxuICAvKipcbiAgICpcbiAgICovXG4gIHJlc2V0TG9jYXRpb24oKSB7XG4gICAgdGhpcy5sb2NhdGlvbiA9IG51bGw7XG4gIH1cblxuICAvKipcbiAgICogQmluZCBkYXRhIGZyb20gZWxldmF0aW9uIGFuZCBPU00gaHR0cCByZXN1bHRzIHRvIHRoaXMuX2xvY2F0aW9uXG4gICAqIFBlcmZvcm0gc29tZSB2ZXJpZmljYXRpb25zIHRvIGVuc3VyZSBkYXRhIGludGVncml0eVxuICAgKiBAcGFyYW0gZGF0YSBkYXRhWzBdID0gZWxldmF0aW9uLCBkYXRhWzFdID0gb3NtIGRhdGEgfCBkYXRhID0gb3NtIGRhdGFcbiAgICovXG4gIGJpbmRMb2NhdGlvbk91dHB1dChkYXRhOiBBcnJheTxhbnk+IHwgYW55KTogdm9pZCB7XG4gICAgLy8gaWYgZWxldmF0aW9uID0gMCBvciBudWxsID9cbiAgICAvLyBpZiBvc20gZGF0YSBpbmNvbXBsZXRlID9cbiAgICBsZXQgZWxldmF0aW9uOiBhbnk7XG4gICAgbGV0IG9zbVBsYWNlOiBhbnk7XG4gICAgaWYgKEFycmF5LmlzQXJyYXkoZGF0YSkpIHtcbiAgICAgIGVsZXZhdGlvbiA9IGRhdGFbMF07XG4gICAgICBvc21QbGFjZSA9IGRhdGFbMV07XG4gICAgfSBlbHNlIHtcbiAgICAgIGVsZXZhdGlvbiA9IHRoaXMuZWxldmF0aW9uRm9ybUdyb3VwLmNvbnRyb2xzLmVsZXZhdGlvbklucHV0LnZhbHVlO1xuICAgICAgb3NtUGxhY2UgPSBkYXRhO1xuICAgIH1cbiAgICB0aGlzLl9sb2NhdGlvbi5nZW9tZXRyeSA9IHRoaXMuZHJhd25JdGVtcy50b0dlb0pTT04oKTtcbiAgICAvLyBnZW9kYXR1bVxuICAgIHRoaXMuX2xvY2F0aW9uLmVsZXZhdGlvbiA9IGVsZXZhdGlvbjtcbiAgICB0aGlzLl9sb2NhdGlvbi5sb2NhbGl0eUNvbnNpc3RlbmN5ID0gdGhpcy5fbG9jYXRpb24ubG9jYWxpdHlDb25zaXN0ZW5jeSA/IHRydWUgOiBudWxsOyAgIC8vIHBlcmZvcm0gOiBDb2jDg8KpcmVuY2UgZW50cmUgbGVzIGNvb3Jkb25uw4PCqWVzIGV0IGxhIGxvY2FsaXTDg8KpXG4gICAgdGhpcy5fbG9jYXRpb24ubG9jYXRpb25BY2N1cmFjeSA9IHRoaXMuX2xvY2F0aW9uLmxvY2F0aW9uQWNjdXJhY3kgPyAwIDogbnVsbDsgICAgICAgICAvLyBwZXJmb3JtIDogUHLDg8KpY2lzaW9uIChvdSBpbmNlcnRpdHVkZSkgZGUgbGEgbG9jYWxpc2F0aW9uLCBlbiBtw4PCqHRyZXMgLS0+IHZvaXIgbGUgbm9tYnJlIGRlIGTDg8KpY2ltYWxlcyBwb3VyIGRlY0xhdElucHV0IG91IGRlY0xuZ0lucHV0IHNpIHBvaW50LCBzaW5vbiwgZGVtaS1sb25nZXVyIGRlIGxhIGJvdW5kaW5nLWJveFxuICAgIC8vIHB1Ymxpc2hlZF9sb2NhdGlvbiA6IFByw4PCqWNpc2lvbiBnw4PCqW9ncmFwaGlxdWUgw4PCoCBsYXF1ZWxsZSBlc3QgcHVibGnDg8KpZSBsJ29icywgcGVybWV0IGRlIGfDg8KpcmVyIGxlIGZsb3V0YWdlIC0gUHLDg8KpY2lzZSwgTG9jYWxpdMODwqksIE1haWxsZSAxMHgxMGttXG5cbiAgICB0aGlzLl9sb2NhdGlvbi5vc21Db3VudHJ5ID0gb3NtUGxhY2UuYWRkcmVzcy5jb3VudHJ5O1xuICAgIHRoaXMuX2xvY2F0aW9uLm9zbUNvdW50cnlDb2RlID0gb3NtUGxhY2UuYWRkcmVzcy5jb3VudHJ5X2NvZGU7XG4gICAgdGhpcy5fbG9jYXRpb24ub3NtQ291bnR5ID0gb3NtUGxhY2UuYWRkcmVzcy5jb3VudHk7XG4gICAgdGhpcy5fbG9jYXRpb24ub3NtUG9zdGNvZGUgPSBvc21QbGFjZS5hZGRyZXNzLnBvc3Rjb2RlO1xuICAgIGlmIChvc21QbGFjZS5hZGRyZXNzLmNpdHkpIHsgdGhpcy5fbG9jYXRpb24ubG9jYWxpdHkgPSBvc21QbGFjZS5hZGRyZXNzLmNpdHk7IH1cbiAgICBpZiAob3NtUGxhY2UuYWRkcmVzcy50b3duKSB7IHRoaXMuX2xvY2F0aW9uLmxvY2FsaXR5ID0gb3NtUGxhY2UuYWRkcmVzcy50b3duOyB9XG4gICAgaWYgKG9zbVBsYWNlLmFkZHJlc3MudmlsbGFnZSkgeyB0aGlzLl9sb2NhdGlvbi5sb2NhbGl0eSA9IG9zbVBsYWNlLmFkZHJlc3MudmlsbGFnZTsgfVxuXG4gICAgdGhpcy5fbG9jYXRpb24uc3VibG9jYWxpdHkgPSBvc21QbGFjZS5oYW1sZXQ7XG5cbiAgICB0aGlzLl9sb2NhdGlvbi5vc21Sb2FkID0gb3NtUGxhY2UuYWRkcmVzcy5yb2FkO1xuICAgIHRoaXMuX2xvY2F0aW9uLm9zbVN0YXRlID0gb3NtUGxhY2UuYWRkcmVzcy5zdGF0ZTtcbiAgICB0aGlzLl9sb2NhdGlvbi5vc21TdWJ1cmIgPSBvc21QbGFjZS5hZGRyZXNzLnN1YnVyYjtcblxuICAgIHRoaXMuX2xvY2F0aW9uLm9zbUlkID0gb3NtUGxhY2Uub3NtX2lkO1xuICAgIHRoaXMuX2xvY2F0aW9uLm9zbU5laWdoYm91cmhvb2QgPSBudWxsOyAgICAgIC8vIG5vdCBwcm92aWRlZCBieSBub21pbmF0aW1cbiAgICB0aGlzLl9sb2NhdGlvbi5vc21QbGFjZUlkID0gb3NtUGxhY2UucGxhY2VfaWQ7XG4gICAgdGhpcy5fbG9jYXRpb24ucHVibGlzaGVkTG9jYXRpb24gPSBudWxsOyAgICAgLy8gcGVyZm9ybVxuICAgIHRoaXMuX2xvY2F0aW9uLnN0YXRpb24gPSBudWxsOyAgICAgICAgICAgICAgIC8vIHBlcmZvcm1cblxuICAgIC8vIFZlcmlmaWNhdGlvbnNcbiAgICAvLyBAdG9kb1xuXG4gICAgLy8gRW1pdFxuICAgIHRoaXMubG9jYXRpb24ubmV4dCh0aGlzLl9sb2NhdGlvbik7XG4gIH1cblxuICAvKipcbiAgICogQ2hhbmdlIHRoZSBmb3JtIGNvb3JkaW5hdGVzIGZvcm1hdCA6ICdkZWNpbWFsJyBvciAnZG1zJ1xuICAgKi9cbiAgc2V0TGF0TG5nSW5wdXRGb3JtYXQoZm9ybWF0OiBzdHJpbmcpOiB2b2lkIHtcbiAgICBpZiAoZm9ybWF0ICE9PSAnZGVjaW1hbCcgJiYgZm9ybWF0ICE9PSAnZG1zJykgeyByZXR1cm47IH1cbiAgICB0aGlzLmNvb3JkRm9ybWF0ID0gZm9ybWF0O1xuICB9XG5cbiAgLyoqXG4gICAqIFNldCBpbnB1dHMgdmFsdWVzLCBhZGQgYSBtYXJrZXIgYW5kIGNhbGwgQVBJIGZvciBhIGdlb2xvY2F0ZWQgcGhvdG9cbiAgICovXG4gIGdwc01hcmtlclNldFZhbHVlcyhsYXREZWMsIGxuZ0RlYywgZWxldmF0aW9uKSB7XG4gICAgLy8gc2V0IGlucHV0cyB2YWx1ZXNcbiAgICB0aGlzLmxhdGxuZ0Zvcm1Hcm91cC5jb250cm9scy5sYXRJbnB1dC5zZXRWYWx1ZShsYXREZWMpO1xuICAgIHRoaXMubGF0bG5nRm9ybUdyb3VwLmNvbnRyb2xzLmxuZ0lucHV0LnNldFZhbHVlKGxuZ0RlYyk7XG4gICAgdGhpcy5lbGV2YXRpb25Gb3JtR3JvdXAuY29udHJvbHMuZWxldmF0aW9uSW5wdXQuc2V0VmFsdWUoZWxldmF0aW9uKTtcblxuICAgIC8vIGFkZCBtYXJrZXJcbiAgICB0aGlzLmFkZE1hcmtlckZyb21MYXRMbmdDb29yZCgpO1xuXG4gICAgLy8gY2FsbCBBUElzXG4gICAgdGhpcy5jYWxsR2VvbG9jRWxldmF0aW9uQXBpc1VzaW5nTGF0TG5nSW5wdXRzVmFsdWVzKHRydWUsIGZhbHNlKTtcblxuICAgIC8vIGNsZWFyIGdlb2xvY2F0ZWQgcGhvdG9zIGxheWVyXG4gICAgdGhpcy5nZW9sb2NhdGVkUGhvdG9MYXRMbmdMYXllci5jbGVhckxheWVycygpO1xuICB9XG5cbiAgbGF0TG5nRG1zQXV0b0Zvcm1hdHRlcih2YWx1ZSk6IHN0cmluZyB7XG4gICAgcmV0dXJuICcnO1xuICB9XG59XG4iLCJpbXBvcnQgeyBQaXBlLCBQaXBlVHJhbnNmb3JtIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBPc21QbGFjZU1vZGVsIH0gZnJvbSAnLi4vX21vZGVscy9vc21QbGFjZS5tb2RlbCc7XG5pbXBvcnQgeyBHZW9jb2RpbmdTZXJ2aWNlIH0gZnJvbSAnLi4vX3NlcnZpY2VzL2dlb2NvZGluZy5zZXJ2aWNlJztcblxuLyoqXG4gKiBUbyBzaG93IGFuIGFkZHJlc3MgdG8gdGhlIHVzZXIsIHdlIGNvdWxkIHVzZSB0aGUgZGlzcGxheV9uYW1lIGF0dHJpYnV0ZSByZXR1cm5lZCBieSBub21pbmF0aW1cbiAqIFRoaXMgYXR0cmlidXRlIGlzIGZhciBjb21wbGljYXRlZCB0byByZWFkIChyb2FkLCBuZWlnaGJvdXJob29kLCBzdWJ1cmIsIHRvd24sIGNpdHksIHBvc3Rjb2RlLCBjb3VudHksIGNvdW50cnksIGV0Yy4pXG4gKiBUaGlzIHBpcGUgdXNlIHRoZSBnZXRSZWFkYmxlQWRkcmVzcygpIGZ1bmN0aW9uIG9mIGdlb2NvZGUgc2VydmljZSB0byBzaG93IG1pbmltYWwgaW5mb3JtYXRpb24gYWJvdXQgdGhlIGFkZHJlc3MgcmV0dXJuZWQgYnkgbm9taW5hdGltIEFQSVxuICovXG5AUGlwZSh7XG4gIG5hbWU6ICdvc21QbGFjZVJlYWRhYmxlQWRkcmVzcydcbn0pXG5leHBvcnQgY2xhc3MgT3NtUGxhY2VSZWFkYWJsZUFkZHJlc3NQaXBlIGltcGxlbWVudHMgUGlwZVRyYW5zZm9ybSB7XG5cbiAgY29uc3RydWN0b3IocHJpdmF0ZSBnZW9jb2RlU2VydmljZTogR2VvY29kaW5nU2VydmljZSkgeyB9XG5cbiAgdHJhbnNmb3JtKHZhbHVlOiBPc21QbGFjZU1vZGVsLCBhcmdzPzogYW55KTogc3RyaW5nIHtcbiAgICByZXR1cm4gdGhpcy5nZW9jb2RlU2VydmljZS5nZXRSZWFkYmxlQWRkcmVzcyh2YWx1ZSk7XG4gIH1cblxufVxuIiwiaW1wb3J0IHsgTmdNb2R1bGUgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IENvbW1vbk1vZHVsZSB9IGZyb20gJ0Bhbmd1bGFyL2NvbW1vbic7XG5pbXBvcnQgeyBCcm93c2VyQW5pbWF0aW9uc01vZHVsZSB9IGZyb20gJ0Bhbmd1bGFyL3BsYXRmb3JtLWJyb3dzZXIvYW5pbWF0aW9ucyc7XG5pbXBvcnQgeyBCcm93c2VyTW9kdWxlIH0gZnJvbSAnQGFuZ3VsYXIvcGxhdGZvcm0tYnJvd3Nlcic7XG5pbXBvcnQgeyBIdHRwQ2xpZW50TW9kdWxlIH0gZnJvbSAnQGFuZ3VsYXIvY29tbW9uL2h0dHAnO1xuaW1wb3J0IHsgRm9ybXNNb2R1bGUgfSBmcm9tICdAYW5ndWxhci9mb3Jtcyc7XG5pbXBvcnQgeyBSZWFjdGl2ZUZvcm1zTW9kdWxlIH0gZnJvbSAnQGFuZ3VsYXIvZm9ybXMnO1xuaW1wb3J0IHsgTWF0U2VsZWN0TW9kdWxlLCBNYXRJbnB1dE1vZHVsZSwgTWF0QXV0b2NvbXBsZXRlTW9kdWxlLCBNYXRQcm9ncmVzc1NwaW5uZXJNb2R1bGUsIE1hdFRvb2x0aXBNb2R1bGUsIE1hdENoaXBzTW9kdWxlLCBNYXRJY29uTW9kdWxlLCBNYXRCdXR0b25Nb2R1bGUsIE1hdFJhZGlvTW9kdWxlLCBNYXRQcm9ncmVzc0Jhck1vZHVsZSwgTWF0TWVudU1vZHVsZSwgTWF0VGFibGVNb2R1bGUgfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbCc7XG5pbXBvcnQgeyBMZWFmbGV0TW9kdWxlIH0gZnJvbSAnQGFzeW1tZXRyaWsvbmd4LWxlYWZsZXQnO1xuaW1wb3J0IHsgTGVhZmxldERyYXdNb2R1bGUgfSBmcm9tICdAYXN5bW1ldHJpay9uZ3gtbGVhZmxldC1kcmF3JztcblxuaW1wb3J0IHsgVGJHZW9sb2NMaWJDb21wb25lbnQgfSBmcm9tICcuL3RiLWdlb2xvYy1saWIuY29tcG9uZW50JztcbmltcG9ydCB7IE1hcENvbXBvbmVudCB9IGZyb20gJy4vbWFwL21hcC5jb21wb25lbnQnO1xuaW1wb3J0IHsgR2VvY29kaW5nU2VydmljZSB9IGZyb20gJy4vX3NlcnZpY2VzL2dlb2NvZGluZy5zZXJ2aWNlJztcbmltcG9ydCB7IEVsZXZhdGlvblNlcnZpY2UgfSBmcm9tICcuL19zZXJ2aWNlcy9lbGV2YXRpb24uc2VydmljZSc7XG5pbXBvcnQgeyBPc21QbGFjZVJlYWRhYmxlQWRkcmVzc1BpcGUgfSBmcm9tICcuL19waXBlcy9vc20tcGxhY2UtcmVhZGFibGUtYWRkcmVzcy5waXBlJztcblxuQE5nTW9kdWxlKHtcbiAgaW1wb3J0czogW1xuICAgIENvbW1vbk1vZHVsZSxcbiAgICBCcm93c2VyQW5pbWF0aW9uc01vZHVsZSxcbiAgICBCcm93c2VyTW9kdWxlLFxuICAgIEh0dHBDbGllbnRNb2R1bGUsXG4gICAgTWF0U2VsZWN0TW9kdWxlLCBNYXRJbnB1dE1vZHVsZSwgTWF0QXV0b2NvbXBsZXRlTW9kdWxlLCBNYXRQcm9ncmVzc1NwaW5uZXJNb2R1bGUsIE1hdFRvb2x0aXBNb2R1bGUsIE1hdENoaXBzTW9kdWxlLCBNYXRJY29uTW9kdWxlLCBNYXRCdXR0b25Nb2R1bGUsIE1hdFJhZGlvTW9kdWxlLCBNYXRQcm9ncmVzc0Jhck1vZHVsZSwgTWF0TWVudU1vZHVsZSwgTWF0VGFibGVNb2R1bGUsXG4gICAgTGVhZmxldE1vZHVsZS5mb3JSb290KCksIExlYWZsZXREcmF3TW9kdWxlLmZvclJvb3QoKSxcbiAgICBGb3Jtc01vZHVsZSxcbiAgICBSZWFjdGl2ZUZvcm1zTW9kdWxlXSxcbiAgZGVjbGFyYXRpb25zOiBbIFRiR2VvbG9jTGliQ29tcG9uZW50LCBNYXBDb21wb25lbnQsIE9zbVBsYWNlUmVhZGFibGVBZGRyZXNzUGlwZSBdLFxuICBleHBvcnRzOiBbIFRiR2VvbG9jTGliQ29tcG9uZW50LCBNYXBDb21wb25lbnQgXVxufSlcbmV4cG9ydCBjbGFzcyBUYkdlb2xvY0xpYk1vZHVsZSB7XG4gIHByb3ZpZGVyczogW1xuICAgIEdlb2NvZGluZ1NlcnZpY2UsIEVsZXZhdGlvblNlcnZpY2VcbiAgXTtcbn1cbiJdLCJuYW1lcyI6WyJtYXJrZXIiLCJMLm1hcmtlciIsIkwuaWNvbiIsIkwuQ29udHJvbCIsIkwudGlsZUxheWVyIiwiTC5nZW9KU09OIiwiTC5sYXRMbmciLCJMLkZlYXR1cmVHcm91cCIsImxlYWZsZXRPYmplY3RzLmRyYXdDb250cm9sUGFuZWwiLCJsZWFmbGV0T2JqZWN0cy5kcmF3Q29udHJvbEVkaXRQYW5lbCIsImxlYWZsZXRPYmplY3RzLmNpcmNsZU1hcmtlclN0eWxlIiwibGVhZmxldE9iamVjdHMuY2l0eVN0eWxlIiwibGF0TG5nIiwiTC5NYXJrZXIiLCJsZWFmbGV0T2JqZWN0cy5ncHNQaG90b01hcmtlckljb24iLCJtYXAiLCJMLmNvbnRyb2wiLCJsZWFmbGV0T2JqZWN0cy5kcmFnZ2FibGVNYXJrZXIiLCJwb2x5bGluZSIsIkwucG9seWxpbmUiLCJjb250cm9sIiwiTC5MYXRMbmciLCJMLmxhdExuZ0JvdW5kcyJdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUFBO0lBU0U7S0FBaUI7Ozs7SUFFakIsdUNBQVE7OztJQUFSO0tBQ0M7O2dCQVZGLFNBQVMsU0FBQztvQkFDVCxRQUFRLEVBQUUseUJBQXlCO29CQUNuQyxRQUFRLEVBQUUsRUFBRTtvQkFDWixNQUFNLEVBQUUsRUFBRTtpQkFDWDs7OzsrQkFORDs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUNhQSxJQUFhLFFBQVEsR0FBRyxVQUFTLEdBQUcsRUFBRSxHQUFHO0lBR3ZDLFFBQVEsUUFBTyxHQUFHLENBQUM7UUFFZixLQUFLLFFBQVE7WUFFVCxJQUFJLENBQUMsTUFBTSxHQUFHLElBQUksQ0FBQyxPQUFPLENBQUMsR0FBRyxFQUFFLElBQUksQ0FBQyxPQUFPLENBQUMsQ0FBQztZQUM5QyxJQUFJLENBQUMsTUFBTSxHQUFHLEdBQUcsQ0FBQztZQUVsQixNQUFNO1FBRVYsS0FBSyxR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QUFFLE1BQU0sR0FBRyxNQUFNLENBQUMsS0FBSyxDQUFDLENBQUMsRUFBRSxNQUFNLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUM7YUFBRTs7WUFFbEYsSUFBSSxNQUFNLENBQUMsTUFBTSxDQUFDLEdBQUcsQ0FBQyxFQUFFLEVBQUU7Z0JBQUUsTUFBTSxHQUFHLEtBQUssQ0FBQzthQUFFO1lBQzdDLElBQUksTUFBTSxDQUFDLE1BQU0sQ0FBQyxHQUFHLEVBQUUsRUFBRTtnQkFBRSxNQUFNLEdBQUcsSUFBSSxDQUFDO2FBQUU7U0FDNUM7UUFDRCxJQUFJLENBQUMsQ0FBQyxNQUFNLEtBQUssQ0FBQyxFQUFFO1lBQ2xCLE1BQU0sR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7WUFBQyxNQUFNLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO1lBQzdCLElBQUksTUFBTSxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLENBQUMsRUFBRTtnQkFBRSxNQUFNLEdBQUcsTUFBTSxDQUFDLEtBQUssQ0FBQyxDQUFDLEVBQUUsTUFBTSxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDO2FBQUU7WUFDbEYsSUFBSSxNQUFNLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsQ0FBQyxFQUFFO2dCQUFFLE1BQU0sR0FBRyxNQUFNLENBQUMsS0FBSyxDQUFDLENBQUMsRUFBRSxNQUFNLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUM7YUFBRTtZQUNsRixJQUFJLE1BQU0sQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUFDLEVBQUUsRUFBRTtnQkFBRSxNQUFNLEdBQUcsS0FBSyxDQUFDO2FBQUU7WUFDN0MsSUFBSSxNQUFNLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxFQUFFO2dCQUFFLE1BQU0sR0FBRyxJQUFJLENBQUM7YUFBRTtZQUMzQyxJQUFJLE1BQU0sQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUFDLEVBQUUsRUFBRTtnQkFBRSxNQUFNLEdBQUcsS0FBSyxDQUFDO2FBQUU7WUFDN0MsSUFBSSxNQUFNLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxFQUFFO2dCQUFFLE1BQU0sR0FBRyxJQUFJLENBQUM7YUFBRTtTQUMxQztRQUNILElBQUksQ0FBQyxDQUFDLE1BQU0sS0FBSyxDQUFDLEVBQUU7WUFDbEIsTUFBTSxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUFDLE1BQU0sR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7WUFBQyxNQUFNLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO1lBQzVDLElBQUksTUFBTSxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLENBQUMsRUFBRTtnQkFBRSxNQUFNLEdBQUcsTUFBTSxDQUFDLEtBQUssQ0FBQyxDQUFDLEVBQUUsTUFBTSxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDO2FBQUU7WUFDbEYsSUFBSSxNQUFNLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsQ0FBQyxFQUFFO2dCQUFFLE1BQU0sR0FBRyxNQUFNLENBQUMsS0FBSyxDQUFDLENBQUMsRUFBRSxNQUFNLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUM7YUFBRTtZQUNsRixJQUFJLE1BQU0sQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUFDLEVBQUUsRUFBRTtnQkFBRSxNQUFNLEdBQUcsS0FBSyxDQUFDO2FBQUU7WUFDN0MsSUFBSSxNQUFNLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxFQUFFO2dCQUFFLE1BQU0sR0FBRyxJQUFJLENBQUM7YUFBRTtZQUMzQyxJQUFJLE1BQU0sQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUFDLEVBQUUsRUFBRTtnQkFBRSxNQUFNLEdBQUcsS0FBSyxDQUFDO2FBQUU7WUFDN0MsSUFBSSxNQUFNLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxFQUFFO2dCQUFFLE1BQU0sR0FBRyxJQUFJLENBQUM7YUFBRTtTQUMxQztRQUNILElB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
1721
 
1722
/***/ }),
1723
 
1724
/***/ "./node_modules/@angular/compiler/src sync recursive":
1725
/*!*************************************************!*\
1726
  !*** ./node_modules/@angular/compiler/src sync ***!
1727
  \*************************************************/
1728
/*! no static exports found */
1729
/***/ (function(module, exports) {
1730
 
1731
function webpackEmptyContext(req) {
1732
	var e = new Error('Cannot find module "' + req + '".');
1733
	e.code = 'MODULE_NOT_FOUND';
1734
	throw e;
1735
}
1736
webpackEmptyContext.keys = function() { return []; };
1737
webpackEmptyContext.resolve = webpackEmptyContext;
1738
module.exports = webpackEmptyContext;
1739
webpackEmptyContext.id = "./node_modules/@angular/compiler/src sync recursive";
1740
 
1741
/***/ }),
1742
 
1743
/***/ "./src/$$_lazy_route_resource lazy recursive":
1744
/*!**********************************************************!*\
1745
  !*** ./src/$$_lazy_route_resource lazy namespace object ***!
1746
  \**********************************************************/
1747
/*! no static exports found */
1748
/***/ (function(module, exports) {
1749
 
1750
function webpackEmptyAsyncContext(req) {
1751
	// Here Promise.resolve().then() is used instead of new Promise() to prevent
1752
	// uncaught exception popping up in devtools
1753
	return Promise.resolve().then(function() {
1754
		var e = new Error('Cannot find module "' + req + '".');
1755
		e.code = 'MODULE_NOT_FOUND';
1756
		throw e;
1757
	});
1758
}
1759
webpackEmptyAsyncContext.keys = function() { return []; };
1760
webpackEmptyAsyncContext.resolve = webpackEmptyAsyncContext;
1761
module.exports = webpackEmptyAsyncContext;
1762
webpackEmptyAsyncContext.id = "./src/$$_lazy_route_resource lazy recursive";
1763
 
1764
/***/ }),
1765
 
1766
/***/ "./src/app/app.component.css":
1767
/*!***********************************!*\
1768
  !*** ./src/app/app.component.css ***!
1769
  \***********************************/
1770
/*! no static exports found */
1771
/***/ (function(module, exports) {
1772
 
1773
module.exports = ""
1774
 
1775
/***/ }),
1776
 
1777
/***/ "./src/app/app.component.html":
1778
/*!************************************!*\
1779
  !*** ./src/app/app.component.html ***!
1780
  \************************************/
1781
/*! no static exports found */
1782
/***/ (function(module, exports) {
1783
 
1784
module.exports = "<tb-geoloc-map\n  [geolocatedPhotoLatLng]=testLatLngData\n  [osmClassFilter]=osmClassFilter\n  (location)=locationChange($event)>\n</tb-geoloc-map>\n\n\n<div (click)=\"emitLatLngData()\">Simuler l'import de photos géolocalisées</div>"
1785
 
1786
/***/ }),
1787
 
1788
/***/ "./src/app/app.component.ts":
1789
/*!**********************************!*\
1790
  !*** ./src/app/app.component.ts ***!
1791
  \**********************************/
1792
/*! exports provided: AppComponent */
1793
/***/ (function(module, __webpack_exports__, __webpack_require__) {
1794
 
1795
"use strict";
1796
__webpack_require__.r(__webpack_exports__);
1797
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "AppComponent", function() { return AppComponent; });
1798
/* harmony import */ var _angular_core__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @angular/core */ "./node_modules/@angular/core/fesm5/core.js");
1799
var __decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
1800
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1801
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1802
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1803
    return c > 3 && r && Object.defineProperty(target, key, r), r;
1804
};
1805
 
1806
var AppComponent = /** @class */ (function () {
1807
    function AppComponent() {
1808
        this.testLatLngData = new _angular_core__WEBPACK_IMPORTED_MODULE_0__["EventEmitter"]();
1809
        this.osmClassFilter = ['highway:*'];
1810
    }
1811
    AppComponent.prototype.locationChange = function (data) {
1812
        console.log(data);
1813
    };
1814
    AppComponent.prototype.emitLatLngData = function () {
1815
        var data = [
1816
            {
1817
                lat: { deg: 44, min: 27, sec: 8.976 },
1818
                lng: { deg: 1, min: 9, sec: 24.84 },
1819
                altitude: 187.6,
1820
                photoName: 'PA050156.JPG'
1821
            },
1822
            {
1823
                lat: { deg: 46, min: 27, sec: 5.432 },
1824
                lng: { deg: 3, min: 12, sec: 24.84 },
1825
                altitude: 187.6,
1826
                photoName: 'PA050234.JPG'
1827
            },
1828
            {
1829
                lat: { deg: 48, min: 25, sec: 8.765 },
1830
                lng: { deg: 6, min: 15, sec: 24.84 },
1831
                altitude: 187.6,
1832
                photoName: 'PA050789.JPG'
1833
            }
1834
        ];
1835
        console.log('app emit gps data...');
1836
        this.testLatLngData.next(data);
1837
    };
1838
    AppComponent = __decorate([
1839
        Object(_angular_core__WEBPACK_IMPORTED_MODULE_0__["Component"])({
1840
            selector: 'app-root',
1841
            template: __webpack_require__(/*! ./app.component.html */ "./src/app/app.component.html"),
1842
            styles: [__webpack_require__(/*! ./app.component.css */ "./src/app/app.component.css")]
1843
        })
1844
    ], AppComponent);
1845
    return AppComponent;
1846
}());
1847
 
1848
 
1849
 
1850
/***/ }),
1851
 
1852
/***/ "./src/app/app.module.ts":
1853
/*!*******************************!*\
1854
  !*** ./src/app/app.module.ts ***!
1855
  \*******************************/
1856
/*! exports provided: AppModule */
1857
/***/ (function(module, __webpack_exports__, __webpack_require__) {
1858
 
1859
"use strict";
1860
__webpack_require__.r(__webpack_exports__);
1861
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "AppModule", function() { return AppModule; });
1862
/* harmony import */ var _angular_platform_browser__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @angular/platform-browser */ "./node_modules/@angular/platform-browser/fesm5/platform-browser.js");
1863
/* harmony import */ var _angular_core__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @angular/core */ "./node_modules/@angular/core/fesm5/core.js");
1864
/* harmony import */ var _app_component__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./app.component */ "./src/app/app.component.ts");
1865
/* harmony import */ var tb_geoloc_lib__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! tb-geoloc-lib */ "./dist/tb-geoloc-lib/fesm5/tb-geoloc-lib.js");
1866
var __decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
1867
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1868
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1869
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1870
    return c > 3 && r && Object.defineProperty(target, key, r), r;
1871
};
1872
 
1873
 
1874
 
1875
 
1876
var AppModule = /** @class */ (function () {
1877
    function AppModule() {
1878
    }
1879
    AppModule = __decorate([
1880
        Object(_angular_core__WEBPACK_IMPORTED_MODULE_1__["NgModule"])({
1881
            declarations: [
1882
                _app_component__WEBPACK_IMPORTED_MODULE_2__["AppComponent"]
1883
            ],
1884
            imports: [
1885
                _angular_platform_browser__WEBPACK_IMPORTED_MODULE_0__["BrowserModule"],
1886
                tb_geoloc_lib__WEBPACK_IMPORTED_MODULE_3__["TbGeolocLibModule"]
1887
            ],
1888
            providers: [],
1889
            bootstrap: [_app_component__WEBPACK_IMPORTED_MODULE_2__["AppComponent"]]
1890
        })
1891
    ], AppModule);
1892
    return AppModule;
1893
}());
1894
 
1895
 
1896
 
1897
/***/ }),
1898
 
1899
/***/ "./src/environments/environment.ts":
1900
/*!*****************************************!*\
1901
  !*** ./src/environments/environment.ts ***!
1902
  \*****************************************/
1903
/*! exports provided: environment */
1904
/***/ (function(module, __webpack_exports__, __webpack_require__) {
1905
 
1906
"use strict";
1907
__webpack_require__.r(__webpack_exports__);
1908
/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "environment", function() { return environment; });
1909
// This file can be replaced during build by using the `fileReplacements` array.
1910
// `ng build ---prod` replaces `environment.ts` with `environment.prod.ts`.
1911
// The list of file replacements can be found in `angular.json`.
1912
var environment = {
1913
    production: false
1914
};
1915
/*
1916
 * In development mode, to ignore zone related error stack frames such as
1917
 * `zone.run`, `zoneDelegate.invokeTask` for easier debugging, you can
1918
 * import the following file, but please comment it out in production mode
1919
 * because it will have performance impact when throw error
1920
 */
1921
// import 'zone.js/dist/zone-error';  // Included with Angular CLI.
1922
 
1923
 
1924
/***/ }),
1925
 
1926
/***/ "./src/main.ts":
1927
/*!*********************!*\
1928
  !*** ./src/main.ts ***!
1929
  \*********************/
1930
/*! no exports provided */
1931
/***/ (function(module, __webpack_exports__, __webpack_require__) {
1932
 
1933
"use strict";
1934
__webpack_require__.r(__webpack_exports__);
1935
/* harmony import */ var _angular_core__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @angular/core */ "./node_modules/@angular/core/fesm5/core.js");
1936
/* harmony import */ var _angular_platform_browser_dynamic__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @angular/platform-browser-dynamic */ "./node_modules/@angular/platform-browser-dynamic/fesm5/platform-browser-dynamic.js");
1937
/* harmony import */ var _app_app_module__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./app/app.module */ "./src/app/app.module.ts");
1938
/* harmony import */ var _environments_environment__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./environments/environment */ "./src/environments/environment.ts");
1939
 
1940
 
1941
 
1942
 
1943
if (_environments_environment__WEBPACK_IMPORTED_MODULE_3__["environment"].production) {
1944
    Object(_angular_core__WEBPACK_IMPORTED_MODULE_0__["enableProdMode"])();
1945
}
1946
Object(_angular_platform_browser_dynamic__WEBPACK_IMPORTED_MODULE_1__["platformBrowserDynamic"])().bootstrapModule(_app_app_module__WEBPACK_IMPORTED_MODULE_2__["AppModule"])
1947
    .catch(function (err) { return console.log(err); });
1948
 
1949
 
1950
/***/ }),
1951
 
1952
/***/ 0:
1953
/*!***************************!*\
1954
  !*** multi ./src/main.ts ***!
1955
  \***************************/
1956
/*! no static exports found */
1957
/***/ (function(module, exports, __webpack_require__) {
1958
 
1959
module.exports = __webpack_require__(/*! /home/stephane/dev/tb-geoloc-lib/src/main.ts */"./src/main.ts");
1960
 
1961
 
1962
/***/ })
1963
 
1964
},[[0,"runtime","vendor"]]]);
1965
//# sourceMappingURL=main.js.map