@yelon/bis 16.2.5 → 16.3.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 (68) hide show
  1. package/LICENSE +21 -21
  2. package/README.md +23 -23
  3. package/esm2022/bis.mjs +4 -4
  4. package/esm2022/index.mjs +1 -1
  5. package/esm2022/layout/bis.config.mjs +14 -14
  6. package/esm2022/layout/html-names.mjs +32 -32
  7. package/esm2022/layout/icon/style-icons.mjs +795 -795
  8. package/esm2022/layout/layout-basic/index.mjs +2 -2
  9. package/esm2022/layout/layout-basic/interface.mjs +1 -1
  10. package/esm2022/layout/layout-basic/layout-basic.component.mjs +372 -372
  11. package/esm2022/layout/layout-nav/index.mjs +3 -3
  12. package/esm2022/layout/layout-nav/layout-nav-application.component.mjs +364 -364
  13. package/esm2022/layout/layout-nav/layout-nav-group.component.mjs +122 -122
  14. package/esm2022/layout/layout-nav/layout-nav-tile.component.mjs +14 -14
  15. package/esm2022/layout/layout.mjs +4 -4
  16. package/esm2022/layout/public_api.mjs +12 -12
  17. package/esm2022/layout/widgets/index.mjs +6 -6
  18. package/esm2022/layout/widgets/yunzai-clear-storage.component.mjs +44 -44
  19. package/esm2022/layout/widgets/yunzai-fullscreen.component.mjs +44 -44
  20. package/esm2022/layout/widgets/yunzai-i18n.component.mjs +145 -145
  21. package/esm2022/layout/widgets/yunzai-notify.component.mjs +182 -182
  22. package/esm2022/layout/widgets/yunzai-theme-btn.component.mjs +199 -199
  23. package/esm2022/layout/widgets/yunzai-user.component.mjs +129 -129
  24. package/esm2022/layout/yunzai-act.guard.mjs +106 -106
  25. package/esm2022/layout/yunzai-auth.service.mjs +107 -107
  26. package/esm2022/layout/yunzai-default.interceptor.mjs +200 -201
  27. package/esm2022/layout/yunzai-i18n.service.mjs +101 -101
  28. package/esm2022/layout/yunzai-lang.mjs +113 -113
  29. package/esm2022/layout/yunzai-layout.module.mjs +76 -76
  30. package/esm2022/layout/yunzai-startup.service.mjs +151 -151
  31. package/esm2022/public_api.mjs +1 -1
  32. package/fesm2022/bis.mjs +6 -6
  33. package/fesm2022/layout.mjs +3197 -3198
  34. package/fesm2022/layout.mjs.map +1 -1
  35. package/index.d.ts +1 -1
  36. package/index.less +1 -1
  37. package/layout/bis.config.d.ts +3 -3
  38. package/layout/html-names.d.ts +31 -31
  39. package/layout/icon/style-icons.d.ts +1 -1
  40. package/layout/index.d.ts +5 -5
  41. package/layout/layout-basic/index.d.ts +2 -2
  42. package/layout/layout-basic/interface.d.ts +8 -8
  43. package/layout/layout-basic/layout-basic.component.d.ts +28 -28
  44. package/layout/layout-nav/index.d.ts +3 -3
  45. package/layout/layout-nav/layout-nav-application.component.d.ts +31 -31
  46. package/layout/layout-nav/layout-nav-group.component.d.ts +16 -16
  47. package/layout/layout-nav/layout-nav-tile.component.d.ts +6 -6
  48. package/layout/public_api.d.ts +12 -12
  49. package/layout/style/index.less +154 -154
  50. package/layout/widgets/index.d.ts +6 -6
  51. package/layout/widgets/yunzai-clear-storage.component.d.ts +11 -11
  52. package/layout/widgets/yunzai-fullscreen.component.d.ts +8 -8
  53. package/layout/widgets/yunzai-i18n.component.d.ts +21 -21
  54. package/layout/widgets/yunzai-notify.component.d.ts +30 -30
  55. package/layout/widgets/yunzai-theme-btn.component.d.ts +32 -32
  56. package/layout/widgets/yunzai-user.component.d.ts +26 -26
  57. package/layout/yunzai-act.guard.d.ts +20 -20
  58. package/layout/yunzai-auth.service.d.ts +19 -19
  59. package/layout/yunzai-default.interceptor.d.ts +27 -27
  60. package/layout/yunzai-i18n.service.d.ts +26 -26
  61. package/layout/yunzai-lang.d.ts +11 -11
  62. package/layout/yunzai-layout.module.d.ts +22 -22
  63. package/layout/yunzai-startup.service.d.ts +34 -34
  64. package/package.json +39 -39
  65. package/public_api.d.ts +2 -2
  66. package/theme-compact.less +3 -3
  67. package/theme-dark.less +46 -46
  68. package/theme-default.less +46 -46
