@wizishop/img-manager 18.2.2-beta → 19.0.0-beta.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (111) hide show
  1. package/README.md +24 -394
  2. package/fesm2022/wizishop-img-manager.mjs +1150 -953
  3. package/fesm2022/wizishop-img-manager.mjs.map +1 -1
  4. package/lib/components/images-view/images-actions-handler.d.ts +3 -2
  5. package/lib/components/images-view/images-view.component.d.ts +11 -5
  6. package/lib/components/images-view/table-view/table-view.component.d.ts +1 -0
  7. package/lib/components/img-editor/img-editor.component.d.ts +8 -1
  8. package/lib/components/img-editor/info-video/info-video.component.d.ts +20 -0
  9. package/lib/components/img-editor/show-iframe/show-iframe.component.d.ts +16 -0
  10. package/lib/components/img-selection/img-selection.component.d.ts +4 -3
  11. package/lib/components/img-tabs/img-tabs.component.d.ts +1 -0
  12. package/lib/dto/img-manager.dto.d.ts +9 -0
  13. package/lib/services/api.service.d.ts +1 -0
  14. package/lib/services/img-event.service.d.ts +3 -0
  15. package/lib/services/img-manager.service.d.ts +11 -14
  16. package/lib/services/rename-picture.service.d.ts +1 -0
  17. package/lib/services/table/filters-table.service.d.ts +1 -0
  18. package/lib/services/video-info.service.d.ts +23 -0
  19. package/lib/wz-img-manager.component.d.ts +2 -2
  20. package/lib/wz-img-manager.module.d.ts +46 -44
  21. package/package.json +17 -24
  22. package/assets/canva/icon_canva.svg +0 -4
  23. package/assets/i18n/en.json +0 -1
  24. package/assets/i18n/es.json +0 -1
  25. package/assets/i18n/fr.json +0 -1
  26. package/assets/i18n/it.json +0 -1
  27. package/assets/img/fake.png +0 -0
  28. package/assets/img/icon_picture.svg +0 -11
  29. package/esm2022/lib/animations/easeInOut/ease-in-out.animation.mjs +0 -12
  30. package/esm2022/lib/animations/insertRemove/insert-remove.animation.mjs +0 -9
  31. package/esm2022/lib/animations/listAnnimation/list.animation.mjs +0 -16
  32. package/esm2022/lib/components/canva-btn/canva-btn.component.mjs +0 -73
  33. package/esm2022/lib/components/images-view/images-actions-handler.mjs +0 -168
  34. package/esm2022/lib/components/images-view/images-view.component.mjs +0 -391
  35. package/esm2022/lib/components/images-view/mosaic-view/img-card/img-card.component.mjs +0 -70
  36. package/esm2022/lib/components/images-view/mosaic-view/mosaic-view.component.mjs +0 -73
  37. package/esm2022/lib/components/images-view/table-view/table-view.component.mjs +0 -48
  38. package/esm2022/lib/components/img-editor/cropper/cropper.component.mjs +0 -313
  39. package/esm2022/lib/components/img-editor/img-editor.component.mjs +0 -129
  40. package/esm2022/lib/components/img-editor/info-section/info-section.component.mjs +0 -58
  41. package/esm2022/lib/components/img-selection/img-selection.component.mjs +0 -58
  42. package/esm2022/lib/components/img-tabs/img-tabs.component.mjs +0 -128
  43. package/esm2022/lib/components/img-upload/img-upload.component.mjs +0 -133
  44. package/esm2022/lib/components/loader/loader.component.mjs +0 -21
  45. package/esm2022/lib/components/pexels-lib/pexels-lib.component.mjs +0 -211
  46. package/esm2022/lib/components/shared/alert/alert.component.mjs +0 -26
  47. package/esm2022/lib/components/shared/checkbox/checkbox.component.mjs +0 -56
  48. package/esm2022/lib/components/shared/dropdown/dropdown.component.mjs +0 -21
  49. package/esm2022/lib/components/shared/input-search/input-search.component.mjs +0 -53
  50. package/esm2022/lib/components/shared/pagination/page-selector/page-selector.component.mjs +0 -50
  51. package/esm2022/lib/components/shared/pagination/pagination.component.mjs +0 -49
  52. package/esm2022/lib/components/shared/select/call-to-action.model.mjs +0 -2
  53. package/esm2022/lib/components/shared/select/select-items.dto.mjs +0 -2
  54. package/esm2022/lib/components/shared/select/select.component.mjs +0 -117
  55. package/esm2022/lib/components/shared/table/table.component.mjs +0 -124
  56. package/esm2022/lib/components/upload-list/upload-list.component.mjs +0 -85
  57. package/esm2022/lib/directives/abstract-debounce/abstract-debounce.directive.mjs +0 -41
  58. package/esm2022/lib/directives/abstract-debounce/debounce-keyup.directive.mjs +0 -24
  59. package/esm2022/lib/directives/auto-hide.directive.mjs +0 -51
  60. package/esm2022/lib/directives/copy-to-clipboard.directive.mjs +0 -36
  61. package/esm2022/lib/directives/drag-drop.directive.mjs +0 -55
  62. package/esm2022/lib/directives/loading.directive.mjs +0 -43
  63. package/esm2022/lib/directives/table/checkBoxRow.directive.mjs +0 -130
  64. package/esm2022/lib/directives/table/column.directive.mjs +0 -50
  65. package/esm2022/lib/directives/table/columnHeader.directive.mjs +0 -215
  66. package/esm2022/lib/directives/table/raw.directive.mjs +0 -34
  67. package/esm2022/lib/directives/zindex-toggle.directive.mjs +0 -45
  68. package/esm2022/lib/dto/ImgManagerDisplayConfig.dto.mjs +0 -2
  69. package/esm2022/lib/dto/canva-create-design.dto.mjs +0 -9
  70. package/esm2022/lib/dto/canva.dto.mjs +0 -6
  71. package/esm2022/lib/dto/config/apis/api.dto.mjs +0 -11
  72. package/esm2022/lib/dto/config/external/external-config.dto.mjs +0 -5
  73. package/esm2022/lib/dto/config/image-cdn/image-cdn-config.dto.mjs +0 -2
  74. package/esm2022/lib/dto/config/img-manager.mjs +0 -8
  75. package/esm2022/lib/dto/export-dtos.api.mjs +0 -11
  76. package/esm2022/lib/dto/img-editor-config.dto.mjs +0 -2
  77. package/esm2022/lib/dto/img-manager.dto.mjs +0 -2
  78. package/esm2022/lib/dto/pexels-img.dto.mjs +0 -2
  79. package/esm2022/lib/dto/picture-name-update.dto.mjs +0 -2
  80. package/esm2022/lib/dto/stateDisplayed.dto.mjs +0 -2
  81. package/esm2022/lib/dto/tabDisplayed.dto.mjs +0 -2
  82. package/esm2022/lib/dto/wizi-block-media.dto.mjs +0 -7
  83. package/esm2022/lib/pipes/images/img-src.pipe.mjs +0 -29
  84. package/esm2022/lib/pipes/number-to-array.pipe.mjs +0 -16
  85. package/esm2022/lib/pipes/pagination/array-total-pages/array-pages.pipe.mjs +0 -28
  86. package/esm2022/lib/pipes/pagination/large-number-of-page/large-number-of-page.pipe.mjs +0 -53
  87. package/esm2022/lib/pipes/pagination/text/custom-text.pipe.mjs +0 -36
  88. package/esm2022/lib/pipes/pagination/total-pages/is-last-page.pipe.mjs +0 -25
  89. package/esm2022/lib/pipes/select/select-filters.pipe.mjs +0 -19
  90. package/esm2022/lib/services/alert.service.mjs +0 -53
  91. package/esm2022/lib/services/api.service.mjs +0 -10
  92. package/esm2022/lib/services/canva.service.mjs +0 -165
  93. package/esm2022/lib/services/config/img-cdn.service.mjs +0 -21
  94. package/esm2022/lib/services/dom.service.mjs +0 -31
  95. package/esm2022/lib/services/icon.service.mjs +0 -18
  96. package/esm2022/lib/services/image-not-found.service.mjs +0 -13
  97. package/esm2022/lib/services/img-event.service.mjs +0 -33
  98. package/esm2022/lib/services/img-manager.service.mjs +0 -134
  99. package/esm2022/lib/services/img-selection.service.mjs +0 -75
  100. package/esm2022/lib/services/pexels.service.mjs +0 -66
  101. package/esm2022/lib/services/rename-picture.service.mjs +0 -66
  102. package/esm2022/lib/services/snackbar.service.mjs +0 -67
  103. package/esm2022/lib/services/table/filters-table.service.mjs +0 -61
  104. package/esm2022/lib/services/upload.service.mjs +0 -20
  105. package/esm2022/lib/services/user-settings.service.mjs +0 -23
  106. package/esm2022/lib/wz-img-manager.component.mjs +0 -209
  107. package/esm2022/lib/wz-img-manager.module.mjs +0 -225
  108. package/esm2022/public-api.mjs +0 -14
  109. package/esm2022/wizishop-img-manager.mjs +0 -5
  110. package/wizishop-img-manager-18.2.2-beta.tgz +0 -0
  111. package/wz-img-manager.scss +0 -4085
