@sumaris-net/ngx-components 2.0.0-rc9 → 2.0.2
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.
- package/README.md +3 -1
- package/esm2020/public_api.mjs +35 -22
- package/esm2020/src/app/admin/admin-routing.module.mjs +6 -6
- package/esm2020/src/app/admin/admin.module.mjs +6 -6
- package/esm2020/src/app/admin/services/person.service.mjs +3 -3
- package/esm2020/src/app/admin/services/validator/person.validator.mjs +3 -3
- package/esm2020/src/app/admin/users/users.mjs +233 -0
- package/esm2020/src/app/admin/users/users.module.mjs +54 -0
- package/esm2020/src/app/core/about/about.modal.mjs +71 -0
- package/esm2020/src/app/core/about/about.module.mjs +34 -0
- package/esm2020/src/app/core/account/account.module.mjs +43 -0
- package/esm2020/src/app/core/account/account.page.mjs +239 -0
- package/esm2020/src/app/core/auth/auth.form.mjs +131 -0
- package/esm2020/src/app/core/auth/auth.modal.mjs +72 -0
- package/esm2020/src/app/core/auth/auth.module.mjs +47 -0
- package/esm2020/src/app/core/core.module.mjs +86 -125
- package/esm2020/src/app/core/core.testing.module.mjs +7 -7
- package/esm2020/src/app/core/form/{form-buttons-bar.component.mjs → buttons/form-buttons-bar.component.mjs} +7 -7
- package/esm2020/src/app/core/form/buttons/form-buttons-bar.module.mjs +35 -0
- package/esm2020/src/app/core/form/entity/editor.class.mjs +675 -0
- package/esm2020/src/app/core/form/entity/entity-editor-modal.class.mjs +421 -0
- package/esm2020/src/app/core/form/entity/entity-editor.class.mjs +646 -0
- package/esm2020/src/app/core/form/{entity-metadata.component.mjs → entity/entity-metadata.component.mjs} +6 -6
- package/esm2020/src/app/core/form/entity/entity.module.mjs +38 -0
- package/esm2020/src/app/core/form/form.class.mjs +4 -4
- package/esm2020/src/app/core/form/form.module.mjs +66 -0
- package/esm2020/src/app/core/form/list/list.form.mjs +222 -0
- package/esm2020/src/app/core/form/list/list.module.mjs +35 -0
- package/esm2020/src/app/core/form/properties/properties.form.mjs +3 -3
- package/esm2020/src/app/core/form/properties/properties.module.mjs +35 -0
- package/esm2020/src/app/core/form/properties/property.validator.mjs +4 -4
- package/esm2020/src/app/core/form/properties/testing/properties-form.test.mjs +3 -3
- package/esm2020/src/app/core/form/properties/testing/properties-form.testing.module.mjs +4 -4
- package/esm2020/src/app/core/{text-popover → form/text-popover}/testing/text-popover.testing.mjs +4 -4
- package/esm2020/src/app/core/form/text-popover/testing/text-popover.testing.module.mjs +45 -0
- package/esm2020/src/app/core/form/text-popover/text-form.component.mjs +89 -0
- package/esm2020/src/app/core/form/text-popover/text-popover.component.mjs +105 -0
- package/esm2020/src/app/core/form/text-popover/text-popover.module.mjs +40 -0
- package/esm2020/src/app/core/graphql/graphql.module.mjs +4 -4
- package/esm2020/src/app/core/graphql/graphql.service.mjs +12 -7
- package/esm2020/src/app/core/graphql/graphql.utils.mjs +2 -2
- package/esm2020/src/app/core/home/home.mjs +8 -8
- package/esm2020/src/app/core/home/home.module.mjs +48 -0
- package/esm2020/src/app/core/icon/icon.component.mjs +3 -3
- package/esm2020/src/app/core/icon/icon.module.mjs +4 -4
- package/esm2020/src/app/core/install/install-upgrade-card.component.mjs +3 -3
- package/esm2020/src/app/core/install/install-upgrade-card.module.mjs +17 -15
- package/esm2020/src/app/core/menu/menu.component.mjs +5 -5
- package/esm2020/src/app/core/menu/menu.module.mjs +9 -10
- package/esm2020/src/app/core/menu/menu.service.mjs +3 -3
- package/esm2020/src/app/core/offline/update-offline-mode-card.component.mjs +3 -3
- package/esm2020/src/app/core/offline/update-offline-mode-card.module.mjs +35 -0
- package/esm2020/src/app/core/peer/select-peer.modal.mjs +55 -11
- package/esm2020/src/app/core/peer/select-peer.module.mjs +17 -10
- package/esm2020/src/app/core/register/register-confirm.page.mjs +81 -0
- package/esm2020/src/app/core/register/register.form.mjs +181 -0
- package/esm2020/src/app/core/register/register.modal.mjs +52 -0
- package/esm2020/src/app/core/register/register.module.mjs +17 -15
- package/esm2020/src/app/core/services/account.service.mjs +22 -23
- package/esm2020/src/app/core/services/auth-guard.service.mjs +6 -6
- package/esm2020/src/app/core/services/base-entity-service.class.mjs +3 -3
- package/esm2020/src/app/core/services/base-graphql-service.class.mjs +8 -8
- package/esm2020/src/app/core/services/base58.mjs +2 -2
- package/esm2020/src/app/core/services/config.service.mjs +4 -4
- package/esm2020/src/app/core/services/crypto.service.mjs +82 -97
- package/esm2020/src/app/core/services/local-settings.service.mjs +8 -10
- package/esm2020/src/app/core/services/model/entity.decorators.mjs +44 -54
- package/esm2020/src/app/core/services/model/peer.model.mjs +3 -3
- package/esm2020/src/app/core/services/network.service.mjs +7 -7
- package/esm2020/src/app/core/services/pipes/account.pipes.mjs +8 -8
- package/esm2020/src/app/core/services/pipes/department-to-string.pipe.mjs +4 -4
- package/esm2020/src/app/core/services/pipes/person-to-string.pipe.mjs +4 -4
- package/esm2020/src/app/core/services/pipes/usage-mode.pipes.mjs +8 -8
- package/esm2020/src/app/core/services/platform.service.mjs +9 -10
- package/esm2020/src/app/core/services/storage/entities-storage.service.mjs +3 -3
- package/esm2020/src/app/core/services/storage/entity-store.class.mjs +4 -4
- package/esm2020/src/app/core/services/testing/referential.validator.mjs +3 -3
- package/esm2020/src/app/core/services/validator/account.validator.mjs +3 -3
- package/esm2020/src/app/core/services/validator/base.validator.class.mjs +3 -3
- package/esm2020/src/app/core/services/validator/local-settings.validator.mjs +3 -3
- package/esm2020/src/app/core/services/validator/user-settings.validator.mjs +3 -3
- package/esm2020/src/app/core/settings/settings.module.mjs +34 -0
- package/esm2020/src/app/core/settings/settings.page.mjs +12 -9
- package/esm2020/src/app/core/table/actions-column.component.mjs +3 -3
- package/esm2020/src/app/core/table/entities-table-datasource.class.mjs +13 -8
- package/esm2020/src/app/core/table/memory-table.class.mjs +3 -3
- package/esm2020/src/app/core/table/table-select-columns.component.mjs +3 -3
- package/esm2020/src/app/core/table/table.class.mjs +11 -16
- package/esm2020/src/app/core/table/table.module.mjs +40 -0
- package/esm2020/src/app/core/table/testing/table.testing.mjs +8 -8
- package/esm2020/src/app/core/table/testing/table.testing.module.mjs +4 -4
- package/esm2020/src/app/shared/audio/audio.mjs +3 -3
- package/esm2020/src/app/shared/audio/audio.testing.mjs +3 -3
- package/esm2020/src/app/shared/audio/audio.testing.module.mjs +4 -4
- package/esm2020/src/app/shared/capacitor/keyboard.mjs +3 -3
- package/esm2020/src/app/shared/constants.mjs +4 -2
- package/esm2020/src/app/shared/dates.mjs +20 -14
- package/esm2020/src/app/shared/debug/debug.component.mjs +3 -3
- package/esm2020/src/app/shared/debug/debug.module.mjs +4 -4
- package/esm2020/src/app/shared/directives/autofocus.directive.mjs +3 -3
- package/esm2020/src/app/shared/directives/autotitle.directive.mjs +3 -3
- package/esm2020/src/app/shared/directives/directives.module.mjs +4 -4
- package/esm2020/src/app/shared/directives/drag-and-drop.directive.mjs +3 -3
- package/esm2020/src/app/shared/directives/ng-var.directive.mjs +3 -3
- package/esm2020/src/app/shared/directives/resizable/resizable.component.mjs +3 -3
- package/esm2020/src/app/shared/directives/resizable/resizable.directive.mjs +3 -3
- package/esm2020/src/app/shared/directives/resizable/resizable.module.mjs +4 -4
- package/esm2020/src/app/shared/file/file.service.mjs +5 -5
- package/esm2020/src/app/shared/form/field.component.mjs +3 -3
- package/esm2020/src/app/shared/form/loading-spinner.mjs +3 -3
- package/esm2020/src/app/shared/gesture/gesture-config.mjs +3 -3
- package/esm2020/src/app/shared/guard/component-dirty.guard.mjs +3 -3
- package/esm2020/src/app/shared/help/help.modal.mjs +3 -3
- package/esm2020/src/app/shared/hotkeys/dialog/hotkeys-dialog.component.mjs +3 -3
- package/esm2020/src/app/shared/hotkeys/hotkeys.service.mjs +3 -3
- package/esm2020/src/app/shared/hotkeys/shared-hotkeys.module.mjs +4 -4
- package/esm2020/src/app/shared/image/gallery/image-gallery.component.mjs +134 -60
- package/esm2020/src/app/shared/image/gallery/image-gallery.module.mjs +19 -7
- package/esm2020/src/app/shared/image/gallery/testing/gallery.service.testing.mjs +3 -3
- package/esm2020/src/app/shared/image/gallery/testing/gallery.testing.mjs +13 -7
- package/esm2020/src/app/shared/image/gallery/testing/gallery.testing.module.mjs +4 -4
- package/esm2020/src/app/shared/image/image.module.mjs +5 -5
- package/esm2020/src/app/shared/image/image.service.mjs +3 -3
- package/esm2020/src/app/shared/material/autocomplete/material.autocomplete.mjs +7 -6
- package/esm2020/src/app/shared/material/autocomplete/material.autocomplete.module.mjs +4 -4
- package/esm2020/src/app/shared/material/autocomplete/testing/autocomplete.test.mjs +3 -3
- package/esm2020/src/app/shared/material/badge/badge.directive.mjs +3 -3
- package/esm2020/src/app/shared/material/badge/badge.module.mjs +4 -4
- package/esm2020/src/app/shared/material/badge/badge.test.mjs +3 -3
- package/esm2020/src/app/shared/material/boolean/boolean.module.mjs +4 -4
- package/esm2020/src/app/shared/material/boolean/material.boolean.mjs +5 -5
- package/esm2020/src/app/shared/material/chips/chips.module.mjs +4 -4
- package/esm2020/src/app/shared/material/chips/material.chips.mjs +5 -5
- package/esm2020/src/app/shared/material/chips/testing/chips.test.mjs +3 -3
- package/esm2020/src/app/shared/material/datetime/datetime.module.mjs +4 -4
- package/esm2020/src/app/shared/material/datetime/material.date.mjs +7 -8
- package/esm2020/src/app/shared/material/datetime/material.dateshort.mjs +6 -6
- package/esm2020/src/app/shared/material/datetime/material.datetime.mjs +7 -8
- package/esm2020/src/app/shared/material/datetime/testing/mat-date-time.test.mjs +5 -7
- package/esm2020/src/app/shared/material/datetime/testing/mat-date.test.mjs +7 -8
- package/esm2020/src/app/shared/material/duration/duration.module.mjs +4 -4
- package/esm2020/src/app/shared/material/duration/material.duration.mjs +3 -3
- package/esm2020/src/app/shared/material/latlong/material.latlong.mjs +3 -3
- package/esm2020/src/app/shared/material/latlong/material.latlong.module.mjs +4 -4
- package/esm2020/src/app/shared/material/latlong/testing/latlong.test.mjs +3 -3
- package/esm2020/src/app/shared/material/material.module.mjs +4 -4
- package/esm2020/src/app/shared/material/material.testing.module.mjs +4 -4
- package/esm2020/src/app/shared/material/numpad/numpad.append-to-input.directive.mjs +3 -3
- package/esm2020/src/app/shared/material/numpad/numpad.component.mjs +3 -3
- package/esm2020/src/app/shared/material/numpad/numpad.container.mjs +3 -3
- package/esm2020/src/app/shared/material/numpad/numpad.content.mjs +3 -3
- package/esm2020/src/app/shared/material/numpad/numpad.directive.mjs +3 -3
- package/esm2020/src/app/shared/material/numpad/numpad.dom-service.mjs +3 -3
- package/esm2020/src/app/shared/material/numpad/numpad.module.mjs +4 -4
- package/esm2020/src/app/shared/material/numpad/testing/numpad.test.mjs +3 -3
- package/esm2020/src/app/shared/material/paginator/material.paginator-i18n.mjs +3 -3
- package/esm2020/src/app/shared/material/stepper/material.stepper-i18n.mjs +3 -3
- package/esm2020/src/app/shared/material/swipe/material.swipe.mjs +3 -3
- package/esm2020/src/app/shared/material/swipe/swipe.module.mjs +4 -4
- package/esm2020/src/app/shared/material/swipe/testing/swipe.test.mjs +11 -12
- package/esm2020/src/app/shared/modules.mjs +11 -0
- package/esm2020/src/app/shared/pipes/arrays.pipe.mjs +24 -24
- package/esm2020/src/app/shared/pipes/colors.pipe.mjs +4 -4
- package/esm2020/src/app/shared/pipes/date-diff-duration.pipe.mjs +8 -9
- package/esm2020/src/app/shared/pipes/date-format.pipe.mjs +38 -14
- package/esm2020/src/app/shared/pipes/date-from-now.pipe.mjs +4 -4
- package/esm2020/src/app/shared/pipes/duration.pipe.mjs +4 -4
- package/esm2020/src/app/shared/pipes/file-size.pipe.mjs +3 -3
- package/esm2020/src/app/shared/pipes/form.pipes.mjs +18 -18
- package/esm2020/src/app/shared/pipes/highlight.pipe.mjs +4 -4
- package/esm2020/src/app/shared/pipes/latlong-format.pipe.mjs +9 -9
- package/esm2020/src/app/shared/pipes/maps.pipe.mjs +12 -12
- package/esm2020/src/app/shared/pipes/math.pipes.mjs +12 -12
- package/esm2020/src/app/shared/pipes/ng-init.pipe.mjs +3 -3
- package/esm2020/src/app/shared/pipes/number-format.pipe.mjs +4 -4
- package/esm2020/src/app/shared/pipes/pipes.module.mjs +14 -6
- package/esm2020/src/app/shared/pipes/property.pipes.mjs +9 -12
- package/esm2020/src/app/shared/pipes/string.pipes.mjs +43 -17
- package/esm2020/src/app/shared/pipes/translate-context.pipe.mjs +8 -8
- package/esm2020/src/app/shared/services/memory-entity-service.class.mjs +3 -3
- package/esm2020/src/app/shared/services/progress-bar.service.mjs +3 -3
- package/esm2020/src/app/shared/services/storage/storage.service.mjs +3 -3
- package/esm2020/src/app/shared/services/translate-context.service.mjs +3 -3
- package/esm2020/src/app/shared/shared-routing.module.mjs +7 -7
- package/esm2020/src/app/shared/shared.module.mjs +11 -7
- package/esm2020/src/app/shared/shared.testing.module.mjs +4 -4
- package/esm2020/src/app/shared/testing/observable.test.mjs +6 -7
- package/esm2020/src/app/shared/testing/tests.page.mjs +3 -3
- package/esm2020/src/app/shared/toast/toast.testing.mjs +3 -3
- package/esm2020/src/app/shared/toast/toast.testing.module.mjs +4 -4
- package/esm2020/src/app/shared/toast/toasts.mjs +1 -1
- package/esm2020/src/app/shared/toolbar/modal-toolbar.mjs +3 -3
- package/esm2020/src/app/shared/toolbar/toolbar.mjs +3 -3
- package/esm2020/src/app/shared/toolbar/toolbar.module.mjs +4 -4
- package/esm2020/src/app/shared/upload-file/testing/upload-file.testing.mjs +3 -3
- package/esm2020/src/app/shared/upload-file/testing/upload-file.testing.module.mjs +4 -4
- package/esm2020/src/app/shared/upload-file/upload-file-popover.component.mjs +5 -5
- package/esm2020/src/app/shared/upload-file/upload-file.component.mjs +3 -3
- package/esm2020/src/app/shared/validator/form-error-adapter.class.mjs +3 -3
- package/esm2020/src/app/shared/validator/validators.mjs +4 -5
- package/esm2020/src/app/social/job/job.module.mjs +4 -4
- package/esm2020/src/app/social/job/job.service.mjs +3 -3
- package/esm2020/src/app/social/job/progression/job-progression.icon.mjs +3 -3
- package/esm2020/src/app/social/job/progression/job-progression.list.mjs +4 -4
- package/esm2020/src/app/social/job/testing/job-progression.testing.mjs +3 -3
- package/esm2020/src/app/social/job/testing/job-progression.testing.service.mjs +3 -3
- package/esm2020/src/app/social/job/testing/job.testing.module.mjs +4 -4
- package/esm2020/src/app/social/message/message.form.mjs +3 -3
- package/esm2020/src/app/social/message/message.modal.mjs +3 -3
- package/esm2020/src/app/social/message/message.module.mjs +4 -4
- package/esm2020/src/app/social/message/message.service.mjs +3 -3
- package/esm2020/src/app/social/social.module.mjs +4 -4
- package/esm2020/src/app/social/social.testing.module.mjs +4 -4
- package/esm2020/src/app/social/user-event/notification/user-event-notification.icon.mjs +3 -3
- package/esm2020/src/app/social/user-event/notification/user-event-notification.list.mjs +7 -7
- package/esm2020/src/app/social/user-event/testing/user-event.testing.mjs +13 -12
- package/esm2020/src/app/social/user-event/testing/user-event.testing.module.mjs +4 -4
- package/esm2020/src/app/social/user-event/testing/user-event.testing.service.mjs +3 -3
- package/esm2020/src/app/social/user-event/user-event.module.mjs +4 -4
- package/esm2020/src/app/social/user-event/user-event.service.mjs +6 -8
- package/fesm2015/sumaris-net.ngx-components.mjs +10176 -9570
- package/fesm2015/sumaris-net.ngx-components.mjs.map +1 -1
- package/fesm2020/sumaris-net.ngx-components.mjs +10390 -9791
- package/fesm2020/sumaris-net.ngx-components.mjs.map +1 -1
- package/package.json +2 -1
- package/plugins/clovelced-plugin-audiomanagement/README.md +66 -0
- package/plugins/cordova-plugin-camera/README.md +703 -0
- package/plugins/cordova-plugin-device/README.md +309 -0
- package/plugins/cordova-plugin-file/README.md +848 -0
- package/plugins/cordova-plugin-file-transfer/README.md +598 -0
- package/plugins/cordova-plugin-file-transfer/doc/de/README.md +311 -0
- package/plugins/cordova-plugin-file-transfer/doc/es/README.md +311 -0
- package/plugins/cordova-plugin-file-transfer/doc/fr/README.md +270 -0
- package/plugins/cordova-plugin-file-transfer/doc/it/README.md +311 -0
- package/plugins/cordova-plugin-file-transfer/doc/ja/README.md +311 -0
- package/plugins/cordova-plugin-file-transfer/doc/ko/README.md +311 -0
- package/plugins/cordova-plugin-file-transfer/doc/pl/README.md +311 -0
- package/plugins/cordova-plugin-file-transfer/doc/zh/README.md +311 -0
- package/plugins/cordova-plugin-ionic-keyboard/README.md +220 -0
- package/plugins/cordova-plugin-ionic-webview/README.md +181 -0
- package/plugins/cordova-plugin-media-capture/README.md +626 -0
- package/plugins/cordova-plugin-splashscreen/README.md +387 -0
- package/plugins/cordova-plugin-statusbar/README.md +341 -0
- package/plugins/cordova-plugin-telerik-imagepicker/README.md +155 -0
- package/plugins/cordova-plugin-whitelist/README.md +185 -0
- package/plugins/cordova-sqlite-storage/README.md +1848 -0
- package/plugins/integrator-cordova-plugin-downloader/README.md +49 -0
- package/public_api.d.ts +34 -21
- package/src/app/admin/admin.module.d.ts +1 -1
- package/src/app/admin/users/{list/users.d.ts → users.d.ts} +11 -11
- package/src/app/admin/users/users.module.d.ts +13 -0
- package/src/app/core/about/{modal-about.d.ts → about.modal.d.ts} +1 -1
- package/src/app/core/about/about.module.d.ts +10 -0
- package/src/app/core/account/account.module.d.ts +11 -0
- package/src/app/core/account/{account.d.ts → account.page.d.ts} +5 -1
- package/src/app/core/auth/{form/form-auth.d.ts → auth.form.d.ts} +9 -9
- package/src/app/core/auth/{modal/modal-auth.d.ts → auth.modal.d.ts} +4 -4
- package/src/app/core/auth/auth.module.d.ts +11 -0
- package/src/app/core/core.module.d.ts +20 -29
- package/src/app/core/core.testing.module.d.ts +1 -1
- package/src/app/core/form/{form-buttons-bar.component.d.ts → buttons/form-buttons-bar.component.d.ts} +2 -2
- package/src/app/core/form/buttons/form-buttons-bar.module.d.ts +9 -0
- package/src/app/core/form/{editor.class.d.ts → entity/editor.class.d.ts} +9 -9
- package/src/app/core/form/{entity-editor-modal.class.d.ts → entity/entity-editor-modal.class.d.ts} +8 -8
- package/src/app/core/form/{entity-editor.class.d.ts → entity/entity-editor.class.d.ts} +11 -11
- package/src/app/core/form/{entity-metadata.component.d.ts → entity/entity-metadata.component.d.ts} +1 -1
- package/src/app/core/form/entity/entity.module.d.ts +10 -0
- package/src/app/core/form/form.module.d.ts +13 -0
- package/src/app/core/form/{list.form.d.ts → list/list.form.d.ts} +3 -3
- package/src/app/core/form/list/list.module.d.ts +9 -0
- package/src/app/core/form/properties/properties.module.d.ts +9 -0
- package/src/app/core/{text-popover → form/text-popover}/testing/text-popover.testing.d.ts +0 -0
- package/src/app/core/{text-popover → form/text-popover}/testing/text-popover.testing.module.d.ts +0 -0
- package/src/app/core/{text-popover → form/text-popover}/text-form.component.d.ts +4 -3
- package/src/app/core/{text-popover → form/text-popover}/text-popover.component.d.ts +7 -2
- package/src/app/core/form/text-popover/text-popover.module.d.ts +10 -0
- package/src/app/core/home/home.module.d.ts +12 -0
- package/src/app/core/install/install-upgrade-card.module.d.ts +6 -7
- package/src/app/core/menu/menu.component.d.ts +1 -1
- package/src/app/core/offline/update-offline-mode-card.module.d.ts +9 -0
- package/src/app/core/peer/select-peer.modal.d.ts +19 -5
- package/src/app/core/peer/select-peer.module.d.ts +6 -4
- package/src/app/core/register/{confirm/confirm.d.ts → register-confirm.page.d.ts} +4 -4
- package/src/app/core/register/{form/form-register.d.ts → register.form.d.ts} +7 -7
- package/src/app/core/register/{modal/modal-register.d.ts → register.modal.d.ts} +2 -2
- package/src/app/core/register/register.module.d.ts +6 -6
- package/src/app/core/services/account.service.d.ts +8 -9
- package/src/app/core/services/base-graphql-service.class.d.ts +9 -8
- package/src/app/core/services/crypto.service.d.ts +23 -18
- package/src/app/core/services/model/entity.decorators.d.ts +1 -9
- package/src/app/core/services/network.service.d.ts +3 -4
- package/src/app/core/settings/settings.module.d.ts +10 -0
- package/src/app/core/settings/settings.page.d.ts +2 -4
- package/src/app/core/table/entities-table-datasource.class.d.ts +1 -0
- package/src/app/core/table/table.class.d.ts +2 -6
- package/src/app/core/table/table.module.d.ts +10 -0
- package/src/app/shared/constants.d.ts +1 -1
- package/src/app/shared/dates.d.ts +5 -3
- package/src/app/shared/image/gallery/image-gallery.component.d.ts +39 -17
- package/src/app/shared/image/gallery/image-gallery.module.d.ts +6 -4
- package/src/app/shared/image/gallery/testing/gallery.testing.d.ts +1 -0
- package/src/app/shared/material/datetime/testing/mat-date.test.d.ts +1 -0
- package/src/app/shared/material/swipe/testing/swipe.test.d.ts +5 -6
- package/src/app/shared/modules.d.ts +8 -0
- package/src/app/shared/pipes/date-format.pipe.d.ts +22 -11
- package/src/app/shared/pipes/pipes.module.d.ts +1 -1
- package/src/app/shared/pipes/property.pipes.d.ts +4 -6
- package/src/app/shared/pipes/string.pipes.d.ts +10 -0
- package/src/app/shared/shared.module.d.ts +2 -1
- package/src/assets/i18n/en-US.json +20 -5
- package/src/assets/i18n/en.json +18 -4
- package/src/assets/i18n/fr.json +17 -6
- package/src/theme/_ngx-components.scss +22 -4
- package/esm2020/src/app/admin/users/list/users.mjs +0 -233
- package/esm2020/src/app/admin/users/list/users.module.mjs +0 -58
- package/esm2020/src/app/core/about/modal-about.mjs +0 -71
- package/esm2020/src/app/core/account/account.mjs +0 -230
- package/esm2020/src/app/core/auth/form/form-auth.mjs +0 -131
- package/esm2020/src/app/core/auth/modal/modal-auth.mjs +0 -72
- package/esm2020/src/app/core/form/editor.class.mjs +0 -675
- package/esm2020/src/app/core/form/entity-editor-modal.class.mjs +0 -421
- package/esm2020/src/app/core/form/entity-editor.class.mjs +0 -646
- package/esm2020/src/app/core/form/list.form.mjs +0 -222
- package/esm2020/src/app/core/register/confirm/confirm.mjs +0 -81
- package/esm2020/src/app/core/register/form/form-register.mjs +0 -181
- package/esm2020/src/app/core/register/modal/modal-register.mjs +0 -52
- package/esm2020/src/app/core/text-popover/testing/text-popover.testing.module.mjs +0 -45
- package/esm2020/src/app/core/text-popover/text-form.component.mjs +0 -84
- package/esm2020/src/app/core/text-popover/text-popover.component.mjs +0 -92
- package/esm2020/src/app/vendor.mjs +0 -16
- package/src/app/admin/users/list/users.module.d.ts +0 -14
- package/src/app/vendor.d.ts +0 -11
|
@@ -1,675 +0,0 @@
|
|
|
1
|
-
import { Directive, EventEmitter, Input, Optional, Output, ViewChild } from '@angular/core';
|
|
2
|
-
import { IonContent } from '@ionic/angular';
|
|
3
|
-
import { BehaviorSubject, Subject, Subscription } from 'rxjs';
|
|
4
|
-
import { AppTable } from '../table/table.class';
|
|
5
|
-
import { AppForm } from './form.class';
|
|
6
|
-
import { FormButtonsBarToken } from './form-buttons-bar.component';
|
|
7
|
-
import { AppFormProvider, AppFormUtils } from './form.utils';
|
|
8
|
-
import { Toasts } from '../../shared/toast/toasts';
|
|
9
|
-
import { ToolbarToken } from '../../shared/toolbar/toolbar';
|
|
10
|
-
import { isNotNil, toNumber } from '../../shared/functions';
|
|
11
|
-
import { AbstractControl } from '@angular/forms';
|
|
12
|
-
import { waitForFalse, waitForTrue } from '../../shared/observables';
|
|
13
|
-
import * as i0 from "@angular/core";
|
|
14
|
-
import * as i1 from "@angular/router";
|
|
15
|
-
import * as i2 from "@ionic/angular";
|
|
16
|
-
import * as i3 from "@ngx-translate/core";
|
|
17
|
-
export class AppTabEditorOptions {
|
|
18
|
-
}
|
|
19
|
-
// eslint-disable-next-line @angular-eslint/directive-class-suffix
|
|
20
|
-
export class AppEditor {
|
|
21
|
-
constructor(route, router, alertCtrl, translate) {
|
|
22
|
-
this.route = route;
|
|
23
|
-
this.router = router;
|
|
24
|
-
this.alertCtrl = alertCtrl;
|
|
25
|
-
this.translate = translate;
|
|
26
|
-
this._subscription = new Subscription();
|
|
27
|
-
this._enabled = false;
|
|
28
|
-
this.destroySubject = new Subject();
|
|
29
|
-
this.readySubject = new BehaviorSubject(false);
|
|
30
|
-
this.dirtySubject = new BehaviorSubject(false);
|
|
31
|
-
this.loadingSubject = new BehaviorSubject(true);
|
|
32
|
-
this.errorSubject = new BehaviorSubject(undefined);
|
|
33
|
-
this.savingSubject = new BehaviorSubject(false);
|
|
34
|
-
this.touchedSubject = new BehaviorSubject(false);
|
|
35
|
-
this.debug = false;
|
|
36
|
-
this.submitted = false;
|
|
37
|
-
this.toolbar = null;
|
|
38
|
-
this.formButtonsBar = null;
|
|
39
|
-
}
|
|
40
|
-
/**
|
|
41
|
-
* @deprecated
|
|
42
|
-
*/
|
|
43
|
-
set _loading(value) {
|
|
44
|
-
this.loadingSubject.next(value);
|
|
45
|
-
}
|
|
46
|
-
/**
|
|
47
|
-
* @deprecated
|
|
48
|
-
*/
|
|
49
|
-
get _loading() {
|
|
50
|
-
return this.loadingSubject.value;
|
|
51
|
-
}
|
|
52
|
-
/**
|
|
53
|
-
* @deprecated
|
|
54
|
-
*/
|
|
55
|
-
get _$ready() {
|
|
56
|
-
return this.readySubject;
|
|
57
|
-
}
|
|
58
|
-
/**
|
|
59
|
-
* @deprecated
|
|
60
|
-
*/
|
|
61
|
-
get _$loading() {
|
|
62
|
-
return this.loadingSubject;
|
|
63
|
-
}
|
|
64
|
-
get error() {
|
|
65
|
-
return this.errorSubject.value;
|
|
66
|
-
}
|
|
67
|
-
set error(error) {
|
|
68
|
-
this.setError(error);
|
|
69
|
-
}
|
|
70
|
-
get saving() {
|
|
71
|
-
return this.savingSubject.value || this.editors?.some(e => e.saving);
|
|
72
|
-
}
|
|
73
|
-
get destroyed() {
|
|
74
|
-
return this.destroySubject?.closed !== false;
|
|
75
|
-
}
|
|
76
|
-
get tables() {
|
|
77
|
-
return this._children && this._children.filter(c => c instanceof AppTable);
|
|
78
|
-
}
|
|
79
|
-
get forms() {
|
|
80
|
-
return this._children && this._children.filter(c => c instanceof AppForm);
|
|
81
|
-
}
|
|
82
|
-
get editors() {
|
|
83
|
-
return this._children && this._children.filter(c => c instanceof AppEditor);
|
|
84
|
-
}
|
|
85
|
-
get dirty() {
|
|
86
|
-
return this.dirtySubject.value || (this._children && this._children.findIndex(c => c.enabled && c.dirty) !== -1) || false;
|
|
87
|
-
}
|
|
88
|
-
/**
|
|
89
|
-
* Is valid (tables and forms)
|
|
90
|
-
*/
|
|
91
|
-
get valid() {
|
|
92
|
-
// Important: Should be not invalid AND not pending, so use '!valid' (DO NOT use 'invalid')
|
|
93
|
-
return !this._children || this._children.findIndex(c => c.enabled && !c.valid) === -1;
|
|
94
|
-
}
|
|
95
|
-
get invalid() {
|
|
96
|
-
return (this._children && this._children.findIndex(c => c.enabled && c.invalid) !== -1) || false;
|
|
97
|
-
}
|
|
98
|
-
get pending() {
|
|
99
|
-
return (this._children && this._children.findIndex(c => c.enabled && c.pending) !== -1) || false;
|
|
100
|
-
}
|
|
101
|
-
get loading() {
|
|
102
|
-
return this.loadingSubject.value || (this._children && this._children.findIndex(c => c.enabled && c.loading) !== -1) || false;
|
|
103
|
-
}
|
|
104
|
-
get loaded() {
|
|
105
|
-
return !this.loadingSubject.value && (!this._children || this._children.findIndex(c => c.enabled && c.loading) === -1) || false;
|
|
106
|
-
}
|
|
107
|
-
get touched() {
|
|
108
|
-
return this.touchedSubject.value || (this._children && this._children.findIndex(c => c.enabled && c.touched) !== -1) || false;
|
|
109
|
-
}
|
|
110
|
-
get untouched() {
|
|
111
|
-
return !this.touchedSubject.value && (!this._children || this._children.findIndex(c => c.enabled && c.touched) === -1) || false;
|
|
112
|
-
}
|
|
113
|
-
get enabled() {
|
|
114
|
-
return this._enabled;
|
|
115
|
-
}
|
|
116
|
-
get disabled() {
|
|
117
|
-
return !this._enabled;
|
|
118
|
-
}
|
|
119
|
-
get children() {
|
|
120
|
-
return this._children;
|
|
121
|
-
}
|
|
122
|
-
get empty() {
|
|
123
|
-
return !this._enabled;
|
|
124
|
-
}
|
|
125
|
-
ngOnInit() {
|
|
126
|
-
if (this.formButtonsBar) {
|
|
127
|
-
this.registerSubscription(this.formButtonsBar.onBack.subscribe(event => this.goBack(event)));
|
|
128
|
-
}
|
|
129
|
-
}
|
|
130
|
-
ngAfterViewInit() {
|
|
131
|
-
// Can be overridden by subclasses
|
|
132
|
-
}
|
|
133
|
-
ngOnDestroy() {
|
|
134
|
-
this._subscription.unsubscribe();
|
|
135
|
-
this.readySubject.unsubscribe();
|
|
136
|
-
this.loadingSubject.unsubscribe();
|
|
137
|
-
this.errorSubject.unsubscribe();
|
|
138
|
-
this.destroySubject.next();
|
|
139
|
-
this.destroySubject.unsubscribe();
|
|
140
|
-
}
|
|
141
|
-
addChildForm(form) {
|
|
142
|
-
if (!form)
|
|
143
|
-
throw new Error('Trying to register an undefined child form');
|
|
144
|
-
this._children = this._children || [];
|
|
145
|
-
if (typeof form === 'function') {
|
|
146
|
-
this._children.push(new AppFormProvider(form));
|
|
147
|
-
}
|
|
148
|
-
else {
|
|
149
|
-
this._children.push(form);
|
|
150
|
-
}
|
|
151
|
-
return this;
|
|
152
|
-
}
|
|
153
|
-
addChildForms(forms) {
|
|
154
|
-
(forms || []).forEach(form => this.addChildForm(form));
|
|
155
|
-
}
|
|
156
|
-
removeChildForm(form) {
|
|
157
|
-
if (!form)
|
|
158
|
-
throw new Error('Trying to remove an undefined child form');
|
|
159
|
-
const index = (this._children || []).findIndex(c => c === form);
|
|
160
|
-
if (index !== -1) {
|
|
161
|
-
return this._children.splice(index, 1)[0];
|
|
162
|
-
}
|
|
163
|
-
return undefined;
|
|
164
|
-
}
|
|
165
|
-
disable(opts) {
|
|
166
|
-
this._enabled = false;
|
|
167
|
-
this._children?.forEach(c => c.disable(opts));
|
|
168
|
-
if (!this.loading && (!opts || opts.emitEvent !== false))
|
|
169
|
-
this.markForCheck();
|
|
170
|
-
}
|
|
171
|
-
enable(opts) {
|
|
172
|
-
this._enabled = true;
|
|
173
|
-
this._children?.forEach(c => c.enable(opts));
|
|
174
|
-
if (!this.loading && (!opts || opts.emitEvent !== false))
|
|
175
|
-
this.markForCheck();
|
|
176
|
-
}
|
|
177
|
-
markAsPristine(opts) {
|
|
178
|
-
this.error = null;
|
|
179
|
-
this.submitted = false;
|
|
180
|
-
if (this.dirtySubject.value !== false) {
|
|
181
|
-
this.dirtySubject.next(false);
|
|
182
|
-
}
|
|
183
|
-
this._children?.forEach(c => c.markAsPristine(opts));
|
|
184
|
-
if (!this.loading && (!opts || opts.emitEvent !== false))
|
|
185
|
-
this.markForCheck();
|
|
186
|
-
}
|
|
187
|
-
markAsUntouched(opts) {
|
|
188
|
-
if (this.touchedSubject.value !== false) {
|
|
189
|
-
this.touchedSubject.next(false);
|
|
190
|
-
}
|
|
191
|
-
this._children?.forEach(c => c.markAsUntouched());
|
|
192
|
-
if (!this.loading && (!opts || opts.emitEvent !== false))
|
|
193
|
-
this.markForCheck();
|
|
194
|
-
}
|
|
195
|
-
/**
|
|
196
|
-
* @deprecated prefer to use markAllAsTouched()
|
|
197
|
-
* @param opts
|
|
198
|
-
*/
|
|
199
|
-
markAsTouched(opts) {
|
|
200
|
-
if (!this.touchedSubject.value !== true) {
|
|
201
|
-
this.touchedSubject.next(true);
|
|
202
|
-
}
|
|
203
|
-
this._children?.forEach(c => c.markAsTouched(opts));
|
|
204
|
-
if (!this.loading && (!opts || opts.emitEvent !== false))
|
|
205
|
-
this.markForCheck();
|
|
206
|
-
}
|
|
207
|
-
markAllAsTouched(opts) {
|
|
208
|
-
if (this.touchedSubject.value !== true) {
|
|
209
|
-
this.touchedSubject.next(true);
|
|
210
|
-
}
|
|
211
|
-
this._children?.forEach(c => c.markAllAsTouched(opts));
|
|
212
|
-
if (!this.loading && (!opts || opts.emitEvent !== false))
|
|
213
|
-
this.markForCheck();
|
|
214
|
-
}
|
|
215
|
-
markAsDirty(opts) {
|
|
216
|
-
if (!this.dirtySubject.value) {
|
|
217
|
-
this.dirtySubject.next(true);
|
|
218
|
-
if (!this.loading && (!opts || opts.emitEvent !== false))
|
|
219
|
-
this.markForCheck();
|
|
220
|
-
}
|
|
221
|
-
}
|
|
222
|
-
markAsLoading(opts) {
|
|
223
|
-
if (!this.loadingSubject.value) {
|
|
224
|
-
this.loadingSubject.next(true);
|
|
225
|
-
if (!opts || opts.emitEvent !== false)
|
|
226
|
-
this.markForCheck();
|
|
227
|
-
}
|
|
228
|
-
}
|
|
229
|
-
markAsLoaded(opts) {
|
|
230
|
-
if (this.loadingSubject.value) {
|
|
231
|
-
this.loadingSubject.next(false);
|
|
232
|
-
if (!opts || opts.onlySelf !== true) {
|
|
233
|
-
// Emit to children forms and editors
|
|
234
|
-
// note: tables should be changed by parent
|
|
235
|
-
this.forms?.forEach(f => f.markAsLoaded(opts));
|
|
236
|
-
this.editors?.forEach(e => e.markAsLoaded(opts));
|
|
237
|
-
}
|
|
238
|
-
if (!opts || opts.emitEvent !== false) {
|
|
239
|
-
this.markForCheck();
|
|
240
|
-
}
|
|
241
|
-
}
|
|
242
|
-
}
|
|
243
|
-
markAsReady(opts) {
|
|
244
|
-
this._children?.forEach(c => c.markAsReady(opts));
|
|
245
|
-
this.readySubject.next(true);
|
|
246
|
-
}
|
|
247
|
-
ready(opts) {
|
|
248
|
-
if (this.readySubject.value)
|
|
249
|
-
return Promise.resolve();
|
|
250
|
-
return waitForTrue(this.readySubject, opts);
|
|
251
|
-
}
|
|
252
|
-
waitIdle(opts) {
|
|
253
|
-
if (!this.loadingSubject.value)
|
|
254
|
-
return Promise.resolve();
|
|
255
|
-
return waitForFalse(this.loadingSubject, opts);
|
|
256
|
-
}
|
|
257
|
-
markAsSaving(opts) {
|
|
258
|
-
if (this.savingSubject.value !== true) {
|
|
259
|
-
this.savingSubject.next(true);
|
|
260
|
-
if (!opts || opts.emitEvent !== false)
|
|
261
|
-
this.markForCheck();
|
|
262
|
-
}
|
|
263
|
-
}
|
|
264
|
-
markAsSaved(opts) {
|
|
265
|
-
if (this.savingSubject.value !== false) {
|
|
266
|
-
this.savingSubject.next(false);
|
|
267
|
-
if (!opts || opts.emitEvent !== false)
|
|
268
|
-
this.markForCheck();
|
|
269
|
-
}
|
|
270
|
-
}
|
|
271
|
-
async cancel(event) {
|
|
272
|
-
if (this.isNewData) {
|
|
273
|
-
await this.unload(); // async reset
|
|
274
|
-
}
|
|
275
|
-
else if (this.dirty) {
|
|
276
|
-
await this.reload(); // async reload
|
|
277
|
-
}
|
|
278
|
-
}
|
|
279
|
-
/**
|
|
280
|
-
* Unload the page (remove all data). Useful when reusing angular cache a cancelled page
|
|
281
|
-
*
|
|
282
|
-
* @param opts
|
|
283
|
-
*/
|
|
284
|
-
async unload(opts) {
|
|
285
|
-
console.debug('[editor] Unloading data...');
|
|
286
|
-
this.markAsLoading();
|
|
287
|
-
this._children?.forEach(f => {
|
|
288
|
-
if (f instanceof AppForm) {
|
|
289
|
-
f.reset(null, opts);
|
|
290
|
-
}
|
|
291
|
-
else if (f instanceof AppTable) {
|
|
292
|
-
f.dataSource.disconnect();
|
|
293
|
-
}
|
|
294
|
-
else if (f instanceof AppEditor) {
|
|
295
|
-
f.unload(opts);
|
|
296
|
-
}
|
|
297
|
-
});
|
|
298
|
-
this.markAsPristine(opts);
|
|
299
|
-
this.markAsSaved(opts);
|
|
300
|
-
}
|
|
301
|
-
async reloadWithConfirmation(confirm) {
|
|
302
|
-
const needConfirm = this.dirty;
|
|
303
|
-
// if not confirm yet: ask confirmation
|
|
304
|
-
if (!confirm && needConfirm) {
|
|
305
|
-
const translations = this.translate.instant(['COMMON.BTN_ABORT_CHANGES', 'COMMON.BTN_CANCEL', 'CONFIRM.CANCEL_CHANGES', 'CONFIRM.ALERT_HEADER']);
|
|
306
|
-
const alert = await this.alertCtrl.create({
|
|
307
|
-
header: translations['CONFIRM.ALERT_HEADER'],
|
|
308
|
-
message: translations['CONFIRM.CANCEL_CHANGES'],
|
|
309
|
-
buttons: [
|
|
310
|
-
{
|
|
311
|
-
text: translations['COMMON.BTN_ABORT_CHANGES'],
|
|
312
|
-
cssClass: 'secondary',
|
|
313
|
-
handler: () => {
|
|
314
|
-
confirm = true; // update upper value
|
|
315
|
-
}
|
|
316
|
-
},
|
|
317
|
-
{
|
|
318
|
-
text: translations['COMMON.BTN_CANCEL'],
|
|
319
|
-
role: 'cancel',
|
|
320
|
-
handler: () => {
|
|
321
|
-
}
|
|
322
|
-
}
|
|
323
|
-
]
|
|
324
|
-
});
|
|
325
|
-
await alert.present();
|
|
326
|
-
await alert.onDidDismiss();
|
|
327
|
-
}
|
|
328
|
-
// If confirm: execute the reload
|
|
329
|
-
if (confirm || !needConfirm) {
|
|
330
|
-
this.scrollToTop();
|
|
331
|
-
this.disable();
|
|
332
|
-
return await this.reload();
|
|
333
|
-
}
|
|
334
|
-
}
|
|
335
|
-
async goBack(event) {
|
|
336
|
-
// Go back
|
|
337
|
-
if (this.toolbar?.canGoBack) {
|
|
338
|
-
return this.toolbar.goBack();
|
|
339
|
-
}
|
|
340
|
-
else {
|
|
341
|
-
// Back to home
|
|
342
|
-
return this.router.navigateByUrl('/');
|
|
343
|
-
}
|
|
344
|
-
}
|
|
345
|
-
logFormErrors(prefix) {
|
|
346
|
-
if (this.debug)
|
|
347
|
-
console.debug('[editor] Editor not valid. Checking where (forms, tables)...');
|
|
348
|
-
this._children?.forEach(c => this.logChildrenErrors(c, prefix));
|
|
349
|
-
}
|
|
350
|
-
/* -- protected methods -- */
|
|
351
|
-
async scrollToTop(duration) {
|
|
352
|
-
duration = toNumber(duration, 500);
|
|
353
|
-
if (!this.content) {
|
|
354
|
-
console.warn(`[tab-editor] Cannot scroll to top. (no 'ion-content' tag found ${this.constructor.name}`);
|
|
355
|
-
// TODO: FIXME (not working as the page is not the window)
|
|
356
|
-
const scrollToTop = window.setInterval(() => {
|
|
357
|
-
const pos = window.scrollY;
|
|
358
|
-
if (pos > 0) {
|
|
359
|
-
window.scrollTo(0, pos - 20); // how far to scroll on each step
|
|
360
|
-
}
|
|
361
|
-
else {
|
|
362
|
-
window.clearInterval(scrollToTop);
|
|
363
|
-
}
|
|
364
|
-
}, 16);
|
|
365
|
-
return;
|
|
366
|
-
}
|
|
367
|
-
return this.content.scrollToTop(duration);
|
|
368
|
-
}
|
|
369
|
-
registerSubscription(sub) {
|
|
370
|
-
this._subscription.add(sub);
|
|
371
|
-
}
|
|
372
|
-
unregisterSubscription(sub) {
|
|
373
|
-
this._subscription.remove(sub);
|
|
374
|
-
}
|
|
375
|
-
async saveIfDirtyAndConfirm(event, opts) {
|
|
376
|
-
if (!this.dirty)
|
|
377
|
-
return true;
|
|
378
|
-
let confirmed = opts?.confirmed || false;
|
|
379
|
-
if (!confirmed) {
|
|
380
|
-
let cancel = false;
|
|
381
|
-
const translations = this.translate.instant(['COMMON.BTN_SAVE', 'COMMON.BTN_CANCEL', 'COMMON.BTN_ABORT_CHANGES', 'CONFIRM.SAVE', 'CONFIRM.ALERT_HEADER']);
|
|
382
|
-
const alert = await this.alertCtrl.create({
|
|
383
|
-
header: translations['CONFIRM.ALERT_HEADER'],
|
|
384
|
-
message: translations['CONFIRM.SAVE'],
|
|
385
|
-
buttons: [
|
|
386
|
-
{
|
|
387
|
-
text: translations['COMMON.BTN_CANCEL'],
|
|
388
|
-
role: 'cancel',
|
|
389
|
-
cssClass: 'secondary',
|
|
390
|
-
handler: () => {
|
|
391
|
-
cancel = true;
|
|
392
|
-
}
|
|
393
|
-
},
|
|
394
|
-
{
|
|
395
|
-
text: translations['COMMON.BTN_ABORT_CHANGES'],
|
|
396
|
-
cssClass: 'secondary',
|
|
397
|
-
handler: () => {
|
|
398
|
-
}
|
|
399
|
-
},
|
|
400
|
-
{
|
|
401
|
-
text: translations['COMMON.BTN_SAVE'],
|
|
402
|
-
handler: () => {
|
|
403
|
-
confirmed = true; // update upper value
|
|
404
|
-
}
|
|
405
|
-
}
|
|
406
|
-
]
|
|
407
|
-
});
|
|
408
|
-
await alert.present();
|
|
409
|
-
await alert.onDidDismiss();
|
|
410
|
-
if (!confirmed) {
|
|
411
|
-
return !cancel;
|
|
412
|
-
}
|
|
413
|
-
}
|
|
414
|
-
return await this.save(event, opts);
|
|
415
|
-
}
|
|
416
|
-
async showToast(opts) {
|
|
417
|
-
if (!this.toastController)
|
|
418
|
-
throw new Error('Missing toastController in component\'s constructor');
|
|
419
|
-
await Toasts.show(this.toastController, this.translate, opts);
|
|
420
|
-
}
|
|
421
|
-
logChildrenErrors(c, prefix, path) {
|
|
422
|
-
prefix = prefix || '[app-tab-editor] ';
|
|
423
|
-
// If editor
|
|
424
|
-
if (c instanceof AppEditor) {
|
|
425
|
-
c.logFormErrors();
|
|
426
|
-
}
|
|
427
|
-
// Angular form control
|
|
428
|
-
else if (c instanceof AbstractControl) {
|
|
429
|
-
AppFormUtils.logFormErrors(c, prefix, path);
|
|
430
|
-
}
|
|
431
|
-
// If form provider: get delegate
|
|
432
|
-
else if (c instanceof AppFormProvider) {
|
|
433
|
-
if (!c.empty && !c.valid) {
|
|
434
|
-
c.waitDelegate({ timeout: 1000 }).then(delegate => this.logChildrenErrors(delegate, prefix, 'provider'));
|
|
435
|
-
}
|
|
436
|
-
}
|
|
437
|
-
// If table
|
|
438
|
-
else if (c instanceof AppTable) {
|
|
439
|
-
if (c.invalid && c.editedRow && c.editedRow.validator) {
|
|
440
|
-
const path = c.constructor.name.toLowerCase();
|
|
441
|
-
AppFormUtils.logFormErrors(c.editedRow.validator, prefix, path);
|
|
442
|
-
}
|
|
443
|
-
}
|
|
444
|
-
// If form
|
|
445
|
-
else if (c instanceof AppForm) {
|
|
446
|
-
if (!c.empty && !c.valid) {
|
|
447
|
-
if (c.pending) {
|
|
448
|
-
const path = c.constructor.name.toLowerCase();
|
|
449
|
-
console.warn(`${prefix} -> ${path}: waiting while pending...`);
|
|
450
|
-
AppFormUtils.waitWhilePending(c, { timeout: 1000 })
|
|
451
|
-
.then(() => this.logChildrenErrors(c.form, prefix, path));
|
|
452
|
-
}
|
|
453
|
-
else {
|
|
454
|
-
AppFormUtils.logFormErrors(c.form, prefix);
|
|
455
|
-
}
|
|
456
|
-
}
|
|
457
|
-
}
|
|
458
|
-
// If editor
|
|
459
|
-
else if (c instanceof AppEditor) {
|
|
460
|
-
if (!c.empty && !c.valid) {
|
|
461
|
-
if (c.pending) {
|
|
462
|
-
const path = c.constructor.name.toLowerCase();
|
|
463
|
-
console.warn(`${prefix} -> ${path}: waiting while pending...`);
|
|
464
|
-
AppFormUtils.waitWhilePending(c, { timeout: 1000 })
|
|
465
|
-
.then(() => c.logFormErrors(prefix));
|
|
466
|
-
}
|
|
467
|
-
else {
|
|
468
|
-
c.logFormErrors(prefix);
|
|
469
|
-
}
|
|
470
|
-
}
|
|
471
|
-
}
|
|
472
|
-
else {
|
|
473
|
-
console.warn(`${prefix} Unknown children sub-form: `, c);
|
|
474
|
-
}
|
|
475
|
-
}
|
|
476
|
-
setError(value, opts) {
|
|
477
|
-
if (this.errorSubject.value !== value) {
|
|
478
|
-
this.errorSubject.next(value);
|
|
479
|
-
if (!opts || opts.emitEvent !== false)
|
|
480
|
-
this.markForCheck();
|
|
481
|
-
}
|
|
482
|
-
}
|
|
483
|
-
resetError(opts) {
|
|
484
|
-
this.setError(undefined, opts);
|
|
485
|
-
}
|
|
486
|
-
markForCheck() {
|
|
487
|
-
// Should be override by subclasses, if change detection is Push
|
|
488
|
-
}
|
|
489
|
-
}
|
|
490
|
-
AppEditor.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.5", ngImport: i0, type: AppEditor, deps: [{ token: i1.ActivatedRoute }, { token: i1.Router }, { token: i2.AlertController }, { token: i3.TranslateService }], target: i0.ɵɵFactoryTarget.Directive });
|
|
491
|
-
AppEditor.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.2.5", type: AppEditor, viewQueries: [{ propertyName: "toolbar", first: true, predicate: ToolbarToken, descendants: true }, { propertyName: "formButtonsBar", first: true, predicate: FormButtonsBarToken, descendants: true, static: true }, { propertyName: "content", first: true, predicate: IonContent, descendants: true, static: true }], ngImport: i0 });
|
|
492
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.2.5", ngImport: i0, type: AppEditor, decorators: [{
|
|
493
|
-
type: Directive
|
|
494
|
-
}], ctorParameters: function () { return [{ type: i1.ActivatedRoute }, { type: i1.Router }, { type: i2.AlertController }, { type: i3.TranslateService }]; }, propDecorators: { toolbar: [{
|
|
495
|
-
type: ViewChild,
|
|
496
|
-
args: [ToolbarToken]
|
|
497
|
-
}], formButtonsBar: [{
|
|
498
|
-
type: ViewChild,
|
|
499
|
-
args: [FormButtonsBarToken, { static: true }]
|
|
500
|
-
}], content: [{
|
|
501
|
-
type: ViewChild,
|
|
502
|
-
args: [IonContent, { static: true }]
|
|
503
|
-
}] } });
|
|
504
|
-
// eslint-disable-next-line @angular-eslint/directive-class-suffix
|
|
505
|
-
export class AppTabEditor extends AppEditor {
|
|
506
|
-
constructor(route, // Modal editor give 'null'
|
|
507
|
-
router, alertCtrl, translate, options) {
|
|
508
|
-
super(route, router, alertCtrl, translate);
|
|
509
|
-
this.route = route;
|
|
510
|
-
this.router = router;
|
|
511
|
-
this.alertCtrl = alertCtrl;
|
|
512
|
-
this.translate = translate;
|
|
513
|
-
this._selectedTabIndex = 0;
|
|
514
|
-
this.selectedTabIndexChange = new EventEmitter();
|
|
515
|
-
options = {
|
|
516
|
-
tabCount: 1,
|
|
517
|
-
enableSwipe: true,
|
|
518
|
-
tabGroupAnimationDuration: '200ms',
|
|
519
|
-
...options
|
|
520
|
-
};
|
|
521
|
-
this.tabCount = options.tabCount;
|
|
522
|
-
this.enableSwipe = options.enableSwipe;
|
|
523
|
-
this.tabGroupAnimationDuration = options.tabGroupAnimationDuration;
|
|
524
|
-
this.queryTabIndexParamName = 'tab';
|
|
525
|
-
}
|
|
526
|
-
set selectedTabIndex(value) {
|
|
527
|
-
this.setSelectedTabIndex(value);
|
|
528
|
-
}
|
|
529
|
-
get selectedTabIndex() {
|
|
530
|
-
return this._selectedTabIndex;
|
|
531
|
-
}
|
|
532
|
-
ngOnInit() {
|
|
533
|
-
super.ngOnInit();
|
|
534
|
-
// Read the selected tab index, from path query params
|
|
535
|
-
if (this.tabGroup && this.route && this.queryTabIndexParamName) {
|
|
536
|
-
this.registerSubscription(this.route.queryParams
|
|
537
|
-
.subscribe(queryParams => {
|
|
538
|
-
this.queryParams = { ...queryParams };
|
|
539
|
-
// Parse tab param
|
|
540
|
-
if (this.tabCount > 1 && this.queryTabIndexParamName) {
|
|
541
|
-
const tabIndex = queryParams[this.queryTabIndexParamName];
|
|
542
|
-
this.queryParams[this.queryTabIndexParamName] = tabIndex && parseInt(tabIndex) || undefined;
|
|
543
|
-
if (isNotNil(this.queryParams[this.queryTabIndexParamName])) {
|
|
544
|
-
this.selectedTabIndex = this.queryParams[this.queryTabIndexParamName];
|
|
545
|
-
}
|
|
546
|
-
}
|
|
547
|
-
// Realign tab, after a delay because the tab can be disabled when component is created
|
|
548
|
-
setTimeout(() => this.tabGroup.realignInkBar(), 500);
|
|
549
|
-
}));
|
|
550
|
-
}
|
|
551
|
-
}
|
|
552
|
-
ngOnDestroy() {
|
|
553
|
-
super.ngOnDestroy();
|
|
554
|
-
this.selectedTabIndexChange.complete();
|
|
555
|
-
this.loadingSubject.unsubscribe();
|
|
556
|
-
this.errorSubject.unsubscribe();
|
|
557
|
-
}
|
|
558
|
-
setSelectedTabIndex(value, opts) {
|
|
559
|
-
// Fix value
|
|
560
|
-
if (value < 0) {
|
|
561
|
-
value = 0;
|
|
562
|
-
}
|
|
563
|
-
else if (value > this.tabCount - 1) {
|
|
564
|
-
console.warn(`[tab-editor] Invalid tab index ${value}. Max value is ${this.tabCount - 1}`);
|
|
565
|
-
value = this._selectedTabIndex;
|
|
566
|
-
}
|
|
567
|
-
this._selectedTabIndex = value;
|
|
568
|
-
this.selectedTabIndexChange.next(value);
|
|
569
|
-
if (this.tabGroup && (!opts || opts.realignInkBar !== false)) {
|
|
570
|
-
this.tabGroup.selectedIndex = value;
|
|
571
|
-
this.markForCheck();
|
|
572
|
-
// Wait tab change in UI, before realign ink tab
|
|
573
|
-
setTimeout(() => this.tabGroup.realignInkBar(), 200);
|
|
574
|
-
}
|
|
575
|
-
else if (!opts || opts.emitEvent !== false) {
|
|
576
|
-
this.markForCheck();
|
|
577
|
-
}
|
|
578
|
-
}
|
|
579
|
-
realignInkBar() {
|
|
580
|
-
this.tabGroup?.realignInkBar();
|
|
581
|
-
}
|
|
582
|
-
onTabChange(event, queryTabIndexParamName) {
|
|
583
|
-
queryTabIndexParamName = queryTabIndexParamName || this.queryTabIndexParamName;
|
|
584
|
-
if (!queryTabIndexParamName || !this.route)
|
|
585
|
-
return true; // Skip if tab query param not set, or no route
|
|
586
|
-
if (!this.queryParams || +this.queryParams[queryTabIndexParamName] !== event.index) {
|
|
587
|
-
this.queryParams = this.queryParams || {};
|
|
588
|
-
this.queryParams[queryTabIndexParamName] = event.index;
|
|
589
|
-
if (queryTabIndexParamName === 'tab' && isNotNil(this.queryParams['subtab'])) {
|
|
590
|
-
delete this.queryParams.subtab; // clean subtab
|
|
591
|
-
}
|
|
592
|
-
this.router.navigate(['.'], {
|
|
593
|
-
relativeTo: this.route,
|
|
594
|
-
queryParams: this.queryParams,
|
|
595
|
-
replaceUrl: true
|
|
596
|
-
});
|
|
597
|
-
return true;
|
|
598
|
-
}
|
|
599
|
-
return false;
|
|
600
|
-
}
|
|
601
|
-
/**
|
|
602
|
-
* Action triggered when user swipes
|
|
603
|
-
*/
|
|
604
|
-
onSwipeTab(event) {
|
|
605
|
-
// DEBUG
|
|
606
|
-
// if (this.debug) console.debug("[tab-page] onSwipeTab()");
|
|
607
|
-
// Skip, if not a valid swipe event
|
|
608
|
-
if (!this.enableSwipe || !event
|
|
609
|
-
|| event.defaultPrevented || (event.srcEvent && event.srcEvent.defaultPrevented)
|
|
610
|
-
|| event.pointerType !== 'touch') {
|
|
611
|
-
return false;
|
|
612
|
-
}
|
|
613
|
-
// DEBUG
|
|
614
|
-
//if (this.debug)
|
|
615
|
-
//console.debug("[tab-page] Detected swipe: " + event.type, event);
|
|
616
|
-
let selectTabIndex = this.selectedTabIndex;
|
|
617
|
-
switch (event.type) {
|
|
618
|
-
// Open next tab
|
|
619
|
-
case 'swipeleft':
|
|
620
|
-
const isLast = selectTabIndex >= (this.tabCount - 1);
|
|
621
|
-
selectTabIndex = isLast ? 0 : selectTabIndex + 1;
|
|
622
|
-
break;
|
|
623
|
-
// Open previous tab
|
|
624
|
-
case 'swiperight':
|
|
625
|
-
const isFirst = selectTabIndex <= 0;
|
|
626
|
-
selectTabIndex = isFirst ? this.tabCount : selectTabIndex - 1;
|
|
627
|
-
break;
|
|
628
|
-
// Other case
|
|
629
|
-
default:
|
|
630
|
-
console.error('[tab-page] Unknown swipe action: ' + event.type);
|
|
631
|
-
return false;
|
|
632
|
-
}
|
|
633
|
-
setTimeout(() => {
|
|
634
|
-
this.selectedTabIndex = selectTabIndex;
|
|
635
|
-
this.markForCheck();
|
|
636
|
-
});
|
|
637
|
-
return true;
|
|
638
|
-
}
|
|
639
|
-
onSubTabChange(event) {
|
|
640
|
-
this.onTabChange(event, 'subtab');
|
|
641
|
-
}
|
|
642
|
-
async unload(opts) {
|
|
643
|
-
this.selectedTabIndex = 0;
|
|
644
|
-
await super.unload(opts);
|
|
645
|
-
}
|
|
646
|
-
async saveDirtyChildren() {
|
|
647
|
-
// Save all dirty tables
|
|
648
|
-
const results = await Promise.all([
|
|
649
|
-
...this.tables,
|
|
650
|
-
...this.editors
|
|
651
|
-
]
|
|
652
|
-
.filter(c => c.dirty)
|
|
653
|
-
.map(c => c.save()));
|
|
654
|
-
return !results.some(saved => saved !== true);
|
|
655
|
-
}
|
|
656
|
-
}
|
|
657
|
-
AppTabEditor.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.5", ngImport: i0, type: AppTabEditor, deps: [{ token: i1.ActivatedRoute, optional: true }, { token: i1.Router }, { token: i2.AlertController }, { token: i3.TranslateService }, { token: AppTabEditorOptions, optional: true }], target: i0.ɵɵFactoryTarget.Directive });
|
|
658
|
-
AppTabEditor.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.2.5", type: AppTabEditor, inputs: { queryTabIndexParamName: "queryTabIndexParamName", selectedTabIndex: "selectedTabIndex" }, outputs: { selectedTabIndexChange: "selectedTabIndexChange" }, viewQueries: [{ propertyName: "tabGroup", first: true, predicate: ["tabGroup"], descendants: true, static: true }], usesInheritance: true, ngImport: i0 });
|
|
659
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.2.5", ngImport: i0, type: AppTabEditor, decorators: [{
|
|
660
|
-
type: Directive
|
|
661
|
-
}], ctorParameters: function () { return [{ type: i1.ActivatedRoute, decorators: [{
|
|
662
|
-
type: Optional
|
|
663
|
-
}] }, { type: i1.Router }, { type: i2.AlertController }, { type: i3.TranslateService }, { type: AppTabEditorOptions, decorators: [{
|
|
664
|
-
type: Optional
|
|
665
|
-
}] }]; }, propDecorators: { queryTabIndexParamName: [{
|
|
666
|
-
type: Input
|
|
667
|
-
}], selectedTabIndex: [{
|
|
668
|
-
type: Input
|
|
669
|
-
}], selectedTabIndexChange: [{
|
|
670
|
-
type: Output
|
|
671
|
-
}], tabGroup: [{
|
|
672
|
-
type: ViewChild,
|
|
673
|
-
args: ['tabGroup', { static: true }]
|
|
674
|
-
}] } });
|
|
675
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZWRpdG9yLmNsYXNzLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9jb3JlL2Zvcm0vZWRpdG9yLmNsYXNzLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBZ0IsU0FBUyxFQUFFLFlBQVksRUFBRSxLQUFLLEVBQXFCLFFBQVEsRUFBRSxNQUFNLEVBQUUsU0FBUyxFQUFDLE1BQU0sZUFBZSxDQUFDO0FBRzVILE9BQU8sRUFBa0IsVUFBVSxFQUFrQixNQUFNLGdCQUFnQixDQUFDO0FBRTVFLE9BQU8sRUFBQyxlQUFlLEVBQUUsT0FBTyxFQUFFLFlBQVksRUFBZ0IsTUFBTSxNQUFNLENBQUM7QUFDM0UsT0FBTyxFQUFDLFFBQVEsRUFBQyxNQUFNLHNCQUFzQixDQUFDO0FBQzlDLE9BQU8sRUFBQyxPQUFPLEVBQUMsTUFBTSxjQUFjLENBQUM7QUFDckMsT0FBTyxFQUFDLG1CQUFtQixFQUFDLE1BQU0sOEJBQThCLENBQUM7QUFDakUsT0FBTyxFQUFDLGVBQWUsRUFBRSxZQUFZLEVBQTJCLE1BQU0sY0FBYyxDQUFDO0FBQ3JGLE9BQU8sRUFBbUIsTUFBTSxFQUFDLE1BQU0sMkJBQTJCLENBQUM7QUFFbkUsT0FBTyxFQUFDLFlBQVksRUFBQyxNQUFNLDhCQUE4QixDQUFDO0FBQzFELE9BQU8sRUFBQyxRQUFRLEVBQUUsUUFBUSxFQUFDLE1BQU0sd0JBQXdCLENBQUM7QUFFMUQsT0FBTyxFQUFDLGVBQWUsRUFBQyxNQUFNLGdCQUFnQixDQUFDO0FBQy9DLE9BQU8sRUFBQyxZQUFZLEVBQWtCLFdBQVcsRUFBQyxNQUFNLDBCQUEwQixDQUFDOzs7OztBQWVuRixNQUFNLE9BQU8sbUJBQW1CO0NBZ0IvQjtBQUdELGtFQUFrRTtBQUNsRSxNQUFNLE9BQWdCLFNBQVM7SUF1STdCLFlBQ1ksS0FBcUIsRUFDckIsTUFBYyxFQUNkLFNBQTBCLEVBQzFCLFNBQTJCO1FBSDNCLFVBQUssR0FBTCxLQUFL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QUFDLEtBQUssRUFBRSxRQUFRLENBQUMsQ0FBQztJQUNwQyxDQUFDO0lBRUQsS0FBSyxDQUFDLE1BQU0sQ0FBQyxJQUE4QjtRQUN6QyxJQUFJLENBQUMsZ0JBQWdCLEdBQUcsQ0FBQyxDQUFDO1FBQzFCLE1BQU0sS0FBSyxDQUFDLE1BQU0sQ0FBQyxJQUFJLENBQUMsQ0FBQztJQUMzQixDQUFDO0lBSVMsS0FBSyxDQUFDLGlCQUFpQjtRQUMvQix3QkFBd0I7UUFDeEIsTUFBTSxPQUFPLEdBQUcsTUFBTSxPQUFPLENBQUMsR0FBRyxDQUFDO1lBQ2hDLEdBQUcsSUFBSSxDQUFDLE1BQU07WUFDZCxHQUFHLElBQUksQ0FBQyxPQUFPO1NBQ2hCO2FBQ0UsTUFBTSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEtBQUssQ0FBQzthQUNwQixHQUFHLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsSUFBSSxFQUFFLENBQUMsQ0FBQyxDQUFDO1FBRXZCLE9BQU8sQ0FBQyxPQUFPLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxFQUFFLENBQUMsS0FBSyxLQUFLLElBQUksQ0FBQyxDQUFDO0lBQ2hELENBQUM7O3lHQXBNbUIsWUFBWTs2RkFBWixZQUFZOzJGQUFaLFlBQVk7a0JBRmpDLFNBQVM7OzBCQTJCTCxRQUFROzswQkFJUixRQUFROzRDQWxCRixzQkFBc0I7c0JBQTlCLEtBQUs7Z0JBRU8sZ0JBQWdCO3NCQUE1QixLQUFLO2dCQU9hLHNCQUFzQjtzQkFBeEMsTUFBTTtnQkFFa0MsUUFBUTtzQkFBaEQsU0FBUzt1QkFBQyxVQUFVLEVBQUUsRUFBRSxNQUFNLEVBQUUsSUFBSSxFQUFFIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHtBZnRlclZpZXdJbml0LCBEaXJlY3RpdmUsIEV2ZW50RW1pdHRlciwgSW5wdXQsIE9uRGVzdHJveSwgT25Jbml0LCBPcHRpb25hbCwgT3V0cHV0LCBWaWV3Q2hpbGR9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHtBY3RpdmF0ZWRSb3V0ZSwgUGFyYW1zLCBSb3V0ZXJ9IGZyb20gJ0Bhbmd1bGFyL3JvdXRlcic7XG5pbXBvcnQge01hdFRhYkNoYW5nZUV2ZW50LCBNYXRUYWJHcm91cH0gZnJvbSAnQGFuZ3VsYXIvbWF0ZXJpYWwvdGFicyc7XG5pbXBvcnQge0FsZXJ0Q29udHJvbGxlciwgSW9uQ29udGVudCwgVG9hc3RDb250cm9sbGVyfSBmcm9tICdAaW9uaWMvYW5ndWxhcic7XG5pbXBvcnQge1RyYW5zbGF0ZVNlcnZpY2V9IGZyb20gJ0BuZ3gtdHJhbnNsYXRlL2NvcmUnO1xuaW1wb3J0IHtCZWhhdmlvclN1YmplY3QsIFN1YmplY3QsIFN1YnNjcmlwdGlvbiwgVGVhcmRvd25Mb2dpY30gZnJvbSAncnhqcyc7XG5pbXBvcnQge0FwcFRhYmxlfSBmcm9tICcuLi90YWJsZS90YWJsZS5jbGFzcyc7XG5pbXBvcnQge0FwcEZvcm19IGZyb20gJy4vZm9ybS5jbGFzcyc7XG5pbXBvcnQge0Zvcm1CdXR0b25zQmFyVG9rZW59IGZyb20gJy4vZm9ybS1idXR0b25zLWJhci5jb21wb25lbnQnO1xuaW1wb3J0IHtBcHBGb3JtUHJvdmlkZXIsIEFwcEZvcm1VdGlscywgSUFwcEZvcm0sIElBcHBGb3JtR2V0dGVyfSBmcm9tICcuL2Zvcm0udXRpbHMnO1xuaW1wb3J0IHtTaG93VG9hc3RPcHRpb25zLCBUb2FzdHN9IGZyb20gJy4uLy4uL3NoYXJlZC90b2FzdC90b2FzdHMnO1xuaW1wb3J0IHtIYW1tZXJTd2lwZUV2ZW50fSBmcm9tICcuLi8uLi9zaGFyZWQvZ2VzdHVyZS9oYW1tZXIudXRpbHMnO1xuaW1wb3J0IHtUb29sYmFyVG9rZW59IGZyb20gJy4uLy4uL3NoYXJlZC90b29sYmFyL3Rvb2xiYXInO1xuaW1wb3J0IHtpc05vdE5pbCwgdG9OdW1iZXJ9IGZyb20gJy4uLy4uL3NoYXJlZC9mdW5jdGlvbnMnO1xuaW1wb3J0IHtDYW5MZWF2ZX0gZnJvbSAnLi4vLi4vc2hhcmVkL2d1YXJkL2NvbXBvbmVudC1kaXJ0eS5ndWFyZCc7XG5pbXBvcnQge0Fic3RyYWN0Q29udHJvbH0gZnJvbSAnQGFuZ3VsYXIvZm9ybXMnO1xuaW1wb3J0IHt3YWl0Rm9yRmFsc2UsIFdhaXRGb3JPcHRpb25zLCB3YWl0Rm9yVHJ1ZX0gZnJvbSAnLi4vLi4vc2hhcmVkL29ic2VydmFibGVzJztcblxuZXhwb3J0IGludGVyZmFjZSBJQXBwRWRpdG9yIGV4dGVuZHMgQ2FuTGVhdmUsIElBcHBGb3JtIHtcbiAgc2F2ZShldmVudD86IEV2ZW50LCBvcHRpb25zPzogYW55KTogUHJvbWlzZTxib29sZWFuPjtcbiAgY2FuY2VsKGV2ZW50PzogRXZlbnQpOiBQcm9taXNlPHZvaWQ+O1xuICBhZGRDaGlsZEZvcm0oZm9ybTogSUFwcEZvcm0gfCBJQXBwRm9ybUdldHRlcik6IHZvaWQ7XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgSUFwcFRhYkVkaXRvciBleHRlbmRzIElBcHBFZGl0b3Ige1xuICBzZWxlY3RlZFRhYkluZGV4OiBudW1iZXI7XG4gIHNldFNlbGVjdGVkVGFiSW5kZXgodmFsdWU6IG51bWJlciwgb3B0cz86IHtlbWl0RXZlbnQ/OiBib29sZWFuOyByZWFsaWduSW5rQmFyPzogYm9vbGVhbjt9KTogdm9pZDtcbiAgdW5sb2FkKG9wdHM/OiB7ZW1pdEV2ZW50PzogYm9vbGVhbn0pOiBQcm9taXNlPHZvaWQ+O1xuICByZWFsaWduSW5rQmFyKCk7XG59XG5cbmV4cG9ydCBjbGFzcyBBcHBUYWJFZGl0b3JPcHRpb25zIHtcblxuICAvKipcbiAgICogTnVtYmVyIG9mIHRhYi4gMSBieSBkZWZhdWx0XG4gICAqL1xuICB0YWJDb3VudD86IG51bWJlcjtcblxuICAvKipcbiAgICogJzIwMG1zJyBieSBkZWZhdWx0XG4gICAqL1xuICB0YWJHcm91cEFuaW1hdGlvbkR1cmF0aW9uPzogc3RyaW5nO1xuXG4gIC8qKlxuICAgKiBTaG91bGQgZW5hYmxlIHN3aXBlIGJldHdlZW4gdGFiLCBvbiB0b3VjaCBzY3JlZW5cbiAgICovXG4gIGVuYWJsZVN3aXBlPzogYm9vbGVhbjsgLy8gdHJ1ZSBieSBkZWZhdWx0XG59XG5cbkBEaXJlY3RpdmUoKVxuLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEBhbmd1bGFyLWVzbGludC9kaXJlY3RpdmUtY2xhc3Mtc3VmZml4XG5leHBvcnQgYWJzdHJhY3QgY2xhc3MgQXBwRWRpdG9yPFQgPSBhbnksIElEID0gbnVtYmVyLCBPID0gYW55PlxuICBpbXBsZW1lbnRzIElBcHBFZGl0b3IsIE9uSW5pdCwgT25EZXN0cm95LCBBZnRlclZpZXdJbml0IHtcblxuICBwcml2YXRlIF9jaGlsZHJlbjogSUFwcEZvcm1bXTtcbiAgcHJpdmF0ZSBfc3Vic2NyaXB0aW9uID0gbmV3IFN1YnNjcmlwdGlvbigpO1xuXG4gIHByb3RlY3RlZCBfZW5hYmxlZCA9IGZhbHNlO1xuICBwcm90ZWN0ZWQgdG9hc3RDb250cm9sbGVyOiBUb2FzdENvbnRyb2xsZXI7XG4gIHByb3RlY3RlZCByZWFkb25seSBkZXN0cm95U3ViamVjdCA9IG5ldyBTdWJqZWN0PHZvaWQ+KCk7XG5cbiAgcmVhZG9ubHkgcmVhZHlTdWJqZWN0ID0gbmV3IEJlaGF2aW9yU3ViamVjdDxib29sZWFuPihmYWxzZSk7XG4gIHJlYWRvbmx5IGRpcnR5U3ViamVjdCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8Ym9vbGVhbj4oZmFsc2UpO1xuICByZWFkb25seSBsb2FkaW5nU3ViamVjdCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8Ym9vbGVhbj4odHJ1ZSk7XG4gIHJlYWRvbmx5IGVycm9yU3ViamVjdCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8c3RyaW5nPih1bmRlZmluZWQpO1xuICByZWFkb25seSBzYXZpbmdTdWJqZWN0ID0gbmV3IEJlaGF2aW9yU3ViamVjdDxib29sZWFuPihmYWxzZSk7XG4gIHJlYWRvbmx5IHRvdWNoZWRTdWJqZWN0ID0gbmV3IEJlaGF2aW9yU3ViamVjdDxib29sZWFuPihmYWxzZSk7XG5cbiAgZGVidWcgPSBmYWxzZTtcbiAgcHJldmlvdXNEYXRhSWQ6IElEO1xuICBzdWJtaXR0ZWQgPSBmYWxzZTtcbiAgcXVlcnlQYXJhbXM6IFBhcmFtcztcbiAgaTE4bkNvbnRleHQ6IHtcbiAgICBwcmVmaXg6IHN0cmluZztcbiAgICBzdWZmaXg6IHN0cmluZztcbiAgfTtcblxuICAvKipcbiAgICogIEBkZXByZWNhdGVkXG4gICAqL1xuICBwcm90ZWN0ZWQgc2V0IF9sb2FkaW5nKHZhbHVlOiBib29sZWFuKSB7XG4gICAgdGhpcy5sb2FkaW5nU3ViamVjdC5uZXh0KHZhbHVlKTtcbiAgfVxuXG4gIC8qKlxuICAgKiAgQGRlcHJlY2F0ZWRcbiAgICovXG4gIHByb3RlY3RlZCBnZXQgX2xvYWRpbmcoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMubG9hZGluZ1N1YmplY3QudmFsdWU7XG4gIH1cbiAgLyoqXG4gICAqICBAZGVwcmVjYXRlZFxuICAgKi9cbiAgcHJvdGVjdGVkIGdldCBfJHJlYWR5KCk6IEJlaGF2aW9yU3ViamVjdDxib29sZWFuPiB7XG4gICAgcmV0dXJuIHRoaXMucmVhZHlTdWJqZWN0O1xuICB9XG4gIC8qKlxuICAgKiAgQGRlcHJlY2F0ZWRcbiAgICovXG4gIHByb3RlY3RlZCBnZXQgXyRsb2FkaW5nKCk6IEJlaGF2aW9yU3ViamVjdDxib29sZWFuPiB7XG4gICAgcmV0dXJuIHRoaXMubG9hZGluZ1N1YmplY3Q7XG4gIH1cblxuICBnZXQgZXJyb3IoKTogc3RyaW5nIHtcbiAgICByZXR1cm4gdGhpcy5lcnJvclN1YmplY3QudmFsdWU7XG4gIH1cblxuICBzZXQgZXJyb3IoZXJyb3I6IHN0cmluZykge1xuICAgIHRoaXMuc2V0RXJyb3IoZXJyb3IpO1xuICB9XG5cbiAgZ2V0IHNhdmluZygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5zYXZpbmdTdWJqZWN0LnZhbHVlIHx8IHRoaXMuZWRpdG9ycz8uc29tZShlID0+IGUuc2F2aW5nKTtcbiAgfVxuXG4gIGdldCBkZXN0cm95ZWQoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMuZGVzdHJveVN1YmplY3Q/LmNsb3NlZCAhPT0gZmFsc2VcbiAgfVxuXG4gIEBWaWV3Q2hpbGQoVG9vbGJhclRva2VuKSB0b29sYmFyOiBUb29sYmFyVG9rZW58bnVsbCA9IG51bGw7XG4gIEBWaWV3Q2hpbGQoRm9ybUJ1dHRvbnNCYXJUb2tlbiwgeyBzdGF0aWM6IHRydWUgfSkgZm9ybUJ1dHRvbnNCYXI6IEZvcm1CdXR0b25zQmFyVG9rZW58bnVsbCA9IG51bGw7XG4gIEBWaWV3Q2hpbGQoSW9uQ29udGVudCwge3N0YXRpYzogdHJ1ZX0pIGNvbnRlbnQ6IElvbkNvbnRlbnQ7XG5cbiAgZ2V0IHRhYmxlcygpOiBBcHBUYWJsZTxhbnk+W10ge1xuICAgIHJldHVybiB0aGlzLl9jaGlsZHJlbiAmJiAodGhpcy5fY2hpbGRyZW4uZmlsdGVyKGMgPT4gYyBpbnN0YW5jZW9mIEFwcFRhYmxlKSBhcyBBcHBUYWJsZTxhbnk+W10pO1xuICB9XG4gIGdldCBmb3JtcygpOiBBcHBGb3JtPGFueT5bXSB7XG4gICAgcmV0dXJuIHRoaXMuX2NoaWxkcmVuICYmICh0aGlzLl9jaGlsZHJlbi5maWx0ZXIoYyA9PiBjIGluc3RhbmNlb2YgQXBwRm9ybSkgYXMgQXBwRm9ybTxhbnk+W10pO1xuICB9XG4gIGdldCBlZGl0b3JzKCk6IEFwcEVkaXRvcjxhbnk+W10ge1xuICAgIHJldHVybiB0aGlzLl9jaGlsZHJlbiAmJiAodGhpcy5fY2hpbGRyZW4uZmlsdGVyKGMgPT4gYyBpbnN0YW5jZW9mIEFwcEVkaXRvcikgYXMgQXBwRWRpdG9yW10pO1xuICB9XG4gIGdldCBkaXJ0eSgpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5kaXJ0eVN1YmplY3QudmFsdWUgfHwgKHRoaXMuX2NoaWxkcmVuICYmIHRoaXMuX2NoaWxkcmVuLmZpbmRJbmRleChjID0+IGMuZW5hYmxlZCAmJiBjLmRpcnR5KSAhPT0gLTEpIHx8IGZhbHNlO1xuICB9XG5cbiAgLyoqXG4gICAqIElzIHZhbGlkICh0YWJsZXMgYW5kIGZvcm1zKVxuICAgKi9cbiAgZ2V0IHZhbGlkKCk6IGJvb2xlYW4ge1xuICAgIC8vIEltcG9ydGFudDogU2hvdWxkIGJlIG5vdCBpbnZhbGlkIEFORCBub3QgcGVuZGluZywgc28gdXNlICchdmFsaWQnIChETyBOT1QgdXNlICdpbnZhbGlkJylcbiAgICByZXR1cm4gIXRoaXMuX2NoaWxkcmVuIHx8IHRoaXMuX2NoaWxkcmVuLmZpbmRJbmRleChjID0+IGMuZW5hYmxlZCAmJiAhYy52YWxpZCkgPT09IC0xO1xuICB9XG5cbiAgZ2V0IGludmFsaWQoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuICh0aGlzLl9jaGlsZHJlbiAmJiB0aGlzLl9jaGlsZHJlbi5maW5kSW5kZXgoYyA9PiBjLmVuYWJsZWQgJiYgYy5pbnZhbGlkKSAhPT0gLTEpIHx8IGZhbHNlO1xuICB9XG5cbiAgZ2V0IHBlbmRpbmcoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuICh0aGlzLl9jaGlsZHJlbiAmJiB0aGlzLl9jaGlsZHJlbi5maW5kSW5kZXgoYyA9PiBjLmVuYWJsZWQgJiYgYy5wZW5kaW5nKSAhPT0gLTEpIHx8IGZhbHNlO1xuICB9XG5cbiAgZ2V0IGxvYWRpbmcoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMubG9hZGluZ1N1YmplY3QudmFsdWUgfHwgKHRoaXMuX2NoaWxkcmVuICYmIHRoaXMuX2NoaWxkcmVuLmZpbmRJbmRleChjID0+IGMuZW5hYmxlZCAmJiBjLmxvYWRpbmcpICE9PSAtMSkgfHwgZmFsc2U7XG4gIH1cblxuICBnZXQgbG9hZGVkKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiAhdGhpcy5sb2FkaW5nU3ViamVjdC52YWx1ZSAmJiAoIXRoaXMuX2NoaWxkcmVuIHx8IHRoaXMuX2NoaWxkcmVuLmZpbmRJbmRleChjID0+IGMuZW5hYmxlZCAmJiBjLmxvYWRpbmcpID09PSAtMSkgfHwgZmFsc2U7XG4gIH1cblxuICBnZXQgdG91Y2hlZCgpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy50b3VjaGVkU3ViamVjdC52YWx1ZSB8fCAodGhpcy5fY2hpbGRyZW4gJiYgdGhpcy5fY2hpbGRyZW4uZmluZEluZGV4KGMgPT4gYy5lbmFibGVkICYmIGMudG91Y2hlZCkgIT09IC0xKSB8fCBmYWxzZTtcbiAgfVxuXG4gIGdldCB1bnRvdWNoZWQoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuICF0aGlzLnRvdWNoZWRTdWJqZWN0LnZhbHVlICYmICghdGhpcy5fY2hpbGRyZW4gfHwgdGhpcy5fY2hpbGRyZW4uZmluZEluZGV4KGMgPT4gYy5lbmFibGVkICYmIGMudG91Y2hlZCkgPT09IC0xKSB8fCBmYWxzZTtcbiAgfVxuXG4gIGdldCBlbmFibGVkKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLl9lbmFibGVkO1xuICB9XG5cbiAgZ2V0IGRpc2FibGVkKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiAhdGhpcy5fZW5hYmxlZDtcbiAgfVxuXG4gIGdldCBjaGlsZHJlbigpOiBJQXBwRm9ybVtdIHtcbiAgICByZXR1cm4gdGhpcy5fY2hpbGRyZW47XG4gIH1cblxuICBnZXQgZW1wdHkoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuICF0aGlzLl9lbmFibGVkO1xuICB9XG5cbiAgYWJzdHJhY3QgZ2V0IGlzTmV3RGF0YSgpOiBib29sZWFuO1xuXG4gIHByb3RlY3RlZCBjb25zdHJ1Y3RvcihcbiAgICBwcm90ZWN0ZWQgcm91dGU6IEFjdGl2YXRlZFJvdXRlLFxuICAgIHByb3RlY3RlZCByb3V0ZXI6IFJvdXRlcixcbiAgICBwcm90ZWN0ZWQgYWxlcnRDdHJsOiBBbGVydENvbnRyb2xsZXIsXG4gICAgcHJvdGVjdGVkIHRyYW5zbGF0ZTogVHJhbnNsYXRlU2VydmljZVxuICApIHtcbiAgfVxuXG4gIG5nT25Jbml0KCkge1xuXG4gICAgaWYgKHRoaXMuZm9ybUJ1dHRvbnNCYXIpIHtcbiAgICAgIHRoaXMucmVnaXN0ZXJTdWJzY3JpcHRpb24odGhpcy5mb3JtQnV0dG9uc0Jhci5vbkJhY2suc3Vic2NyaWJlKGV2ZW50ID0+IHRoaXMuZ29CYWNrKGV2ZW50KSkpO1xuICAgIH1cbiAgfVxuXG4gIG5nQWZ0ZXJWaWV3SW5pdCgpIHtcbiAgICAvLyBDYW4gYmUgb3ZlcnJpZGRlbiBieSBzdWJjbGFzc2VzXG4gIH1cblxuICBuZ09uRGVzdHJveSgpIHtcbiAgICB0aGlzLl9zdWJzY3JpcHRpb24udW5zdWJzY3JpYmUoKTtcblxuICAgIHRoaXMucmVhZHlTdWJqZWN0LnVuc3Vic2NyaWJlKCk7XG4gICAgdGhpcy5sb2FkaW5nU3ViamVjdC51bnN1YnNjcmliZSgpO1xuICAgIHRoaXMuZXJyb3JTdWJqZWN0LnVuc3Vic2NyaWJlKCk7XG5cbiAgICB0aGlzLmRlc3Ryb3lTdWJqZWN0Lm5leHQoKTtcbiAgICB0aGlzLmRlc3Ryb3lTdWJqZWN0LnVuc3Vic2NyaWJlKCk7XG4gIH1cblxuICBhZGRDaGlsZEZvcm0oZm9ybTogSUFwcEZvcm0gfCBJQXBwRm9ybUdldHRlcikge1xuICAgIGlmICghZm9ybSkgdGhyb3cgbmV3IEVycm9yKCdUcnlpbmcgdG8gcmVnaXN0ZXIgYW4gdW5kZWZpbmVkIGNoaWxkIGZvcm0nKTtcbiAgICB0aGlzLl9jaGlsZHJlbiA9IHRoaXMuX2NoaWxkcmVuIHx8IFtdO1xuICAgIGlmICh0eXBlb2YgZm9ybSA9PT0gJ2Z1bmN0aW9uJykge1xuICAgICAgdGhpcy5fY2hpbGRyZW4ucHVzaChuZXcgQXBwRm9ybVByb3ZpZGVyKGZvcm0pKTtcbiAgICB9XG4gICAgZWxzZSB7XG4gICAgICB0aGlzLl9jaGlsZHJlbi5wdXNoKGZvcm0pO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIGFkZENoaWxkRm9ybXMoZm9ybXM6IChJQXBwRm9ybSB8IElBcHBGb3JtR2V0dGVyKVtdKSB7XG4gICAgKGZvcm1zIHx8IFtdKS5mb3JFYWNoKGZvcm0gPT4gdGhpcy5hZGRDaGlsZEZvcm0oZm9ybSkpO1xuICB9XG5cbiAgcmVtb3ZlQ2hpbGRGb3JtKGZvcm06IElBcHBGb3JtIHwgSUFwcEZvcm1HZXR0ZXIpOiBJQXBwRm9ybSB8IElBcHBGb3JtR2V0dGVyIHtcbiAgICBpZiAoIWZvcm0pIHRocm93IG5ldyBFcnJvcignVHJ5aW5nIHRvIHJlbW92ZSBhbiB1bmRlZmluZWQgY2hpbGQgZm9ybScpO1xuICAgIGNvbnN0IGluZGV4ID0gKHRoaXMuX2NoaWxkcmVuIHx8IFtdKS5maW5kSW5kZXgoYyA9PiBjID09PSBmb3JtKTtcbiAgICBpZiAoaW5kZXggIT09IC0xKSB7XG4gICAgICByZXR1cm4gdGhpcy5fY2hpbGRyZW4uc3BsaWNlKGluZGV4LCAxKVswXTtcbiAgICB9XG4gICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgfVxuXG4gIGRpc2FibGUob3B0cz86IHtvbmx5U2VsZj86IGJvb2xlYW47IGVtaXRFdmVudD86IGJvb2xlYW4gfSkge1xuICAgIHRoaXMuX2VuYWJsZWQgPSBmYWxzZTtcbiAgICB0aGlzLl9jaGlsZHJlbj8uZm9yRWFjaChjID0+IGMuZGlzYWJsZShvcHRzKSk7XG4gICAgaWYgKCF0aGlzLmxvYWRpbmcgJiYgKCFvcHRzIHx8IG9wdHMuZW1pdEV2ZW50ICE9PSBmYWxzZSkpIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gIH1cblxuICBlbmFibGUob3B0cz86IHtvbmx5U2VsZj86IGJvb2xlYW47IGVtaXRFdmVudD86IGJvb2xlYW4gfSkge1xuICAgIHRoaXMuX2VuYWJsZWQgPSB0cnVlO1xuICAgIHRoaXMuX2NoaWxkcmVuPy5mb3JFYWNoKGMgPT4gYy5lbmFibGUob3B0cykpO1xuICAgIGlmICghdGhpcy5sb2FkaW5nICYmICghb3B0cyB8fCBvcHRzLmVtaXRFdmVudCAhPT0gZmFsc2UpKSB0aGlzLm1hcmtGb3JDaGVjaygpO1xuICB9XG5cbiAgbWFya0FzUHJpc3RpbmUob3B0cz86IHtvbmx5U2VsZj86IGJvb2xlYW47IGVtaXRFdmVudD86IGJvb2xlYW4gfSkge1xuICAgIHRoaXMuZXJyb3IgPSBudWxsO1xuICAgIHRoaXMuc3VibWl0dGVkID0gZmFsc2U7XG4gICAgaWYgKHRoaXMuZGlydHlTdWJqZWN0LnZhbHVlICE9PSBmYWxzZSkge1xuICAgICAgdGhpcy5kaXJ0eVN1YmplY3QubmV4dChmYWxzZSk7XG4gICAgfVxuICAgIHRoaXMuX2NoaWxkcmVuPy5mb3JFYWNoKGMgPT4gYy5tYXJrQXNQcmlzdGluZShvcHRzKSk7XG4gICAgaWYgKCF0aGlzLmxvYWRpbmcgJiYgKCFvcHRzIHx8IG9wdHMuZW1pdEV2ZW50ICE9PSBmYWxzZSkpIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gIH1cblxuICBtYXJrQXNVbnRvdWNoZWQob3B0cz86IHtvbmx5U2VsZj86IGJvb2xlYW47IGVtaXRFdmVudD86IGJvb2xlYW4gfSkge1xuICAgIGlmICh0aGlzLnRvdWNoZWRTdWJqZWN0LnZhbHVlICE9PSBmYWxzZSkge1xuICAgICAgdGhpcy50b3VjaGVkU3ViamVjdC5uZXh0KGZhbHNlKTtcbiAgICB9XG4gICAgdGhpcy5fY2hpbGRyZW4/LmZvckVhY2goYyA9PiBjLm1hcmtBc1VudG91Y2hlZCgpKTtcbiAgICBpZiAoIXRoaXMubG9hZGluZyAmJiAoIW9wdHMgfHwgb3B0cy5lbWl0RXZlbnQgIT09IGZhbHNlKSkgdGhpcy5tYXJrRm9yQ2hlY2soKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBAZGVwcmVjYXRlZCBwcmVmZXIgdG8gdXNlIG1hcmtBbGxBc1RvdWNoZWQoKVxuICAgKiBAcGFyYW0gb3B0c1xuICAgKi9cbiAgbWFya0FzVG91Y2hlZChvcHRzPzoge29ubHlTZWxmPzogYm9vbGVhbjsgZW1pdEV2ZW50PzogYm9vbGVhbiB9KSB7XG4gICAgaWYgKCF0aGlzLnRvdWNoZWRTdWJqZWN0LnZhbHVlICE9PSB0cnVlKSB7XG4gICAgICB0aGlzLnRvdWNoZWRTdWJqZWN0Lm5leHQodHJ1ZSk7XG4gICAgfVxuICAgIHRoaXMuX2NoaWxkcmVuPy5mb3JFYWNoKGMgPT4gYy5tYXJrQXNUb3VjaGVkKG9wdHMpKTtcbiAgICBpZiAoIXRoaXMubG9hZGluZyAmJiAoIW9wdHMgfHwgb3B0cy5lbWl0RXZlbnQgIT09IGZhbHNlKSkgdGhpcy5tYXJrRm9yQ2hlY2soKTtcbiAgfVxuXG4gIG1hcmtBbGxBc1RvdWNoZWQob3B0cz86IHtlbWl0RXZlbnQ/OiBib29sZWFuIH0pIHtcbiAgICBpZiAodGhpcy50b3VjaGVkU3ViamVjdC52YWx1ZSAhPT0gdHJ1ZSkge1xuICAgICAgdGhpcy50b3VjaGVkU3ViamVjdC5uZXh0KHRydWUpO1xuICAgIH1cbiAgICB0aGlzLl9jaGlsZHJlbj8uZm9yRWFjaChjID0+IGMubWFya0FsbEFzVG91Y2hlZChvcHRzKSk7XG4gICAgaWYgKCF0aGlzLmxvYWRpbmcgJiYgKCFvcHRzIHx8IG9wdHMuZW1pdEV2ZW50ICE9PSBmYWxzZSkpIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gIH1cblxuICBtYXJrQXNEaXJ0eShvcHRzPzoge29ubHlTZWxmPzogYm9vbGVhbjsgZW1pdEV2ZW50PzogYm9vbGVhbjt9KXtcbiAgICBpZiAoIXRoaXMuZGlydHlTdWJqZWN0LnZhbHVlKSB7XG4gICAgICB0aGlzLmRpcnR5U3ViamVjdC5uZXh0KHRydWUpO1xuICAgICAgaWYgKCF0aGlzLmxvYWRpbmcgJiYgKCFvcHRzIHx8IG9wdHMuZW1pdEV2ZW50ICE9PSBmYWxzZSkpIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gICAgfVxuICB9XG5cbiAgbWFya0FzTG9hZGluZyhvcHRzPzoge29ubHlTZWxmPzogYm9vbGVhbjsgZW1pdEV2ZW50PzogYm9vbGVhbjt9KXtcbiAgICBpZiAoIXRoaXMubG9hZGluZ1N1YmplY3QudmFsdWUpIHtcbiAgICAgIHRoaXMubG9hZGluZ1N1YmplY3QubmV4dCh0cnVlKTtcbiAgICAgIGlmICghb3B0cyB8fCBvcHRzLmVtaXRFdmVudCAhPT0gZmFsc2UpIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gICAgfVxuICB9XG5cbiAgbWFya0FzTG9hZGVkKG9wdHM/OiB7XG4gICAgb25seVNlbGY/OiBib29sZWFuO1xuICAgIGVtaXRFdmVudD86IGJvb2xlYW47XG4gIH0pe1xuICAgIGlmICh0aGlzLmxvYWRpbmdTdWJqZWN0LnZhbHVlKSB7XG4gICAgICB0aGlzLmxvYWRpbmdTdWJqZWN0Lm5leHQoZmFsc2UpO1xuICAgICAgaWYgKCFvcHRzIHx8IG9wdHMub25seVNlbGYgIT09IHRydWUpIHtcbiAgICAgICAgLy8gRW1pdCB0byBjaGlsZHJlbiBmb3JtcyBhbmQgZWRpdG9yc1xuICAgICAgICAvLyBub3RlOiB0YWJsZXMgc2hvdWxkIGJlIGNoYW5nZWQgYnkgcGFyZW50XG4gICAgICAgIHRoaXMuZm9ybXM/LmZvckVhY2goZiA9PiBmLm1hcmtBc0xvYWRlZChvcHRzKSk7XG4gICAgICAgIHRoaXMuZWRpdG9ycz8uZm9yRWFjaChlID0+IGUubWFya0FzTG9hZGVkKG9wdHMpKTtcbiAgICAgIH1cbiAgICAgIGlmICghb3B0cyB8fCBvcHRzLmVtaXRFdmVudCAhPT0gZmFsc2UpIHtcbiAgICAgICAgdGhpcy5tYXJrRm9yQ2hlY2soKTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICBtYXJrQXNSZWFkeShvcHRzPzoge2VtaXRFdmVudD86IGJvb2xlYW4gfSkge1xuICAgIHRoaXMuX2NoaWxkcmVuPy5mb3JFYWNoKGMgPT4gYy5tYXJrQXNSZWFkeShvcHRzKSk7XG4gICAgdGhpcy5yZWFkeVN1YmplY3QubmV4dCh0cnVlKTtcbiAgfVxuXG4gIHJlYWR5KG9wdHM/OiBXYWl0Rm9yT3B0aW9ucyk6IFByb21pc2U8dm9pZD4ge1xuICAgIGlmICh0aGlzLnJlYWR5U3ViamVjdC52YWx1ZSkgcmV0dXJuIFByb21pc2UucmVzb2x2ZSgpO1xuICAgIHJldHVybiB3YWl0Rm9yVHJ1ZSh0aGlzLnJlYWR5U3ViamVjdCwgb3B0cyk7XG4gIH1cblxuICB3YWl0SWRsZShvcHRzPzogV2FpdEZvck9wdGlvbnMpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBpZiAoIXRoaXMubG9hZGluZ1N1YmplY3QudmFsdWUpIHJldHVybiBQcm9taXNlLnJlc29sdmUoKTtcbiAgICByZXR1cm4gd2FpdEZvckZhbHNlKHRoaXMubG9hZGluZ1N1YmplY3QsIG9wdHMpO1xuICB9XG5cbiAgbWFya0FzU2F2aW5nKG9wdHM/OiB7IGVtaXRFdmVudD86IGJvb2xlYW4gfSl7XG4gICAgaWYgKHRoaXMuc2F2aW5nU3ViamVjdC52YWx1ZSAhPT0gdHJ1ZSkge1xuICAgICAgdGhpcy5zYXZpbmdTdWJqZWN0Lm5leHQodHJ1ZSk7XG4gICAgICBpZiAoIW9wdHMgfHwgb3B0cy5lbWl0RXZlbnQgIT09IGZhbHNlKSB0aGlzLm1hcmtGb3JDaGVjaygpO1xuICAgIH1cbiAgfVxuXG4gIG1hcmtBc1NhdmVkKG9wdHM/OiB7IGVtaXRFdmVudD86IGJvb2xlYW4gfSl7XG4gICAgaWYgKHRoaXMuc2F2aW5nU3ViamVjdC52YWx1ZSAhPT0gZmFsc2UpIHtcbiAgICAgIHRoaXMuc2F2aW5nU3ViamVjdC5uZXh0KGZhbHNlKTtcbiAgICAgIGlmICghb3B0cyB8fCBvcHRzLmVtaXRFdmVudCAhPT0gZmFsc2UpIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gICAgfVxuICB9XG5cbiAgYXN5bmMgY2FuY2VsKGV2ZW50PzogRXZlbnQpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBpZiAodGhpcy5pc05ld0RhdGEpIHtcbiAgICAgIGF3YWl0IHRoaXMudW5sb2FkKCk7IC8vIGFzeW5jIHJlc2V0XG4gICAgfVxuICAgIGVsc2UgaWYgKHRoaXMuZGlydHkpe1xuICAgICAgYXdhaXQgdGhpcy5yZWxvYWQoKTsgLy8gYXN5bmMgcmVsb2FkXG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIFVubG9hZCB0aGUgcGFnZSAocmVtb3ZlIGFsbCBkYXRhKS4gVXNlZnVsIHdoZW4gcmV1c2luZyBhbmd1bGFyIGNhY2hlIGEgY2FuY2VsbGVkIHBhZ2VcbiAgICpcbiAgICogQHBhcmFtIG9wdHNcbiAgICovXG4gIGFzeW5jIHVubG9hZChvcHRzPzoge2VtaXRFdmVudD86IGJvb2xlYW4gfSk6IFByb21pc2U8dm9pZD4ge1xuICAgIGNvbnNvbGUuZGVidWcoJ1tlZGl0b3JdIFVubG9hZGluZyBkYXRhLi4uJyk7XG4gICAgdGhpcy5tYXJrQXNMb2FkaW5nKCk7XG4gICAgdGhpcy5fY2hpbGRyZW4/LmZvckVhY2goZiA9PiB7XG4gICAgICBpZiAoZiBpbnN0YW5jZW9mIEFwcEZvcm0pIHtcbiAgICAgICAgZi5yZXNldChudWxsLCBvcHRzKTtcbiAgICAgIH1cbiAgICAgIGVsc2UgaWYgKGYgaW5zdGFuY2VvZiBBcHBUYWJsZSkge1xuICAgICAgICBmLmRhdGFTb3VyY2UuZGlzY29ubmVjdCgpO1xuICAgICAgfVxuICAgICAgZWxzZSBpZiAoZiBpbnN0YW5jZW9mIEFwcEVkaXRvcikge1xuICAgICAgICBmLnVubG9hZChvcHRzKTtcbiAgICAgIH1cbiAgICB9KTtcblxuICAgIHRoaXMubWFya0FzUHJpc3RpbmUob3B0cyk7XG4gICAgdGhpcy5tYXJrQXNTYXZlZChvcHRzKTtcbiAgfVxuXG4gIGFzeW5jIHJlbG9hZFdpdGhDb25maXJtYXRpb24oY29uZmlybT86IGJvb2xlYW4pIHtcbiAgICBjb25zdCBuZWVkQ29uZmlybSA9IHRoaXMuZGlydHk7XG4gICAgLy8gaWYgbm90IGNvbmZpcm0geWV0OiBhc2sgY29uZmlybWF0aW9uXG4gICAgaWYgKCFjb25maXJtICYmIG5lZWRDb25maXJtKSB7XG4gICAgICBjb25zdCB0cmFuc2xhdGlvbnMgPSB0aGlzLnRyYW5zbGF0ZS5pbnN0YW50KFsnQ09NTU9OLkJUTl9BQk9SVF9DSEFOR0VTJywgJ0NPTU1PTi5CVE5fQ0FOQ0VMJywgJ0NPTkZJUk0uQ0FOQ0VMX0NIQU5HRVMnLCAnQ09ORklSTS5BTEVSVF9IRUFERVInXSk7XG4gICAgICBjb25zdCBhbGVydCA9IGF3YWl0IHRoaXMuYWxlcnRDdHJsLmNyZWF0ZSh7XG4gICAgICAgIGhlYWRlcjogdHJhbnNsYXRpb25zWydDT05GSVJNLkFMRVJUX0hFQURFUiddLFxuICAgICAgICBtZXNzYWdlOiB0cmFuc2xhdGlvbnNbJ0NPTkZJUk0uQ0FOQ0VMX0NIQU5HRVMnXSxcbiAgICAgICAgYnV0dG9uczogW1xuICAgICAgICAgIHtcbiAgICAgICAgICAgIHRleHQ6IHRyYW5zbGF0aW9uc1snQ09NTU9OLkJUTl9BQk9SVF9DSEFOR0VTJ10sXG4gICAgICAgICAgICBjc3NDbGFzczogJ3NlY29uZGFyeScsXG4gICAgICAgICAgICBoYW5kbGVyOiAoKSA9PiB7XG4gICAgICAgICAgICAgIGNvbmZpcm0gPSB0cnVlOyAvLyB1cGRhdGUgdXBwZXIgdmFsdWVcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9LFxuICAgICAgICAgIHtcbiAgICAgICAgICAgIHRleHQ6IHRyYW5zbGF0aW9uc1snQ09NTU9OLkJUTl9DQU5DRUwnXSxcbiAgICAgICAgICAgIHJvbGU6ICdjYW5jZWwnLFxuICAgICAgICAgICAgaGFuZGxlcjogKCkgPT4ge1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cbiAgICAgICAgXVxuICAgICAgfSk7XG4gICAgICBhd2FpdCBhbGVydC5wcmVzZW50KCk7XG4gICAgICBhd2FpdCBhbGVydC5vbkRpZERpc21pc3MoKTtcbiAgICB9XG5cbiAgICAvLyBJZiBjb25maXJtOiBleGVjdXRlIHRoZSByZWxvYWRcbiAgICBpZiAoY29uZmlybSB8fCAhbmVlZENvbmZpcm0pIHtcbiAgICAgIHRoaXMuc2Nyb2xsVG9Ub3AoKTtcbiAgICAgIHRoaXMuZGlzYWJsZSgpO1xuICAgICAgcmV0dXJuIGF3YWl0IHRoaXMucmVsb2FkKCk7XG4gICAgfVxuICB9XG5cbiAgYXN5bmMgZ29CYWNrKGV2ZW50PzogRXZlbnQpOiBQcm9taXNlPHZvaWQgfCBib29sZWFuPiB7XG4gICAgLy8gR28gYmFja1xuICAgIGlmICh0aGlzLnRvb2xiYXI/LmNhbkdvQmFjaykge1xuICAgICAgcmV0dXJuIHRoaXMudG9vbGJhci5nb0JhY2soKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gQmFjayB0byBob21lXG4gICAgICByZXR1cm4gdGhpcy5yb3V0ZXIubmF2aWdhdGVCeVVybCgnLycpO1xuICAgIH1cbiAgfVxuXG5cblxuICBhYnN0cmFjdCBsb2FkKGlkPzogSUQsIG9wdGlvbnM/OiBPKTogUHJvbWlzZTx2b2lkPjtcblxuICBhYnN0cmFjdCBzYXZlKGV2ZW50PzogRXZlbnQsIG9wdGlvbnM/OiBhbnkpOiBQcm9taXNlPGJvb2xlYW4+O1xuXG4gIGFic3RyYWN0IHJlbG9hZCgpOiBQcm9taXNlPHZvaWQ+O1xuXG4gIGxvZ0Zvcm1FcnJvcnMocHJlZml4Pzogc3RyaW5nKSB7XG4gICAgaWYgKHRoaXMuZGVidWcpIGNvbnNvbGUuZGVidWcoJ1tlZGl0b3JdIEVkaXRvciBub3QgdmFsaWQuIENoZWNraW5nIHdoZXJlIChmb3JtcywgdGFibGVzKS4uLicpO1xuICAgIHRoaXMuX2NoaWxkcmVuPy5mb3JFYWNoKGMgPT4gdGhpcy5sb2dDaGlsZHJlbkVycm9ycyhjLCBwcmVmaXgpKTtcbiAgfVxuXG4gIC8qIC0tIHByb3RlY3RlZCBtZXRob2RzIC0tICovXG5cbiAgcHJvdGVjdGVkIGFzeW5jIHNjcm9sbFRvVG9wKGR1cmF0aW9uPzogbnVtYmVyKSB7XG4gICAgZHVyYXRpb24gPSB0b051bWJlcihkdXJhdGlvbiwgNTAwKTtcblxuICAgIGlmICghdGhpcy5jb250ZW50KSB7XG4gICAgICBjb25zb2xlLndhcm4oYFt0YWItZWRpdG9yXSBDYW5ub3Qgc2Nyb2xsIHRvIHRvcC4gKG5vICdpb24tY29udGVudCcgdGFnIGZvdW5kICR7dGhpcy5jb25zdHJ1Y3Rvci5uYW1lfWApO1xuXG4gICAgICAvLyBUT0RPOiBGSVhNRSAobm90IHdvcmtpbmcgYXMgdGhlIHBhZ2UgaXMgbm90IHRoZSB3aW5kb3cpXG4gICAgICBjb25zdCBzY3JvbGxUb1RvcCA9IHdpbmRvdy5zZXRJbnRlcnZhbCgoKSA9PiB7XG4gICAgICAgIGNvbnN0IHBvcyA9IHdpbmRvdy5zY3JvbGxZO1xuICAgICAgICBpZiAocG9zID4gMCkge1xuICAgICAgICAgIHdpbmRvdy5zY3JvbGxUbygwLCBwb3MgLSAyMCk7IC8vIGhvdyBmYXIgdG8gc2Nyb2xsIG9uIGVhY2ggc3RlcFxuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgIHdpbmRvdy5jbGVhckludGVydmFsKHNjcm9sbFRvVG9wKTtcbiAgICAgICAgfVxuICAgICAgfSwgMTYpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHJldHVybiB0aGlzLmNvbnRlbnQuc2Nyb2xsVG9Ub3AoZHVyYXRpb24pO1xuICB9XG5cbiAgcHJvdGVjdGVkIHJlZ2lzdGVyU3Vic2NyaXB0aW9uKHN1YjogU3Vic2NyaXB0aW9ufFRlYXJkb3duTG9naWMpIHtcbiAgICB0aGlzLl9zdWJzY3JpcHRpb24uYWRkKHN1Yik7XG4gIH1cblxuICBwcm90ZWN0ZWQgdW5yZWdpc3RlclN1YnNjcmlwdGlvbihzdWI6IFN1YnNjcmlwdGlvbikge1xuICAgIHRoaXMuX3N1YnNjcmlwdGlvbi5yZW1vdmUoc3ViKTtcbiAgfVxuXG4gIHByb3RlY3RlZCBhc3luYyBzYXZlSWZEaXJ0eUFuZENvbmZpcm0oZXZlbnQ/OiBFdmVudCwgb3B0cz86IHtcbiAgICBlbWl0RXZlbnQ/OiBib29sZWFuO1xuICAgIGNvbmZpcm1lZD86IGJvb2xlYW5cbiAgfSk6IFByb21pc2U8Ym9vbGVhbj4ge1xuICAgIGlmICghdGhpcy5kaXJ0eSkgcmV0dXJuIHRydWU7XG5cbiAgICBsZXQgY29uZmlybWVkID0gb3B0cz8uY29uZmlybWVkIHx8IGZhbHNlO1xuICAgIGlmICghY29uZmlybWVkKSB7XG4gICAgICBsZXQgY2FuY2VsID0gZmFsc2U7XG4gICAgICBjb25zdCB0cmFuc2xhdGlvbnMgPSB0aGlzLnRyYW5zbGF0ZS5pbnN0YW50KFsnQ09NTU9OLkJUTl9TQVZFJywgJ0NPTU1PTi5CVE5fQ0FOQ0VMJywgJ0NPTU1PTi5CVE5fQUJPUlRfQ0hBTkdFUycsICdDT05GSVJNLlNBVkUnLCAnQ09ORklSTS5BTEVSVF9IRUFERVInXSk7XG4gICAgICBjb25zdCBhbGVydCA9IGF3YWl0IHRoaXMuYWxlcnRDdHJsLmNyZWF0ZSh7XG4gICAgICAgIGhlYWRlcjogdHJhbnNsYXRpb25zWydDT05GSVJNLkFMRVJUX0hFQURFUiddLFxuICAgICAgICBtZXNzYWdlOiB0cmFuc2xhdGlvbnNbJ0NPTkZJUk0uU0FWRSddLFxuICAgICAgICBidXR0b25zOiBbXG4gICAgICAgICAge1xuICAgICAgICAgICAgdGV4dDogdHJhbnNsYXRpb25zWydDT01NT04uQlROX0NBTkNFTCddLFxuICAgICAgICAgICAgcm9sZTogJ2NhbmNlbCcsXG4gICAgICAgICAgICBjc3NDbGFzczogJ3NlY29uZGFyeScsXG4gICAgICAgICAgICBoYW5kbGVyOiAoKSA9PiB7XG4gICAgICAgICAgICAgIGNhbmNlbCA9IHRydWU7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfSxcbiAgICAgICAgICB7XG4gICAgICAgICAgICB0ZXh0OiB0cmFuc2xhdGlvbnNbJ0NPTU1PTi5CVE5fQUJPUlRfQ0hBTkdFUyddLFxuICAgICAgICAgICAgY3NzQ2xhc3M6ICdzZWNvbmRhcnknLFxuICAgICAgICAgICAgaGFuZGxlcjogKCkgPT4ge1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgdGV4dDogdHJhbnNsYXRpb25zWydDT01NT04uQlROX1NBVkUnXSxcbiAgICAgICAgICAgIGhhbmRsZXI6ICgpID0+IHtcbiAgICAgICAgICAgICAgY29uZmlybWVkID0gdHJ1ZTsgLy8gdXBkYXRlIHVwcGVyIHZhbHVlXG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICBdXG4gICAgICB9KTtcbiAgICAgIGF3YWl0IGFsZXJ0LnByZXNlbnQoKTtcbiAgICAgIGF3YWl0IGFsZXJ0Lm9uRGlkRGlzbWlzcygpO1xuXG4gICAgICBpZiAoIWNvbmZpcm1lZCkge1xuICAgICAgICByZXR1cm4gIWNhbmNlbDtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gYXdhaXQgdGhpcy5zYXZlKGV2ZW50LCBvcHRzKTtcbiAgfVxuXG4gIHByb3RlY3RlZCBhc3luYyBzaG93VG9hc3Qob3B0czogU2hvd1RvYXN0T3B0aW9ucykge1xuICAgIGlmICghdGhpcy50b2FzdENvbnRyb2xsZXIpIHRocm93IG5ldyBFcnJvcignTWlzc2luZyB0b2FzdENvbnRyb2xsZXIgaW4gY29tcG9uZW50XFwncyBjb25zdHJ1Y3RvcicpO1xuICAgIGF3YWl0IFRvYXN0cy5zaG93KHRoaXMudG9hc3RDb250cm9sbGVyLCB0aGlzLnRyYW5zbGF0ZSwgb3B0cyk7XG4gIH1cblxuICBwcm90ZWN0ZWQgbG9nQ2hpbGRyZW5FcnJvcnMoYzogSUFwcEZvcm0gfCBBYnN0cmFjdENvbnRyb2wsIHByZWZpeD86IHN0cmluZywgcGF0aD86IHN0cmluZykge1xuICAgIHByZWZpeCA9IHByZWZpeCB8fCAnW2FwcC10YWItZWRpdG9yXSAnO1xuICAgIC8vIElmIGVkaXRvclxuICAgIGlmIChjIGluc3RhbmNlb2YgQXBwRWRpdG9yKSB7XG4gICAgICBjLmxvZ0Zvcm1FcnJvcnMoKTtcbiAgICB9XG4gICAgLy8gQW5ndWxhciBmb3JtIGNvbnRyb2xcbiAgICBlbHNlIGlmIChjIGluc3RhbmNlb2YgQWJzdHJhY3RDb250cm9sKSB7XG4gICAgICBBcHBGb3JtVXRpbHMubG9nRm9ybUVycm9ycyhjLCBwcmVmaXgsIHBhdGgpO1xuICAgIH1cbiAgICAvLyBJZiBmb3JtIHByb3ZpZGVyOiBnZXQgZGVsZWdhdGVcbiAgICBlbHNlIGlmIChjIGluc3RhbmNlb2YgQXBwRm9ybVByb3ZpZGVyKSB7XG4gICAgICBpZiAoIWMuZW1wdHkgJiYgIWMudmFsaWQpIHtcbiAgICAgICAgYy53YWl0RGVsZWdhdGUoe3RpbWVvdXQ6IDEwMDB9KS50aGVuKGRlbGVnYXRlID0+IHRoaXMubG9nQ2hpbGRyZW5FcnJvcnMoZGVsZWdhdGUsIHByZWZpeCwgJ3Byb3ZpZGVyJykpO1xuICAgICAgfVxuICAgIH1cbiAgICAvLyBJZiB0YWJsZVxuICAgIGVsc2UgaWYgKGMgaW5zdGFuY2VvZiBBcHBUYWJsZSkge1xuICAgICAgaWYgKGMuaW52YWxpZCAmJiBjLmVkaXRlZFJvdyAmJiBjLmVkaXRlZFJvdy52YWxpZGF0b3IpIHtcbiAgICAgICAgY29uc3QgcGF0aCA9IGMuY29uc3RydWN0b3IubmFtZS50b0xvd2VyQ2FzZSgpO1xuICAgICAgICBBcHBGb3JtVXRpbHMubG9nRm9ybUVycm9ycyhjLmVkaXRlZFJvdy52YWxpZGF0b3IsIHByZWZpeCwgcGF0aCk7XG4gICAgICB9XG4gICAgfVxuICAgIC8vIElmIGZvcm1cbiAgICBlbHNlIGlmIChjIGluc3RhbmNlb2YgQXBwRm9ybSkge1xuICAgICAgaWYgKCFjLmVtcHR5ICYmICFjLnZhbGlkKSB7XG4gICAgICAgIGlmIChjLnBlbmRpbmcpIHtcbiAgICAgICAgICBjb25zdCBwYXRoID0gYy5jb25zdHJ1Y3Rvci5uYW1lLnRvTG93ZXJDYXNlKCk7XG4gICAgICAgICAgY29uc29sZS53YXJuKCBgJHtwcmVmaXh9IC0+ICR7cGF0aH06IHdhaXRpbmcgd2hpbGUgcGVuZGluZy4uLmApO1xuICAgICAgICAgIEFwcEZvcm1VdGlscy53YWl0V2hpbGVQZW5kaW5nKGMsIHt0aW1lb3V0OiAxMDAwfSlcbiAgICAgICAgICAgIC50aGVuKCgpID0+IHRoaXMubG9nQ2hpbGRyZW5FcnJvcnMoYy5mb3JtLCBwcmVmaXgsIHBhdGgpKTtcbiAgICAgICAgfVxuICAgICAgICBlbHNlIHtcbiAgICAgICAgICBBcHBGb3JtVXRpbHMubG9nRm9ybUVycm9ycyhjLmZvcm0sIHByZWZpeCk7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG4gICAgLy8gSWYgZWRpdG9yXG4gICAgZWxzZSBpZiAoYyBpbnN0YW5jZW9mIEFwcEVkaXRvcikge1xuICAgICAgaWYgKCFjLmVtcHR5ICYmICFjLnZhbGlkKSB7XG4gICAgICAgIGlmIChjLnBlbmRpbmcpIHtcbiAgICAgICAgICBjb25zdCBwYXRoID0gYy5jb25zdHJ1Y3Rvci5uYW1lLnRvTG93ZXJDYXNlKCk7XG4gICAgICAgICAgY29uc29sZS53YXJuKCBgJHtwcmVmaXh9IC0+ICR7cGF0aH06IHdhaXRpbmcgd2hpbGUgcGVuZGluZy4uLmApO1xuICAgICAgICAgIEFwcEZvcm1VdGlscy53YWl0V2hpbGVQZW5kaW5nKGMsIHt0aW1lb3V0OiAxMDAwfSlcbiAgICAgICAgICAgIC50aGVuKCgpID0+IGMubG9nRm9ybUVycm9ycyhwcmVmaXgpKTtcbiAgICAgICAgfVxuICAgICAgICBlbHNlIHtcbiAgICAgICAgICBjLmxvZ0Zvcm1FcnJvcnMocHJlZml4KTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cbiAgICBlbHNlIHtcbiAgICAgIGNvbnNvbGUud2FybiggYCR7cHJlZml4fSBVbmtub3duIGNoaWxkcmVuIHN1Yi1mb3JtOiBgLCBjKTtcbiAgICB9XG4gIH1cblxuICBwcm90ZWN0ZWQgc2V0RXJyb3IodmFsdWU6IHN0cmluZywgb3B0cz86IHtlbWl0RXZlbnQ/OiBib29sZWFuO30pIHtcbiAgICBpZiAodGhpcy5lcnJvclN1YmplY3QudmFsdWUgIT09IHZhbHVlKSB7XG4gICAgICB0aGlzLmVycm9yU3ViamVjdC5uZXh0KHZhbHVlKTtcbiAgICAgIGlmICghb3B0cyB8fCBvcHRzLmVtaXRFdmVudCAhPT0gZmFsc2UpIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gICAgfVxuICB9XG5cbiAgcHJvdGVjdGVkIHJlc2V0RXJyb3Iob3B0cz86IHtlbWl0RXZlbnQ/OiBib29sZWFufSkge1xuICAgIHRoaXMuc2V0RXJyb3IodW5kZWZpbmVkLCBvcHRzKTtcbiAgfVxuXG4gIHByb3RlY3RlZCBtYXJrRm9yQ2hlY2soKSB7XG4gICAgLy8gU2hvdWxkIGJlIG92ZXJyaWRlIGJ5IHN1YmNsYXNzZXMsIGlmIGNoYW5nZSBkZXRlY3Rpb24gaXMgUHVzaFxuICB9XG59XG5cbkBEaXJlY3RpdmUoKVxuLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEBhbmd1bGFyLWVzbGludC9kaXJlY3RpdmUtY2xhc3Mtc3VmZml4XG5leHBvcnQgYWJzdHJhY3QgY2xhc3MgQXBwVGFiRWRpdG9yPFQgPSBhbnksIElEID0gbnVtYmVyLCBPID0gYW55PlxuICBleHRlbmRzIEFwcEVkaXRvcjxULCBJRCwgTz5cbiAgaW1wbGVtZW50cyBJQXBwVGFiRWRpdG9yIHtcblxuICBwcm90ZWN0ZWQgX3NlbGVjdGVkVGFiSW5kZXggPSAwO1xuXG4gIC8vIEVkaXRvciBvcHRpb25zXG4gIHRhYkNvdW50OiBudW1iZXI7XG4gIGVuYWJsZVN3aXBlOiBib29sZWFuO1xuICB0YWJHcm91cEFuaW1hdGlvbkR1cmF0aW9uOiBzdHJpbmc7XG5cbiAgQElucHV0KCkgcXVlcnlUYWJJbmRleFBhcmFtTmFtZTogc3RyaW5nO1xuXG4gIEBJbnB1dCgpIHNldCBzZWxlY3RlZFRhYkluZGV4KHZhbHVlOiBudW1iZXIpIHtcbiAgICB0aGlzLnNldFNlbGVjdGVkVGFiSW5kZXgodmFsdWUpO1xuICB9XG4gIGdldCBzZWxlY3RlZFRhYkluZGV4KCk6IG51bWJlciB7XG4gICAgcmV0dXJuIHRoaXMuX3NlbGVjdGVkVGFiSW5kZXg7XG4gIH1cblxuICBAT3V0cHV0KCkgcmVhZG9ubHkgc2VsZWN0ZWRUYWJJbmRleENoYW5nZSA9IG5ldyBFdmVudEVtaXR0ZXI8bnVtYmVyPigpO1xuXG4gIEBWaWV3Q2hpbGQoJ3RhYkdyb3VwJywgeyBzdGF0aWM6IHRydWUgfSkgdGFiR3JvdXA6IE1hdFRhYkdyb3VwO1xuXG4gIHByb3RlY3RlZCBjb25zdHJ1Y3RvcihcbiAgICBAT3B0aW9uYWwoKSBwcm90ZWN0ZWQgcm91dGU6IEFjdGl2YXRlZFJvdXRlLCAvLyBNb2RhbCBlZGl0b3IgZ2l2ZSAnbnVsbCdcbiAgICBwcm90ZWN0ZWQgcm91dGVyOiBSb3V0ZXIsXG4gICAgcHJvdGVjdGVkIGFsZXJ0Q3RybDogQWxlcnRDb250cm9sbGVyLFxuICAgIHByb3RlY3RlZCB0cmFuc2xhdGU6IFRyYW5zbGF0ZVNlcnZpY2UsXG4gICAgQE9wdGlvbmFsKCkgb3B0aW9ucz86IEFwcFRhYkVkaXRvck9wdGlvbnMpIHtcbiAgICBzdXBlcihyb3V0ZSwgcm91dGVyLCBhbGVydEN0cmwsIHRyYW5zbGF0ZSk7XG4gICAgb3B0aW9ucyA9IHtcbiAgICAgIHRhYkNvdW50OiAxLFxuICAgICAgZW5hYmxlU3dpcGU6IHRydWUsXG4gICAgICB0YWJHcm91cEFuaW1hdGlvbkR1cmF0aW9uOiAnMjAwbXMnLFxuICAgICAgLi4ub3B0aW9uc1xuICAgIH1cbiAgICB0aGlzLnRhYkNvdW50ID0gb3B0aW9ucy50YWJDb3VudDtcbiAgICB0aGlzLmVuYWJsZVN3aXBlID0gb3B0aW9ucy5lbmFibGVTd2lwZTtcbiAgICB0aGlzLnRhYkdyb3VwQW5pbWF0aW9uRHVyYXRpb24gPSBvcHRpb25zLnRhYkdyb3VwQW5pbWF0aW9uRHVyYXRpb247XG4gICAgdGhpcy5xdWVyeVRhYkluZGV4UGFyYW1OYW1lID0gJ3RhYic7XG4gIH1cblxuICBuZ09uSW5pdCgpIHtcbiAgICBzdXBlci5uZ09uSW5pdCgpO1xuXG4gICAgLy8gUmVhZCB0aGUgc2VsZWN0ZWQgdGFiIGluZGV4LCBmcm9tIHBhdGggcXVlcnkgcGFyYW1zXG4gICAgaWYgKHRoaXMudGFiR3JvdXAgJiYgdGhpcy5yb3V0ZSAmJiB0aGlzLnF1ZXJ5VGFiSW5kZXhQYXJhbU5hbWUpIHtcbiAgICAgIHRoaXMucmVnaXN0ZXJTdWJzY3JpcHRpb24odGhpcy5yb3V0ZS5xdWVyeVBhcmFtc1xuICAgICAgICAuc3Vic2NyaWJlKHF1ZXJ5UGFyYW1zID0+IHtcbiAgICAgICAgICB0aGlzLnF1ZXJ5UGFyYW1zID0gey4uLnF1ZXJ5UGFyYW1zfTtcblxuICAgICAgICAgIC8vIFBhcnNlIHRhYiBwYXJhbVxuICAgICAgICAgIGlmICh0aGlzLnRhYkNvdW50ID4gMSAmJiB0aGlzLnF1ZXJ5VGFiSW5kZXhQYXJhbU5hbWUpIHtcbiAgICAgICAgICAgIGNvbnN0IHRhYkluZGV4ID0gcXVlcnlQYXJhbXNbdGhpcy5xdWVyeVRhYkluZGV4UGFyYW1OYW1lXTtcbiAgICAgICAgICAgIHRoaXMucXVlcnlQYXJhbXNbdGhpcy5xdWVyeVRhYkluZGV4UGFyYW1OYW1lXSA9IHRhYkluZGV4ICYmIHBhcnNlSW50KHRhYkluZGV4KSB8fCB1bmRlZmluZWQ7XG4gICAgICAgICAgICBpZiAoaXNOb3ROaWwodGhpcy5xdWVyeVBhcmFtc1t0aGlzLnF1ZXJ5VGFiSW5kZXhQYXJhbU5hbWVdKSkge1xuICAgICAgICAgICAgICB0aGlzLnNlbGVjdGVkVGFiSW5kZXggPSB0aGlzLnF1ZXJ5UGFyYW1zW3RoaXMucXVlcnlUYWJJbmRleFBhcmFtTmFtZV07XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuXG4gICAgICAgICAgLy8gUmVhbGlnbiB0YWIsIGFmdGVyIGEgZGVsYXkgYmVjYXVzZSB0aGUgdGFiIGNhbiBiZSBkaXNhYmxlZCB3aGVuIGNvbXBvbmVudCBpcyBjcmVhdGVkXG4gICAgICAgICAgc2V0VGltZW91dCgoKSA9PiB0aGlzLnRhYkdyb3VwLnJlYWxpZ25JbmtCYXIoKSwgNTAwKTtcbiAgICAgICAgfSkpO1xuICAgIH1cbiAgfVxuXG5cbiAgbmdPbkRlc3Ryb3koKSB7XG4gICAgc3VwZXIubmdPbkRlc3Ryb3koKTtcbiAgICB0aGlzLnNlbGVjdGVkVGFiSW5kZXhDaGFuZ2UuY29tcGxldGUoKTtcbiAgICB0aGlzLmxvYWRpbmdTdWJqZWN0LnVuc3Vic2NyaWJlKCk7XG4gICAgdGhpcy5lcnJvclN1YmplY3QudW5zdWJzY3JpYmUoKTtcbiAgfVxuXG4gIHNldFNlbGVjdGVkVGFiSW5kZXgodmFsdWU6IG51bWJlciwgb3B0cz86IHtlbWl0RXZlbnQ/OiBib29sZWFuOyByZWFsaWduSW5rQmFyPzogYm9vbGVhbiB9KSB7XG4gICAgLy8gRml4IHZhbHVlXG4gICAgaWYgKHZhbHVlIDwgMCkge1xuICAgICAgdmFsdWUgPSAwO1xuICAgIH1cbiAgICBlbHNlIGlmICh2YWx1ZSA+IHRoaXMudGFiQ291bnQgLSAxKSB7XG4gICAgICBjb25zb2xlLndhcm4oYFt0YWItZWRpdG9yXSBJbnZhbGlkIHRhYiBpbmRleCAke3ZhbHVlfS4gTWF4IHZhbHVlIGlzICR7dGhpcy50YWJDb3VudC0xfWApXG4gICAgICB2YWx1ZSA9IHRoaXMuX3NlbGVjdGVkVGFiSW5kZXg7XG4gICAgfVxuXG4gICAgdGhpcy5fc2VsZWN0ZWRUYWJJbmRleCA9IHZhbHVlO1xuICAgIHRoaXMuc2VsZWN0ZWRUYWJJbmRleENoYW5nZS5uZXh0KHZhbHVlKTtcblxuICAgIGlmICh0aGlzLnRhYkdyb3VwICYmICghb3B0cyB8fCBvcHRzLnJlYWxpZ25JbmtCYXIgIT09IGZhbHNlKSkge1xuICAgICAgdGhpcy50YWJHcm91cC5zZWxlY3RlZEluZGV4ID0gdmFsdWU7XG4gICAgICB0aGlzLm1hcmtGb3JDaGVjaygpO1xuICAgICAgLy8gV2FpdCB0YWIgY2hhbmdlIGluIFVJLCBiZWZvcmUgcmVhbGlnbiBpbmsgdGFiXG4gICAgICBzZXRUaW1lb3V0KCgpID0+IHRoaXMudGFiR3JvdXAucmVhbGlnbklua0JhcigpLCAyMDApO1xuICAgIH1cbiAgICBlbHNlIGlmICghb3B0cyB8fCBvcHRzLmVtaXRFdmVudCAhPT0gZmFsc2UpIHtcbiAgICAgIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gICAgfVxuICB9XG5cbiAgcmVhbGlnbklua0JhcigpIHtcbiAgICB0aGlzLnRhYkdyb3VwPy5yZWFsaWduSW5rQmFyKCk7XG4gIH1cblxuXG4gIG9uVGFiQ2hhbmdlKGV2ZW50OiBNYXRUYWJDaGFuZ2VFdmVudCwgcXVlcnlUYWJJbmRleFBhcmFtTmFtZT86IHN0cmluZyk6IGJvb2xlYW4ge1xuICAgIHF1ZXJ5VGFiSW5kZXhQYXJhbU5hbWUgPSBxdWVyeVRhYkluZGV4UGFyYW1OYW1lIHx8IHRoaXMucXVlcnlUYWJJbmRleFBhcmFtTmFtZTtcblxuICAgIGlmICghcXVlcnlUYWJJbmRleFBhcmFtTmFtZSB8fCAhdGhpcy5yb3V0ZSkgcmV0dXJuIHRydWU7IC8vIFNraXAgaWYgdGFiIHF1ZXJ5IHBhcmFtIG5vdCBzZXQsIG9yIG5vIHJvdXRlXG5cbiAgICBpZiAoIXRoaXMucXVlcnlQYXJhbXMgfHwgK3RoaXMucXVlcnlQYXJhbXNbcXVlcnlUYWJJbmRleFBhcmFtTmFtZV0gIT09IGV2ZW50LmluZGV4KSB7XG5cbiAgICAgIHRoaXMucXVlcnlQYXJhbXMgPSB0aGlzLnF1ZXJ5UGFyYW1zIHx8IHt9O1xuICAgICAgdGhpcy5xdWVyeVBhcmFtc1txdWVyeVRhYkluZGV4UGFyYW1OYW1lXSA9IGV2ZW50LmluZGV4O1xuXG4gICAgICBpZiAocXVlcnlUYWJJbmRleFBhcmFtTmFtZSA9PT0gJ3RhYicgJiYgaXNOb3ROaWwodGhpcy5xdWVyeVBhcmFtc1snc3VidGFiJ10pKSB7XG4gICAgICAgIGRlbGV0ZSB0aGlzLnF1ZXJ5UGFyYW1zLnN1YnRhYjsgLy8gY2xlYW4gc3VidGFiXG4gICAgICB9XG4gICAgICB0aGlzLnJvdXRlci5uYXZpZ2F0ZShbJy4nXSwge1xuICAgICAgICByZWxhdGl2ZVRvOiB0aGlzLnJvdXRlLFxuICAgICAgICBxdWVyeVBhcmFtczogdGhpcy5xdWVyeVBhcmFtcyxcbiAgICAgICAgcmVwbGFjZVVybDogdHJ1ZVxuICAgICAgfSk7XG4gICAgICByZXR1cm4gdHJ1ZTtcbiAgICB9XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgLyoqXG4gICAqIEFjdGlvbiB0cmlnZ2VyZWQgd2hlbiB1c2VyIHN3aXBlc1xuICAgKi9cbiAgb25Td2lwZVRhYihldmVudDogSGFtbWVyU3dpcGVFdmVudCk6IGJvb2xlYW4ge1xuICAgIC8vIERFQlVHXG4gICAgLy8gaWYgKHRoaXMuZGVidWcpIGNvbnNvbGUuZGVidWcoXCJbdGFiLXBhZ2VdIG9uU3dpcGVUYWIoKVwiKTtcblxuICAgIC8vIFNraXAsIGlmIG5vdCBhIHZhbGlkIHN3aXBlIGV2ZW50XG4gICAgaWYgKCF0aGlzLmVuYWJsZVN3aXBlIHx8ICFldmVudFxuICAgICAgfHwgZXZlbnQuZGVmYXVsdFByZXZlbnRlZCB8fCAoZXZlbnQuc3JjRXZlbnQgJiYgZXZlbnQuc3JjRXZlbnQuZGVmYXVsdFByZXZlbnRlZClcbiAgICAgIHx8IGV2ZW50LnBvaW50ZXJUeXBlICE9PSAndG91Y2gnXG4gICAgKSB7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuXG4gICAgLy8gREVCVUdcbiAgICAvL2lmICh0aGlzLmRlYnVnKVxuICAgIC8vY29uc29sZS5kZWJ1ZyhcIlt0YWItcGFnZV0gRGV0ZWN0ZWQgc3dpcGU6IFwiICsgZXZlbnQudHlwZSwgZXZlbnQpO1xuXG4gICAgbGV0IHNlbGVjdFRhYkluZGV4ID0gdGhpcy5zZWxlY3RlZFRhYkluZGV4O1xuICAgIHN3aXRjaCAoZXZlbnQudHlwZSkge1xuICAgICAgLy8gT3BlbiBuZXh0IHRhYlxuICAgICAgY2FzZSAnc3dpcGVsZWZ0JzpcbiAgICAgICAgY29uc3QgaXNMYXN0ID0gc2VsZWN0VGFiSW5kZXggPj0gKHRoaXMudGFiQ291bnQgLSAxKTtcbiAgICAgICAgc2VsZWN0VGFiSW5kZXggPSBpc0xhc3QgPyAwIDogc2VsZWN0VGFiSW5kZXggKyAxO1xuICAgICAgICBicmVhaztcblxuXG4gICAgICAvLyBPcGVuIHByZXZpb3VzIHRhYlxuICAgICAgY2FzZSAnc3dpcGVyaWdodCc6XG4gICAgICAgIGNvbnN0IGlzRmlyc3QgPSBzZWxlY3RUYWJJbmRleCA8PSAwO1xuICAgICAgICBzZWxlY3RUYWJJbmRleCA9IGlzRmlyc3QgPyB0aGlzLnRhYkNvdW50IDogc2VsZWN0VGFiSW5kZXggLSAxO1xuICAgICAgICBicmVhaztcblxuICAgICAgLy8gT3RoZXIgY2FzZVxuICAgICAgZGVmYXVsdDpcbiAgICAgICAgY29uc29sZS5lcnJvcignW3RhYi1wYWdlXSBVbmtub3duIHN3aXBlIGFjdGlvbjogJyArIGV2ZW50LnR5cGUpO1xuICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuXG4gICAgc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICB0aGlzLnNlbGVjdGVkVGFiSW5kZXggPSBzZWxlY3RUYWJJbmRleDtcbiAgICAgIHRoaXMubWFya0ZvckNoZWNrKCk7XG4gICAgfSk7XG5cbiAgICByZXR1cm4gdHJ1ZTtcbiAgfVxuXG4gIG9uU3ViVGFiQ2hhbmdlKGV2ZW50OiBNYXRUYWJDaGFuZ2VFdmVudCkge1xuICAgIHRoaXMub25UYWJDaGFuZ2UoZXZlbnQsICdzdWJ0YWInKTtcbiAgfVxuXG4gIGFzeW5jIHVubG9hZChvcHRzPzogeyBlbWl0RXZlbnQ/OiBib29sZWFuIH0pOiBQcm9taXNlPHZvaWQ+IHtcbiAgICB0aGlzLnNlbGVjdGVkVGFiSW5kZXggPSAwO1xuICAgIGF3YWl0IHN1cGVyLnVubG9hZChvcHRzKTtcbiAgfVxuXG4gIHByb3RlY3RlZCBhYnN0cmFjdCBnZXRGaXJzdEludmFsaWRUYWJJbmRleCgpOiBudW1iZXI7XG5cbiAgcHJvdGVjdGVkIGFzeW5jIHNhdmVEaXJ0eUNoaWxkcmVuKCk6IFByb21pc2U8Ym9vbGVhbj4ge1xuICAgIC8vIFNhdmUgYWxsIGRpcnR5IHRhYmxlc1xuICAgIGNvbnN0IHJlc3VsdHMgPSBhd2FpdCBQcm9taXNlLmFsbChbXG4gICAgICAuLi50aGlzLnRhYmxlcyxcbiAgICAgIC4uLnRoaXMuZWRpdG9yc1xuICAgIF1cbiAgICAgIC5maWx0ZXIoYyA9PiBjLmRpcnR5KVxuICAgICAgLm1hcChjID0+IGMuc2F2ZSgpKSk7XG5cbiAgICByZXR1cm4gIXJlc3VsdHMuc29tZShzYXZlZCA9PiBzYXZlZCAhPT0gdHJ1ZSk7XG4gIH1cbn1cbiJdfQ==
|