ngx-dynamic-entity 1.3.0 → 1.4.0
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 +14 -0
- package/fesm2022/ngx-dynamic-entity.mjs +228 -150
- package/fesm2022/ngx-dynamic-entity.mjs.map +1 -1
- package/package.json +6 -7
- package/types/ngx-dynamic-entity.d.ts +1719 -0
- package/esm2022/lib/field-types/array-field.component.mjs +0 -168
- package/esm2022/lib/field-types/boolean-field.component.mjs +0 -101
- package/esm2022/lib/field-types/checkbox-field.component.mjs +0 -82
- package/esm2022/lib/field-types/currency-field.component.mjs +0 -102
- package/esm2022/lib/field-types/date-field.component.mjs +0 -91
- package/esm2022/lib/field-types/date-time-field.component.mjs +0 -138
- package/esm2022/lib/field-types/dropdown-field.component.mjs +0 -176
- package/esm2022/lib/field-types/email-field.component.mjs +0 -102
- package/esm2022/lib/field-types/entity-ref-field.component.mjs +0 -195
- package/esm2022/lib/field-types/field-component.contract.mjs +0 -2
- package/esm2022/lib/field-types/file-field.component.mjs +0 -157
- package/esm2022/lib/field-types/group-field.component.mjs +0 -89
- package/esm2022/lib/field-types/image-field.component.mjs +0 -169
- package/esm2022/lib/field-types/month-year-field.component.mjs +0 -152
- package/esm2022/lib/field-types/multi-select-field.component.mjs +0 -146
- package/esm2022/lib/field-types/number-field.component.mjs +0 -112
- package/esm2022/lib/field-types/password-field.component.mjs +0 -110
- package/esm2022/lib/field-types/radio-field.component.mjs +0 -153
- package/esm2022/lib/field-types/text-field.component.mjs +0 -121
- package/esm2022/lib/field-types/textarea-field.component.mjs +0 -85
- package/esm2022/lib/field-types/time-field.component.mjs +0 -96
- package/esm2022/lib/form/dynamic-field/dynamic-field.component.mjs +0 -152
- package/esm2022/lib/form/dynamic-form.component.mjs +0 -899
- package/esm2022/lib/form/dynamic-record-form.component.mjs +0 -531
- package/esm2022/lib/providers/provide-field-types.mjs +0 -75
- package/esm2022/lib/providers/provide-ngx-dynamic-entity.mjs +0 -27
- package/esm2022/lib/services/cascade-data.service.mjs +0 -129
- package/esm2022/lib/services/config-source.service.mjs +0 -67
- package/esm2022/lib/services/entity-ref-cache.mjs +0 -20
- package/esm2022/lib/services/entity-ref-registry.service.mjs +0 -31
- package/esm2022/lib/services/entity-ref-selection.service.mjs +0 -27
- package/esm2022/lib/services/entity-reference.service.mjs +0 -168
- package/esm2022/lib/services/field-registry.service.mjs +0 -55
- package/esm2022/lib/services/file-upload.service.mjs +0 -89
- package/esm2022/lib/services/hook-registry.service.mjs +0 -26
- package/esm2022/lib/services/lookup-registry.service.mjs +0 -246
- package/esm2022/lib/services/rbac.service.mjs +0 -46
- package/esm2022/lib/services/rules-evaluation.service.mjs +0 -27
- package/esm2022/lib/services/validation-messages.service.mjs +0 -56
- package/esm2022/lib/services/validator-registry.service.mjs +0 -99
- package/esm2022/lib/tokens/injection-tokens.mjs +0 -126
- package/esm2022/ngx-dynamic-entity.mjs +0 -5
- package/esm2022/public-api.mjs +0 -58
- package/index.d.ts +0 -5
- package/lib/field-types/array-field.component.d.ts +0 -28
- package/lib/field-types/boolean-field.component.d.ts +0 -18
- package/lib/field-types/checkbox-field.component.d.ts +0 -13
- package/lib/field-types/currency-field.component.d.ts +0 -17
- package/lib/field-types/date-field.component.d.ts +0 -15
- package/lib/field-types/date-time-field.component.d.ts +0 -30
- package/lib/field-types/dropdown-field.component.d.ts +0 -34
- package/lib/field-types/email-field.component.d.ts +0 -15
- package/lib/field-types/entity-ref-field.component.d.ts +0 -49
- package/lib/field-types/field-component.contract.d.ts +0 -49
- package/lib/field-types/file-field.component.d.ts +0 -25
- package/lib/field-types/group-field.component.d.ts +0 -17
- package/lib/field-types/image-field.component.d.ts +0 -30
- package/lib/field-types/month-year-field.component.d.ts +0 -28
- package/lib/field-types/multi-select-field.component.d.ts +0 -27
- package/lib/field-types/number-field.component.d.ts +0 -16
- package/lib/field-types/password-field.component.d.ts +0 -17
- package/lib/field-types/radio-field.component.d.ts +0 -33
- package/lib/field-types/text-field.component.d.ts +0 -23
- package/lib/field-types/textarea-field.component.d.ts +0 -14
- package/lib/field-types/time-field.component.d.ts +0 -27
- package/lib/form/dynamic-field/dynamic-field.component.d.ts +0 -78
- package/lib/form/dynamic-form.component.d.ts +0 -293
- package/lib/form/dynamic-record-form.component.d.ts +0 -199
- package/lib/providers/provide-field-types.d.ts +0 -24
- package/lib/providers/provide-ngx-dynamic-entity.d.ts +0 -56
- package/lib/services/cascade-data.service.d.ts +0 -45
- package/lib/services/config-source.service.d.ts +0 -14
- package/lib/services/entity-ref-cache.d.ts +0 -27
- package/lib/services/entity-ref-registry.service.d.ts +0 -21
- package/lib/services/entity-ref-selection.service.d.ts +0 -24
- package/lib/services/entity-reference.service.d.ts +0 -49
- package/lib/services/field-registry.service.d.ts +0 -32
- package/lib/services/file-upload.service.d.ts +0 -27
- package/lib/services/hook-registry.service.d.ts +0 -12
- package/lib/services/lookup-registry.service.d.ts +0 -94
- package/lib/services/rbac.service.d.ts +0 -27
- package/lib/services/rules-evaluation.service.d.ts +0 -17
- package/lib/services/validation-messages.service.d.ts +0 -43
- package/lib/services/validator-registry.service.d.ts +0 -32
- package/lib/tokens/injection-tokens.d.ts +0 -134
- package/public-api.d.ts +0 -42
|
@@ -1,152 +0,0 @@
|
|
|
1
|
-
import { ChangeDetectionStrategy, Component, Injector, Input, ViewChild, ViewContainerRef, inject, isDevMode, } from '@angular/core';
|
|
2
|
-
import { findTab } from '@dynamic-entity/core';
|
|
3
|
-
import { FieldRegistryService } from '../../services/field-registry.service';
|
|
4
|
-
import { RbacService } from '../../services/rbac.service';
|
|
5
|
-
import * as i0 from "@angular/core";
|
|
6
|
-
/**
|
|
7
|
-
* DynamicFieldComponent — mounts the correct field component for a given NestedFieldConfig.
|
|
8
|
-
* Uses ViewContainerRef.createComponent() and passes inputs via setInput(); see
|
|
9
|
-
* DynamicFieldComponentContract for the five inputs every field component receives.
|
|
10
|
-
* Never add field-type-specific logic here — this component must remain generic.
|
|
11
|
-
*
|
|
12
|
-
* The 5 inputs (field, control, language, readonly, masked) are passed to every mounted
|
|
13
|
-
* component uniformly — no special-casing per type.
|
|
14
|
-
*/
|
|
15
|
-
export class DynamicFieldComponent {
|
|
16
|
-
field;
|
|
17
|
-
control;
|
|
18
|
-
config;
|
|
19
|
-
currentTabId;
|
|
20
|
-
language = 'en';
|
|
21
|
-
readonly = false;
|
|
22
|
-
userRoles = [];
|
|
23
|
-
fieldHost;
|
|
24
|
-
fieldRegistry = inject(FieldRegistryService);
|
|
25
|
-
rbacService = inject(RbacService);
|
|
26
|
-
/**
|
|
27
|
-
* Passed into `createComponent` so a hosted field sees this host's injector — including
|
|
28
|
-
* `DynamicFormComponent`'s scoped `EntityRefSelectionService`. Without it, a standalone
|
|
29
|
-
* field resolves the root bus and `autoPatch` never runs.
|
|
30
|
-
*/
|
|
31
|
-
injector = inject(Injector);
|
|
32
|
-
componentRef = null;
|
|
33
|
-
ngOnChanges(_changes) {
|
|
34
|
-
this.mountField();
|
|
35
|
-
}
|
|
36
|
-
mountField() {
|
|
37
|
-
if (!this.field || !this.control)
|
|
38
|
-
return;
|
|
39
|
-
const ComponentClass = this.fieldRegistry.resolve(this.field.type);
|
|
40
|
-
if (!ComponentClass) {
|
|
41
|
-
this.warnUnresolved(this.field.type);
|
|
42
|
-
return; // Unknown field type — render nothing
|
|
43
|
-
}
|
|
44
|
-
// Determine masking for this specific field
|
|
45
|
-
const tab = this.currentTabId ? findTab(this.config?.tabs, this.currentTabId) : null;
|
|
46
|
-
const masked = this.rbacService.shouldMaskField(this.field, tab ?? undefined, this.config, this.userRoles);
|
|
47
|
-
// Re-use existing component if same type, otherwise recreate
|
|
48
|
-
if (this.componentRef && this.componentRef.instance instanceof ComponentClass) {
|
|
49
|
-
this.setInputs(this.componentRef, masked);
|
|
50
|
-
return;
|
|
51
|
-
}
|
|
52
|
-
this.fieldHost.clear();
|
|
53
|
-
this.componentRef = this.fieldHost.createComponent(ComponentClass, {
|
|
54
|
-
injector: this.injector,
|
|
55
|
-
});
|
|
56
|
-
this.setInputs(this.componentRef, masked);
|
|
57
|
-
this.watchControl();
|
|
58
|
-
this.componentRef.changeDetectorRef.detectChanges();
|
|
59
|
-
}
|
|
60
|
-
/**
|
|
61
|
-
* Field types are opt-in (see `provideFieldTypes` / `provideBuiltInFieldTypes`), so an
|
|
62
|
-
* unregistered type renders nothing. Say so once per type in dev builds rather than
|
|
63
|
-
* leaving a silently blank slot.
|
|
64
|
-
*/
|
|
65
|
-
warnUnresolved(type) {
|
|
66
|
-
if (!isDevMode() || DynamicFieldComponent.warnedTypes.has(type))
|
|
67
|
-
return;
|
|
68
|
-
DynamicFieldComponent.warnedTypes.add(type);
|
|
69
|
-
console.warn(`[ngx-dynamic-entity] No component registered for field type "${type}" — the field was not rendered. ` +
|
|
70
|
-
`Register it with provideFieldTypes({ '${type}': MyComponent }) or provideBuiltInFieldTypes().`);
|
|
71
|
-
}
|
|
72
|
-
static warnedTypes = new Set();
|
|
73
|
-
/**
|
|
74
|
-
* Re-check the hosted field component.
|
|
75
|
-
*
|
|
76
|
-
* The field components are OnPush, so they re-render on an input change, an event from
|
|
77
|
-
* their own template, or a signal they read. `form.markAllAsTouched()` is none of those —
|
|
78
|
-
* it flips `touched` from outside, and every field's error message depends on it. Without
|
|
79
|
-
* this, a blocked submit would mark the form touched and no error would appear.
|
|
80
|
-
*/
|
|
81
|
-
refresh() {
|
|
82
|
-
this.componentRef?.changeDetectorRef.detectChanges();
|
|
83
|
-
}
|
|
84
|
-
/**
|
|
85
|
-
* Re-check the hosted component whenever its control changes from outside.
|
|
86
|
-
*
|
|
87
|
-
* The field components are OnPush, so they re-render on an input change or an event from
|
|
88
|
-
* their own template. A control mutated externally is neither — and that is not an edge
|
|
89
|
-
* case: patchForm, reset, autoPatch and patchOnTrue all do exactly that. Without this, a
|
|
90
|
-
* field patched from a record would keep rendering its previous value.
|
|
91
|
-
*
|
|
92
|
-
* `detectChanges()` rather than `markForCheck()`: a selection that arrives from a native
|
|
93
|
-
* `change` event (or Playwright) may not be followed by another Angular tick, so a dirty
|
|
94
|
-
* flag would never be flushed. Running CD on the hosted component now is the copy showing up.
|
|
95
|
-
*
|
|
96
|
-
* Done here rather than in each of the eighteen field components: the host owns the
|
|
97
|
-
* component reference, so one subscription covers every type including custom ones.
|
|
98
|
-
*/
|
|
99
|
-
watchControl() {
|
|
100
|
-
this.controlSub?.unsubscribe();
|
|
101
|
-
if (!this.control)
|
|
102
|
-
return;
|
|
103
|
-
this.controlSub = this.control.valueChanges.subscribe(() => this.refresh());
|
|
104
|
-
}
|
|
105
|
-
controlSub;
|
|
106
|
-
ngOnDestroy() {
|
|
107
|
-
this.controlSub?.unsubscribe();
|
|
108
|
-
}
|
|
109
|
-
/**
|
|
110
|
-
* Pass all 5 contract inputs via ComponentRef.setInput() — uniform for all types.
|
|
111
|
-
* The public shape is DynamicFieldComponentContract.
|
|
112
|
-
* Must use setInput(), not property assignment: the field components declare inputs with
|
|
113
|
-
* definite assignment and no initializer, and the lib compiles with
|
|
114
|
-
* useDefineForClassFields:false, so `'field' in instance` is false until first set.
|
|
115
|
-
*/
|
|
116
|
-
setInputs(ref, masked) {
|
|
117
|
-
ref.setInput('field', this.field);
|
|
118
|
-
ref.setInput('control', this.control);
|
|
119
|
-
ref.setInput('language', this.language);
|
|
120
|
-
ref.setInput('readonly', this.readonly || !!this.field.readonly);
|
|
121
|
-
ref.setInput('masked', masked);
|
|
122
|
-
}
|
|
123
|
-
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: DynamicFieldComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
124
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.12", type: DynamicFieldComponent, isStandalone: true, selector: "ngx-dynamic-field", inputs: { field: "field", control: "control", config: "config", currentTabId: "currentTabId", language: "language", readonly: "readonly", userRoles: "userRoles" }, viewQueries: [{ propertyName: "fieldHost", first: true, predicate: ["fieldHost"], descendants: true, read: ViewContainerRef, static: true }], usesOnChanges: true, ngImport: i0, template: `<ng-container #fieldHost></ng-container>`, isInline: true, changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
125
|
-
}
|
|
126
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: DynamicFieldComponent, decorators: [{
|
|
127
|
-
type: Component,
|
|
128
|
-
args: [{
|
|
129
|
-
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
130
|
-
selector: 'ngx-dynamic-field',
|
|
131
|
-
standalone: true,
|
|
132
|
-
template: `<ng-container #fieldHost></ng-container>`,
|
|
133
|
-
}]
|
|
134
|
-
}], propDecorators: { field: [{
|
|
135
|
-
type: Input
|
|
136
|
-
}], control: [{
|
|
137
|
-
type: Input
|
|
138
|
-
}], config: [{
|
|
139
|
-
type: Input
|
|
140
|
-
}], currentTabId: [{
|
|
141
|
-
type: Input
|
|
142
|
-
}], language: [{
|
|
143
|
-
type: Input
|
|
144
|
-
}], readonly: [{
|
|
145
|
-
type: Input
|
|
146
|
-
}], userRoles: [{
|
|
147
|
-
type: Input
|
|
148
|
-
}], fieldHost: [{
|
|
149
|
-
type: ViewChild,
|
|
150
|
-
args: ['fieldHost', { read: ViewContainerRef, static: true }]
|
|
151
|
-
}] } });
|
|
152
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZHluYW1pYy1maWVsZC5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi9zcmMvbGliL2Zvcm0vZHluYW1pYy1maWVsZC9keW5hbWljLWZpZWxkLmNvbXBvbmVudC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQ0wsdUJBQXVCLEVBQ3ZCLFNBQVMsRUFFVCxRQUFRLEVBQ1IsS0FBSyxFQUdMLFNBQVMsRUFDVCxnQkFBZ0IsRUFDaEIsTUFBTSxFQUNOLFNBQVMsR0FDVixNQUFNLGVBQWUsQ0FBQztBQUl2QixPQUFPLEVBQUUsT0FBTyxFQUFFLE1BQU0sc0JBQXNCLENBQUM7QUFDL0MsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0sdUNBQXVDLENBQUM7QUFDN0UsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLDZCQUE2QixDQUFDOztBQUUxRDs7Ozs7Ozs7R0FRRztBQU9ILE1BQU0sT0FBTyxxQkFBcUI7SUFDdkIsS0FBSyxDQUFxQjtJQUMxQixPQUFPLENBQW1CO0lBQzFCLE1BQU0sQ0FBb0I7SUFDMUIsWUFBWSxDQUFVO0lBQ3RCLFFBQVEsR0FBVyxJQUFJLENBQUM7SUFDeEIsUUFBUSxHQUFZLEtBQUssQ0FBQztJQUMxQixTQUFTLEdBQWEsRUFBRSxDQUFDO0lBR2pCLFNBQVMsQ0FBb0I7SUFFN0IsYUFBYSxHQUFHLE1BQU0sQ0FBQyxvQkFBb0IsQ0FBQyxDQUFDO0lBQzdDLFdBQVcsR0FBRyxNQUFNLENBQUMsV0FBVyxDQUFDLENBQUM7SUFDbkQ7Ozs7T0FJRztJQUNjLFFBQVEsR0FBRyxNQUFNLENBQUMsUUFBUSxDQUFDLENBQUM7SUFFckMsWUFBWSxHQUFpQyxJQUFJLENBQUM7SUFFMUQsV0FBVyxDQUFDLFFBQXVCO1FBQ2pDLElBQUksQ0FBQyxVQUFVLEVBQUUsQ0FBQztJQUNwQixDQUFDO0lBRU8sVUFBVTtRQUNoQixJQUFJLENBQUMsSUFBSSxDQUFDLEtBQUssSUFBSSxDQUFD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QUFDLEtBQUssQ0FBQyxDQUFDO1FBQ2xDLEdBQUcsQ0FBQyxRQUFRLENBQUMsU0FBUyxFQUFFLElBQUksQ0FBQyxPQUFPLENBQUMsQ0FBQztRQUN0QyxHQUFHLENBQUMsUUFBUSxDQUFDLFVBQVUsRUFBRSxJQUFJLENBQUMsUUFBUSxDQUFDLENBQUM7UUFDeEMsR0FBRyxDQUFDLFFBQVEsQ0FBQyxVQUFVLEVBQUUsSUFBSSxDQUFDLFFBQVEsSUFBSSxDQUFDLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxRQUFRLENBQUMsQ0FBQztRQUNqRSxHQUFHLENBQUMsUUFBUSxDQUFDLFFBQVEsRUFBRSxNQUFNLENBQUMsQ0FBQztJQUNqQyxDQUFDO3dHQTVIVSxxQkFBcUI7NEZBQXJCLHFCQUFxQixvVUFTQSxnQkFBZ0IsZ0VBWHRDLDBDQUEwQzs7NEZBRXpDLHFCQUFxQjtrQkFOakMsU0FBUzttQkFBQztvQkFDVCxlQUFlLEVBQUUsdUJBQXVCLENBQUMsTUFBTTtvQkFDL0MsUUFBUSxFQUFFLG1CQUFtQjtvQkFDN0IsVUFBVSxFQUFFLElBQUk7b0JBQ2hCLFFBQVEsRUFBRSwwQ0FBMEM7aUJBQ3JEOzhCQUVVLEtBQUs7c0JBQWIsS0FBSztnQkFDRyxPQUFPO3NCQUFmLEtBQUs7Z0JBQ0csTUFBTTtzQkFBZCxLQUFLO2dCQUNHLFlBQVk7c0JBQXBCLEtBQUs7Z0JBQ0csUUFBUTtzQkFBaEIsS0FBSztnQkFDRyxRQUFRO3NCQUFoQixLQUFLO2dCQUNHLFNBQVM7c0JBQWpCLEtBQUs7Z0JBR1csU0FBUztzQkFEekIsU0FBUzt1QkFBQyxXQUFXLEVBQUUsRUFBRSxJQUFJLEVBQUUsZ0JBQWdCLEVBQUUsTUFBTSxFQUFFLElBQUksRUFBRSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG4gIENoYW5nZURldGVjdGlvblN0cmF0ZWd5LFxuICBDb21wb25lbnQsXG4gIENvbXBvbmVudFJlZixcbiAgSW5qZWN0b3IsXG4gIElucHV0LFxuICBPbkNoYW5nZXMsIE9uRGVzdHJveSxcbiAgU2ltcGxlQ2hhbmdlcyxcbiAgVmlld0NoaWxkLFxuICBWaWV3Q29udGFpbmVyUmVmLFxuICBpbmplY3QsXG4gIGlzRGV2TW9kZSxcbn0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBBYnN0cmFjdENvbnRyb2wgfSBmcm9tICdAYW5ndWxhci9mb3Jtcyc7XG5pbXBvcnQgeyBTdWJzY3JpcHRpb24gfSBmcm9tICdyeGpzJztcbmltcG9ydCB0eXBlIHsgTmVzdGVkRmllbGRDb25maWcsIEVudGl0eUZvcm1Db25maWcsIE5lc3RlZFRhYkNvbmZpZyB9IGZyb20gJ0BkeW5hbWljLWVudGl0eS9jb3JlJztcbmltcG9ydCB7IGZpbmRUYWIgfSBmcm9tICdAZHluYW1pYy1lbnRpdHkvY29yZSc7XG5pbXBvcnQgeyBGaWVsZFJlZ2lzdHJ5U2VydmljZSB9IGZyb20gJy4uLy4uL3NlcnZpY2VzL2ZpZWxkLXJlZ2lzdHJ5LnNlcnZpY2UnO1xuaW1wb3J0IHsgUmJhY1NlcnZpY2UgfSBmcm9tICcuLi8uLi9zZXJ2aWNlcy9yYmFjLnNlcnZpY2UnO1xuXG4vKipcbiAqIER5bmFtaWNGaWVsZENvbXBvbmVudCDigJQgbW91bnRzIHRoZSBjb3JyZWN0IGZpZWxkIGNvbXBvbmVudCBmb3IgYSBnaXZlbiBOZXN0ZWRGaWVsZENvbmZpZy5cbiAqIFVzZXMgVmlld0NvbnRhaW5lclJlZi5jcmVhdGVDb21wb25lbnQoKSBhbmQgcGFzc2VzIGlucHV0cyB2aWEgc2V0SW5wdXQoKTsgc2VlXG4gKiBEeW5hbWljRmllbGRDb21wb25lbnRDb250cmFjdCBmb3IgdGhlIGZpdmUgaW5wdXRzIGV2ZXJ5IGZpZWxkIGNvbXBvbmVudCByZWNlaXZlcy5cbiAqIE5ldmVyIGFkZCBmaWVsZC10eXBlLXNwZWNpZmljIGxvZ2ljIGhlcmUg4oCUIHRoaXMgY29tcG9uZW50IG11c3QgcmVtYWluIGdlbmVyaWMuXG4gKlxuICogVGhlIDUgaW5wdXRzIChmaWVsZCwgY29udHJvbCwgbGFuZ3VhZ2UsIHJlYWRvbmx5LCBtYXNrZWQpIGFyZSBwYXNzZWQgdG8gZXZlcnkgbW91bnRlZFxuICogY29tcG9uZW50IHVuaWZvcm1seSDigJQgbm8gc3BlY2lhbC1jYXNpbmcgcGVyIHR5cGUuXG4gKi9cbkBDb21wb25lbnQoe1xuICBjaGFuZ2VEZXRlY3Rpb246IENoYW5nZURldGVjdGlvblN0cmF0ZWd5Lk9uUHVzaCxcbiAgc2VsZWN0b3I6ICduZ3gtZHluYW1pYy1maWVsZCcsXG4gIHN0YW5kYWxvbmU6IHRydWUsXG4gIHRlbXBsYXRlOiBgPG5nLWNvbnRhaW5lciAjZmllbGRIb3N0PjwvbmctY29udGFpbmVyPmAsXG59KVxuZXhwb3J0IGNsYXNzIER5bmFtaWNGaWVsZENvbXBvbmVudCBpbXBsZW1lbnRzIE9uQ2hhbmdlcywgT25EZXN0cm95IHtcbiAgQElucHV0KCkgZmllbGQhOiBOZXN0ZWRGaWVsZENvbmZpZztcbiAgQElucHV0KCkgY29udHJvbCE6IEFic3RyYWN0Q29udHJvbDtcbiAgQElucHV0KCkgY29uZmlnITogRW50aXR5Rm9ybUNvbmZpZztcbiAgQElucHV0KCkgY3VycmVudFRhYklkPzogc3RyaW5nO1xuICBASW5wdXQoKSBsYW5ndWFnZTogc3RyaW5nID0gJ2VuJztcbiAgQElucHV0KCkgcmVhZG9ubHk6IGJvb2xlYW4gPSBmYWxzZTtcbiAgQElucHV0KCkgdXNlclJvbGVzOiBzdHJpbmdbXSA9IFtdO1xuXG4gIEBWaWV3Q2hpbGQoJ2ZpZWxkSG9zdCcsIHsgcmVhZDogVmlld0NvbnRhaW5lclJlZiwgc3RhdGljOiB0cnVlIH0pXG4gIHByaXZhdGUgcmVhZG9ubHkgZmllbGRIb3N0ITogVmlld0NvbnRhaW5lclJlZjtcblxuICBwcml2YXRlIHJlYWRvbmx5IGZpZWxkUmVnaXN0cnkgPSBpbmplY3QoRmllbGRSZWdpc3RyeVNlcnZpY2UpO1xuICBwcml2YXRlIHJlYWRvbmx5IHJiYWNTZXJ2aWNlID0gaW5qZWN0KFJiYWNTZXJ2aWNlKTtcbiAgLyoqXG4gICAqIFBhc3NlZCBpbnRvIGBjcmVhdGVDb21wb25lbnRgIHNvIGEgaG9zdGVkIGZpZWxkIHNlZXMgdGhpcyBob3N0J3MgaW5qZWN0b3Ig4oCUIGluY2x1ZGluZ1xuICAgKiBgRHluYW1pY0Zvcm1Db21wb25lbnRgJ3Mgc2NvcGVkIGBFbnRpdHlSZWZTZWxlY3Rpb25TZXJ2aWNlYC4gV2l0aG91dCBpdCwgYSBzdGFuZGFsb25lXG4gICAqIGZpZWxkIHJlc29sdmVzIHRoZSByb290IGJ1cyBhbmQgYGF1dG9QYXRjaGAgbmV2ZXIgcnVucy5cbiAgICovXG4gIHByaXZhdGUgcmVhZG9ubHkgaW5qZWN0b3IgPSBpbmplY3QoSW5qZWN0b3IpO1xuXG4gIHByaXZhdGUgY29tcG9uZW50UmVmOiBDb21wb25lbnRSZWY8dW5rbm93bj4gfCBudWxsID0gbnVsbDtcblxuICBuZ09uQ2hhbmdlcyhfY2hhbmdlczogU2ltcGxlQ2hhbmdlcyk6IHZvaWQge1xuICAgIHRoaXMubW91bnRGaWVsZCgpO1xuICB9XG5cbiAgcHJpdmF0ZSBtb3VudEZpZWxkKCk6IHZvaWQge1xuICAgIGlmICghdGhpcy5maWVsZCB8fCAhdGhpcy5jb250cm9sKSByZXR1cm47XG5cbiAgICBjb25zdCBDb21wb25lbnRDbGFzcyA9IHRoaXMuZmllbGRSZWdpc3RyeS5yZXNvbHZlKHRoaXMuZmllbGQudHlwZSk7XG4gICAgaWYgKCFDb21wb25lbnRDbGFzcykge1xuICAgICAgdGhpcy53YXJuVW5yZXNvbHZlZCh0aGlzLmZpZWxkLnR5cGUpO1xuICAgICAgcmV0dXJuOyAvLyBVbmtub3duIGZpZWxkIHR5cGUg4oCUIHJlbmRlciBub3RoaW5nXG4gICAgfVxuXG4gICAgLy8gRGV0ZXJtaW5lIG1hc2tpbmcgZm9yIHRoaXMgc3BlY2lmaWMgZmllbGRcbiAgICBjb25zdCB0YWI6IE5lc3RlZFRhYkNvbmZpZyB8IG51bGwgPSB0aGlzLmN1cnJlbnRUYWJJZCA/IGZpbmRUYWIodGhpcy5jb25maWc/LnRhYnMsIHRoaXMuY3VycmVudFRhYklkKSA6IG51bGw7XG4gICAgY29uc3QgbWFza2VkID0gdGhpcy5yYmFjU2VydmljZS5zaG91bGRNYXNrRmllbGQodGhpcy5maWVsZCwgdGFiID8/IHVuZGVmaW5lZCwgdGhpcy5jb25maWcsIHRoaXMudXNlclJvbGVzKTtcblxuICAgIC8vIFJlLXVzZSBleGlzdGluZyBjb21wb25lbnQgaWYgc2FtZSB0eXBlLCBvdGhlcndpc2UgcmVjcmVhdGVcbiAgICBpZiAodGhpcy5jb21wb25lbnRSZWYgJiYgdGhpcy5jb21wb25lbnRSZWYuaW5zdGFuY2UgaW5zdGFuY2VvZiBDb21wb25lbnRDbGFzcykge1xuICAgICAgdGhpcy5zZXRJbnB1dHModGhpcy5jb21wb25lbnRSZWYsIG1hc2tlZCk7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5maWVsZEhvc3QuY2xlYXIoKTtcbiAgICB0aGlzLmNvbXBvbmVudFJlZiA9IHRoaXMuZmllbGRIb3N0LmNyZWF0ZUNvbXBvbmVudChDb21wb25lbnRDbGFzcywge1xuICAgICAgaW5qZWN0b3I6IHRoaXMuaW5qZWN0b3IsXG4gICAgfSk7XG4gICAgdGhpcy5zZXRJbnB1dHModGhpcy5jb21wb25lbnRSZWYsIG1hc2tlZCk7XG4gICAgdGhpcy53YXRjaENvbnRyb2woKTtcbiAgICB0aGlzLmNvbXBvbmVudFJlZi5jaGFuZ2VEZXRlY3RvclJlZi5kZXRlY3RDaGFuZ2VzKCk7XG4gIH1cblxuICAvKipcbiAgICogRmllbGQgdHlwZXMgYXJlIG9wdC1pbiAoc2VlIGBwcm92aWRlRmllbGRUeXBlc2AgLyBgcHJvdmlkZUJ1aWx0SW5GaWVsZFR5cGVzYCksIHNvIGFuXG4gICAqIHVucmVnaXN0ZXJlZCB0eXBlIHJlbmRlcnMgbm90aGluZy4gU2F5IHNvIG9uY2UgcGVyIHR5cGUgaW4gZGV2IGJ1aWxkcyByYXRoZXIgdGhhblxuICAgKiBsZWF2aW5nIGEgc2lsZW50bHkgYmxhbmsgc2xvdC5cbiAgICovXG4gIHByaXZhdGUgd2FyblVucmVzb2x2ZWQodHlwZTogc3RyaW5nKTogdm9pZCB7XG4gICAgaWYgKCFpc0Rldk1vZGUoKSB8fCBEeW5hbWljRmllbGRDb21wb25lbnQud2FybmVkVHlwZXMuaGFzKHR5cGUpKSByZXR1cm47XG4gICAgRHluYW1pY0ZpZWxkQ29tcG9uZW50Lndhcm5lZFR5cGVzLmFkZCh0eXBlKTtcbiAgICBjb25zb2xlLndhcm4oXG4gICAgICBgW25neC1keW5hbWljLWVudGl0eV0gTm8gY29tcG9uZW50IHJlZ2lzdGVyZWQgZm9yIGZpZWxkIHR5cGUgXCIke3R5cGV9XCIg4oCUIHRoZSBmaWVsZCB3YXMgbm90IHJlbmRlcmVkLiBgICtcbiAgICAgICAgYFJlZ2lzdGVyIGl0IHdpdGggcHJvdmlkZUZpZWxkVHlwZXMoeyAnJHt0eXBlfSc6IE15Q29tcG9uZW50IH0pIG9yIHByb3ZpZGVCdWlsdEluRmllbGRUeXBlcygpLmAsXG4gICAgKTtcbiAgfVxuXG4gIHByaXZhdGUgc3RhdGljIHJlYWRvbmx5IHdhcm5lZFR5cGVzID0gbmV3IFNldDxzdHJpbmc+KCk7XG5cbiAgLyoqXG4gICAqIFJlLWNoZWNrIHRoZSBob3N0ZWQgZmllbGQgY29tcG9uZW50LlxuICAgKlxuICAgKiBUaGUgZmllbGQgY29tcG9uZW50cyBhcmUgT25QdXNoLCBzbyB0aGV5IHJlLXJlbmRlciBvbiBhbiBpbnB1dCBjaGFuZ2UsIGFuIGV2ZW50IGZyb21cbiAgICogdGhlaXIgb3duIHRlbXBsYXRlLCBvciBhIHNpZ25hbCB0aGV5IHJlYWQuIGBmb3JtLm1hcmtBbGxBc1RvdWNoZWQoKWAgaXMgbm9uZSBvZiB0aG9zZSDigJRcbiAgICogaXQgZmxpcHMgYHRvdWNoZWRgIGZyb20gb3V0c2lkZSwgYW5kIGV2ZXJ5IGZpZWxkJ3MgZXJyb3IgbWVzc2FnZSBkZXBlbmRzIG9uIGl0LiBXaXRob3V0XG4gICAqIHRoaXMsIGEgYmxvY2tlZCBzdWJtaXQgd291bGQgbWFyayB0aGUgZm9ybSB0b3VjaGVkIGFuZCBubyBlcnJvciB3b3VsZCBhcHBlYXIuXG4gICAqL1xuICByZWZyZXNoKCk6IHZvaWQge1xuICAgIHRoaXMuY29tcG9uZW50UmVmPy5jaGFuZ2VEZXRlY3RvclJlZi5kZXRlY3RDaGFuZ2VzKCk7XG4gIH1cblxuICAvKipcbiAgICogUmUtY2hlY2sgdGhlIGhvc3RlZCBjb21wb25lbnQgd2hlbmV2ZXIgaXRzIGNvbnRyb2wgY2hhbmdlcyBmcm9tIG91dHNpZGUuXG4gICAqXG4gICAqIFRoZSBmaWVsZCBjb21wb25lbnRzIGFyZSBPblB1c2gsIHNvIHRoZXkgcmUtcmVuZGVyIG9uIGFuIGlucHV0IGNoYW5nZSBvciBhbiBldmVudCBmcm9tXG4gICAqIHRoZWlyIG93biB0ZW1wbGF0ZS4gQSBjb250cm9sIG11dGF0ZWQgZXh0ZXJuYWxseSBpcyBuZWl0aGVyIOKAlCBhbmQgdGhhdCBpcyBub3QgYW4gZWRnZVxuICAgKiBjYXNlOiBwYXRjaEZvcm0sIHJlc2V0LCBhdXRvUGF0Y2ggYW5kIHBhdGNoT25UcnVlIGFsbCBkbyBleGFjdGx5IHRoYXQuIFdpdGhvdXQgdGhpcywgYVxuICAgKiBmaWVsZCBwYXRjaGVkIGZyb20gYSByZWNvcmQgd291bGQga2VlcCByZW5kZXJpbmcgaXRzIHByZXZpb3VzIHZhbHVlLlxuICAgKlxuICAgKiBgZGV0ZWN0Q2hhbmdlcygpYCByYXRoZXIgdGhhbiBgbWFya0ZvckNoZWNrKClgOiBhIHNlbGVjdGlvbiB0aGF0IGFycml2ZXMgZnJvbSBhIG5hdGl2ZVxuICAgKiBgY2hhbmdlYCBldmVudCAob3IgUGxheXdyaWdodCkgbWF5IG5vdCBiZSBmb2xsb3dlZCBieSBhbm90aGVyIEFuZ3VsYXIgdGljaywgc28gYSBkaXJ0eVxuICAgKiBmbGFnIHdvdWxkIG5ldmVyIGJlIGZsdXNoZWQuIFJ1bm5pbmcgQ0Qgb24gdGhlIGhvc3RlZCBjb21wb25lbnQgbm93IGlzIHRoZSBjb3B5IHNob3dpbmcgdXAuXG4gICAqXG4gICAqIERvbmUgaGVyZSByYXRoZXIgdGhhbiBpbiBlYWNoIG9mIHRoZSBlaWdodGVlbiBmaWVsZCBjb21wb25lbnRzOiB0aGUgaG9zdCBvd25zIHRoZVxuICAgKiBjb21wb25lbnQgcmVmZXJlbmNlLCBzbyBvbmUgc3Vic2NyaXB0aW9uIGNvdmVycyBldmVyeSB0eXBlIGluY2x1ZGluZyBjdXN0b20gb25lcy5cbiAgICovXG4gIHByaXZhdGUgd2F0Y2hDb250cm9sKCk6IHZvaWQge1xuICAgIHRoaXMuY29udHJvbFN1Yj8udW5zdWJzY3JpYmUoKTtcbiAgICBpZiAoIXRoaXMuY29udHJvbCkgcmV0dXJuO1xuXG4gICAgdGhpcy5jb250cm9sU3ViID0gdGhpcy5jb250cm9sLnZhbHVlQ2hhbmdlcy5zdWJzY3JpYmUoKCkgPT4gdGhpcy5yZWZyZXNoKCkpO1xuICB9XG5cbiAgcHJpdmF0ZSBjb250cm9sU3ViPzogU3Vic2NyaXB0aW9uO1xuXG4gIG5nT25EZXN0cm95KCk6IHZvaWQge1xuICAgIHRoaXMuY29udHJvbFN1Yj8udW5zdWJzY3JpYmUoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBQYXNzIGFsbCA1IGNvbnRyYWN0IGlucHV0cyB2aWEgQ29tcG9uZW50UmVmLnNldElucHV0KCkg4oCUIHVuaWZvcm0gZm9yIGFsbCB0eXBlcy5cbiAgICogVGhlIHB1YmxpYyBzaGFwZSBpcyBEeW5hbWljRmllbGRDb21wb25lbnRDb250cmFjdC5cbiAgICogTXVzdCB1c2Ugc2V0SW5wdXQoKSwgbm90IHByb3BlcnR5IGFzc2lnbm1lbnQ6IHRoZSBmaWVsZCBjb21wb25lbnRzIGRlY2xhcmUgaW5wdXRzIHdpdGhcbiAgICogZGVmaW5pdGUgYXNzaWdubWVudCBhbmQgbm8gaW5pdGlhbGl6ZXIsIGFuZCB0aGUgbGliIGNvbXBpbGVzIHdpdGhcbiAgICogdXNlRGVmaW5lRm9yQ2xhc3NGaWVsZHM6ZmFsc2UsIHNvIGAnZmllbGQnIGluIGluc3RhbmNlYCBpcyBmYWxzZSB1bnRpbCBmaXJzdCBzZXQuXG4gICAqL1xuICBwcml2YXRlIHNldElucHV0cyhyZWY6IENvbXBvbmVudFJlZjx1bmtub3duPiwgbWFza2VkOiBib29sZWFuKTogdm9pZCB7XG4gICAgcmVmLnNldElucHV0KCdmaWVsZCcsIHRoaXMuZmllbGQpO1xuICAgIHJlZi5zZXRJbnB1dCgnY29udHJvbCcsIHRoaXMuY29udHJvbCk7XG4gICAgcmVmLnNldElucHV0KCdsYW5ndWFnZScsIHRoaXMubGFuZ3VhZ2UpO1xuICAgIHJlZi5zZXRJbnB1dCgncmVhZG9ubHknLCB0aGlzLnJlYWRvbmx5IHx8ICEhdGhpcy5maWVsZC5yZWFkb25seSk7XG4gICAgcmVmLnNldElucHV0KCdtYXNrZWQnLCBtYXNrZWQpO1xuICB9XG59XG4iXX0=
|