@@ -1,391 +0,0 @@
1
- import { Component, Input, ViewChild, ElementRef, Output, EventEmitter, ChangeDetectorRef } from '@angular/core';
2
- import { ImgManagerService } from '../../services/img-manager.service';
3
- import { Subject, combineLatest } from 'rxjs';
4
- import { filter, map, take } from 'rxjs/operators';
5
- import { ImgEventService } from '../../services/img-event.service';
6
- import { ImgSelectionService } from '../../services/img-selection.service';
7
- import { UserSettingsService } from '../../services/user-settings.service';
8
- import { easeInOut } from '../../animations/easeInOut/ease-in-out.animation';
9
- import { insertRemove } from '../../animations/insertRemove/insert-remove.animation';
10
- import { RenamePictureService } from '../../services/rename-picture.service';
11
- import { AlertService } from '../../services/alert.service';
12
- import * as i0 from "@angular/core";
13
- import * as i1 from "../../services/img-manager.service";
14
- import * as i2 from "../../services/img-event.service";
15
- import * as i3 from "../../services/img-selection.service";
16
- import * as i4 from "../../services/alert.service";
17
- import * as i5 from "../../services/user-settings.service";
18
- import * as i6 from "../../services/rename-picture.service";
19
- import * as i7 from "@angular/common";
20
- import * as i8 from "ngx-scrollbar";
21
- import * as i9 from "../pexels-lib/pexels-lib.component";
22
- import * as i10 from "./mosaic-view/mosaic-view.component";
23
- import * as i11 from "./table-view/table-view.component";
24
- import * as i12 from "../../directives/loading.directive";
25
- import * as i13 from "@ngx-translate/core";
26
- export class ImagesViewComponent {
27
- imgManager;
28
- imgEventService;
29
- imgSelectionService;
30
- alertService;
31
- userSettingsService;
32
- renamePictureService;
33
- changeDetectorRef;
34
- stateDisplayed;
35
- tabDisplayed;
36
- fullSize;
37
- nbRowToShow;
38
- listDisplayed = false; // Display format list or mosaic
39
- multipleImgMode = false;
40
- switchDisplayWindow = new EventEmitter();
41
- imgLibContainer;
42
- widthLargeCard = 219; // Default value of a card width 199 + margin 20
43
- widthSmallCard = 160; // Default value of a card width 140 + margin 20
44
- nbMinImgPerLine;
45
- nbMaxImgPerLine;
46
- nbFakeImg = 0;
47
- imgFullWidthConfig = [
48
- {
49
- max: 419,
50
- largeImgWidthFactor: 1,
51
- smallImgWidthFactor: 0.5
52
- },
53
- {
54
- max: 499,
55
- largeImgWidthFactor: 1,
56
- smallImgWidthFactor: 0.5
57
- },
58
- {
59
- max: 719, // tablet
60
- largeImgWidthFactor: 0.5,
61
- smallImgWidthFactor: 0.3333
62
- },
63
- {
64
- max: 1023, // deskop
65
- largeImgWidthFactor: 0.3333,
66
- smallImgWidthFactor: 0.2
67
- },
68
- {
69
- max: 1399,
70
- largeImgWidthFactor: 0.25,
71
- smallImgWidthFactor: 0.125
72
- },
73
- {
74
- max: 1599,
75
- largeImgWidthFactor: 0.2,
76
- smallImgWidthFactor: 0.1111
77
- },
78
- {
79
- largeImgWidthFactor: 0.1666,
80
- smallImgWidthFactor: 0.1
81
- }
82
- ];
83
- imgWidthConfig = [
84
- {
85
- max: 1024,
86
- largeImgWidthFactor: 0.25,
87
- smallImgWidthFactor: 0.125
88
- },
89
- {
90
- max: 1199,
91
- largeImgWidthFactor: 0.3333,
92
- smallImgWidthFactor: 0.2
93
- },
94
- {
95
- max: 1299,
96
- largeImgWidthFactor: 0.3333,
97
- smallImgWidthFactor: 0.1666
98
- },
99
- {
100
- max: 1399,
101
- largeImgWidthFactor: 0.25,
102
- smallImgWidthFactor: 0.1666
103
- },
104
- {
105
- max: 1599,
106
- largeImgWidthFactor: 0.25,
107
- smallImgWidthFactor: 0.14
108
- },
109
- {
110
- largeImgWidthFactor: 0.25,
111
- smallImgWidthFactor: 0.125
112
- }
113
- ];
114
- nbImgToDelSelected = 0;
115
- disable = false; // Use to disable action during server request
116
- delListImgLoader = false;
117
- initComponent = true;
118
- failLoaded = false;
119
- confirmImgSup = false;
120
- previousSearchValue;
121
- get searchImagesParameters$() {
122
- return this.imgManager.searchImagesParameters$;
123
- }
124
- // Api Img manager Params
125
- params;
126
- errorGetAllImg = 'ImgManager.ImgLib.errorGetAllImg';
127
- errorGetTotalImg = 'ImgManager.ImgLib.errorGetTotalImg';
128
- errorGetImg = 'ImgManager.ImgLib.errorGetCanvaImg';
129
- errorRemoveImg = 'ImgManager.ImgList.errorRemoveImg';
130
- destroy$ = new Subject();
131
- vm$;
132
- constructor(imgManager, imgEventService, imgSelectionService, alertService, userSettingsService, renamePictureService, changeDetectorRef) {
133
- this.imgManager = imgManager;
134
- this.imgEventService = imgEventService;
135
- this.imgSelectionService = imgSelectionService;
136
- this.alertService = alertService;
137
- this.userSettingsService = userSettingsService;
138
- this.renamePictureService = renamePictureService;
139
- this.changeDetectorRef = changeDetectorRef;
140
- }
141
- ngOnInit() {
142
- this.vm$ = combineLatest({
143
- imageSelection: this.imgSelectionService.imgSelection$,
144
- imageListData: this.imgManager.imageList$,
145
- isLoading: this.imgManager.isLoading$,
146
- searchImagesParameters: this.imgManager.searchImagesParameters$,
147
- }).pipe(map(({ imageSelection, imageListData: { imageList, imageTotal }, isLoading, searchImagesParameters }) => {
148
- this.initVariables(true); // Si cette méthode est nécessaire à l'initialisation
149
- this.calculateNbImgFake(imageList.data.length); // Même chose ici
150
- const picturesList = this.setSelectedProperty(imageSelection, imageList.data);
151
- this.renamePictureService.setPicturesList(picturesList);
152
- const tableFilters = this.getTableFilters(searchImagesParameters, imageTotal);
153
- const keepImagesDisplayed = (this.tabDisplayed === 'img-upload' && searchImagesParameters.page === '1') ||
154
- (this.tabDisplayed === 'images-view' && imageList.data.length && searchImagesParameters.page === '1');
155
- const skipSetImagesToDisplay = !!picturesList?.length && this.tabDisplayed === 'img-upload' && searchImagesParameters.page === '1';
156
- const hideUntilFetchedFirstPageImagesForTabUpload = this.tabDisplayed === 'img-upload' &&
157
- (searchImagesParameters.page !== '1' || imageList?.page !== 1);
158
- return {
159
- isLoading: hideUntilFetchedFirstPageImagesForTabUpload || (!keepImagesDisplayed && isLoading),
160
- displayPexelsResults: !isLoading && imageTotal === 0,
161
- picturesList,
162
- imageTotal,
163
- tableFilters,
164
- skipSetImagesToDisplay
165
- };
166
- }));
167
- }
168
- getTableFilters(searchImagesParameters, imageTotal) {
169
- return {
170
- sort: undefined,
171
- order: undefined,
172
- searchValue: searchImagesParameters.search,
173
- totalItems: imageTotal,
174
- itemsPerPage: parseInt(searchImagesParameters.limit),
175
- currentPage: parseInt(searchImagesParameters.page)
176
- };
177
- }
178
- ngAfterViewInit() {
179
- this.vm$.pipe(take(1), filter(({ skipSetImagesToDisplay }) => !skipSetImagesToDisplay)).subscribe(({ tableFilters }) => {
180
- this.setNbImgToDisplay(tableFilters);
181
- });
182
- }
183
- /**
184
- * true : go to list display
185
- * false : go to mosaic display
186
- * @param activate
187
- */
188
- onSwitchFormatDisplayed(activate) {
189
- this.listDisplayed = activate;
190
- this.userSettingsService.setUserDisplayPreference(activate);
191
- this.imgEventService.emitlistDisplayedChange(activate);
192
- }
193
- /**
194
- * Calcul the number of img selected for masse deletion
195
- */
196
- onImgSelected(picturesList) {
197
- this.setNbImgToDelSelected(picturesList);
198
- }
199
- onRenamePicture(pictureRenamed) {
200
- this.renamePictureService.renamePicture(pictureRenamed);
201
- }
202
- removeListImg(picturesList) {
203
- if (this.disable) {
204
- return;
205
- }
206
- this.disable = true;
207
- this.delListImgLoader = true;
208
- this.confirmImgSup = false;
209
- // Get the id of the img to remove
210
- // And add deleted property
211
- const idImgToRemove = [];
212
- picturesList.forEach(img => {
213
- if (img.delSelected) {
214
- img.deleted = true;
215
- idImgToRemove.push(img.id_file);
216
- }
217
- });
218
- this.imgManager.removeMultipleImg(idImgToRemove).subscribe({
219
- next: () => {
220
- this.imgSelectionService.removeImgSelectionByIds(idImgToRemove);
221
- },
222
- error: error => {
223
- this.imgManager.refreshImageList$.next();
224
- this.alertService.openAlert(this.errorRemoveImg);
225
- }
226
- });
227
- }
228
- selectImgChosen(picturesList) {
229
- if (this.disable) {
230
- return;
231
- }
232
- const picturesListSelected = [];
233
- picturesList.map(img => {
234
- if (img.delSelected) {
235
- img.delSelected = false;
236
- img.selected = true;
237
- }
238
- if (img.selected) {
239
- picturesListSelected.push(img);
240
- }
241
- });
242
- this.setNbImgToDelSelected(picturesList);
243
- this.imgSelectionService.setImgSelection(picturesListSelected);
244
- }
245
- displayConfirmImgSup() {
246
- if (this.disable) {
247
- return;
248
- }
249
- this.confirmImgSup = true;
250
- }
251
- cancelSup() {
252
- this.confirmImgSup = false;
253
- }
254
- /**
255
- * Event emit when a img selected in order to delete
256
- */
257
- onPicturesListChange(picturesList) {
258
- this.setNbImgToDelSelected(picturesList);
259
- }
260
- /**
261
- * Set default number of img per page to display at the initialisation
262
- * This number is between 30 and 50
263
- */
264
- setNbImgToDisplay(tableFilters) {
265
- const containerWidth = this.imgLibContainer.nativeElement.offsetWidth + 30; // + 30px -> left + right margin
266
- const scrollWidth = window.innerWidth - document.body.offsetWidth;
267
- const [maxImgWidthFactor, minImgWidthFactor] = this.getImgWidthFactors();
268
- const minImgWidth = Math.floor(containerWidth * minImgWidthFactor);
269
- const maxImgWidth = Math.ceil((containerWidth + scrollWidth) * maxImgWidthFactor);
270
- this.nbMaxImgPerLine = Math.floor(containerWidth / minImgWidth);
271
- this.nbMinImgPerLine = Math.floor((containerWidth + scrollWidth) / maxImgWidth);
272
- this.searchImagesParameters$.next(this.getParams({
273
- ...tableFilters,
274
- itemsPerPage: this.getTotalImgPerPage(),
275
- currentPage: 1
276
- }));
277
- }
278
- getImgWidthFactors() {
279
- const screenWidth = window.innerWidth;
280
- let minWidth = 0;
281
- let imgSizesConfig = [];
282
- const currentImgWidthConfig = this.fullSize ? this.imgFullWidthConfig : this.imgWidthConfig;
283
- for (const widthConfig of currentImgWidthConfig) {
284
- if (!widthConfig.max) {
285
- imgSizesConfig = [widthConfig.largeImgWidthFactor, widthConfig.smallImgWidthFactor];
286
- break;
287
- }
288
- if (minWidth < screenWidth && screenWidth <= widthConfig.max) {
289
- imgSizesConfig = [widthConfig.largeImgWidthFactor, widthConfig.smallImgWidthFactor];
290
- break;
291
- }
292
- minWidth = widthConfig.max;
293
- }
294
- return imgSizesConfig;
295
- }
296
- getTotalImgPerPage() {
297
- if (this.nbRowToShow) {
298
- const nbImgPerLine = this.stateDisplayed === 'full' ? this.nbMinImgPerLine : this.nbMaxImgPerLine;
299
- return nbImgPerLine * this.nbRowToShow;
300
- }
301
- let total = this.nbMinImgPerLine;
302
- while (total < 30 || total % this.nbMaxImgPerLine !== 0 || total % this.nbMinImgPerLine !== 0) {
303
- total += this.nbMinImgPerLine;
304
- }
305
- return total;
306
- }
307
- getParams(tableFilters) {
308
- return {
309
- limit: tableFilters.itemsPerPage.toString(),
310
- page: tableFilters.currentPage.toString(),
311
- ...(tableFilters.searchValue && { search: tableFilters.searchValue.toString() }),
312
- };
313
- }
314
- initVariables(loadingSuccess) {
315
- this.nbImgToDelSelected = 0;
316
- this.disable = false;
317
- this.delListImgLoader = false;
318
- this.initComponent = false;
319
- this.failLoaded = !loadingSuccess;
320
- this.nbFakeImg = 0;
321
- }
322
- setSelectedProperty(imgSelectedList, picturesList) {
323
- const picturesListSelected = JSON.parse(JSON.stringify(picturesList));
324
- imgSelectedList.forEach(img => {
325
- const selectedImg = picturesListSelected.find(picture => picture.id_file === img.id_file);
326
- if (selectedImg) {
327
- selectedImg.selected = true;
328
- }
329
- });
330
- return picturesListSelected;
331
- }
332
- /**
333
- * Set a img list in order to fill properly all the line of images displayed in mosaic.
334
- * Otherwise, the space-between css will do a bad display
335
- */
336
- calculateNbImgFake(nbImgDisplayed) {
337
- const nbImgPerLine = this.stateDisplayed === 'small' || this.tabDisplayed === 'img-upload' ? this.nbMaxImgPerLine : this.nbMinImgPerLine;
338
- if (isNaN(nbImgDisplayed % nbImgPerLine)) {
339
- this.nbFakeImg = 0;
340
- return;
341
- }
342
- if (nbImgDisplayed % nbImgPerLine !== 0) {
343
- setTimeout(() => {
344
- this.nbFakeImg = nbImgPerLine - nbImgDisplayed % nbImgPerLine;
345
- }, 0);
346
- }
347
- }
348
- setNbImgToDelSelected(picturesList) {
349
- this.nbImgToDelSelected = picturesList.filter(img => img.delSelected).length;
350
- if (!this.nbImgToDelSelected) {
351
- this.confirmImgSup = false;
352
- }
353
- }
354
- switchDisplayWindowMosaic() {
355
- this.switchDisplayWindow.emit(true);
356
- }
357
- ngOnDestroy() {
358
- this.destroy$.next();
359
- this.destroy$.complete();
360
- }
361
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.5", ngImport: i0, type: ImagesViewComponent, deps: [{ token: i1.ImgManagerService }, { token: i2.ImgEventService }, { token: i3.ImgSelectionService }, { token: i4.AlertService }, { token: i5.UserSettingsService }, { token: i6.RenamePictureService }, { token: i0.ChangeDetectorRef }], target: i0.ɵɵFactoryTarget.Component });
362
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.5", type: ImagesViewComponent, selector: "images-view", inputs: { stateDisplayed: "stateDisplayed", tabDisplayed: "tabDisplayed", fullSize: "fullSize", nbRowToShow: "nbRowToShow", listDisplayed: "listDisplayed", multipleImgMode: "multipleImgMode" }, outputs: { switchDisplayWindow: "switchDisplayWindow" }, viewQueries: [{ propertyName: "imgLibContainer", first: true, predicate: ["imgLibContainer"], descendants: true }], ngImport: i0, template: "<ng-container *ngIf=\"vm$ | async as vm\">\r\n\r\n <div class=\"images-view\" [ngClass]=\"{'fullSize': fullSize, 'small': stateDisplayed === 'small'}\" [@easeInOut]=\"'in'\">\r\n <!-- Subheader : Img number and actions btn (sup img list, switch forma display) -->\r\n <div\r\n *ngIf=\"(stateDisplayed !== 'small' || tabDisplayed === 'img-upload')\"\r\n class=\"images-view__container\"\r\n [ngClass]=\"{'images-view__container--uploadTab': tabDisplayed === 'img-upload', 'images-view__container--window': stateDisplayed === 'window'}\"\r\n >\r\n\r\n <div *ngIf=\"tabDisplayed !== 'img-upload'\">\r\n <p class=\"mainColor\" [ngClass]=\"{'images-view__container__total--hide': vm.displayPexelsResults}\">{{ 'ImgManager.ImgLib.nbImg' | translate }} : {{vm.imageTotal}}</p>\r\n </div>\r\n <div *ngIf=\"tabDisplayed === 'img-upload'\">\r\n <p class=\"mainColor\">{{ 'ImgManager.ImgLib.lastImgs' | translate }}</p>\r\n </div>\r\n\r\n <div class=\"field has-addons subHeaderActions\" *ngIf=\"tabDisplayed !== 'img-upload'\">\r\n\r\n <!-- For listforma : Display btn del multiple img & Confirm action -->\r\n <div class=\"images-view__container__boxAction\">\r\n\r\n\r\n <!-- Select -->\r\n <button\r\n class=\"button success images-view__container__boxAction__import\"\r\n @insertRemoveAnnim\r\n *ngIf=\"listDisplayed && nbImgToDelSelected && !confirmImgSup && !delListImgLoader && multipleImgMode\"\r\n (click)=\"selectImgChosen(vm.picturesList)\"\r\n type=\"button\"\r\n >\r\n <i class=\"fal fa-check\"></i>\r\n {{ 'ImgManager.ImgLib.select' | translate }} ({{nbImgToDelSelected}})\r\n </button>\r\n\r\n <!-- Display btn del multiple img -->\r\n <button\r\n *ngIf=\"listDisplayed && nbImgToDelSelected && !confirmImgSup\"\r\n (click)=\"displayConfirmImgSup()\"\r\n class=\"button images-view__container__boxAction__delBtn danger\"\r\n @insertRemoveAnnim\r\n type=\"button\"\r\n >\r\n <i class=\"fal fa-times\"></i>{{ 'ImgManager.ImgLib.delMlt' | translate }} ({{nbImgToDelSelected}})\r\n <span btnLoadingAnim *ngIf=\"delListImgLoader\" class=\"btnLoadingAnnimation\"></span>\r\n </button>\r\n\r\n <!-- Confirm action -->\r\n <div\r\n class=\"images-view__container__boxAction__confirmSup\"\r\n [ngClass]=\"{'images-view__container__boxAction__confirmSup--visible': confirmImgSup}\">\r\n <p *ngIf=\"nbImgToDelSelected > 1\" class=\"images-view__container__boxAction__confirmSup__text\">{{ 'ImgManager.ImgLib.confirmSupQuestions' | translate:{nbImage: nbImgToDelSelected} }}</p>\r\n <p *ngIf=\"nbImgToDelSelected === 1\" class=\"images-view__container__boxAction__confirmSup__text\">{{ 'ImgManager.ImgLib.confirmSupQuestion' | translate:{nbImage: nbImgToDelSelected} }}</p>\r\n <div>\r\n <button\r\n class=\"button images-view__container__boxAction__confirmSup__cancel\"\r\n (click)=\"cancelSup()\"\r\n type=\"button\"\r\n >\r\n {{ 'ImgManager.ImgLib.cancel' | translate }}\r\n </button>\r\n <button\r\n (click)=\"removeListImg(vm.picturesList)\"\r\n class=\"button images-view__container__delBtn danger\"\r\n type=\"button\"\r\n >\r\n {{ 'ImgManager.ImgLib.confirm' | translate }}\r\n </button>\r\n </div>\r\n </div>\r\n\r\n </div>\r\n\r\n\r\n <!-- Swith mosaic/list forma -->\r\n <div class=\"field has-addons images-view__container__buttonBox\">\r\n <div class=\"control\">\r\n <div\r\n class=\"button is-lighted images-view__container__buttonBox__btn\"\r\n [ngClass]=\"{'actifDisplayed': !listDisplayed}\"\r\n (click)=\"onSwitchFormatDisplayed(false)\"\r\n >\r\n <span class=\"icon is-small\">\r\n <i class=\"fa-solid fa-th\"></i>\r\n </span>\r\n </div>\r\n </div>\r\n\r\n <div class=\"control\">\r\n <div class=\"button is-lighted images-view__container__buttonBox__btn\"\r\n [ngClass]=\"{'actifDisplayed': listDisplayed}\"\r\n (click)=\"onSwitchFormatDisplayed(true)\"\r\n >\r\n <span class=\"icon is-small\">\r\n <i class=\"fa-solid fa-bars\"></i>\r\n </span>\r\n </div>\r\n </div>\r\n </div>\r\n </div>\r\n </div>\r\n </div>\r\n\r\n\r\n <!-- Images section -->\r\n <ng-scrollbar\r\n class=\"images-view__scroll\"\r\n [ngClass]=\"{\r\n 'images-view__scroll--hide--mosaic': vm.displayPexelsResults && !listDisplayed,\r\n 'images-view__scroll--hide--table': vm.displayPexelsResults && listDisplayed,\r\n 'images-view__scroll--full': stateDisplayed === 'full',\r\n 'images-view__scroll--smallDisplay' : stateDisplayed === 'small' && tabDisplayed !== 'img-upload',\r\n 'images-view__scroll--smallUploadDisplay' : stateDisplayed === 'small' && tabDisplayed === 'img-upload',\r\n 'images-view__scroll--window': stateDisplayed === 'window'\r\n }\"\r\n >\r\n <div #imgLibContainer class=\"images-view__wrapper\">\r\n\r\n <div *ngIf=\"!listDisplayed || stateDisplayed === 'small'\" [@easeInOut]=\"'in'\">\r\n <mosaic-view\r\n [picturesList]=\"vm.picturesList\"\r\n (picturesListChange)=\"onPicturesListChange(vm.picturesList)\"\r\n [tableFilters]=\"vm.tableFilters\"\r\n (filtersChange)=\"searchImagesParameters$.next(getParams(vm.tableFilters));\"\r\n [(disable)]=\"disable\"\r\n (pictureNameChange)=\"onRenamePicture($event)\"\r\n (switchDisplayWindow)=\"switchDisplayWindowMosaic()\"\r\n [nbFakeImg]=\"nbFakeImg\"\r\n [stateDisplayed]=\"stateDisplayed\"\r\n [tabDisplayed]=\"tabDisplayed\"\r\n [displayPexelsResults]=\"vm.displayPexelsResults\"\r\n [isLoading]=\"vm.isLoading\"\r\n [fullSize]=\"fullSize\"\r\n >\r\n </mosaic-view>\r\n </div>\r\n\r\n <div *ngIf=\"listDisplayed && stateDisplayed !== 'small'\" [@easeInOut]=\"'in'\">\r\n <table-view\r\n [picturesList]=\"vm.picturesList\"\r\n (picturesListChange)=\"onPicturesListChange(vm.picturesList)\"\r\n [tableFilters]=\"vm.tableFilters\"\r\n (filtersChange)=\"searchImagesParameters$.next(getParams(vm.tableFilters));\"\r\n [(disable)]=\"disable\"\r\n (pictureNameChange)=\"onRenamePicture($event)\"\r\n [displayPexelsResults]=\"vm.displayPexelsResults\"\r\n [stateDisplayed]=\"stateDisplayed\"\r\n [isLoading]=\"vm.isLoading\"\r\n >\r\n </table-view>\r\n </div>\r\n </div>\r\n </ng-scrollbar>\r\n\r\n <!-- Pexels Section - When no img found -->\r\n <div\r\n *ngIf=\"vm.displayPexelsResults\"\r\n class=\"images-view--pexels\"\r\n [@easeInOut]=\"'in'\">\r\n <pexels-lib\r\n [searchValue]=\"vm.tableFilters.searchValue\"\r\n [disableSearch]=\"true\"\r\n >\r\n </pexels-lib>\r\n </div>\r\n</ng-container>\r\n", dependencies: [{ kind: "directive", type: i7.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: i7.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: i8.NgScrollbar, selector: "ng-scrollbar", inputs: ["disabled", "sensorDisabled", "pointerEventsDisabled", "viewportPropagateMouseMove", "autoHeightDisabled", "autoWidthDisabled", "viewClass", "trackClass", "thumbClass", "minThumbSize", "trackClickScrollDuration", "pointerEventsMethod", "track", "visibility", "appearance", "position", "sensorDebounce", "scrollAuditTime"], outputs: ["updated"], exportAs: ["ngScrollbar"] }, { kind: "component", type: i9.PexelLibComponent, selector: "pexels-lib", inputs: ["stateDisplayed", "searchValue", "disableSearch"] }, { kind: "component", type: i10.MosaicViewComponent, selector: "mosaic-view", inputs: ["tabDisplayed", "fullSize", "nbFakeImg"], outputs: ["switchDisplayWindow"] }, { kind: "component", type: i11.TableViewComponent, selector: "table-view" }, { kind: "directive", type: i12.LoadingDirective, selector: "[btnLoadingAnim]" }, { kind: "pipe", type: i7.AsyncPipe, name: "async" }, { kind: "pipe", type: i13.TranslatePipe, name: "translate" }], animations: [
363
- easeInOut,
364
- insertRemove
365
- ] });
366
- }
367
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.5", ngImport: i0, type: ImagesViewComponent, decorators: [{
368
- type: Component,
369
- args: [{ selector: 'images-view', animations: [
370
- easeInOut,
371
- insertRemove
372
- ], template: "<ng-container *ngIf=\"vm$ | async as vm\">\r\n\r\n <div class=\"images-view\" [ngClass]=\"{'fullSize': fullSize, 'small': stateDisplayed === 'small'}\" [@easeInOut]=\"'in'\">\r\n <!-- Subheader : Img number and actions btn (sup img list, switch forma display) -->\r\n <div\r\n *ngIf=\"(stateDisplayed !== 'small' || tabDisplayed === 'img-upload')\"\r\n class=\"images-view__container\"\r\n [ngClass]=\"{'images-view__container--uploadTab': tabDisplayed === 'img-upload', 'images-view__container--window': stateDisplayed === 'window'}\"\r\n >\r\n\r\n <div *ngIf=\"tabDisplayed !== 'img-upload'\">\r\n <p class=\"mainColor\" [ngClass]=\"{'images-view__container__total--hide': vm.displayPexelsResults}\">{{ 'ImgManager.ImgLib.nbImg' | translate }} : {{vm.imageTotal}}</p>\r\n </div>\r\n <div *ngIf=\"tabDisplayed === 'img-upload'\">\r\n <p class=\"mainColor\">{{ 'ImgManager.ImgLib.lastImgs' | translate }}</p>\r\n </div>\r\n\r\n <div class=\"field has-addons subHeaderActions\" *ngIf=\"tabDisplayed !== 'img-upload'\">\r\n\r\n <!-- For listforma : Display btn del multiple img & Confirm action -->\r\n <div class=\"images-view__container__boxAction\">\r\n\r\n\r\n <!-- Select -->\r\n <button\r\n class=\"button success images-view__container__boxAction__import\"\r\n @insertRemoveAnnim\r\n *ngIf=\"listDisplayed && nbImgToDelSelected && !confirmImgSup && !delListImgLoader && multipleImgMode\"\r\n (click)=\"selectImgChosen(vm.picturesList)\"\r\n type=\"button\"\r\n >\r\n <i class=\"fal fa-check\"></i>\r\n {{ 'ImgManager.ImgLib.select' | translate }} ({{nbImgToDelSelected}})\r\n </button>\r\n\r\n <!-- Display btn del multiple img -->\r\n <button\r\n *ngIf=\"listDisplayed && nbImgToDelSelected && !confirmImgSup\"\r\n (click)=\"displayConfirmImgSup()\"\r\n class=\"button images-view__container__boxAction__delBtn danger\"\r\n @insertRemoveAnnim\r\n type=\"button\"\r\n >\r\n <i class=\"fal fa-times\"></i>{{ 'ImgManager.ImgLib.delMlt' | translate }} ({{nbImgToDelSelected}})\r\n <span btnLoadingAnim *ngIf=\"delListImgLoader\" class=\"btnLoadingAnnimation\"></span>\r\n </button>\r\n\r\n <!-- Confirm action -->\r\n <div\r\n class=\"images-view__container__boxAction__confirmSup\"\r\n [ngClass]=\"{'images-view__container__boxAction__confirmSup--visible': confirmImgSup}\">\r\n <p *ngIf=\"nbImgToDelSelected > 1\" class=\"images-view__container__boxAction__confirmSup__text\">{{ 'ImgManager.ImgLib.confirmSupQuestions' | translate:{nbImage: nbImgToDelSelected} }}</p>\r\n <p *ngIf=\"nbImgToDelSelected === 1\" class=\"images-view__container__boxAction__confirmSup__text\">{{ 'ImgManager.ImgLib.confirmSupQuestion' | translate:{nbImage: nbImgToDelSelected} }}</p>\r\n <div>\r\n <button\r\n class=\"button images-view__container__boxAction__confirmSup__cancel\"\r\n (click)=\"cancelSup()\"\r\n type=\"button\"\r\n >\r\n {{ 'ImgManager.ImgLib.cancel' | translate }}\r\n </button>\r\n <button\r\n (click)=\"removeListImg(vm.picturesList)\"\r\n class=\"button images-view__container__delBtn danger\"\r\n type=\"button\"\r\n >\r\n {{ 'ImgManager.ImgLib.confirm' | translate }}\r\n </button>\r\n </div>\r\n </div>\r\n\r\n </div>\r\n\r\n\r\n <!-- Swith mosaic/list forma -->\r\n <div class=\"field has-addons images-view__container__buttonBox\">\r\n <div class=\"control\">\r\n <div\r\n class=\"button is-lighted images-view__container__buttonBox__btn\"\r\n [ngClass]=\"{'actifDisplayed': !listDisplayed}\"\r\n (click)=\"onSwitchFormatDisplayed(false)\"\r\n >\r\n <span class=\"icon is-small\">\r\n <i class=\"fa-solid fa-th\"></i>\r\n </span>\r\n </div>\r\n </div>\r\n\r\n <div class=\"control\">\r\n <div class=\"button is-lighted images-view__container__buttonBox__btn\"\r\n [ngClass]=\"{'actifDisplayed': listDisplayed}\"\r\n (click)=\"onSwitchFormatDisplayed(true)\"\r\n >\r\n <span class=\"icon is-small\">\r\n <i class=\"fa-solid fa-bars\"></i>\r\n </span>\r\n </div>\r\n </div>\r\n </div>\r\n </div>\r\n </div>\r\n </div>\r\n\r\n\r\n <!-- Images section -->\r\n <ng-scrollbar\r\n class=\"images-view__scroll\"\r\n [ngClass]=\"{\r\n 'images-view__scroll--hide--mosaic': vm.displayPexelsResults && !listDisplayed,\r\n 'images-view__scroll--hide--table': vm.displayPexelsResults && listDisplayed,\r\n 'images-view__scroll--full': stateDisplayed === 'full',\r\n 'images-view__scroll--smallDisplay' : stateDisplayed === 'small' && tabDisplayed !== 'img-upload',\r\n 'images-view__scroll--smallUploadDisplay' : stateDisplayed === 'small' && tabDisplayed === 'img-upload',\r\n 'images-view__scroll--window': stateDisplayed === 'window'\r\n }\"\r\n >\r\n <div #imgLibContainer class=\"images-view__wrapper\">\r\n\r\n <div *ngIf=\"!listDisplayed || stateDisplayed === 'small'\" [@easeInOut]=\"'in'\">\r\n <mosaic-view\r\n [picturesList]=\"vm.picturesList\"\r\n (picturesListChange)=\"onPicturesListChange(vm.picturesList)\"\r\n [tableFilters]=\"vm.tableFilters\"\r\n (filtersChange)=\"searchImagesParameters$.next(getParams(vm.tableFilters));\"\r\n [(disable)]=\"disable\"\r\n (pictureNameChange)=\"onRenamePicture($event)\"\r\n (switchDisplayWindow)=\"switchDisplayWindowMosaic()\"\r\n [nbFakeImg]=\"nbFakeImg\"\r\n [stateDisplayed]=\"stateDisplayed\"\r\n [tabDisplayed]=\"tabDisplayed\"\r\n [displayPexelsResults]=\"vm.displayPexelsResults\"\r\n [isLoading]=\"vm.isLoading\"\r\n [fullSize]=\"fullSize\"\r\n >\r\n </mosaic-view>\r\n </div>\r\n\r\n <div *ngIf=\"listDisplayed && stateDisplayed !== 'small'\" [@easeInOut]=\"'in'\">\r\n <table-view\r\n [picturesList]=\"vm.picturesList\"\r\n (picturesListChange)=\"onPicturesListChange(vm.picturesList)\"\r\n [tableFilters]=\"vm.tableFilters\"\r\n (filtersChange)=\"searchImagesParameters$.next(getParams(vm.tableFilters));\"\r\n [(disable)]=\"disable\"\r\n (pictureNameChange)=\"onRenamePicture($event)\"\r\n [displayPexelsResults]=\"vm.displayPexelsResults\"\r\n [stateDisplayed]=\"stateDisplayed\"\r\n [isLoading]=\"vm.isLoading\"\r\n >\r\n </table-view>\r\n </div>\r\n </div>\r\n </ng-scrollbar>\r\n\r\n <!-- Pexels Section - When no img found -->\r\n <div\r\n *ngIf=\"vm.displayPexelsResults\"\r\n class=\"images-view--pexels\"\r\n [@easeInOut]=\"'in'\">\r\n <pexels-lib\r\n [searchValue]=\"vm.tableFilters.searchValue\"\r\n [disableSearch]=\"true\"\r\n >\r\n </pexels-lib>\r\n </div>\r\n</ng-container>\r\n" }]
373
- }], ctorParameters: () => [{ type: i1.ImgManagerService }, { type: i2.ImgEventService }, { type: i3.ImgSelectionService }, { type: i4.AlertService }, { type: i5.UserSettingsService }, { type: i6.RenamePictureService }, { type: i0.ChangeDetectorRef }], propDecorators: { stateDisplayed: [{
374
- type: Input
375
- }], tabDisplayed: [{
376
- type: Input
377
- }], fullSize: [{
378
- type: Input
379
- }], nbRowToShow: [{
380
- type: Input
381
- }], listDisplayed: [{
382
- type: Input
383
- }], multipleImgMode: [{
384
- type: Input
385
- }], switchDisplayWindow: [{
386
- type: Output
387
- }], imgLibContainer: [{
388
- type: ViewChild,
389
- args: ['imgLibContainer']
390
- }] } });
391
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW1hZ2VzLXZpZXcuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvd3otaW1nLW1hbmFnZXIvc3JjL2xpYi9jb21wb25lbnRzL2ltYWdlcy12aWV3L2ltYWdlcy12aWV3LmNvbXBvbmVudC50cyIsIi4uLy4uLy4uLy4uLy4uLy4uLy4uL3Byb2plY3RzL3d6LWltZy1tYW5hZ2VyL3NyYy9saWIvY29tcG9uZW50cy9pbWFnZXMtdmlldy9pbWFnZXMtdmlldy5jb21wb25lbnQuaHRtbCJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUMsU0FBUyxFQUFFLEtBQUssRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUFpQixNQUFNLEVBQUUsWUFBWSxFQUFFLGlCQUFpQixFQUFDLE1BQU0sZUFBZSxDQUFDO0FBRTlILE9BQU8sRUFBRSxpQkFBaUIsRUFBRSxNQUFNLG9DQUFvQyxDQUFDO0FBQ3ZFLE9BQU8sRUFBRSxPQUFPLEVBQUUsYUFBYSxFQUFjLE1BQU0sTUFBTSxDQUFDO0FBQzFELE9BQU8sRUFBRSxNQUFNLEVBQUUsR0FBRyxFQUFFLElBQUksRUFBTyxNQUFNLGdCQUFnQixDQUFDO0FBQ3hELE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSxrQ0FBa0MsQ0FBQztBQUNuRSxPQUFPLEVBQUUsbUJBQW1CLEVBQUUsTUFBTSxzQ0FBc0MsQ0FBQztBQUMzRSxPQUFPLEVBQUUsbUJBQW1CLEVBQUUsTUFBTSxzQ0FBc0MsQ0FBQztBQUczRSxPQUFPLEVBQUUsU0FBUyxFQUFFLE1BQU0sa0RBQWtELENBQUM7QUFDN0UsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLHVEQUF1RCxDQUFDO0FBRXJGLE9BQU8sRUFBRSxvQkFBb0IsRUFBRSxNQUFNLHVDQUF1QyxDQUFDO0FBQzdFLE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSw4QkFBOEIsQ0FBQzs7Ozs7Ozs7Ozs7Ozs7O0FBVTVELE1BQU0s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QUM7WUFDaEUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDO1FBQ1IsQ0FBQztJQUNILENBQUM7SUFFTyxxQkFBcUIsQ0FBRSxZQUE2QjtRQUMxRCxJQUFJLENBQUMsa0JBQWtCLEdBQUcsWUFBWSxDQUFDLE1BQU0sQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDLEdBQUcsQ0FBQyxXQUFXLENBQUMsQ0FBQyxNQUFNLENBQUM7UUFFN0UsSUFBSSxDQUFDLElBQUksQ0FBQyxrQkFBa0IsRUFBRSxDQUFDO1lBQzdCLElBQUksQ0FBQyxhQUFhLEdBQUcsS0FBSyxDQUFDO1FBQzdCLENBQUM7SUFDSCxDQUFDO0lBRUQseUJBQXlCO1FBQ3ZCLElBQUksQ0FBQyxtQkFBbUIsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUM7SUFDdEMsQ0FBQztJQUVELFdBQVc7UUFDVCxJQUFJLENBQUMsUUFBUSxDQUFDLElBQUksRUFBRSxDQUFDO1FBQ3JCLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUSxFQUFFLENBQUM7SUFDM0IsQ0FBQzt1R0E3WFUsbUJBQW1COzJGQUFuQixtQkFBbUIsa2FDeEJoQyxzd1BBc0tBLGd1Q0RuSmM7WUFDVixTQUFTO1lBQ1QsWUFBWTtTQUNiOzsyRkFFVSxtQkFBbUI7a0JBUi9CLFNBQVM7K0JBQ0UsYUFBYSxjQUVYO3dCQUNWLFNBQVM7d0JBQ1QsWUFBWTtxQkFDYjtzUkFJUSxjQUFjO3NCQUF0QixLQUFLO2dCQUNHLFlBQVk7c0JBQXBCLEtBQUs7Z0JBQ0csUUFBUTtzQkFBaEIsS0FBSztnQkFDRyxXQUFXO3NCQUFuQixLQUFLO2dCQUNHLGFBQWE7c0JBQXJCLEtBQUs7Z0JBQ0csZUFBZTtzQkFBdkIsS0FBSztnQkFFTixtQkFBbUI7c0JBRGxCLE1BQU07Z0JBR3VCLGVBQWU7c0JBQTVDLFNBQVM7dUJBQUMsaUJBQWlCIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHtDb21wb25lbnQsIElucHV0LCBWaWV3Q2hpbGQsIEVsZW1lbnRSZWYsIEFmdGVyVmlld0luaXQsIE91dHB1dCwgRXZlbnRFbWl0dGVyLCBDaGFuZ2VEZXRlY3RvclJlZn0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XHJcbmltcG9ydCB7IEltZ1BpY3R1cmVEVE8sIFBhcmFtc0ltZ01hbmFnZXJEVE8gfSBmcm9tICcuLi8uLi9kdG8vaW1nLW1hbmFnZXIuZHRvJztcclxuaW1wb3J0IHsgSW1nTWFuYWdlclNlcnZpY2UgfSBmcm9tICcuLi8uLi9zZXJ2aWNlcy9pbWctbWFuYWdlci5zZXJ2aWNlJztcclxuaW1wb3J0IHsgU3ViamVjdCwgY29tYmluZUxhdGVzdCwgT2JzZXJ2YWJsZSB9IGZyb20gJ3J4anMnO1xyXG5pbXBvcnQgeyBmaWx0ZXIsIG1hcCwgdGFrZSwgdGFwIH0gZnJvbSAncnhqcy9vcGVyYXRvcnMnO1xyXG5pbXBvcnQgeyBJbWdFdmVudFNlcnZpY2UgfSBmcm9tICcuLi8uLi9zZXJ2aWNlcy9pbWctZXZlbnQuc2VydmljZSc7XHJcbmltcG9ydCB7IEltZ1NlbGVjdGlvblNlcnZpY2UgfSBmcm9tICcuLi8uLi9zZXJ2aWNlcy9pbWctc2VsZWN0aW9uLnNlcnZpY2UnO1xyXG5pbXBvcnQgeyBVc2VyU2V0dGluZ3NTZXJ2aWNlIH0gZnJvbSAnLi4vLi4vc2VydmljZXMvdXNlci1zZXR0aW5ncy5zZXJ2aWNlJztcclxuaW1wb3J0IHsgVGFibGVGaWx0ZXJzIH0gZnJvbSAnLi4vLi4vc2VydmljZXMvdGFibGUvZmlsdGVycy10YWJsZS5zZXJ2aWNlJztcclxuaW1wb3J0IHsgUGljdHVyZU5hbWVVcGRhdGUgfSBmcm9tICcuLi8uLi9kdG8vcGljdHVyZS1uYW1lLXVwZGF0ZS5kdG8nO1xyXG5pbXBvcnQgeyBlYXNlSW5PdXQgfSBmcm9tICcuLi8uLi9hbmltYXRpb25zL2Vhc2VJbk91dC9lYXNlLWluLW91dC5hbmltYXRpb24nO1xyXG5pbXBvcnQgeyBpbnNlcnRSZW1vdmUgfSBmcm9tICcuLi8uLi9hbmltYXRpb25zL2luc2VydFJlbW92ZS9pbnNlcnQtcmVtb3ZlLmFuaW1hdGlvbic7XHJcbmltcG9ydCB7IHN0YXRlRGlzcGxheWVkLCB0YWJEaXNwbGF5ZWQgfSBmcm9tICcuLi8uLi9kdG8vZXhwb3J0LWR0b3MuYXBpJztcclxuaW1wb3J0IHsgUmVuYW1lUGljdHVyZVNlcnZpY2UgfSBmcm9tICcuLi8uLi9zZXJ2aWNlcy9yZW5hbWUtcGljdHVyZS5zZXJ2aWNlJztcclxuaW1wb3J0IHsgQWxlcnRTZXJ2aWNlIH0gZnJvbSAnLi4vLi4vc2VydmljZXMvYWxlcnQuc2VydmljZSc7XHJcblxyXG5AQ29tcG9uZW50KHtcclxuICBzZWxlY3RvcjogJ2ltYWdlcy12aWV3JyxcclxuICB0ZW1wbGF0ZVVybDogJy4vaW1hZ2VzLXZpZXcuY29tcG9uZW50Lmh0bWwnLFxyXG4gIGFuaW1hdGlvbnM6IFtcclxuICAgIGVhc2VJbk91dCxcclxuICAgIGluc2VydFJlbW92ZVxyXG4gIF1cclxufSlcclxuZXhwb3J0IGNsYXNzIEltYWdlc1ZpZXdDb21wb25lbnQgaW1wbGVtZW50cyBBZnRlclZpZXdJbml0IHtcclxuXHJcbiAgQElucHV0KCkgc3RhdGVEaXNwbGF5ZWQ6IHN0YXRlRGlzcGxheWVkO1xyXG4gIEBJbnB1dCgpIHRhYkRpc3BsYXllZDogdGFiRGlzcGxheWVkO1xyXG4gIEBJbnB1dCgpIGZ1bGxTaXplOiBib29sZWFuO1xyXG4gIEBJbnB1dCgpIG5iUm93VG9TaG93OiBudW1iZXI7XHJcbiAgQElucHV0KCkgbGlzdERpc3BsYXllZCA9IGZhbHNlOyAvLyBEaXNwbGF5IGZvcm1hdCBsaXN0IG9yIG1vc2FpY1xyXG4gIEBJbnB1dCgpIG11bHRpcGxlSW1nTW9kZSA9IGZhbHNlO1xyXG4gIEBPdXRwdXQoKVxyXG4gIHN3aXRjaERpc3BsYXlXaW5kb3c6IEV2ZW50RW1pdHRlcjxib29sZWFuPiA9IG5ldyBFdmVudEVtaXR0ZXIoKTtcclxuXHJcbiAgQFZpZXdDaGlsZCgnaW1nTGliQ29udGFpbmVyJykgaW1nTGliQ29udGFpbmVyOiBFbGVtZW50UmVmO1xyXG4gIHdpZHRoTGFyZ2VDYXJkOiBudW1iZXIgPSAyMTk7IC8vIERlZmF1bHQgdmFsdWUgb2YgYSBjYXJkIHdpZHRoIDE5OSArIG1hcmdpbiAyMFxyXG4gIHdpZHRoU21hbGxDYXJkOiBudW1iZXIgPSAxNjA7IC8vIERlZmF1bHQgdmFsdWUgb2YgYSBjYXJkIHdpZHRoIDE0MCArIG1hcmdpbiAyMFxyXG4gIG5iTWluSW1nUGVyTGluZTogbnVtYmVyO1xyXG4gIG5iTWF4SW1nUGVyTGluZTogbnVtYmVyO1xyXG4gIG5iRmFrZUltZzogbnVtYmVyID0gMDtcclxuXHJcbiAgaW1nRnVsbFdpZHRoQ29uZmlnOmFueSA9IFtcclxuICAgIHtcclxuICAgICAgbWF4OiA0MTksXHJcbiAgICAgIGxhcmdlSW1nV2lkdGhGYWN0b3IgOiAxLFxyXG4gICAgICBzbWFsbEltZ1dpZHRoRmFjdG9yIDogMC41XHJcbiAgICB9LFxyXG4gICAge1xyXG4gICAgICBtYXg6IDQ5OSxcclxuICAgICAgbGFyZ2VJbWdXaWR0aEZhY3RvciA6IDEsXHJcbiAgICAgIHNtYWxsSW1nV2lkdGhGYWN0b3IgOiAwLjVcclxuICAgIH0sXHJcbiAgICB7XHJcbiAgICAgIG1heDogNzE5LCAvLyB0YWJsZXRcclxuICAgICAgbGFyZ2VJbWdXaWR0aEZhY3RvciA6IDAuNSxcclxuICAgICAgc21hbGxJbWdXaWR0aEZhY3RvciA6IDAuMzMzM1xyXG4gICAgfSxcclxuICAgIHtcclxuICAgICAgbWF4OiAxMDIzLCAvLyBkZXNrb3BcclxuICAgICAgbGFyZ2VJbWdXaWR0aEZhY3RvciA6IDAuMzMzMyxcclxuICAgICAgc21hbGxJbWdXaWR0aEZhY3RvciA6IDAuMlxyXG4gICAgfSxcclxuICAgIHtcclxuICAgICAgbWF4OiAxMzk5LFxyXG4gICAgICBsYXJnZUltZ1dpZHRoRmFjdG9yIDogMC4yNSxcclxuICAgICAgc21hbGxJbWdXaWR0aEZhY3RvciA6IDAuMTI1XHJcbiAgICB9LFxyXG4gICAge1xyXG4gICAgICBtYXg6IDE1OTksXHJcbiAgICAgIGxhcmdlSW1nV2lkdGhGYWN0b3IgOiAwLjIsXHJcbiAgICAgIHNtYWxsSW1nV2lkdGhGYWN0b3IgOiAwLjExMTFcclxuICAgIH0sXHJcbiAgICB7XHJcbiAgICAgIGxhcmdlSW1nV2lkdGhGYWN0b3IgOiAwLjE2NjYsXHJcbiAgICAgIHNtYWxsSW1nV2lkdGhGYWN0b3IgOiAwLjFcclxuICAgIH1cclxuICBdO1xyXG5cclxuICBpbWdXaWR0aENvbmZpZzphbnkgPSBbXHJcbiAgICB7XHJcbiAgICAgIG1heDogMTAyNCxcclxuICAgICAgbGFyZ2VJbWdXaWR0aEZhY3RvciA6IDAuMjUsXHJcbiAgICAgIHNtYWxsSW1nV2lkdGhGYWN0b3IgOiAwLjEyNVxyXG4gICAgfSxcclxuICAgIHtcclxuICAgICAgbWF4OiAxMTk5LFxyXG4gICAgICBsYXJnZUltZ1dpZHRoRmFjdG9yIDogMC4zMzMzLFxyXG4gICAgICBzbWFsbEltZ1dpZHRoRmFjdG9yIDogMC4yXHJcbiAgICB9LFxyXG4gICAge1xyXG4gICAgICBtYXg6IDEyOTksXHJcbiAgICAgIGxhcmdlSW1nV2lkdGhGYWN0b3IgOiAwLjMzMzMsXHJcbiAgICAgIHNtYWxsSW1nV2lkdGhGYWN0b3IgOiAwLjE2NjZcclxuICAgIH0sXHJcbiAgICB7XHJcbiAgICAgIG1heDogMTM5OSxcclxuICAgICAgbGFyZ2VJbWdXaWR0aEZhY3RvciA6IDAuMjUsXHJcbiAgICAgIHNtYWxsSW1nV2lkdGhGYWN0b3IgOiAwLjE2NjZcclxuICAgIH0sXHJcbiAgICB7XHJcbiAgICAgIG1heDogMTU5OSxcclxuICAgICAgbGFyZ2VJbWdXaWR0aEZhY3RvciA6IDAuMjUsXHJcbiAgICAgIHNtYWxsSW1nV2lkdGhGYWN0b3IgOiAwLjE0XHJcbiAgICB9LFxyXG4gICAge1xyXG4gICAgICBsYXJnZUltZ1dpZHRoRmFjdG9yIDogMC4yNSxcclxuICAgICAgc21hbGxJbWdXaWR0aEZhY3RvciA6IDAuMTI1XHJcbiAgICB9XHJcbiAgXTtcclxuXHJcbiAgbmJJbWdUb0RlbFNlbGVjdGVkOiBudW1iZXIgPSAwO1xyXG4gIGRpc2FibGU6IGJvb2xlYW4gPSBmYWxzZTsgLy8gVXNlIHRvIGRpc2FibGUgYWN0aW9uIGR1cmluZyBzZXJ2ZXIgcmVxdWVzdFxyXG4gIGRlbExpc3RJbWdMb2FkZXIgPSBmYWxzZTtcclxuICBpbml0Q29tcG9uZW50OiBib29sZWFuID0gdHJ1ZTtcclxuICBmYWlsTG9hZGVkOiBib29sZWFuID0gZmFsc2U7XHJcbiAgY29uZmlybUltZ1N1cDpib29sZWFuID0gZmFsc2U7XHJcbiAgcHJldmlvdXNTZWFyY2hWYWx1ZTogc3RyaW5nO1xyXG5cclxuICBnZXQgc2VhcmNoSW1hZ2VzUGFyYW1ldGVycyQoKSB7XHJcbiAgICByZXR1cm4gdGhpcy5pbWdNYW5hZ2VyLnNlYXJjaEltYWdlc1BhcmFtZXRlcnMkO1xyXG4gIH1cclxuXHJcbiAgLy8gQXBpIEltZyBtYW5hZ2VyIFBhcmFtc1xyXG4gIHBhcmFtczpQYXJhbXNJbWdNYW5hZ2VyRFRPO1xyXG5cclxuICBwcml2YXRlIGVycm9yR2V0QWxsSW1nID0gJ0ltZ01hbmFnZXIuSW1nTGliLmVycm9yR2V0QWxsSW1nJztcclxuICBwcml2YXRlIGVycm9yR2V0VG90YWxJbWcgPSAnSW1nTWFuYWdlci5JbWdMaWIuZXJyb3JHZXRUb3RhbEltZyc7XHJcbiAgcHJpdmF0ZSBlcnJvckdldEltZyA9ICdJbWdNYW5hZ2VyLkltZ0xpYi5lcnJvckdldENhbnZhSW1nJztcclxuICBwcml2YXRlIGVycm9yUmVtb3ZlSW1nID0gJ0ltZ01hbmFnZXIuSW1nTGlzdC5lcnJvclJlbW92ZUltZyc7XHJcblxyXG4gIHByaXZhdGUgZGVzdHJveSQgPSBuZXcgU3ViamVjdDx2b2lkPigpO1xyXG5cclxuICB2bSQ6IE9ic2VydmFibGU8YW55PjtcclxuXHJcbiAgY29uc3RydWN0b3IoXHJcbiAgICBwcml2YXRlIGltZ01hbmFnZXI6IEltZ01hbmFnZXJTZXJ2aWNlLFxyXG4gICAgcHJpdmF0ZSBpbWdFdmVudFNlcnZpY2U6IEltZ0V2ZW50U2VydmljZSxcclxuICAgIHByaXZhdGUgaW1nU2VsZWN0aW9uU2VydmljZTogSW1nU2VsZWN0aW9uU2VydmljZSxcclxuICAgIHByaXZhdGUgYWxlcnRTZXJ2aWNlOiBBbGVydFNlcnZpY2UsXHJcbiAgICBwcml2YXRlIHVzZXJTZXR0aW5nc1NlcnZpY2U6IFVzZXJTZXR0aW5nc1NlcnZpY2UsXHJcbiAgICBwcml2YXRlIHJlbmFtZVBpY3R1cmVTZXJ2aWNlOiBSZW5hbWVQaWN0dXJlU2VydmljZSxcclxuICAgIHByaXZhdGUgY2hhbmdlRGV0ZWN0b3JSZWY6IENoYW5nZURldGVjdG9yUmVmKSB7IH1cclxuXHJcbiAgbmdPbkluaXQoKTogdm9pZCB7XHJcbiAgICB0aGlzLnZtJCA9IGNvbWJpbmVMYXRlc3Qoe1xyXG4gICAgICBpbWFnZVNlbGVjdGlvbjogdGhpcy5pbWdTZWxlY3Rpb25TZXJ2aWNlLmltZ1NlbGVjdGlvbiQsXHJcbiAgICAgIGltYWdlTGlzdERhdGE6IHRoaXMuaW1nTWFuYWdlci5pbWFnZUxpc3QkLFxyXG4gICAgICBpc0xvYWRpbmc6IHRoaXMuaW1nTWFuYWdlci5pc0xvYWRpbmckLFxyXG4gICAgICBzZWFyY2hJbWFnZXNQYXJhbWV0ZXJzOiB0aGlzLmltZ01hbmFnZXIuc2VhcmNoSW1hZ2VzUGFyYW1ldGVycyQsXHJcbiAgICB9KS5waXBlKFxyXG4gICAgICBtYXAoKHtpbWFnZVNlbGVjdGlvbiwgaW1hZ2VMaXN0RGF0YToge2ltYWdlTGlzdCwgaW1hZ2VUb3RhbH0sIGlzTG9hZGluZywgc2VhcmNoSW1hZ2VzUGFyYW1ldGVyc30pID0+IHtcclxuICAgICAgICB0aGlzLmluaXRWYXJpYWJsZXModHJ1ZSk7IC8vIFNpIGNldHRlIG3DqXRob2RlIGVzdCBuw6ljZXNzYWlyZSDDoCBsJ2luaXRpYWxpc2F0aW9uXHJcbiAgICAgICAgdGhpcy5jYWxjdWxhdGVOYkltZ0Zha2UoaW1hZ2VMaXN0LmRhdGEubGVuZ3RoKTsgLy8gTcOqbWUgY2hvc2UgaWNpXHJcbiAgICAgICAgY29uc3QgcGljdHVyZXNMaXN0ID0gdGhpcy5zZXRTZWxlY3RlZFByb3BlcnR5KGltYWdlU2VsZWN0aW9uLCBpbWFnZUxpc3QuZGF0YSk7XHJcbiAgICAgICAgdGhpcy5yZW5hbWVQaWN0dXJlU2VydmljZS5zZXRQaWN0dXJlc0xpc3QocGljdHVyZXNMaXN0KTtcclxuXHJcbiAgICAgICAgY29uc3QgdGFibGVGaWx0ZXJzOiBUYWJsZUZpbHRlcnMgPSB0aGlzLmdldFRhYmxlRmlsdGVycyhzZWFyY2hJbWFnZXNQYXJhbWV0ZXJzLCBpbWFnZVRvdGFsKTtcclxuICAgICAgICBjb25zdCBrZWVwSW1hZ2VzRGlzcGxheWVkID0gKHRoaXMudGFiRGlzcGxheWVkID09PSAnaW1nLXVwbG9hZCcgJiYgc2VhcmNoSW1hZ2VzUGFyYW1ldGVycy5wYWdlID09PSAnMScpIHx8XHJcbiAgICAgICAgICAodGhpcy50YWJEaXNwbGF5ZWQgPT09ICdpbWFnZXMtdmlldycgJiYgaW1hZ2VMaXN0LmRhdGEubGVuZ3RoICYmIHNlYXJjaEltYWdlc1BhcmFtZXRlcnMucGFnZSA9PT0gJzEnKTtcclxuXHJcbiAgICAgICAgY29uc3Qgc2tpcFNldEltYWdlc1RvRGlzcGxheSA9ICEhcGljdHVyZXNMaXN0Py5sZW5ndGggJiYgdGhpcy50YWJEaXNwbGF5ZWQgPT09ICdpbWctdXBsb2FkJyAmJiBzZWFyY2hJbWFnZXNQYXJhbWV0ZXJzLnBhZ2UgPT09ICcxJztcclxuICAgICAgICBjb25zdCBoaWRlVW50aWxGZXRjaGVkRmlyc3RQYWdlSW1hZ2VzRm9yVGFiVXBsb2FkID0gdGhpcy50YWJEaXNwbGF5ZWQgPT09ICdpbWctdXBsb2FkJyAmJlxyXG4gICAgICAgICAgKHNlYXJjaEltYWdlc1BhcmFtZXRlcnMucGFnZSAhPT0gJzEnIHx8IGltYWdlTGlzdD8ucGFnZSAhPT0gMSk7XHJcblxyXG4gICAgICAgIHJldHVybiB7XHJcbiAgICAgICAgICBpc0xvYWRpbmc6IGhpZGVVbnRpbEZldGNoZWRGaXJzdFBhZ2VJbWFnZXNGb3JUYWJVcGxvYWQgfHwgKCFrZWVwSW1hZ2VzRGlzcGxheWVkICYmIGlzTG9hZGluZyksXHJcbiAgICAgICAgICBkaXNwbGF5UGV4ZWxzUmVzdWx0czogIWlzTG9hZGluZyAmJiBpbWFnZVRvdGFsID09PSAwLFxyXG4gICAgICAgICAgcGljdHVyZXNMaXN0LFxyXG4gICAgICAgICAgaW1hZ2VUb3RhbCxcclxuICAgICAgICAgIHRhYmxlRmlsdGVycyxcclxuICAgICAgICAgIHNraXBTZXRJbWFnZXNUb0Rpc3BsYXlcclxuICAgICAgICB9O1xyXG4gICAgICB9KVxyXG4gICAgKTtcclxuICB9XHJcblxyXG4gIHByaXZhdGUgZ2V0VGFibGVGaWx0ZXJzKHNlYXJjaEltYWdlc1BhcmFtZXRlcnM6IGFueSwgaW1hZ2VUb3RhbDogYW55KTogVGFibGVGaWx0ZXJzIHtcclxuICAgIHJldHVybiB7XHJcbiAgICAgIHNvcnQ6IHVuZGVmaW5lZCxcclxuICAgICAgb3JkZXI6IHVuZGVmaW5lZCxcclxuICAgICAgc2VhcmNoVmFsdWU6IHNlYXJjaEltYWdlc1BhcmFtZXRlcnMuc2VhcmNoLFxyXG4gICAgICB0b3RhbEl0ZW1zOiBpbWFnZVRvdGFsLFxyXG4gICAgICBpdGVtc1BlclBhZ2U6IHBhcnNlSW50KHNlYXJjaEltYWdlc1BhcmFtZXRlcnMubGltaXQpLFxyXG4gICAgICBjdXJyZW50UGFnZTogcGFyc2VJbnQoc2VhcmNoSW1hZ2VzUGFyYW1ldGVycy5wYWdlKVxyXG4gICAgfTtcclxuICB9XHJcblxyXG4gIG5nQWZ0ZXJWaWV3SW5pdCgpIHtcclxuICAgIHRoaXMudm0kLnBpcGUoXHJcbiAgICAgIHRha2UoMSksXHJcbiAgICAgIGZpbHRlcigoe3NraXBTZXRJbWFnZXNUb0Rpc3BsYXl9KSA9PiAhc2tpcFNldEltYWdlc1RvRGlzcGxheSlcclxuICAgICAgKS5zdWJzY3JpYmUoKHt0YWJsZUZpbHRlcnN9KSA9PntcclxuICAgICAgICAgdGhpcy5zZXROYkltZ1RvRGlzcGxheSh0YWJsZUZpbHRlcnMpXHJcbiAgICAgICAgfSk7XHJcbiAgfVxyXG5cclxuICAvKipcclxuICAgKiB0cnVlIDogZ28gdG8gbGlzdCBkaXNwbGF5XHJcbiAgICogZmFsc2UgOiBnbyB0byBtb3NhaWMgZGlzcGxheVxyXG4gICAqIEBwYXJhbSBhY3RpdmF0ZVxyXG4gICAqL1xyXG4gIG9uU3dpdGNoRm9ybWF0RGlzcGxheWVkKGFjdGl2YXRlOiBib29sZWFuKSB7XHJcbiAgICB0aGlzLmxpc3REaXNwbGF5ZWQgPSBhY3RpdmF0ZTtcclxuICAgIHRoaXMudXNlclNldHRpbmdzU2VydmljZS5zZXRVc2VyRGlzcGxheVByZWZlcmVuY2UoYWN0aXZhdGUpO1xyXG4gICAgdGhpcy5pbWdFdmVudFNlcnZpY2UuZW1pdGxpc3REaXNwbGF5ZWRDaGFuZ2UoYWN0aXZhdGUpO1xyXG4gIH1cclxuXHJcbiAgLyoqXHJcbiAgICogQ2FsY3VsIHRoZSBudW1iZXIgb2YgaW1nIHNlbGVjdGVkIGZvciBtYXNzZSBkZWxldGlvblxyXG4gICAqL1xyXG4gIG9uSW1nU2VsZWN0ZWQocGljdHVyZXNMaXN0OiBJbWdQaWN0dXJlRFRPW10pIHtcclxuICAgIHRoaXMuc2V0TmJJbWdUb0RlbFNlbGVjdGVkKHBpY3R1cmVzTGlzdCk7XHJcbiAgfVxyXG5cclxuICBvblJlbmFtZVBpY3R1cmUocGljdHVyZVJlbmFtZWQ6IFBpY3R1cmVOYW1lVXBkYXRlKSB7XHJcbiAgICB0aGlzLnJlbmFtZVBpY3R1cmVTZXJ2aWNlLnJlbmFtZVBpY3R1cmUocGljdHVyZVJlbmFtZWQpO1xyXG4gIH1cclxuXHJcbiAgcmVtb3ZlTGlzdEltZyhwaWN0dXJlc0xpc3Q6IEltZ1BpY3R1cmVEVE9bXSkge1xyXG4gICAgaWYgKHRoaXMuZGlzYWJsZSkge1xyXG4gICAgICByZXR1cm47XHJcbiAgICB9XHJcbiAgICB0aGlzLmRpc2FibGUgPSB0cnVlO1xyXG4gICAgdGhpcy5kZWxMaXN0SW1nTG9hZGVyID0gdHJ1ZTtcclxuICAgIHRoaXMuY29uZmlybUltZ1N1cCA9IGZhbHNlO1xyXG5cclxuICAgIC8vIEdldCB0aGUgaWQgb2YgdGhlIGltZyB0byByZW1vdmVcclxuICAgIC8vIEFuZCBhZGQgZGVsZXRlZCBwcm9wZXJ0eVxyXG4gICAgY29uc3QgaWRJbWdUb1JlbW92ZTogc3RyaW5nW10gPSBbXTtcclxuICAgIHBpY3R1cmVzTGlzdC5mb3JFYWNoKCBpbWcgPT4ge1xyXG4gICAgICBpZiAoaW1nLmRlbFNlbGVjdGVkKSB7XHJcbiAgICAgICAgaW1nLmRlbGV0ZWQgPSB0cnVlO1xyXG4gICAgICAgIGlkSW1nVG9SZW1vdmUucHVzaChpbWcuaWRfZmlsZSk7XHJcbiAgICAgIH1cclxuICAgIH0pO1xyXG5cclxuICAgIHRoaXMuaW1nTWFuYWdlci5yZW1vdmVNdWx0aXBsZUltZyhpZEltZ1RvUmVtb3ZlKS5zdWJzY3JpYmUoe1xyXG4gICAgICBuZXh0OiAoKSA9PiB7XHJcbiAgICAgICAgdGhpcy5pbWdTZWxlY3Rpb25TZXJ2aWNlLnJlbW92ZUltZ1NlbGVjdGlvbkJ5SWRzKGlkSW1nVG9SZW1vdmUpO1xyXG4gICAgICB9LFxyXG4gICAgICBlcnJvcjogZXJyb3IgPT4ge1xyXG4gICAgICAgIHRoaXMuaW1nTWFuYWdlci5yZWZyZXNoSW1hZ2VMaXN0JC5uZXh0KCk7XHJcbiAgICAgICAgdGhpcy5hbGVydFNlcnZpY2Uub3BlbkFsZXJ0KHRoaXMuZXJyb3JSZW1vdmVJbWcpO1xyXG4gICAgICB9XHJcbiAgICB9KTtcclxuICB9XHJcblxyXG4gIHNlbGVjdEltZ0Nob3NlbihwaWN0dXJlc0xpc3Q6IEltZ1BpY3R1cmVEVE9bXSkge1xyXG4gICAgaWYgKHRoaXMuZGlzYWJsZSkge1xyXG4gICAgICByZXR1cm47XHJcbiAgICB9XHJcbiAgICBjb25zdCBwaWN0dXJlc0xpc3RTZWxlY3RlZDogSW1nUGljdHVyZURUT1tdID0gW107XHJcbiAgICBwaWN0dXJlc0xpc3QubWFwKGltZyA9PiB7XHJcbiAgICAgIGlmKGltZy5kZWxTZWxlY3RlZCkge1xyXG4gICAgICAgIGltZy5kZWxTZWxlY3RlZCA9ZmFsc2U7XHJcbiAgICAgICAgaW1nLnNlbGVjdGVkID0gdHJ1ZTtcclxuICAgICAgfVxyXG4gICAgICBpZiAoaW1nLnNlbGVjdGVkKSB7XHJcbiAgICAgICAgcGljdHVyZXNMaXN0U2VsZWN0ZWQucHVzaChpbWcpO1xyXG4gICAgICB9XHJcbiAgICB9KTtcclxuICAgIHRoaXMuc2V0TmJJbWdUb0RlbFNlbGVjdGVkKHBpY3R1cmVzTGlzdCk7XHJcbiAgICB0aGlzLmltZ1NlbGVjdGlvblNlcnZpY2Uuc2V0SW1nU2VsZWN0aW9uKHBpY3R1cmVzTGlzdFNlbGVjdGVkKTtcclxuICB9XHJcblxyXG4gIGRpc3BsYXlDb25maXJtSW1nU3VwKCl7XHJcbiAgICBpZiAodGhpcy5kaXNhYmxlKSB7XHJcbiAgICAgIHJldHVybjtcclxuICAgIH1cclxuICAgIHRoaXMuY29uZmlybUltZ1N1cCA9IHRydWU7XHJcbiAgfVxyXG5cclxuICBjYW5jZWxTdXAoKSB7XHJcbiAgICB0aGlzLmNvbmZpcm1JbWdTdXAgPSBmYWxzZTtcclxuICB9XHJcblxyXG4gIC8qKlxyXG4gICAqIEV2ZW50IGVtaXQgd2hlbiBhIGltZyBzZWxlY3RlZCBpbiBvcmRlciB0byBkZWxldGVcclxuICAgKi9cclxuICBvblBpY3R1cmVzTGlzdENoYW5nZShwaWN0dXJlc0xpc3Q6IEltZ1BpY3R1cmVEVE9bXSkge1xyXG4gICAgdGhpcy5zZXROYkltZ1RvRGVsU2VsZWN0ZWQocGljdHVyZXNMaXN0KTtcclxuICB9XHJcblxyXG4gIC8qKlxyXG4gICAqIFNldCBkZWZhdWx0IG51bWJlciBvZiBpbWcgcGVyIHBhZ2UgdG8gZGlzcGxheSBhdCB0aGUgaW5pdGlhbGlzYXRpb25cclxuICAgKiBUaGlzIG51bWJlciBpcyBiZXR3ZWVuIDMwIGFuZCA1MFxyXG4gICAqL1xyXG4gIHByaXZhdGUgc2V0TmJJbWdUb0Rpc3BsYXkodGFibGVGaWx0ZXJzOiBUYWJsZUZpbHRlcnMpIHtcclxuICAgIGNvbnN0IGNvbnRhaW5lcldpZHRoID0gdGhpcy5pbWdMaWJDb250YWluZXIubmF0aXZlRWxlbWVudC5vZmZzZXRXaWR0aCArIDMwOyAvLyArIDMwcHggLT4gbGVmdCArIHJpZ2h0IG1hcmdpblxyXG4gICAgY29uc3Qgc2Nyb2xsV2lkdGggPSB3aW5kb3cuaW5uZXJXaWR0aCAtIGRvY3VtZW50LmJvZHkub2Zmc2V0V2lkdGg7XHJcblxyXG4gICAgY29uc3QgW21heEltZ1dpZHRoRmFjdG9yLCBtaW5JbWdXaWR0aEZhY3Rvcl0gPSB0aGlzLmdldEltZ1dpZHRoRmFjdG9ycygpO1xyXG5cclxuICAgIGNvbnN0IG1pbkltZ1dpZHRoID0gTWF0aC5mbG9vcihjb250YWluZXJXaWR0aCAqIG1pbkltZ1dpZHRoRmFjdG9yKTtcclxuICAgIGNvbnN0IG1heEltZ1dpZHRoID0gTWF0aC5jZWlsKChjb250YWluZXJXaWR0aCArIHNjcm9sbFdpZHRoICkgKiBtYXhJbWdXaWR0aEZhY3Rvcik7XHJcblxyXG4gICAgdGhpcy5uYk1heEltZ1BlckxpbmUgPSBNYXRoLmZsb29yKGNvbnRhaW5lcldpZHRoIC8gbWluSW1nV2lkdGgpO1xyXG4gICAgdGhpcy5uYk1pbkltZ1BlckxpbmUgPSBNYXRoLmZsb29yKCAoY29udGFpbmVyV2lkdGggKyBzY3JvbGxXaWR0aCApIC8gbWF4SW1nV2lkdGgpO1xyXG5cclxuICAgIHRoaXMuc2VhcmNoSW1hZ2VzUGFyYW1ldGVycyQubmV4dCh0aGlzLmdldFBhcmFtcyh7XHJcbiAgICAgIC4uLnRhYmxlRmlsdGVycyxcclxuICAgICAgaXRlbXNQZXJQYWdlOiB0aGlzLmdldFRvdGFsSW1nUGVyUGFnZSgpLFxyXG4gICAgICBjdXJyZW50UGFnZTogMVxyXG4gICAgfSkpO1xyXG4gIH1cclxuXHJcbiAgcHJpdmF0ZSBnZXRJbWdXaWR0aEZhY3RvcnMoKTogbnVtYmVyW10ge1xyXG4gICAgY29uc3Qgc2NyZWVuV2lkdGggPSB3aW5kb3cuaW5uZXJXaWR0aDtcclxuICAgIGxldCBtaW5XaWR0aDpudW1iZXIgPSAwO1xyXG4gICAgbGV0IGltZ1NpemVzQ29uZmlnOiBudW1iZXJbXSA9IFtdO1xyXG5cclxuICAgIGNvbnN0IGN1cnJlbnRJbWdXaWR0aENvbmZpZyA9IHRoaXMuZnVsbFNpemUgPyB0aGlzLmltZ0Z1bGxXaWR0aENvbmZpZyA6IHRoaXMuaW1nV2lkdGhDb25maWc7XHJcblxyXG4gICAgZm9yIChjb25zdCB3aWR0aENvbmZpZyBvZiBjdXJyZW50SW1nV2lkdGhDb25maWcpIHtcclxuICAgICAgICBpZiAoIXdpZHRoQ29uZmlnLm1heCkge1xyXG4gICAgICAgICAgaW1nU2l6ZXNDb25maWcgPSBbd2lkdGhDb25maWcubGFyZ2VJbWdXaWR0aEZhY3Rvciwgd2lkdGhDb25maWcuc21hbGxJbWdXaWR0aEZhY3Rvcl07XHJcbiAgICAgICAgICBicmVhaztcclxuICAgICAgICB9XHJcbiAgICAgICAgaWYgKG1pbldpZHRoIDwgc2NyZWVuV2lkdGggJiYgc2NyZWVuV2lkdGggPD0gd2lkdGhDb25maWcubWF4KSB7XHJcbiAgICAgICAgICBpbWdTaXplc0NvbmZpZyA9IFt3aWR0aENvbmZpZy5sYXJnZUltZ1dpZHRoRmFjdG9yLCB3aWR0aENvbmZpZy5zbWFsbEltZ1dpZHRoRmFjdG9yXTtcclxuICAgICAgICAgIGJyZWFrO1xyXG4gICAgICAgIH1cclxuICAgICAgICBtaW5XaWR0aCA9IHdpZHRoQ29uZmlnLm1heDtcclxuICAgIH1cclxuICAgIHJldHVybiBpbWdTaXplc0NvbmZpZztcclxuICB9XHJcblxyXG4gIHByaXZhdGUgZ2V0VG90YWxJbWdQZXJQYWdlKCk6IG51bWJlciB7XHJcbiAgICBpZiAodGhpcy5uYlJvd1RvU2hvdykge1xyXG4gICAgICBjb25zdCBuYkltZ1BlckxpbmUgPSB0aGlzLnN0YXRlRGlzcGxheWVkID09PSAnZnVsbCcgPyB0aGlzLm5iTWluSW1nUGVyTGluZSA6IHRoaXMubmJNYXhJbWdQZXJMaW5lO1xyXG4gICAgICByZXR1cm4gbmJJbWdQZXJMaW5lICogdGhpcy5uYlJvd1RvU2hvdztcclxuICAgIH1cclxuXHJcbiAgICBsZXQgdG90YWwgPSB0aGlzLm5iTWluSW1nUGVyTGluZTtcclxuXHJcbiAgICB3aGlsZSAodG90YWwgPCAzMCB8fCB0b3RhbCAlIHRoaXMubmJNYXhJbWdQZXJMaW5lICE9PSAwIHx8ICB0b3RhbCAlIHRoaXMubmJNaW5JbWdQZXJMaW5lICE9PSAwKSB7XHJcbiAgICAgIHRvdGFsICs9IHRoaXMubmJNaW5JbWdQZXJMaW5lO1xyXG4gICAgfVxyXG5cclxuICAgIHJldHVybiB0b3RhbDtcclxuICB9XHJcblxyXG4gIGdldFBhcmFtcyh0YWJsZUZpbHRlcnM6IFRhYmxlRmlsdGVycykge1xyXG4gICAgcmV0dXJuIHtcclxuICAgICAgbGltaXQ6IHRhYmxlRmlsdGVycy5pdGVtc1BlclBhZ2UudG9TdHJpbmcoKSxcclxuICAgICAgcGFnZTogdGFibGVGaWx0ZXJzLmN1cnJlbnRQYWdlLnRvU3RyaW5nKCksXHJcbiAgICAgICAuLi4odGFibGVGaWx0ZXJzLnNlYXJjaFZhbHVlICYmIHsgc2VhcmNoOiB0YWJsZUZpbHRlcnMuc2VhcmNoVmFsdWUudG9TdHJpbmcoKSB9KSxcclxuICAgIH07XHJcbiAgfVxyXG5cclxuICBwcml2YXRlIGluaXRWYXJpYWJsZXMobG9hZGluZ1N1Y2Nlc3M6IGJvb2xlYW4pIHtcclxuICAgIHRoaXMubmJJbWdUb0RlbFNlbGVjdGVkID0gMDtcclxuICAgIHRoaXMuZGlzYWJsZSA9IGZhbHNlO1xyXG4gICAgdGhpcy5kZWxMaXN0SW1nTG9hZGVyID0gZmFsc2U7XHJcbiAgICB0aGlzLmluaXRDb21wb25lbnQgPSBmYWxzZTtcclxuICAgIHRoaXMuZmFpbExvYWRlZCA9ICFsb2FkaW5nU3VjY2VzcztcclxuICAgIHRoaXMubmJGYWtlSW1nID0gMDtcclxuICB9XHJcblxyXG4gIHByaXZhdGUgc2V0U2VsZWN0ZWRQcm9wZXJ0eShpbWdTZWxlY3RlZExpc3Q6IEltZ1BpY3R1cmVEVE9bXSwgcGljdHVyZXNMaXN0OiBJbWdQaWN0dXJlRFRPW10pIHtcclxuICAgIGNvbnN0IHBpY3R1cmVzTGlzdFNlbGVjdGVkOiBJbWdQaWN0dXJlRFRPW10gPSBKU09OLnBhcnNlKEpTT04uc3RyaW5naWZ5KHBpY3R1cmVzTGlzdCkpO1xyXG4gICAgaW1nU2VsZWN0ZWRMaXN0LmZvckVhY2goaW1nID0+IHtcclxuICAgICAgY29uc3Qgc2VsZWN0ZWRJbWcgPSBwaWN0dXJlc0xpc3RTZWxlY3RlZC5maW5kKHBpY3R1cmUgPT4gcGljdHVyZS5pZF9maWxlID09PSBpbWcuaWRfZmlsZSk7XHJcbiAgICAgIGlmIChzZWxlY3RlZEltZykge1xyXG4gICAgICAgIHNlbGVjdGVkSW1nLnNlbGVjdGVkID0gdHJ1ZTtcclxuICAgICAgfVxyXG4gICAgfSk7XHJcbiAgICByZXR1cm4gcGljdHVyZXNMaXN0U2VsZWN0ZWQ7XHJcbiAgfVxyXG5cclxuICAvKipcclxuICAgKiBTZXQgYSBpbWcgbGlzdCBpbiBvcmRlciB0byBmaWxsIHByb3Blcmx5IGFsbCB0aGUgbGluZSBvZiBpbWFnZXMgZGlzcGxheWVkIGluIG1vc2FpYy5cclxuICAgKiBPdGhlcndpc2UsIHRoZSBzcGFjZS1iZXR3ZWVuIGNzcyB3aWxsIGRvIGEgYmFkIGRpc3BsYXlcclxuICAgKi9cclxuICBwcml2YXRlIGNhbGN1bGF0ZU5iSW1nRmFrZShuYkltZ0Rpc3BsYXllZDogbnVtYmVyKSB7XHJcbiAgICBjb25zdCBuYkltZ1BlckxpbmUgPSB0aGlzLnN0YXRlRGlzcGxheWVkID09PSAnc21hbGwnIHx8IHRoaXMudGFiRGlzcGxheWVkID09PSAnaW1nLXVwbG9hZCcgPyB0aGlzLm5iTWF4SW1nUGVyTGluZSA6IHRoaXMubmJNaW5JbWdQZXJMaW5lO1xyXG5cclxuICAgIGlmIChpc05hTihuYkltZ0Rpc3BsYXllZCAlIG5iSW1nUGVyTGluZSkpIHtcclxuICAgICAgdGhpcy5uYkZha2VJbWcgPSAwO1xyXG4gICAgICByZXR1cm47XHJcbiAgICB9XHJcblxyXG4gICAgaWYgKG5iSW1nRGlzcGxheWVkICUgbmJJbWdQZXJMaW5lICE9PSAwKSB7XHJcbiAgICAgIHNldFRpbWVvdXQoKCkgPT4ge1xyXG4gICAgICAgIHRoaXMubmJGYWtlSW1nID0gbmJJbWdQZXJMaW5lIC0gbmJJbWdEaXNwbGF5ZWQgJSBuYkltZ1BlckxpbmU7XHJcbiAgICAgIH0sIDApO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgcHJpdmF0ZSBzZXROYkltZ1RvRGVsU2VsZWN0ZWQgKHBpY3R1cmVzTGlzdDogSW1nUGljdHVyZURUT1tdKSB7XHJcbiAgICB0aGlzLm5iSW1nVG9EZWxTZWxlY3RlZCA9IHBpY3R1cmVzTGlzdC5maWx0ZXIoaW1nID0+IGltZy5kZWxTZWxlY3RlZCkubGVuZ3RoO1xyXG5cclxuICAgIGlmICghdGhpcy5uYkltZ1RvRGVsU2VsZWN0ZWQpIHtcclxuICAgICAgdGhpcy5jb25maXJtSW1nU3VwID0gZmFsc2U7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICBzd2l0Y2hEaXNwbGF5V2luZG93TW9zYWljKCkge1xyXG4gICAgdGhpcy5zd2l0Y2hEaXNwbGF5V2luZG93LmVtaXQodHJ1ZSk7XHJcbiAgfVxyXG5cclxuICBuZ09uRGVzdHJveSgpOiB2b2lkIHtcclxuICAgIHRoaXMuZGVzdHJveSQubmV4dCgpO1xyXG4gICAgdGhpcy5kZXN0cm95JC5jb21wbGV0ZSgpO1xyXG4gIH1cclxufVxyXG4iLCI8bmctY29udGFpbmVyICpuZ0lmPVwidm0kIHwgYXN5bmMgYXMgdm1cIj5cclxuXHJcbiAgPGRpdiBjbGFzcz1cImltYWdlcy12aWV3XCIgW25nQ2xhc3NdPVwieydmdWxsU2l6ZSc6IGZ1bGxTaXplLCAnc21hbGwnOiBzdGF0ZURpc3BsYXllZCA9PT0gJ3NtYWxsJ31cIiBbQGVhc2VJbk91dF09XCInaW4nXCI+XHJcbiAgICA8IS0tIFN1YmhlYWRlciA6IEltZyBudW1iZXIgYW5kIGFjdGlvbnMgYnRuIChzdXAgaW1nIGxpc3QsIHN3aXRjaCBmb3JtYSBkaXNwbGF5KSAtLT5cclxuICAgIDxkaXZcclxuICAgICpuZ0lmPVwiKHN0YXRlRGlzcGxheWVkICE9PSAnc21hbGwnIHx8IHRhYkRpc3BsYXllZCA9PT0gJ2ltZy11cGxvYWQnKVwiXHJcbiAgICBjbGFzcz1cImltYWdlcy12aWV3X19jb250YWluZXJcIlxyXG4gICAgW25nQ2xhc3NdPVwieydpbWFnZXMtdmlld19fY29udGFpbmVyLS11cGxvYWRUYWInOiB0YWJEaXNwbGF5ZWQgPT09ICdpbWctdXBsb2FkJywgJ2ltYWdlcy12aWV3X19jb250YWluZXItLXdpbmRvdyc6IHN0YXRlRGlzcGxheWVkID09PSAnd2luZG93J31cIlxyXG4gICAgPlxyXG5cclxuICAgICAgPGRpdiAqbmdJZj1cInRhYkRpc3BsYXllZCAhPT0gJ2ltZy11cGxvYWQnXCI+XHJcbiAgICAgICAgICA8cCBjbGFzcz1cIm1haW5Db2xvclwiIFtuZ0NsYXNzXT1cInsnaW1hZ2VzLXZpZXdfX2NvbnRhaW5lcl9fdG90YWwtLWhpZGUnOiB2bS5kaXNwbGF5UGV4ZWxzUmVzdWx0c31cIj57eyAnSW1nTWFuYWdlci5JbWdMaWIubmJJbWcnIHwgdHJhbnNsYXRlIH19IDoge3t2bS5pbWFnZVRvdGFsfX08L3A+XHJcbiAgICAgIDwvZGl2PlxyXG4gICAgICA8ZGl2ICpuZ0lmPVwidGFiRGlzcGxheWVkID09PSAnaW1nLXVwbG9hZCdcIj5cclxuICAgICAgICAgIDxwIGNsYXNzPVwibWFpbkNvbG9yXCI+e3sgJ0ltZ01hbmFnZXIuSW1nTGliLmxhc3RJbWdzJyB8IHRyYW5zbGF0ZSB9fTwvcD5cclxuICAgICAgPC9kaXY+XHJcblxyXG4gICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgaGFzLWFkZG9ucyBzdWJIZWFkZXJBY3Rpb25zXCIgKm5nSWY9XCJ0YWJEaXNwbGF5ZWQgIT09ICdpbWctdXBsb2FkJ1wiPlxyXG5cclxuICAgICAgICAgIDwhLS0gRm9yIGxpc3Rmb3JtYSA6IERpc3BsYXkgYnRuIGRlbCBtdWx0aXBsZSBpbWcgJiBDb25maXJtIGFjdGlvbiAtLT5cclxuICAgICAgICAgIDxkaXYgY2xhc3M9XCJpbWFnZXMtdmlld19fY29udGFpbmVyX19ib3hBY3Rpb25cIj5cclxuXHJcblxyXG4gICAgICAgICAgICAgIDwhLS0gU2VsZWN0IC0tPlxyXG4gICAgICAgICAgICAgIDxidXR0b25cclxuICAgICAgICAgICAgICAgIGNsYXNzPVwiYnV0dG9uIHN1Y2Nlc3MgaW1hZ2VzLXZpZXdfX2NvbnRhaW5lcl9fYm94QWN0aW9uX19pbXBvcnRcIlxyXG4gICAgICAgICAgICAgICAgQGluc2VydFJlbW92ZUFubmltXHJcbiAgICAgICAgICAgICAgICAqbmdJZj1cImxpc3REaXNwbGF5ZWQgJiYgbmJJbWdUb0RlbFNlbGVjdGVkICYmICFjb25maXJtSW1nU3VwICYmICFkZWxMaXN0SW1nTG9hZGVyICYmIG11bHRpcGxlSW1nTW9kZVwiXHJcbiAgICAgICAgICAgICAgICAoY2xpY2spPVwic2VsZWN0SW1nQ2hvc2VuKHZtLnBpY3R1cmVzTGlzdClcIlxyXG4gICAgICAgICAgICAgICAgdHlwZT1cImJ1dHRvblwiXHJcbiAgICAgICAgICAgICAgICA+XHJcbiAgICAgICAgICAgICAgICAgIDxpIGNsYXNzPVwiZmFsIGZhLWNoZWNrXCI+PC9pPlxyXG4gICAgICAgICAgICAgICAgICB7eyAnSW1nTWFuYWdlci5JbWdMaWIuc2VsZWN0JyB8IHRyYW5zbGF0ZSB9fSAoe3tuYkltZ1RvRGVsU2VsZWN0ZWR9fSlcclxuICAgICAgICAgICAgICA8L2J1dHRvbj5cclxuXHJcbiAgICAgICAgICAgICAgPCEtLSBEaXNwbGF5IGJ0biBkZWwgbXVsdGlwbGUgaW1nIC0tPlxyXG4gICAgICAgICAgICAgIDxidXR0b25cclxuICAgICAgICAgICAgICAgICpuZ0lmPVwibGlzdERpc3BsYXllZCAmJiBuYkltZ1RvRGVsU2VsZWN0ZWQgJiYgIWNvbmZpcm1JbWdTdXBcIlxyXG4gICAgICAgICAgICAgICAgKGNsaWNrKT1cImRpc3BsYXlDb25maXJtSW1nU3VwKClcIlxyXG4gICAgICAgICAgICAgICAgY2xhc3M9XCJidXR0b24gaW1hZ2VzLXZpZXdfX2NvbnRhaW5lcl9fYm94QWN0aW9uX19kZWxCdG4gZGFuZ2VyXCJcclxuICAgICAgICAgICAgICAgIEBpbnNlcnRSZW1vdmVBbm5pbVxyXG4gICAgICAgICAgICAgICAgdHlwZT1cImJ1dHRvblwiXHJcbiAgICAgICAgICAgICAgPlxyXG4gICAgICAgICAgICAgICAgICA8aSBjbGFzcz1cImZhbCBmYS10aW1lc1wiPjwvaT57eyAnSW1nTWFuYWdlci5JbWdMaWIuZGVsTWx0JyB8IHRyYW5zbGF0ZSB9fSAoe3tuYkltZ1RvRGVsU2VsZWN0ZWR9fSlcclxuICAgICAgICAgICAgICAgICAgPHNwYW4gYnRuTG9hZGluZ0FuaW0gKm5nSWY9XCJkZWxMaXN0SW1nTG9hZGVyXCIgY2xhc3M9XCJidG5Mb2FkaW5nQW5uaW1hdGlvblwiPjwvc3Bhbj5cclxuICAgICAgICAgICAgICA8L2J1dHRvbj5cclxuXHJcbiAgICAgICAgICAgICAgPCEtLSBDb25maXJtIGFjdGlvbiAtLT5cclxuICAgICAgICAgICAgICA8ZGl2XHJcbiAgICAgICAgICAgICAgICBjbGFzcz1cImltYWdlcy12aWV3X19jb250YWluZXJfX2JveEFjdGlvbl9fY29uZmlybVN1cFwiXHJcbiAgICAgICAgICAgICAgICBbbmdDbGFzc109XCJ7J2ltYWdlcy12aWV3X19jb250YWluZXJfX2JveEFjdGlvbl9fY29uZmlybVN1cC0tdmlzaWJsZSc6IGNvbmZpcm1JbWdTdXB9XCI+XHJcbiAgICAgICAgICAgICAgICAgIDxwICpuZ0lmPVwibmJJbWdUb0RlbFNlbGVjdGVkID4gMVwiIGNsYXNzPVwiaW1hZ2VzLXZpZXdfX2NvbnRhaW5lcl9fYm94QWN0aW9uX19jb25maXJtU3VwX190ZXh0XCI+e3sgJ0ltZ01hbmFnZXIuSW1nTGliLmNvbmZpcm1TdXBRdWVzdGlvbnMnIHwgdHJhbnNsYXRlOntuYkltYWdlOiBuYkltZ1RvRGVsU2VsZWN0ZWR9IH19PC9wPlxyXG4gICAgICAgICAgICAgICAgICA8cCAqbmdJZj1cIm5iSW1nVG9EZWxTZWxlY3RlZCA9PT0gMVwiIGNsYXNzPVwiaW1hZ2VzLXZpZXdfX2NvbnRhaW5lcl9fYm94QWN0aW9uX19jb25maXJtU3VwX190ZXh0XCI+e3sgJ0ltZ01hbmFnZXIuSW1nTGliLmNvbmZpcm1TdXBRdWVzdGlvbicgfCB0cmFuc2xhdGU6e25iSW1hZ2U6IG5iSW1nVG9EZWxTZWxlY3RlZH0gfX08L3A+XHJcbiAgICAgICAgICAgICAgICAgIDxkaXY+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8YnV0dG9uXHJcbiAgICAgICAgICAgICAgICAgICAgICAgIGNsYXNzPVwiYnV0dG9uIGltYWdlcy12aWV3X19jb250YWluZXJfX2JveEFjdGlvbl9fY29uZmlybVN1cF9fY2FuY2VsXCJcclxuICAgICAgICAgICAgICAgICAgICAgICAgKGNsaWNrKT1cImNhbmNlbFN1cCgpXCJcclxuICAgICAgICAgICAgICAgICAgICAgICAgdHlwZT1cImJ1dHRvblwiXHJcbiAgICAgICAgICAgICAgICAgICAgICA+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgIHt7ICdJbWdNYW5hZ2VyLkltZ0xpYi5jYW5jZWwnIHwgdHJhbnNsYXRlIH19XHJcbiAgICAgICAgICAgICAgICAgICAgICA8L2J1dHRvbj5cclxuICAgICAgICAgICAgICAgICAgICAgIDxidXR0b25cclxuICAgICAgICAgICAgICAgICAgICAgICAgKGNsaWNrKT1cInJlbW92ZUxpc3RJbWcodm0ucGljdHVyZXNMaXN0KVwiXHJcbiAgICAgICAgICAgICAgICAgICAgICAgIGNsYXNzPVwiYnV0dG9uIGltYWdlcy12aWV3X19jb250YWluZXJfX2RlbEJ0biBkYW5nZXJcIlxyXG4gICAgICAgICAgICAgICAgICAgICAgICB0eXBlPVwiYnV0dG9uXCJcclxuICAgICAgICAgICAgICAgICAgICAgID5cclxuICAgICAgICAgICAgICAgICAgICAgICAge3sgJ0ltZ01hbmFnZXIuSW1nTGliLmNvbmZpcm0nIHwgdHJhbnNsYXRlIH19XHJcbiAgICAgICAgICAgICAgICAgICAgPC9idXR0b24+XHJcbiAgICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG5cclxuICAgICAgICAgIDwvZGl2PlxyXG5cclxuXHJcbiAgICAgICAgICA8IS0tIFN3aXRoIG1vc2FpYy9saXN0IGZvcm1hIC0tPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGhhcy1hZGRvbnMgaW1hZ2VzLXZpZXdfX2NvbnRhaW5lcl9fYnV0dG9uQm94XCI+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImNvbnRyb2xcIj5cclxuICAgICAgICAgICAgICAgICAgPGRpdlxyXG4gICAgICAgICAgICAgICAgICAgIGNsYXNzPVwiYnV0dG9uIGlzLWxpZ2h0ZWQgaW1hZ2VzLXZpZXdfX2NvbnRhaW5lcl9fYnV0dG9uQm94X19idG5cIlxyXG4gICAgICAgICAgICAgICAgICAgIFtuZ0NsYXNzXT1cInsnYWN0aWZEaXNwbGF5ZWQnOiAhbGlzdERpc3BsYXllZH1cIlxyXG4gICAgICAgICAgICAgICAgICAgIChjbGljayk9XCJvblN3aXRjaEZvcm1hdERpc3BsYXllZChmYWxzZSlcIlxyXG4gICAgICAgICAgICAgICAgICA+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8c3BhbiBjbGFzcz1cImljb24gaXMtc21hbGxcIj5cclxuICAgICAgICAgICAgICAgICAgICAgICAgPGkgY2xhc3M9XCJmYS1zb2xpZCBmYS10aFwiPjwvaT5cclxuICAgICAgICAgICAgICAgICAgICAgIDwvc3Bhbj5cclxuICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcblxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJjb250cm9sXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJidXR0b24gaXMtbGlnaHRlZCBpbWFnZXMtdmlld19fY29udGFpbmVyX19idXR0b25Cb3hfX2J0blwiXHJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgW25nQ2xhc3NdPVwieydhY3RpZkRpc3BsYXllZCc6IGxpc3REaXNwbGF5ZWR9XCJcclxuICAgICAgICAgICAgICAgICAgICAgICAgICAoY2xpY2spPVwib25Td2l0Y2hGb3JtYXREaXNwbGF5ZWQodHJ1ZSlcIlxyXG4gICAgICAgICAgICAgICAgICA+XHJcbiAgICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJpY29uIGlzLXNtYWxsXCI+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgIDxpIGNsYXNzPVwiZmEtc29saWQgZmEtYmFyc1wiPjwvaT5cclxuICAgICAgICAgICAgICAgICAgICA8L3NwYW4+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgIDwvZGl2PlxyXG4gICAgICA8L2Rpdj5cclxuICAgIDwvZGl2PlxyXG4gIDwvZGl2PlxyXG5cclxuXHJcbiAgICA8IS0tIEltYWdlcyBzZWN0aW9uIC0tPlxyXG4gIDxuZy1zY3JvbGxiYXJcclxuICAgIGNsYXNzPVwiaW1hZ2VzLXZpZXdfX3Njcm9sbFwiXHJcbiAgICBbbmdDbGFzc109XCJ7XHJcbiAgICAgICdpbWFnZXMtdmlld19fc2Nyb2xsLS1oaWRlLS1tb3NhaWMnOiB2bS5kaXNwbGF5UGV4ZWxzUmVzdWx0cyAmJiAhbGlzdERpc3BsYXllZCxcclxuICAgICAgJ2ltYWdlcy12aWV3X19zY3JvbGwtLWhpZGUtLXRhYmxlJzogdm0uZGlzcGxheVBleGVsc1Jlc3VsdHMgJiYgbGlzdERpc3BsYXllZCxcclxuICAgICAgJ2ltYWdlcy12aWV3X19zY3JvbGwtLWZ1bGwnOiBzdGF0ZURpc3BsYXllZCA9PT0gJ2Z1bGwnLFxyXG4gICAgICAnaW1hZ2VzLXZpZXdfX3Njcm9sbC0tc21hbGxEaXNwbGF5JyA6IHN0YXRlRGlzcGxheWVkID09PSAnc21hbGwnICYmIHRhYkRpc3BsYXllZCAhPT0gJ2ltZy11cGxvYWQnLFxyXG4gICAgICAnaW1hZ2VzLXZpZXdfX3Njcm9sbC0tc21hbGxVcGxvYWREaXNwbGF5JyA6IHN0YXRlRGlzcGxheWVkID09PSAnc21hbGwnICYmIHRhYkRpc3BsYXllZCA9PT0gJ2ltZy11cGxvYWQnLFxyXG4gICAgICAnaW1hZ2VzLXZpZXdfX3Njcm9sbC0td2luZG93Jzogc3RhdGVEaXNwbGF5ZWQgPT09ICd3aW5kb3cnXHJcbiAgfVwiXHJcbiAgPlxyXG4gICAgPGRpdiAjaW1nTGliQ29udGFpbmVyIGNsYXNzPVwiaW1hZ2VzLXZpZXdfX3dyYXBwZXJcIj5cclxuXHJcbiAgICAgICAgPGRpdiAqbmdJZj1cIiFsaXN0RGlzcGxheWVkIHx8IHN0YXRlRGlzcGxheWVkID09PSAnc21hbGwnXCIgW0BlYXNlSW5PdXRdPVwiJ2luJ1wiPlxyXG4gICAgICAgICAgPG1vc2FpYy12aWV3XHJcbiAgICAgICAgICAgIFtwaWN0dXJlc0xpc3RdPVwidm0ucGljdHVyZXNMaXN0XCJcclxuICAgICAgICAgICAgKHBpY3R1cmVzTGlzdENoYW5nZSk9XCJvblBpY3R1cmVzTGlzdENoYW5nZSh2bS5waWN0dXJlc0xpc3QpXCJcclxuICAgICAgICAgICAgW3RhYmxlRmlsdGVyc109XCJ2bS50YWJsZUZpbHRlcnNcIlxyXG4gICAgICAgICAgICAoZmlsdGVyc0NoYW5nZSk9XCJzZWFyY2hJbWFnZXNQYXJhbWV0ZXJzJC5uZXh0KGdldFBhcmFtcyh2bS50YWJsZUZpbHRlcnMpKTtcIlxyXG4gICAgICAgICAgICBbKGRpc2FibGUpXT1cImRpc2FibGVcIlxyXG4gICAgICAgICAgICAocGljdHVyZU5hbWVDaGFuZ2UpPVwib25SZW5hbWVQaWN0dXJlKCRldmVudClcIlxyXG4gICAgICAgICAgICAoc3dpdGNoRGlzcGxheVdpbmRvdyk9XCJzd2l0Y2hEaXNwbGF5V2luZG93TW9zYWljKClcIlxyXG4gICAgICAgICAgICBbbmJGYWtlSW1nXT1cIm5iRmFrZUltZ1wiXHJcbiAgICAgICAgICAgIFtzdGF0ZURpc3BsYXllZF09XCJzdGF0ZURpc3BsYXllZFwiXHJcbiAgICAgICAgICAgIFt0YWJEaXNwbGF5ZWRdPVwidGFiRGlzcGxheWVkXCJcclxuICAgICAgICAgICAgW2Rpc3BsYXlQZXhlbHNSZXN1bHRzXT1cInZtLmRpc3BsYXlQZXhlbHNSZXN1bHRzXCJcclxuICAgICAgICAgICAgW2lzTG9hZGluZ109XCJ2bS5pc0xvYWRpbmdcIlxyXG4gICAgICAgICAgICBbZnVsbFNpemVdPVwiZnVsbFNpemVcIlxyXG4gICAgICAgICAgPlxyXG4gICAgICAgICAgPC9tb3NhaWMtdmlldz5cclxuICAgICAgICA8L2Rpdj5cclxuXHJcbiAgICAgICAgPGRpdiAqbmdJZj1cImxpc3REaXNwbGF5ZWQgJiYgc3RhdGVEaXNwbGF5ZWQgIT09ICdzbWFsbCdcIiBbQGVhc2VJbk91dF09XCInaW4nXCI+XHJcbiAgICAgICAgICA8dGFibGUtdmlld1xyXG4gICAgICAgICAgICBbcGljdHVyZXNMaXN0XT1cInZtLnBpY3R1cmVzTGlzdFwiXHJcbiAgICAgICAgICAgIChwaWN0dXJlc0xpc3RDaGFuZ2UpPVwib25QaWN0dXJlc0xpc3RDaGFuZ2Uodm0ucGljdHVyZXNMaXN0KVwiXHJcbiAgICAgICAgICAgIFt0YWJsZUZpbHRlcnNdPVwidm0udGFibGVGaWx0ZXJzXCJcclxuICAgICAgICAgICAgKGZpbHRlcnNDaGFuZ2UpPVwic2VhcmNoSW1hZ2VzUGFyYW1ldGVycyQubmV4dChnZXRQYXJhbXModm0udGFibGVGaWx0ZXJzKSk7XCJcclxuICAgICAgICAgICAgWyhkaXNhYmxlKV09XCJkaXNhYmxlXCJcclxuICAgICAgICAgICAgKHBpY3R1cmVOYW1lQ2hhbmdlKT1cIm9uUmVuYW1lUGljdHVyZSgkZXZlbnQpXCJcclxuICAgICAgICAgICAgW2Rpc3BsYXlQZXhlbHNSZXN1bHRzXT1cInZtLmRpc3BsYXlQZXhlbHNSZXN1bHRzXCJcclxuICAgICAgICAgICAgW3N0YXRlRGlzcGxheWVkXT1cInN0YXRlRGlzcGxheWVkXCJcclxuICAgICAgICAgICAgW2lzTG9hZGluZ109XCJ2bS5pc0xvYWRpbmdcIlxyXG4gICAgICAgICAgICA+XHJcbiAgICAgICAgICA8L3RhYmxlLXZpZXc+XHJcbiAgICAgICAgPC9kaXY+XHJcbiAgICA8L2Rpdj5cclxuICA8L25nLXNjcm9sbGJhcj5cclxuXHJcbiAgPCEtLSBQZXhlbHMgU2VjdGlvbiAtIFdoZW4gbm8gaW1nIGZvdW5kIC0tPlxyXG4gIDxkaXZcclxuICAgICpuZ0lmPVwidm0uZGlzcGxheVBleGVsc1Jlc3VsdHNcIlxyXG4gICAgY2xhc3M9XCJpbWFnZXMtdmlldy0tcGV4ZWxzXCJcclxuICAgIFtAZWFzZUluT3V0XT1cIidpbidcIj5cclxuICAgIDxwZXhlbHMtbGliXHJcbiAgICAgIFtzZWFyY2hWYWx1ZV09XCJ2bS50YWJsZUZpbHRlcnMuc2VhcmNoVmFsdWVcIlxyXG4gICAgICBbZGlzYWJsZVNlYXJjaF09XCJ0cnVlXCJcclxuICAgID5cclxuICAgIDwvcGV4ZWxzLWxpYj5cclxuICA8L2Rpdj5cclxuPC9uZy1jb250YWluZXI+XHJcbiJdfQ==