@@ -1,373 +1,373 @@
1
- import { Component, Inject } from '@angular/core';
2
- import { WINDOW, hasFavicon, log, setFavicon, NavType, useLocalStorageCurrent, useLocalStorageProjectInfo, useLocalStorageHeaderType, useLocalStorageDefaultRoute } from '@yelon/util';
3
- import * as i0 from "@angular/core";
4
- import * as i1 from "@yelon/theme/layout-default";
5
- import * as i2 from "@yelon/socket";
6
- import * as i3 from "@angular/common";
7
- import * as i4 from "@angular/router";
8
- import * as i5 from "@yelon/abc/reuse-tab";
9
- import * as i6 from "ng-zorro-antd/core/transition-patch";
10
- import * as i7 from "ng-zorro-antd/menu";
11
- import * as i8 from "ng-zorro-antd/dropdown";
12
- import * as i9 from "ng-zorro-antd/icon";
13
- import * as i10 from "ng-zorro-antd/avatar";
14
- import * as i11 from "../widgets/yunzai-clear-storage.component";
15
- import * as i12 from "../widgets/yunzai-fullscreen.component";
16
- import * as i13 from "../widgets/yunzai-i18n.component";
17
- import * as i14 from "../widgets/yunzai-notify.component";
18
- import * as i15 from "../widgets/yunzai-theme-btn.component";
19
- import * as i16 from "../widgets/yunzai-user.component";
20
- import * as i17 from "../layout-nav/layout-nav-application.component";
21
- import * as i18 from "../layout-nav/layout-nav-group.component";
22
- import * as i19 from "../layout-nav/layout-nav-tile.component";
23
- import * as i20 from "@yelon/theme";
24
- export class YunzaiLayoutBasicComponent {
25
- get options() {
26
- return this.state.options;
27
- }
28
- get navType() {
29
- return this.state.navType;
30
- }
31
- get aside() {
32
- return this.state.aside;
33
- }
34
- get displayReusetab() {
35
- return this.state.display.reusetab;
36
- }
37
- get reusetabCSS() {
38
- let cascadingStyleSheet = {};
39
- if (!this.state.display.nav) {
40
- cascadingStyleSheet = {
41
- ...cascadingStyleSheet,
42
- top: '0px'
43
- };
44
- }
45
- if (!this.state.display.aside) {
46
- cascadingStyleSheet = {
47
- ...cascadingStyleSheet,
48
- left: '24px'
49
- };
50
- }
51
- return cascadingStyleSheet;
52
- }
53
- constructor(layoutDisplayService, stompService, win) {
54
- this.layoutDisplayService = layoutDisplayService;
55
- this.stompService = stompService;
56
- this.win = win;
57
- this.NavType = NavType;
58
- this.state = {
59
- options: {
60
- logoExpanded: `./assets/logo-full.svg`,
61
- logoCollapsed: `./assets/logo.svg`
62
- },
63
- aside: {
64
- name: '',
65
- intro: '',
66
- icon: ''
67
- },
68
- display: {
69
- nav: true,
70
- aside: true,
71
- reusetab: true
72
- },
73
- navType: NavType.APPLICATION,
74
- };
75
- }
76
- ngOnInit() {
77
- this.initLogo();
78
- this.initFavicon();
79
- this.initNavType();
80
- this.initAside();
81
- this.addLayoutDisplayListener();
82
- this.stompService.listen();
83
- this.toIndex();
84
- }
85
- initFavicon() {
86
- const [, getProjectInfo] = useLocalStorageProjectInfo();
87
- const projectInfo = getProjectInfo();
88
- if (projectInfo.faviconUrl) {
89
- hasFavicon(projectInfo.faviconUrl).then((has) => {
90
- if (has) {
91
- setFavicon(projectInfo.faviconUrl);
92
- }
93
- else {
94
- setFavicon('./assets/favicon.ico');
95
- }
96
- });
97
- }
98
- }
99
- initAside() {
100
- const [, getCurrent] = useLocalStorageCurrent();
101
- const aside = getCurrent();
102
- this.state.aside = { ...aside };
103
- }
104
- initLogo() {
105
- const [, getProjectInfo] = useLocalStorageProjectInfo();
106
- const projectInfo = getProjectInfo();
107
- this.state.options.logoExpanded = projectInfo.maxLogoUrl ? projectInfo.maxLogoUrl : `./assets/logo-full.svg`;
108
- this.state.options.logoCollapsed = projectInfo.miniLogoUrl ? projectInfo.miniLogoUrl : `./assets/logo.svg`;
109
- }
110
- initNavType() {
111
- const [, getHeaderType] = useLocalStorageHeaderType();
112
- const [, getProjectInfo] = useLocalStorageProjectInfo();
113
- const navType = getHeaderType();
114
- const projectInfo = getProjectInfo();
115
- if (navType !== null) {
116
- this.state.navType = navType;
117
- return;
118
- }
119
- let fetchedNavType;
120
- if (projectInfo.headerStyle && projectInfo.headerStyle.length > 0) {
121
- fetchedNavType = projectInfo.headerStyle.pop()?.value;
122
- }
123
- // default value
124
- if (!fetchedNavType) {
125
- fetchedNavType = NavType.APPLICATION;
126
- }
127
- this.state.navType = fetchedNavType;
128
- }
129
- toIndex() {
130
- const [, getDefaultRoute] = useLocalStorageDefaultRoute();
131
- const defaultRoute = getDefaultRoute();
132
- log('YunzaiLayoutBasicComponent: ', `todo: the default route was ${defaultRoute}, 但是还没想好如何实现.`);
133
- }
134
- onNavTypeChange(type) {
135
- const [setHeaderType] = useLocalStorageHeaderType();
136
- setHeaderType(type);
137
- this.win.location.reload();
138
- }
139
- addLayoutDisplayListener() {
140
- this.layoutDisplayService.listen('reuseTab', (display) => {
141
- this.state.display.reusetab = display;
142
- });
143
- this.layoutDisplayService.listen('nav', (display) => {
144
- this.state.display.nav = display;
145
- });
146
- this.layoutDisplayService.listen('aside', (display) => {
147
- this.state.display.aside = display;
148
- });
149
- }
150
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.1", ngImport: i0, type: YunzaiLayoutBasicComponent, deps: [{ token: i1.LayoutDisplayService }, { token: i2.StompService }, { token: WINDOW }], target: i0.ɵɵFactoryTarget.Component }); }
151
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "16.2.1", type: YunzaiLayoutBasicComponent, selector: "yz-layout-basic", ngImport: i0, template: `
152
- <layout-default [options]="options" [asideUser]="asideUserTpl" [content]="displayReusetab ? contentTpl : noneTpl">
153
- <!-- nav -->
154
- <layout-default-header-item direction="left">
155
- <ng-container [ngSwitch]="navType">
156
- <ng-container *ngSwitchCase="NavType.APPLICATION">
157
- <layout-nav-application></layout-nav-application>
158
- </ng-container>
159
- <ng-container *ngSwitchCase="NavType.GROUP">
160
- <layout-nav-group></layout-nav-group>
161
- </ng-container>
162
- <ng-container *ngSwitchCase="NavType.TILE">
163
- <layout-nav-tile></layout-nav-tile>
164
- </ng-container>
165
- <ng-container *ngSwitchDefault>
166
- <layout-nav-application></layout-nav-application>
167
- </ng-container>
168
- </ng-container>
169
- </layout-default-header-item>
170
- <!-- nav end -->
171
- <layout-default-header-item direction="right" hidden="mobile">
172
- <yunzai-notify></yunzai-notify>
173
- </layout-default-header-item>
174
- <layout-default-header-item direction="right" hidden="mobile">
175
- <yunzai-theme-btn></yunzai-theme-btn>
176
- </layout-default-header-item>
177
- <!-- setting -->
178
- <layout-default-header-item direction="right" hidden="mobile">
179
- <div
180
- data-event-id="_nav_settings"
181
- layout-default-header-item-trigger
182
- nz-dropdown
183
- [nzDropdownMenu]="settingsMenu"
184
- nzTrigger="click"
185
- nzPlacement="bottomRight"
186
- >
187
- <i nz-icon nzType="setting"></i>
188
- </div>
189
- <nz-dropdown-menu #settingsMenu="nzDropdownMenu">
190
- <div nz-menu style="width: 200px;">
191
- <div data-event-id="_nav_mode" nz-menu-item>
192
- {{ 'mode.nav' | i18n }}
193
- </div>
194
-
195
- <div
196
- data-event-id="_nav_mode"
197
- data-type="application"
198
- nz-menu-item
199
- (click)="onNavTypeChange(NavType.APPLICATION)"
200
- >
201
- <i nz-icon nzType="appstore" class="mr-sm"></i>
202
- {{ 'mode.nav.application' | i18n }}
203
- </div>
204
- <div data-event-id="_nav_mode" data-type="group" nz-menu-item (click)="onNavTypeChange(NavType.GROUP)">
205
- <i nz-icon nzType="group" class="mr-sm"></i>
206
- {{ 'mode.nav.group' | i18n }}
207
- </div>
208
- <div data-event-id="_nav_mode" data-type="tile" nz-menu-item (click)="onNavTypeChange(NavType.TILE)">
209
- <i nz-icon nzType="appstore" class="mr-sm"></i>
210
- {{ 'mode.nav.tile' | i18n }}
211
- </div>
212
- <div data-event-id="_nav_fullscreen" nz-menu-item>
213
- <yunzai-fullscreen></yunzai-fullscreen>
214
- </div>
215
- <div data-event-id="_nav_clearstorage" nz-menu-item>
216
- <yunzai-clearstorage></yunzai-clearstorage>
217
- </div>
218
- <div data-event-id="_nav_i18n" nz-menu-item>
219
- <yunzai-i18n></yunzai-i18n>
220
- </div>
221
- </div>
222
- </nz-dropdown-menu>
223
- </layout-default-header-item>
224
- <layout-default-header-item direction="right">
225
- <yunzai-user></yunzai-user>
226
- </layout-default-header-item>
227
- <!-- setting end -->
228
- </layout-default>
229
- <ng-template #asideUserTpl>
230
- <div
231
- data-event-id="_route_user"
232
- nz-dropdown
233
- nzTrigger="click"
234
- [nzDropdownMenu]="userMenu"
235
- class="yunzai-default__aside-user"
236
- >
237
- <nz-avatar class="yunzai-default__aside-user-avatar" [nzSrc]="aside.icon"></nz-avatar>
238
- <div class="yunzai-default__aside-user-info">
239
- <strong>{{ aside.name | i18n }}</strong>
240
- <p class="mb0">{{ aside.intro | i18n }}</p>
241
- </div>
242
- </div>
243
- <nz-dropdown-menu #userMenu="nzDropdownMenu">
244
- <ul nz-menu>
245
- <li data-event-id="_route_backhome" nz-menu-item routerLink="/">{{ 'back.home' | i18n }}</li>
246
- </ul>
247
- </nz-dropdown-menu>
248
- </ng-template>
249
- <ng-template #contentTpl>
250
- <reuse-tab #reuseTab [ngStyle]="reusetabCSS"></reuse-tab>
251
- <router-outlet (activate)="reuseTab.activate($event)" (attach)="reuseTab.activate($event)"></router-outlet>
252
- </ng-template>
253
- <ng-template #noneTpl>
254
- <router-outlet></router-outlet>
255
- </ng-template>
256
- `, isInline: true, dependencies: [{ kind: "directive", type: i3.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "directive", type: i3.NgSwitch, selector: "[ngSwitch]", inputs: ["ngSwitch"] }, { kind: "directive", type: i3.NgSwitchCase, selector: "[ngSwitchCase]", inputs: ["ngSwitchCase"] }, { kind: "directive", type: i3.NgSwitchDefault, selector: "[ngSwitchDefault]" }, { kind: "directive", type: i4.RouterOutlet, selector: "router-outlet", inputs: ["name"], outputs: ["activate", "deactivate", "attach", "detach"], exportAs: ["outlet"] }, { kind: "directive", type: i4.RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "component", type: i5.ReuseTabComponent, selector: "reuse-tab, [reuse-tab]", inputs: ["mode", "i18n", "debug", "max", "tabMaxWidth", "excludes", "allowClose", "keepingScroll", "storageState", "keepingScrollContainer", "customContextMenu", "tabBarExtraContent", "tabBarGutter", "tabBarStyle", "tabType", "routeParamMatchMode", "disabled", "titleRender", "canClose"], outputs: ["change", "close"], exportAs: ["reuseTab"] }, { kind: "component", type: i1.LayoutDefaultComponent, selector: "layout-default", inputs: ["options", "asideUser", "asideBottom", "nav", "content", "customError", "fetchingStrictly", "fetching"], exportAs: ["layoutDefault"] }, { kind: "component", type: i1.LayoutDefaultHeaderItemComponent, selector: "layout-default-header-item", inputs: ["hidden", "direction"] }, { kind: "directive", type: i1.LayoutDefaultHeaderItemTriggerDirective, selector: "[layout-default-header-item-trigger]" }, { kind: "directive", type: i6.ɵNzTransitionPatchDirective, selector: "[nz-button], nz-button-group, [nz-icon], [nz-menu-item], [nz-submenu], nz-select-top-control, nz-select-placeholder, nz-input-group", inputs: ["hidden"] }, { kind: "directive", type: i7.NzMenuDirective, selector: "[nz-menu]", inputs: ["nzInlineIndent", "nzTheme", "nzMode", "nzInlineCollapsed", "nzSelectable"], outputs: ["nzClick"], exportAs: ["nzMenu"] }, { kind: "directive", type: i7.NzMenuItemDirective, selector: "[nz-menu-item]", inputs: ["nzPaddingLeft", "nzDisabled", "nzSelected", "nzDanger", "nzMatchRouterExact", "nzMatchRouter"], exportAs: ["nzMenuItem"] }, { kind: "directive", type: i8.NzDropDownDirective, selector: "[nz-dropdown]", inputs: ["nzDropdownMenu", "nzTrigger", "nzMatchWidthElement", "nzBackdrop", "nzClickHide", "nzDisabled", "nzVisible", "nzOverlayClassName", "nzOverlayStyle", "nzPlacement"], outputs: ["nzVisibleChange"], exportAs: ["nzDropdown"] }, { kind: "component", type: i8.NzDropdownMenuComponent, selector: "nz-dropdown-menu", exportAs: ["nzDropdownMenu"] }, { kind: "directive", type: i9.NzIconDirective, selector: "[nz-icon]", inputs: ["nzSpin", "nzRotate", "nzType", "nzTheme", "nzTwotoneColor", "nzIconfont"], exportAs: ["nzIcon"] }, { kind: "component", type: i10.NzAvatarComponent, selector: "nz-avatar", inputs: ["nzShape", "nzSize", "nzGap", "nzText", "nzSrc", "nzSrcSet", "nzAlt", "nzIcon"], outputs: ["nzError"], exportAs: ["nzAvatar"] }, { kind: "component", type: i11.YunzaiClearStorageComponent, selector: "yunzai-clearstorage" }, { kind: "component", type: i12.YunzaiFullScreenComponent, selector: "yunzai-fullscreen" }, { kind: "component", type: i13.YunzaiI18NComponent, selector: "yunzai-i18n", inputs: ["showLangText"] }, { kind: "component", type: i14.YunzaiNotifyComponent, selector: "yunzai-notify" }, { kind: "component", type: i15.YunzaiThemBtnComponent, selector: "yunzai-theme-btn", inputs: ["types", "devTips", "deployUrl"] }, { kind: "component", type: i16.YunzaiUserComponent, selector: "yunzai-user" }, { kind: "component", type: i17.LayoutNavApplicationComponent, selector: "layout-nav-application" }, { kind: "component", type: i18.LayoutNavGroupComponent, selector: "layout-nav-group" }, { kind: "component", type: i19.LayoutNavTileComponent, selector: "layout-nav-tile" }, { kind: "pipe", type: i20.I18nPipe, name: "i18n" }] }); }
257
- }
258
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.1", ngImport: i0, type: YunzaiLayoutBasicComponent, decorators: [{
259
- type: Component,
260
- args: [{
261
- selector: `yz-layout-basic`,
262
- template: `
263
- <layout-default [options]="options" [asideUser]="asideUserTpl" [content]="displayReusetab ? contentTpl : noneTpl">
264
- <!-- nav -->
265
- <layout-default-header-item direction="left">
266
- <ng-container [ngSwitch]="navType">
267
- <ng-container *ngSwitchCase="NavType.APPLICATION">
268
- <layout-nav-application></layout-nav-application>
269
- </ng-container>
270
- <ng-container *ngSwitchCase="NavType.GROUP">
271
- <layout-nav-group></layout-nav-group>
272
- </ng-container>
273
- <ng-container *ngSwitchCase="NavType.TILE">
274
- <layout-nav-tile></layout-nav-tile>
275
- </ng-container>
276
- <ng-container *ngSwitchDefault>
277
- <layout-nav-application></layout-nav-application>
278
- </ng-container>
279
- </ng-container>
280
- </layout-default-header-item>
281
- <!-- nav end -->
282
- <layout-default-header-item direction="right" hidden="mobile">
283
- <yunzai-notify></yunzai-notify>
284
- </layout-default-header-item>
285
- <layout-default-header-item direction="right" hidden="mobile">
286
- <yunzai-theme-btn></yunzai-theme-btn>
287
- </layout-default-header-item>
288
- <!-- setting -->
289
- <layout-default-header-item direction="right" hidden="mobile">
290
- <div
291
- data-event-id="_nav_settings"
292
- layout-default-header-item-trigger
293
- nz-dropdown
294
- [nzDropdownMenu]="settingsMenu"
295
- nzTrigger="click"
296
- nzPlacement="bottomRight"
297
- >
298
- <i nz-icon nzType="setting"></i>
299
- </div>
300
- <nz-dropdown-menu #settingsMenu="nzDropdownMenu">
301
- <div nz-menu style="width: 200px;">
302
- <div data-event-id="_nav_mode" nz-menu-item>
303
- {{ 'mode.nav' | i18n }}
304
- </div>
305
-
306
- <div
307
- data-event-id="_nav_mode"
308
- data-type="application"
309
- nz-menu-item
310
- (click)="onNavTypeChange(NavType.APPLICATION)"
311
- >
312
- <i nz-icon nzType="appstore" class="mr-sm"></i>
313
- {{ 'mode.nav.application' | i18n }}
314
- </div>
315
- <div data-event-id="_nav_mode" data-type="group" nz-menu-item (click)="onNavTypeChange(NavType.GROUP)">
316
- <i nz-icon nzType="group" class="mr-sm"></i>
317
- {{ 'mode.nav.group' | i18n }}
318
- </div>
319
- <div data-event-id="_nav_mode" data-type="tile" nz-menu-item (click)="onNavTypeChange(NavType.TILE)">
320
- <i nz-icon nzType="appstore" class="mr-sm"></i>
321
- {{ 'mode.nav.tile' | i18n }}
322
- </div>
323
- <div data-event-id="_nav_fullscreen" nz-menu-item>
324
- <yunzai-fullscreen></yunzai-fullscreen>
325
- </div>
326
- <div data-event-id="_nav_clearstorage" nz-menu-item>
327
- <yunzai-clearstorage></yunzai-clearstorage>
328
- </div>
329
- <div data-event-id="_nav_i18n" nz-menu-item>
330
- <yunzai-i18n></yunzai-i18n>
331
- </div>
332
- </div>
333
- </nz-dropdown-menu>
334
- </layout-default-header-item>
335
- <layout-default-header-item direction="right">
336
- <yunzai-user></yunzai-user>
337
- </layout-default-header-item>
338
- <!-- setting end -->
339
- </layout-default>
340
- <ng-template #asideUserTpl>
341
- <div
342
- data-event-id="_route_user"
343
- nz-dropdown
344
- nzTrigger="click"
345
- [nzDropdownMenu]="userMenu"
346
- class="yunzai-default__aside-user"
347
- >
348
- <nz-avatar class="yunzai-default__aside-user-avatar" [nzSrc]="aside.icon"></nz-avatar>
349
- <div class="yunzai-default__aside-user-info">
350
- <strong>{{ aside.name | i18n }}</strong>
351
- <p class="mb0">{{ aside.intro | i18n }}</p>
352
- </div>
353
- </div>
354
- <nz-dropdown-menu #userMenu="nzDropdownMenu">
355
- <ul nz-menu>
356
- <li data-event-id="_route_backhome" nz-menu-item routerLink="/">{{ 'back.home' | i18n }}</li>
357
- </ul>
358
- </nz-dropdown-menu>
359
- </ng-template>
360
- <ng-template #contentTpl>
361
- <reuse-tab #reuseTab [ngStyle]="reusetabCSS"></reuse-tab>
362
- <router-outlet (activate)="reuseTab.activate($event)" (attach)="reuseTab.activate($event)"></router-outlet>
363
- </ng-template>
364
- <ng-template #noneTpl>
365
- <router-outlet></router-outlet>
366
- </ng-template>
367
- `
368
- }]
369
- }], ctorParameters: function () { return [{ type: i1.LayoutDisplayService }, { type: i2.StompService }, { type: undefined, decorators: [{
370
- type: Inject,
371
- args: [WINDOW]
372
- }] }]; } });
1
+ import { Component, Inject } from '@angular/core';
2
+ import { WINDOW, hasFavicon, log, setFavicon, NavType, useLocalStorageCurrent, useLocalStorageProjectInfo, useLocalStorageHeaderType, useLocalStorageDefaultRoute } from '@yelon/util';
3
+ import * as i0 from "@angular/core";
4
+ import * as i1 from "@yelon/theme/layout-default";
5
+ import * as i2 from "@yelon/socket";
6
+ import * as i3 from "@angular/common";
7
+ import * as i4 from "@angular/router";
8
+ import * as i5 from "@yelon/abc/reuse-tab";
9
+ import * as i6 from "ng-zorro-antd/core/transition-patch";
10
+ import * as i7 from "ng-zorro-antd/menu";
11
+ import * as i8 from "ng-zorro-antd/dropdown";
12
+ import * as i9 from "ng-zorro-antd/icon";
13
+ import * as i10 from "ng-zorro-antd/avatar";
14
+ import * as i11 from "../widgets/yunzai-clear-storage.component";
15
+ import * as i12 from "../widgets/yunzai-fullscreen.component";
16
+ import * as i13 from "../widgets/yunzai-i18n.component";
17
+ import * as i14 from "../widgets/yunzai-notify.component";
18
+ import * as i15 from "../widgets/yunzai-theme-btn.component";
19
+ import * as i16 from "../widgets/yunzai-user.component";
20
+ import * as i17 from "../layout-nav/layout-nav-application.component";
21
+ import * as i18 from "../layout-nav/layout-nav-group.component";
22
+ import * as i19 from "../layout-nav/layout-nav-tile.component";
23
+ import * as i20 from "@yelon/theme";
24
+ export class YunzaiLayoutBasicComponent {
25
+ get options() {
26
+ return this.state.options;
27
+ }
28
+ get navType() {
29
+ return this.state.navType;
30
+ }
31
+ get aside() {
32
+ return this.state.aside;
33
+ }
34
+ get displayReusetab() {
35
+ return this.state.display.reusetab;
36
+ }
37
+ get reusetabCSS() {
38
+ let cascadingStyleSheet = {};
39
+ if (!this.state.display.nav) {
40
+ cascadingStyleSheet = {
41
+ ...cascadingStyleSheet,
42
+ top: '0px'
43
+ };
44
+ }
45
+ if (!this.state.display.aside) {
46
+ cascadingStyleSheet = {
47
+ ...cascadingStyleSheet,
48
+ left: '24px'
49
+ };
50
+ }
51
+ return cascadingStyleSheet;
52
+ }
53
+ constructor(layoutDisplayService, stompService, win) {
54
+ this.layoutDisplayService = layoutDisplayService;
55
+ this.stompService = stompService;
56
+ this.win = win;
57
+ this.NavType = NavType;
58
+ this.state = {
59
+ options: {
60
+ logoExpanded: `./assets/logo-full.svg`,
61
+ logoCollapsed: `./assets/logo.svg`
62
+ },
63
+ aside: {
64
+ name: '',
65
+ intro: '',
66
+ icon: ''
67
+ },
68
+ display: {
69
+ nav: true,
70
+ aside: true,
71
+ reusetab: true
72
+ },
73
+ navType: NavType.APPLICATION,
74
+ };
75
+ }
76
+ ngOnInit() {
77
+ this.initLogo();
78
+ this.initFavicon();
79
+ this.initNavType();
80
+ this.initAside();
81
+ this.addLayoutDisplayListener();
82
+ this.stompService.listen();
83
+ this.toIndex();
84
+ }
85
+ initFavicon() {
86
+ const [, getProjectInfo] = useLocalStorageProjectInfo();
87
+ const projectInfo = getProjectInfo();
88
+ if (projectInfo.faviconUrl) {
89
+ hasFavicon(projectInfo.faviconUrl).then((has) => {
90
+ if (has) {
91
+ setFavicon(projectInfo.faviconUrl);
92
+ }
93
+ else {
94
+ setFavicon('./assets/favicon.ico');
95
+ }
96
+ });
97
+ }
98
+ }
99
+ initAside() {
100
+ const [, getCurrent] = useLocalStorageCurrent();
101
+ const aside = getCurrent();
102
+ this.state.aside = { ...aside };
103
+ }
104
+ initLogo() {
105
+ const [, getProjectInfo] = useLocalStorageProjectInfo();
106
+ const projectInfo = getProjectInfo();
107
+ this.state.options.logoExpanded = projectInfo.maxLogoUrl ? projectInfo.maxLogoUrl : `./assets/logo-full.svg`;
108
+ this.state.options.logoCollapsed = projectInfo.miniLogoUrl ? projectInfo.miniLogoUrl : `./assets/logo.svg`;
109
+ }
110
+ initNavType() {
111
+ const [, getHeaderType] = useLocalStorageHeaderType();
112
+ const [, getProjectInfo] = useLocalStorageProjectInfo();
113
+ const navType = getHeaderType();
114
+ const projectInfo = getProjectInfo();
115
+ if (navType !== null) {
116
+ this.state.navType = navType;
117
+ return;
118
+ }
119
+ let fetchedNavType;
120
+ if (projectInfo.headerStyle && projectInfo.headerStyle.length > 0) {
121
+ fetchedNavType = projectInfo.headerStyle.pop()?.value;
122
+ }
123
+ // default value
124
+ if (!fetchedNavType) {
125
+ fetchedNavType = NavType.APPLICATION;
126
+ }
127
+ this.state.navType = fetchedNavType;
128
+ }
129
+ toIndex() {
130
+ const [, getDefaultRoute] = useLocalStorageDefaultRoute();
131
+ const defaultRoute = getDefaultRoute();
132
+ log('YunzaiLayoutBasicComponent: ', `todo: the default route was ${defaultRoute}, 但是还没想好如何实现.`);
133
+ }
134
+ onNavTypeChange(type) {
135
+ const [setHeaderType] = useLocalStorageHeaderType();
136
+ setHeaderType(type);
137
+ this.win.location.reload();
138
+ }
139
+ addLayoutDisplayListener() {
140
+ this.layoutDisplayService.listen('reuseTab', (display) => {
141
+ this.state.display.reusetab = display;
142
+ });
143
+ this.layoutDisplayService.listen('nav', (display) => {
144
+ this.state.display.nav = display;
145
+ });
146
+ this.layoutDisplayService.listen('aside', (display) => {
147
+ this.state.display.aside = display;
148
+ });
149
+ }
150
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.7", ngImport: i0, type: YunzaiLayoutBasicComponent, deps: [{ token: i1.LayoutDisplayService }, { token: i2.StompService }, { token: WINDOW }], target: i0.ɵɵFactoryTarget.Component }); }
151
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "16.2.7", type: YunzaiLayoutBasicComponent, selector: "yz-layout-basic", ngImport: i0, template: `
152
+ <layout-default [options]="options" [asideUser]="asideUserTpl" [content]="displayReusetab ? contentTpl : noneTpl">
153
+ <!-- nav -->
154
+ <layout-default-header-item direction="left">
155
+ <ng-container [ngSwitch]="navType">
156
+ <ng-container *ngSwitchCase="NavType.APPLICATION">
157
+ <layout-nav-application></layout-nav-application>
158
+ </ng-container>
159
+ <ng-container *ngSwitchCase="NavType.GROUP">
160
+ <layout-nav-group></layout-nav-group>
161
+ </ng-container>
162
+ <ng-container *ngSwitchCase="NavType.TILE">
163
+ <layout-nav-tile></layout-nav-tile>
164
+ </ng-container>
165
+ <ng-container *ngSwitchDefault>
166
+ <layout-nav-application></layout-nav-application>
167
+ </ng-container>
168
+ </ng-container>
169
+ </layout-default-header-item>
170
+ <!-- nav end -->
171
+ <layout-default-header-item direction="right" hidden="mobile">
172
+ <yunzai-notify></yunzai-notify>
173
+ </layout-default-header-item>
174
+ <layout-default-header-item direction="right" hidden="mobile">
175
+ <yunzai-theme-btn></yunzai-theme-btn>
176
+ </layout-default-header-item>
177
+ <!-- setting -->
178
+ <layout-default-header-item direction="right" hidden="mobile">
179
+ <div
180
+ data-event-id="_nav_settings"
181
+ layout-default-header-item-trigger
182
+ nz-dropdown
183
+ [nzDropdownMenu]="settingsMenu"
184
+ nzTrigger="click"
185
+ nzPlacement="bottomRight"
186
+ >
187
+ <i nz-icon nzType="setting"></i>
188
+ </div>
189
+ <nz-dropdown-menu #settingsMenu="nzDropdownMenu">
190
+ <div nz-menu style="width: 200px;">
191
+ <div data-event-id="_nav_mode" nz-menu-item>
192
+ {{ 'mode.nav' | i18n }}
193
+ </div>
194
+
195
+ <div
196
+ data-event-id="_nav_mode"
197
+ data-type="application"
198
+ nz-menu-item
199
+ (click)="onNavTypeChange(NavType.APPLICATION)"
200
+ >
201
+ <i nz-icon nzType="appstore" class="mr-sm"></i>
202
+ {{ 'mode.nav.application' | i18n }}
203
+ </div>
204
+ <div data-event-id="_nav_mode" data-type="group" nz-menu-item (click)="onNavTypeChange(NavType.GROUP)">
205
+ <i nz-icon nzType="group" class="mr-sm"></i>
206
+ {{ 'mode.nav.group' | i18n }}
207
+ </div>
208
+ <div data-event-id="_nav_mode" data-type="tile" nz-menu-item (click)="onNavTypeChange(NavType.TILE)">
209
+ <i nz-icon nzType="appstore" class="mr-sm"></i>
210
+ {{ 'mode.nav.tile' | i18n }}
211
+ </div>
212
+ <div data-event-id="_nav_fullscreen" nz-menu-item>
213
+ <yunzai-fullscreen></yunzai-fullscreen>
214
+ </div>
215
+ <div data-event-id="_nav_clearstorage" nz-menu-item>
216
+ <yunzai-clearstorage></yunzai-clearstorage>
217
+ </div>
218
+ <div data-event-id="_nav_i18n" nz-menu-item>
219
+ <yunzai-i18n></yunzai-i18n>
220
+ </div>
221
+ </div>
222
+ </nz-dropdown-menu>
223
+ </layout-default-header-item>
224
+ <layout-default-header-item direction="right">
225
+ <yunzai-user></yunzai-user>
226
+ </layout-default-header-item>
227
+ <!-- setting end -->
228
+ </layout-default>
229
+ <ng-template #asideUserTpl>
230
+ <div
231
+ data-event-id="_route_user"
232
+ nz-dropdown
233
+ nzTrigger="click"
234
+ [nzDropdownMenu]="userMenu"
235
+ class="yunzai-default__aside-user"
236
+ >
237
+ <nz-avatar class="yunzai-default__aside-user-avatar" [nzSrc]="aside.icon"></nz-avatar>
238
+ <div class="yunzai-default__aside-user-info">
239
+ <strong>{{ aside.name | i18n }}</strong>
240
+ <p class="mb0">{{ aside.intro | i18n }}</p>
241
+ </div>
242
+ </div>
243
+ <nz-dropdown-menu #userMenu="nzDropdownMenu">
244
+ <ul nz-menu>
245
+ <li data-event-id="_route_backhome" nz-menu-item routerLink="/">{{ 'back.home' | i18n }}</li>
246
+ </ul>
247
+ </nz-dropdown-menu>
248
+ </ng-template>
249
+ <ng-template #contentTpl>
250
+ <reuse-tab #reuseTab [ngStyle]="reusetabCSS"></reuse-tab>
251
+ <router-outlet (activate)="reuseTab.activate($event)" (attach)="reuseTab.activate($event)"></router-outlet>
252
+ </ng-template>
253
+ <ng-template #noneTpl>
254
+ <router-outlet></router-outlet>
255
+ </ng-template>
256
+ `, isInline: true, dependencies: [{ kind: "directive", type: i3.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "directive", type: i3.NgSwitch, selector: "[ngSwitch]", inputs: ["ngSwitch"] }, { kind: "directive", type: i3.NgSwitchCase, selector: "[ngSwitchCase]", inputs: ["ngSwitchCase"] }, { kind: "directive", type: i3.NgSwitchDefault, selector: "[ngSwitchDefault]" }, { kind: "directive", type: i4.RouterOutlet, selector: "router-outlet", inputs: ["name"], outputs: ["activate", "deactivate", "attach", "detach"], exportAs: ["outlet"] }, { kind: "directive", type: i4.RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "component", type: i5.ReuseTabComponent, selector: "reuse-tab, [reuse-tab]", inputs: ["mode", "i18n", "debug", "max", "tabMaxWidth", "excludes", "allowClose", "keepingScroll", "storageState", "keepingScrollContainer", "customContextMenu", "tabBarExtraContent", "tabBarGutter", "tabBarStyle", "tabType", "routeParamMatchMode", "disabled", "titleRender", "canClose"], outputs: ["change", "close"], exportAs: ["reuseTab"] }, { kind: "component", type: i1.LayoutDefaultComponent, selector: "layout-default", inputs: ["options", "asideUser", "asideBottom", "nav", "content", "customError", "fetchingStrictly", "fetching"], exportAs: ["layoutDefault"] }, { kind: "component", type: i1.LayoutDefaultHeaderItemComponent, selector: "layout-default-header-item", inputs: ["hidden", "direction"] }, { kind: "directive", type: i1.LayoutDefaultHeaderItemTriggerDirective, selector: "[layout-default-header-item-trigger]" }, { kind: "directive", type: i6.ɵNzTransitionPatchDirective, selector: "[nz-button], nz-button-group, [nz-icon], [nz-menu-item], [nz-submenu], nz-select-top-control, nz-select-placeholder, nz-input-group", inputs: ["hidden"] }, { kind: "directive", type: i7.NzMenuDirective, selector: "[nz-menu]", inputs: ["nzInlineIndent", "nzTheme", "nzMode", "nzInlineCollapsed", "nzSelectable"], outputs: ["nzClick"], exportAs: ["nzMenu"] }, { kind: "directive", type: i7.NzMenuItemDirective, selector: "[nz-menu-item]", inputs: ["nzPaddingLeft", "nzDisabled", "nzSelected", "nzDanger", "nzMatchRouterExact", "nzMatchRouter"], exportAs: ["nzMenuItem"] }, { kind: "directive", type: i8.NzDropDownDirective, selector: "[nz-dropdown]", inputs: ["nzDropdownMenu", "nzTrigger", "nzMatchWidthElement", "nzBackdrop", "nzClickHide", "nzDisabled", "nzVisible", "nzOverlayClassName", "nzOverlayStyle", "nzPlacement"], outputs: ["nzVisibleChange"], exportAs: ["nzDropdown"] }, { kind: "component", type: i8.NzDropdownMenuComponent, selector: "nz-dropdown-menu", exportAs: ["nzDropdownMenu"] }, { kind: "directive", type: i9.NzIconDirective, selector: "[nz-icon]", inputs: ["nzSpin", "nzRotate", "nzType", "nzTheme", "nzTwotoneColor", "nzIconfont"], exportAs: ["nzIcon"] }, { kind: "component", type: i10.NzAvatarComponent, selector: "nz-avatar", inputs: ["nzShape", "nzSize", "nzGap", "nzText", "nzSrc", "nzSrcSet", "nzAlt", "nzIcon"], outputs: ["nzError"], exportAs: ["nzAvatar"] }, { kind: "component", type: i11.YunzaiClearStorageComponent, selector: "yunzai-clearstorage" }, { kind: "component", type: i12.YunzaiFullScreenComponent, selector: "yunzai-fullscreen" }, { kind: "component", type: i13.YunzaiI18NComponent, selector: "yunzai-i18n", inputs: ["showLangText"] }, { kind: "component", type: i14.YunzaiNotifyComponent, selector: "yunzai-notify" }, { kind: "component", type: i15.YunzaiThemBtnComponent, selector: "yunzai-theme-btn", inputs: ["types", "devTips", "deployUrl"] }, { kind: "component", type: i16.YunzaiUserComponent, selector: "yunzai-user" }, { kind: "component", type: i17.LayoutNavApplicationComponent, selector: "layout-nav-application" }, { kind: "component", type: i18.LayoutNavGroupComponent, selector: "layout-nav-group" }, { kind: "component", type: i19.LayoutNavTileComponent, selector: "layout-nav-tile" }, { kind: "pipe", type: i20.I18nPipe, name: "i18n" }] }); }
257
+ }
258
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.7", ngImport: i0, type: YunzaiLayoutBasicComponent, decorators: [{
259
+ type: Component,
260
+ args: [{
261
+ selector: `yz-layout-basic`,
262
+ template: `
263
+ <layout-default [options]="options" [asideUser]="asideUserTpl" [content]="displayReusetab ? contentTpl : noneTpl">
264
+ <!-- nav -->
265
+ <layout-default-header-item direction="left">
266
+ <ng-container [ngSwitch]="navType">
267
+ <ng-container *ngSwitchCase="NavType.APPLICATION">
268
+ <layout-nav-application></layout-nav-application>
269
+ </ng-container>
270
+ <ng-container *ngSwitchCase="NavType.GROUP">
271
+ <layout-nav-group></layout-nav-group>
272
+ </ng-container>
273
+ <ng-container *ngSwitchCase="NavType.TILE">
274
+ <layout-nav-tile></layout-nav-tile>
275
+ </ng-container>
276
+ <ng-container *ngSwitchDefault>
277
+ <layout-nav-application></layout-nav-application>
278
+ </ng-container>
279
+ </ng-container>
280
+ </layout-default-header-item>
281
+ <!-- nav end -->
282
+ <layout-default-header-item direction="right" hidden="mobile">
283
+ <yunzai-notify></yunzai-notify>
284
+ </layout-default-header-item>
285
+ <layout-default-header-item direction="right" hidden="mobile">
286
+ <yunzai-theme-btn></yunzai-theme-btn>
287
+ </layout-default-header-item>
288
+ <!-- setting -->
289
+ <layout-default-header-item direction="right" hidden="mobile">
290
+ <div
291
+ data-event-id="_nav_settings"
292
+ layout-default-header-item-trigger
293
+ nz-dropdown
294
+ [nzDropdownMenu]="settingsMenu"
295
+ nzTrigger="click"
296
+ nzPlacement="bottomRight"
297
+ >
298
+ <i nz-icon nzType="setting"></i>
299
+ </div>
300
+ <nz-dropdown-menu #settingsMenu="nzDropdownMenu">
301
+ <div nz-menu style="width: 200px;">
302
+ <div data-event-id="_nav_mode" nz-menu-item>
303
+ {{ 'mode.nav' | i18n }}
304
+ </div>
305
+
306
+ <div
307
+ data-event-id="_nav_mode"
308
+ data-type="application"
309
+ nz-menu-item
310
+ (click)="onNavTypeChange(NavType.APPLICATION)"
311
+ >
312
+ <i nz-icon nzType="appstore" class="mr-sm"></i>
313
+ {{ 'mode.nav.application' | i18n }}
314
+ </div>
315
+ <div data-event-id="_nav_mode" data-type="group" nz-menu-item (click)="onNavTypeChange(NavType.GROUP)">
316
+ <i nz-icon nzType="group" class="mr-sm"></i>
317
+ {{ 'mode.nav.group' | i18n }}
318
+ </div>
319
+ <div data-event-id="_nav_mode" data-type="tile" nz-menu-item (click)="onNavTypeChange(NavType.TILE)">
320
+ <i nz-icon nzType="appstore" class="mr-sm"></i>
321
+ {{ 'mode.nav.tile' | i18n }}
322
+ </div>
323
+ <div data-event-id="_nav_fullscreen" nz-menu-item>
324
+ <yunzai-fullscreen></yunzai-fullscreen>
325
+ </div>
326
+ <div data-event-id="_nav_clearstorage" nz-menu-item>
327
+ <yunzai-clearstorage></yunzai-clearstorage>
328
+ </div>
329
+ <div data-event-id="_nav_i18n" nz-menu-item>
330
+ <yunzai-i18n></yunzai-i18n>
331
+ </div>
332
+ </div>
333
+ </nz-dropdown-menu>
334
+ </layout-default-header-item>
335
+ <layout-default-header-item direction="right">
336
+ <yunzai-user></yunzai-user>
337
+ </layout-default-header-item>
338
+ <!-- setting end -->
339
+ </layout-default>
340
+ <ng-template #asideUserTpl>
341
+ <div
342
+ data-event-id="_route_user"
343
+ nz-dropdown
344
+ nzTrigger="click"
345
+ [nzDropdownMenu]="userMenu"
346
+ class="yunzai-default__aside-user"
347
+ >
348
+ <nz-avatar class="yunzai-default__aside-user-avatar" [nzSrc]="aside.icon"></nz-avatar>
349
+ <div class="yunzai-default__aside-user-info">
350
+ <strong>{{ aside.name | i18n }}</strong>
351
+ <p class="mb0">{{ aside.intro | i18n }}</p>
352
+ </div>
353
+ </div>
354
+ <nz-dropdown-menu #userMenu="nzDropdownMenu">
355
+ <ul nz-menu>
356
+ <li data-event-id="_route_backhome" nz-menu-item routerLink="/">{{ 'back.home' | i18n }}</li>
357
+ </ul>
358
+ </nz-dropdown-menu>
359
+ </ng-template>
360
+ <ng-template #contentTpl>
361
+ <reuse-tab #reuseTab [ngStyle]="reusetabCSS"></reuse-tab>
362
+ <router-outlet (activate)="reuseTab.activate($event)" (attach)="reuseTab.activate($event)"></router-outlet>
363
+ </ng-template>
364
+ <ng-template #noneTpl>
365
+ <router-outlet></router-outlet>
366
+ </ng-template>
367
+ `
368
+ }]
369
+ }], ctorParameters: function () { return [{ type: i1.LayoutDisplayService }, { type: i2.StompService }, { type: undefined, decorators: [{
370
+ type: Inject,
371
+ args: [WINDOW]
372
+ }] }]; } });
373
373
  //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibGF5b3V0LWJhc2ljLmNvbXBvbmVudC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uLy4uL3BhY2thZ2VzL2Jpcy9sYXlvdXQvbGF5b3V0LWJhc2ljL2xheW91dC1iYXNpYy5jb21wb25lbnQudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLEVBQVcsTUFBTSxlQUFlLENBQUM7QUFJM0QsT0FBTyxFQUNMLE1BQU0sRUFDTixVQUFVLEVBQ1YsR0FBRyxFQUNILFVBQVUsRUFDVixPQUFPLEVBR1Asc0JBQXNCLEVBQ3RCLDBCQUEwQixFQUMxQix5QkFBeUIsRUFDekIsMkJBQTJCLEVBQzVCLE1BQU0sYUFBYSxDQUFDOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBaUhyQixNQUFNLE9BQU8sMEJBQTBCO0lBb0JyQyxJQUFJLE9BQU87UUFDVCxPQUFPLElBQUksQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDO0lBQzVCLENBQUM7SUFFRCxJQUFJLE9BQU87UUFDVCxPQUFPLElBQUksQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDO0lBQzVCLENBQUM7SUFFRCxJQUFJLEtBQUs7UUFDUCxPQUFPLElBQUksQ0FBQyxLQUFLLENBQUMsS0FBSyxDQUFDO0lBQzFCLENBQUM7SUFFRCxJQUFJLGVBQWU7UUFDakIsT0FBTyxJQUFJLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxRQUFRLENBQUM7SUFDckMsQ0FBQztJQUVELElBQUksV0FBVztRQUNiLElBQUksbUJBQW1CLEdBQUcsRUFBRSxDQUFDO1FBQzdCLElBQUksQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxHQUFHLEVBQUU7WUFDM0IsbUJBQW1CLEdBQUc7Z0JBQ3BCLEdBQUcsbUJBQW1CO2dCQUN0QixHQUFHLEVBQUUsS0FBSzthQUNYLENBQUM7U0FDSDtRQUNELElBQUksQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLE9BQU8s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QUFDLE9BQU8sQ0FBQyxRQUFRLEdBQUcsT0FBTyxDQUFDO1FBQ3hDLENBQUMsQ0FBQyxDQUFDO1FBQ0gsSUFBSSxDQUFDLG9CQUFvQixDQUFDLE1BQU0sQ0FBQyxLQUFLLEVBQUUsQ0FBQyxPQUFnQixFQUFFLEVBQUU7WUFDM0QsSUFBSSxDQUFDLEtBQUssQ0FBQyxPQUFPLENBQUMsR0FBRyxHQUFHLE9BQU8sQ0FBQztRQUNuQyxDQUFDLENBQUMsQ0FBQztRQUVILElBQUksQ0FBQyxvQkFBb0IsQ0FBQyxNQUFNLENBQUMsT0FBTyxFQUFFLENBQUMsT0FBZ0IsRUFBRSxFQUFFO1lBQzdELElBQUksQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDLEtBQUssR0FBRyxPQUFPLENBQUM7UUFDckMsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDOzhHQTNJVSwwQkFBMEIsa0ZBd0QzQixNQUFNO2tHQXhETCwwQkFBMEIsdURBM0czQjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0dBeUdUOzsyRkFFVSwwQkFBMEI7a0JBN0d0QyxTQUFTO21CQUFDO29CQUNULFFBQVEsRUFBRSxpQkFBaUI7b0JBQzNCLFFBQVEsRUFBRTs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0dBeUdUO2lCQUNGOzswQkF5REksTUFBTTsyQkFBQyxNQUFNIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgQ29tcG9uZW50LCBJbmplY3QsICBPbkluaXQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcblxuaW1wb3J0IHsgU3RvbXBTZXJ2aWNlIH0gZnJvbSAnQHllbG9uL3NvY2tldCc7XG5pbXBvcnQgeyBMYXlvdXREZWZhdWx0T3B0aW9ucywgTGF5b3V0RGlzcGxheVNlcnZpY2UgfSBmcm9tICdAeWVsb24vdGhlbWUvbGF5b3V0LWRlZmF1bHQnO1xuaW1wb3J0IHtcbiAgV0lORE9XLFxuICBoYXNGYXZpY29uLFxuICBsb2csXG4gIHNldEZhdmljb24sXG4gIE5hdlR5cGUsXG4gIExheW91dEJhc2ljQXNpZGUsXG4gIFl1bnphaVByb2plY3RJbmZvLFxuICB1c2VMb2NhbFN0b3JhZ2VDdXJyZW50LFxuICB1c2VMb2NhbFN0b3JhZ2VQcm9qZWN0SW5mbyxcbiAgdXNlTG9jYWxTdG9yYWdlSGVhZGVyVHlwZSxcbiAgdXNlTG9jYWxTdG9yYWdlRGVmYXVsdFJvdXRlXG59IGZyb20gJ0B5ZWxvbi91dGlsJztcblxuaW1wb3J0IHsgTGF5b3V0QmFzaWNTdGF0ZSB9IGZyb20gJy4vaW50ZXJmYWNlJztcblxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiBgeXotbGF5b3V0LWJhc2ljYCxcbiAgdGVtcGxhdGU6IGBcbiAgICA8bGF5b3V0LWRlZmF1bHQgW29wdGlvbnNdPVwib3B0aW9uc1wiIFthc2lkZVVzZXJdPVwiYXNpZGVVc2VyVHBsXCIgW2NvbnRlbnRdPVwiZGlzcGxheVJldXNldGFiID8gY29udGVudFRwbCA6IG5vbmVUcGxcIj5cbiAgICAgIDwhLS0gbmF2IC0tPlxuICAgICAgPGxheW91dC1kZWZhdWx0LWhlYWRlci1pdGVtIGRpcmVjdGlvbj1cImxlZnRcIj5cbiAgICAgICAgPG5nLWNvbnRhaW5lciBbbmdTd2l0Y2hdPVwibmF2VHlwZVwiPlxuICAgICAgICAgIDxuZy1jb250YWluZXIgKm5nU3dpdGNoQ2FzZT1cIk5hdlR5cGUuQVBQTElDQVRJT05cIj5cbiAgICAgICAgICAgIDxsYXlvdXQtbmF2LWFwcGxpY2F0aW9uPjwvbGF5b3V0LW5hdi1hcHBsaWNhdGlvbj5cbiAgICAgICAgICA8L25nLWNvbnRhaW5lcj5cbiAgICAgICAgICA8bmctY29udGFpbmVyICpuZ1N3aXRjaENhc2U9XCJOYXZUeXBlLkdST1VQXCI+XG4gICAgICAgICAgICA8bGF5b3V0LW5hdi1ncm91cD48L2xheW91dC1uYXYtZ3JvdXA+XG4gICAgICAgICAgPC9uZy1jb250YWluZXI+XG4gICAgICAgICAgPG5nLWNvbnRhaW5lciAqbmdTd2l0Y2hDYXNlPVwiTmF2VHlwZS5USUxFXCI+XG4gICAgICAgICAgICA8bGF5b3V0LW5hdi10aWxlPjwvbGF5b3V0LW5hdi10aWxlPlxuICAgICAgICAgIDwvbmctY29udGFpbmVyPlxuICAgICAgICAgIDxuZy1jb250YWluZXIgKm5nU3dpdGNoRGVmYXVsdD5cbiAgICAgICAgICAgIDxsYXlvdXQtbmF2LWFwcGxpY2F0aW9uPjwvbGF5b3V0LW5hdi1hcHBsaWNhdGlvbj5cbiAgICAgICAgICA8L25nLWNvbnRhaW5lcj5cbiAgICAgICAgPC9uZy1jb250YWluZXI+XG4gICAgICA8L2xheW91dC1kZWZhdWx0LWhlYWRlci1pdGVtPlxuICAgICAgPCEtLSBuYXYgZW5kIC0tPlxuICAgICAgPGxheW91dC1kZWZhdWx0LWhlYWRlci1pdGVtIGRpcmVjdGlvbj1cInJpZ2h0XCIgaGlkZGVuPVwibW9iaWxlXCI+XG4gICAgICAgIDx5dW56YWktbm90aWZ5PjwveXVuemFpLW5vdGlmeT5cbiAgICAgIDwvbGF5b3V0LWRlZmF1bHQtaGVhZGVyLWl0ZW0+XG4gICAgICA8bGF5b3V0LWRlZmF1bHQtaGVhZGVyLWl0ZW0gZGlyZWN0aW9uPVwicmlnaHRcIiBoaWRkZW49XCJtb2JpbGVcIj5cbiAgICAgICAgPHl1bnphaS10aGVtZS1idG4+PC95dW56YWktdGhlbWUtYnRuPlxuICAgICAgPC9sYXlvdXQtZGVmYXVsdC1oZWFkZXItaXRlbT5cbiAgICAgIDwhLS0gc2V0dGluZyAtLT5cbiAgICAgIDxsYXlvdXQtZGVmYXVsdC1oZWFkZXItaXRlbSBkaXJlY3Rpb249XCJyaWdodFwiIGhpZGRlbj1cIm1vYmlsZVwiPlxuICAgICAgICA8ZGl2XG4gICAgICAgICAgZGF0YS1ldmVudC1pZD1cIl9uYXZfc2V0dGluZ3NcIlxuICAgICAgICAgIGxheW91dC1kZWZhdWx0LWhlYWRlci1pdGVtLXRyaWdnZXJcbiAgICAgICAgICBuei1kcm9wZG93blxuICAgICAgICAgIFtuekRyb3Bkb3duTWVudV09XCJzZXR0aW5nc01lbnVcIlxuICAgICAgICAgIG56VHJpZ2dlcj1cImNsaWNrXCJcbiAgICAgICAgICBuelBsYWNlbWVudD1cImJvdHRvbVJpZ2h0XCJcbiAgICAgICAgPlxuICAgICAgICAgIDxpIG56LWljb24gbnpUeXBlPVwic2V0dGluZ1wiPjwvaT5cbiAgICAgICAgPC9kaXY+XG4gICAgICAgIDxuei1kcm9wZG93bi1tZW51ICNzZXR0aW5nc01lbnU9XCJuekRyb3Bkb3duTWVudVwiPlxuICAgICAgICAgIDxkaXYgbnotbWVudSBzdHlsZT1cIndpZHRoOiAyMDBweDtcIj5cbiAgICAgICAgICAgIDxkaXYgZGF0YS1ldmVudC1pZD1cIl9uYXZfbW9kZVwiIG56LW1lbnUtaXRlbT5cbiAgICAgICAgICAgICAge3sgJ21vZGUubmF2JyB8IGkxOG4gfX1cbiAgICAgICAgICAgIDwvZGl2PlxuXG4gICAgICAgICAgICA8ZGl2XG4gICAgICAgICAgICAgIGRhdGEtZXZlbnQtaWQ9XCJfbmF2X21vZGVcIlxuICAgICAgICAgICAgICBkYXRhLXR5cGU9XCJhcHBsaWNhdGlvblwiXG4gICAgICAgICAgICAgIG56LW1lbnUtaXRlbVxuICAgICAgICAgICAgICAoY2xpY2spPVwib25OYXZUeXBlQ2hhbmdlKE5hdlR5cGUuQVBQTElDQVRJT04pXCJcbiAgICAgICAgICAgID5cbiAgICAgICAgICAgICAgPGkgbnotaWNvbiBuelR5cGU9XCJhcHBzdG9yZVwiIGNsYXNzPVwibXItc21cIj48L2k+XG4gICAgICAgICAgICAgIHt7ICdtb2RlLm5hdi5hcHBsaWNhdGlvbicgfCBpMThuIH19XG4gICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICAgIDxkaXYgZGF0YS1ldmVudC1pZD1cIl9uYXZfbW9kZVwiIGRhdGEtdHlwZT1cImdyb3VwXCIgbnotbWVudS1pdGVtIChjbGljayk9XCJvbk5hdlR5cGVDaGFuZ2UoTmF2VHlwZS5HUk9VUClcIj5cbiAgICAgICAgICAgICAgPGkgbnotaWNvbiBuelR5cGU9XCJncm91cFwiIGNsYXNzPVwibXItc21cIj48L2k+XG4gICAgICAgICAgICAgIHt7ICdtb2RlLm5hdi5ncm91cCcgfCBpMThuIH19XG4gICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICAgIDxkaXYgZGF0YS1ldmVudC1pZD1cIl9uYXZfbW9kZVwiIGRhdGEtdHlwZT1cInRpbGVcIiBuei1tZW51LWl0ZW0gKGNsaWNrKT1cIm9uTmF2VHlwZUNoYW5nZShOYXZUeXBlLlRJTEUpXCI+XG4gICAgICAgICAgICAgIDxpIG56LWljb24gbnpUeXBlPVwiYXBwc3RvcmVcIiBjbGFzcz1cIm1yLXNtXCI+PC9pPlxuICAgICAgICAgICAgICB7eyAnbW9kZS5uYXYudGlsZScgfCBpMThuIH19XG4gICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICAgIDxkaXYgZGF0YS1ldmVudC1pZD1cIl9uYXZfZnVsbHNjcmVlblwiIG56LW1lbnUtaXRlbT5cbiAgICAgICAgICAgICAgPHl1bnphaS1mdWxsc2NyZWVuPjwveXVuemFpLWZ1bGxzY3JlZW4+XG4gICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICAgIDxkaXYgZGF0YS1ldmVudC1pZD1cIl9uYXZfY2xlYXJzdG9yYWdlXCIgbnotbWVudS1pdGVtPlxuICAgICAgICAgICAgICA8eXVuemFpLWNsZWFyc3RvcmFnZT48L3l1bnphaS1jbGVhcnN0b3JhZ2U+XG4gICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICAgIDxkaXYgZGF0YS1ldmVudC1pZD1cIl9uYXZfaTE4blwiIG56LW1lbnUtaXRlbT5cbiAgICAgICAgICAgICAgPHl1bnphaS1pMThuPjwveXVuemFpLWkxOG4+XG4gICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgPC9uei1kcm9wZG93bi1tZW51PlxuICAgICAgPC9sYXlvdXQtZGVmYXVsdC1oZWFkZXItaXRlbT5cbiAgICAgIDxsYXlvdXQtZGVmYXVsdC1oZWFkZXItaXRlbSBkaXJlY3Rpb249XCJyaWdodFwiPlxuICAgICAgICA8eXVuemFpLXVzZXI+PC95dW56YWktdXNlcj5cbiAgICAgIDwvbGF5b3V0LWRlZmF1bHQtaGVhZGVyLWl0ZW0+XG4gICAgICA8IS0tIHNldHRpbmcgZW5kIC0tPlxuICAgIDwvbGF5b3V0LWRlZmF1bHQ+XG4gICAgPG5nLXRlbXBsYXRlICNhc2lkZVVzZXJUcGw+XG4gICAgICA8ZGl2XG4gICAgICAgIGRhdGEtZXZlbnQtaWQ9XCJfcm91dGVfdXNlclwiXG4gICAgICAgIG56LWRyb3Bkb3duXG4gICAgICAgIG56VHJpZ2dlcj1cImNsaWNrXCJcbiAgICAgICAgW256RHJvcGRvd25NZW51XT1cInVzZXJNZW51XCJcbiAgICAgICAgY2xhc3M9XCJ5dW56YWktZGVmYXVsdF9fYXNpZGUtdXNlclwiXG4gICAgICA+XG4gICAgICAgIDxuei1hdmF0YXIgY2xhc3M9XCJ5dW56YWktZGVmYXVsdF9fYXNpZGUtdXNlci1hdmF0YXJcIiBbbnpTcmNdPVwiYXNpZGUuaWNvblwiPjwvbnotYXZhdGFyPlxuICAgICAgICA8ZGl2IGNsYXNzPVwieXVuemFpLWRlZmF1bHRfX2FzaWRlLXVzZXItaW5mb1wiPlxuICAgICAgICAgIDxzdHJvbmc+e3sgYXNpZGUubmFtZSB8IGkxOG4gfX08L3N0cm9uZz5cbiAgICAgICAgICA8cCBjbGFzcz1cIm1iMFwiPnt7IGFzaWRlLmludHJvIHwgaTE4biB9fTwvcD5cbiAgICAgICAgPC9kaXY+XG4gICAgICA8L2Rpdj5cbiAgICAgIDxuei1kcm9wZG93bi1tZW51ICN1c2VyTWVudT1cIm56RHJvcGRvd25NZW51XCI+XG4gICAgICAgIDx1bCBuei1tZW51PlxuICAgICAgICAgIDxsaSBkYXRhLWV2ZW50LWlkPVwiX3JvdXRlX2JhY2tob21lXCIgbnotbWVudS1pdGVtIHJvdXRlckxpbms9XCIvXCI+e3sgJ2JhY2suaG9tZScgfCBpMThuIH19PC9saT5cbiAgICAgICAgPC91bD5cbiAgICAgIDwvbnotZHJvcGRvd24tbWVudT5cbiAgICA8L25nLXRlbXBsYXRlPlxuICAgIDxuZy10ZW1wbGF0ZSAjY29udGVudFRwbD5cbiAgICAgIDxyZXVzZS10YWIgI3JldXNlVGFiIFtuZ1N0eWxlXT1cInJldXNldGFiQ1NTXCI+PC9yZXVzZS10YWI+XG4gICAgICA8cm91dGVyLW91dGxldCAoYWN0aXZhdGUpPVwicmV1c2VUYWIuYWN0aXZhdGUoJGV2ZW50KVwiIChhdHRhY2gpPVwicmV1c2VUYWIuYWN0aXZhdGUoJGV2ZW50KVwiPjwvcm91dGVyLW91dGxldD5cbiAgICA8L25nLXRlbXBsYXRlPlxuICAgIDxuZy10ZW1wbGF0ZSAjbm9uZVRwbD5cbiAgICAgIDxyb3V0ZXItb3V0bGV0Pjwvcm91dGVyLW91dGxldD5cbiAgICA8L25nLXRlbXBsYXRlPlxuICBgXG59KVxuZXhwb3J0IGNsYXNzIFl1bnphaUxheW91dEJhc2ljQ29tcG9uZW50IGltcGxlbWVudHMgT25Jbml0IHtcbiAgcHVibGljIE5hdlR5cGUgPSBOYXZUeXBlO1xuICBwcml2YXRlIHN0YXRlOiBMYXlvdXRCYXNpY1N0YXRlID0ge1xuICAgIG9wdGlvbnM6IHtcbiAgICAgIGxvZ29FeHBhbmRlZDogYC4vYXNzZXRzL2xvZ28tZnVsbC5zdmdgLFxuICAgICAgbG9nb0NvbGxhcHNlZDogYC4vYXNzZXRzL2xvZ28uc3ZnYFxuICAgIH0sXG4gICAgYXNpZGU6IHtcbiAgICAgIG5hbWU6ICcnLFxuICAgICAgaW50cm86ICcnLFxuICAgICAgaWNvbjogJydcbiAgICB9LFxuICAgIGRpc3BsYXk6IHtcbiAgICAgIG5hdjogdHJ1ZSxcbiAgICAgIGFzaWRlOiB0cnVlLFxuICAgICAgcmV1c2V0YWI6IHRydWVcbiAgICB9LFxuICAgIG5hdlR5cGU6IE5hdlR5cGUuQVBQTElDQVRJT04sXG4gIH07XG5cbiAgZ2V0IG9wdGlvbnMoKTogTGF5b3V0RGVmYXVsdE9wdGlvbnMge1xuICAgIHJldHVybiB0aGlzLnN0YXRlLm9wdGlvbnM7XG4gIH1cblxuICBnZXQgbmF2VHlwZSgpOiBOYXZUeXBlIHtcbiAgICByZXR1cm4gdGhpcy5zdGF0ZS5uYXZUeXBlO1xuICB9XG5cbiAgZ2V0IGFzaWRlKCk6IExheW91dEJhc2ljQXNpZGUge1xuICAgIHJldHVybiB0aGlzLnN0YXRlLmFzaWRlO1xuICB9XG5cbiAgZ2V0IGRpc3BsYXlSZXVzZXRhYigpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5zdGF0ZS5kaXNwbGF5LnJldXNldGFiO1xuICB9XG5cbiAgZ2V0IHJldXNldGFiQ1NTKCk6IGFueSB7XG4gICAgbGV0IGNhc2NhZGluZ1N0eWxlU2hlZXQgPSB7fTtcbiAgICBpZiAoIXRoaXMuc3RhdGUuZGlzcGxheS5uYXYpIHtcbiAgICAgIGNhc2NhZGluZ1N0eWxlU2hlZXQgPSB7XG4gICAgICAgIC4uLmNhc2NhZGluZ1N0eWxlU2hlZXQsXG4gICAgICAgIHRvcDogJzBweCdcbiAgICAgIH07XG4gICAgfVxuICAgIGlmICghdGhpcy5zdGF0ZS5kaXNwbGF5LmFzaWRlKSB7XG4gICAgICBjYXNjYWRpbmdTdHlsZVNoZWV0ID0ge1xuICAgICAgICAuLi5jYXNjYWRpbmdTdHlsZVNoZWV0LFxuICAgICAgICBsZWZ0OiAnMjRweCdcbiAgICAgIH07XG4gICAgfVxuICAgIHJldHVybiBjYXNjYWRpbmdTdHlsZVNoZWV0O1xuICB9XG5cbiAgY29uc3RydWN0b3IoXG4gICAgcHJpdmF0ZSBsYXlvdXREaXNwbGF5U2VydmljZTogTGF5b3V0RGlzcGxheVNlcnZpY2UsXG4gICAgcHJpdmF0ZSBzdG9tcFNlcnZpY2U6IFN0b21wU2VydmljZSxcbiAgICBASW5qZWN0KFdJTkRPVykgcHJpdmF0ZSB3aW46IHR5cGVvZiB3aW5kb3dcbiAgKSB7fVxuXG4gIG5nT25Jbml0KCk6IHZvaWQge1xuICAgIHRoaXMuaW5pdExvZ28oKTtcbiAgICB0aGlzLmluaXRGYXZpY29uKCk7XG4gICAgdGhpcy5pbml0TmF2VHlwZSgpO1xuICAgIHRoaXMuaW5pdEFzaWRlKCk7XG4gICAgdGhpcy5hZGRMYXlvdXREaXNwbGF5TGlzdGVuZXIoKTtcbiAgICB0aGlzLnN0b21wU2VydmljZS5saXN0ZW4oKTtcbiAgICB0aGlzLnRvSW5kZXgoKTtcbiAgfVxuXG4gIGluaXRGYXZpY29uKCk6IHZvaWQge1xuICAgIGNvbnN0IFssIGdldFByb2plY3RJbmZvXSA9IHVzZUxvY2FsU3RvcmFnZVByb2plY3RJbmZvKCk7XG4gICAgY29uc3QgcHJvamVjdEluZm86IFl1bnphaVByb2plY3RJbmZvID0gZ2V0UHJvamVjdEluZm8oKSE7XG4gICAgaWYgKHByb2plY3RJbmZvLmZhdmljb25VcmwpIHtcbiAgICAgIGhhc0Zhdmljb24ocHJvamVjdEluZm8uZmF2aWNvblVybCkudGhlbigoaGFzOiBib29sZWFuKSA9PiB7XG4gICAgICAgIGlmIChoYXMpIHtcbiAgICAgICAgICBzZXRGYXZpY29uKHByb2plY3RJbmZvLmZhdmljb25VcmwpO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgIHNldEZhdmljb24oJy4vYXNzZXRzL2Zhdmljb24uaWNvJyk7XG4gICAgICAgIH1cbiAgICAgIH0pO1xuICAgIH1cbiAgfVxuXG4gIGluaXRBc2lkZSgpOiB2b2lkIHtcbiAgICBjb25zdCBbLCBnZXRDdXJyZW50XSA9IHVzZUxvY2FsU3RvcmFnZUN1cnJlbnQoKTtcbiAgICBjb25zdCBhc2lkZTogTGF5b3V0QmFzaWNBc2lkZSA9IGdldEN1cnJlbnQoKSE7XG4gICAgdGhpcy5zdGF0ZS5hc2lkZSA9IHsgLi4uYXNpZGUgfTtcbiAgfVxuXG4gIGluaXRMb2dvKCk6IHZvaWQge1xuICAgIGNvbnN0IFssIGdldFByb2plY3RJbmZvXSA9IHVzZUxvY2FsU3RvcmFnZVByb2plY3RJbmZvKCk7XG4gICAgY29uc3QgcHJvamVjdEluZm86IFl1bnphaVByb2plY3RJbmZvID0gZ2V0UHJvamVjdEluZm8oKSE7XG4gICAgdGhpcy5zdGF0ZS5vcHRpb25zLmxvZ29FeHBhbmRlZCA9IHByb2plY3RJbmZvLm1heExvZ29VcmwgPyBwcm9qZWN0SW5mby5tYXhMb2dvVXJsIDogYC4vYXNzZXRzL2xvZ28tZnVsbC5zdmdgO1xuICAgIHRoaXMuc3RhdGUub3B0aW9ucy5sb2dvQ29sbGFwc2VkID0gcHJvamVjdEluZm8ubWluaUxvZ29VcmwgPyBwcm9qZWN0SW5mby5taW5pTG9nb1VybCA6IGAuL2Fzc2V0cy9sb2dvLnN2Z2A7XG4gIH1cblxuICBpbml0TmF2VHlwZSgpOiB2b2lkIHtcbiAgICBjb25zdCBbLCBnZXRIZWFkZXJUeXBlXSA9IHVzZUxvY2FsU3RvcmFnZUhlYWRlclR5cGUoKTtcbiAgICBjb25zdCBbLCBnZXRQcm9qZWN0SW5mb10gPSB1c2VMb2NhbFN0b3JhZ2VQcm9qZWN0SW5mbygpO1xuICAgIGNvbnN0IG5hdlR5cGU6IE5hdlR5cGUgfCBudWxsID0gZ2V0SGVhZGVyVHlwZSgpO1xuICAgIGNvbnN0IHByb2plY3RJbmZvOiBZdW56YWlQcm9qZWN0SW5mbyA9IGdldFByb2plY3RJbmZvKCkhO1xuICAgIGlmIChuYXZUeXBlICE9PSBudWxsKSB7XG4gICAgICB0aGlzLnN0YXRlLm5hdlR5cGUgPSBuYXZUeXBlO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBsZXQgZmV0Y2hlZE5hdlR5cGU6IGFueTtcbiAgICBpZiAocHJvamVjdEluZm8uaGVhZGVyU3R5bGUgJiYgcHJvamVjdEluZm8uaGVhZGVyU3R5bGUubGVuZ3RoID4gMCkge1xuICAgICAgZmV0Y2hlZE5hdlR5cGUgPSBwcm9qZWN0SW5mby5oZWFkZXJTdHlsZS5wb3AoKT8udmFsdWU7XG4gICAgfVxuICAgIC8vIGRlZmF1bHQgdmFsdWVcbiAgICBpZiAoIWZldGNoZWROYXZUeXBlKSB7XG4gICAgICBmZXRjaGVkTmF2VHlwZSA9IE5hdlR5cGUuQVBQTElDQVRJT047XG4gICAgfVxuICAgIHRoaXMuc3RhdGUubmF2VHlwZSA9IGZldGNoZWROYXZUeXBlO1xuICB9XG5cbiAgdG9JbmRleCgpOiB2b2lkIHtcbiAgICBjb25zdCBbLCBnZXREZWZhdWx0Um91dGVdID0gdXNlTG9jYWxTdG9yYWdlRGVmYXVsdFJvdXRlKCk7XG4gICAgY29uc3QgZGVmYXVsdFJvdXRlID0gZ2V0RGVmYXVsdFJvdXRlKCkhO1xuICAgIGxvZygnWXVuemFpTGF5b3V0QmFzaWNDb21wb25lbnQ6ICcsIGB0b2RvOiB0aGUgZGVmYXVsdCByb3V0ZSB3YXMgJHtkZWZhdWx0Um91dGV9LCDkvYbmmK/ov5jmsqHmg7Plpb3lpoLkvZXlrp7njrAuYCk7XG4gIH1cblxuICBvbk5hdlR5cGVDaGFuZ2UodHlwZTogTmF2VHlwZSk6IHZvaWQge1xuICAgIGNvbnN0IFtzZXRIZWFkZXJUeXBlXSA9IHVzZUxvY2FsU3RvcmFnZUhlYWRlclR5cGUoKTtcbiAgICBzZXRIZWFkZXJUeXBlKHR5cGUpO1xuICAgIHRoaXMud2luLmxvY2F0aW9uLnJlbG9hZCgpO1xuICB9XG5cbiAgYWRkTGF5b3V0RGlzcGxheUxpc3RlbmVyKCk6IHZvaWQge1xuICAgIHRoaXMubGF5b3V0RGlzcGxheVNlcnZpY2UubGlzdGVuKCdyZXVzZVRhYicsIChkaXNwbGF5OiBib29sZWFuKSA9PiB7XG4gICAgICB0aGlzLnN0YXRlLmRpc3BsYXkucmV1c2V0YWIgPSBkaXNwbGF5O1xuICAgIH0pO1xuICAgIHRoaXMubGF5b3V0RGlzcGxheVNlcnZpY2UubGlzdGVuKCduYXYnLCAoZGlzcGxheTogYm9vbGVhbikgPT4ge1xuICAgICAgdGhpcy5zdGF0ZS5kaXNwbGF5Lm5hdiA9IGRpc3BsYXk7XG4gICAgfSk7XG5cbiAgICB0aGlzLmxheW91dERpc3BsYXlTZXJ2aWNlLmxpc3RlbignYXNpZGUnLCAoZGlzcGxheTogYm9vbGVhbikgPT4ge1xuICAgICAgdGhpcy5zdGF0ZS5kaXNwbGF5LmFzaWRlID0gZGlzcGxheTtcbiAgICB9KTtcbiAgfVxuXG59XG4iXX0=