@esfaenza/forms-and-validations 16.2.31 → 17.3.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/esm2022/esfaenza-forms-and-validations.mjs +4 -4
- package/esm2022/lib/forms/base-form-control.mjs +558 -558
- package/esm2022/lib/forms/form-adaptive/form-adaptive.component.loc.mjs +21 -21
- package/esm2022/lib/forms/form-adaptive/form-adaptive.component.mjs +420 -420
- package/esm2022/lib/forms/form-autocomplete/form-autocomplete.component.loc.mjs +20 -20
- package/esm2022/lib/forms/form-autocomplete/form-autocomplete.component.mjs +289 -289
- package/esm2022/lib/forms/form-checkbox/form-checkbox.component.mjs +74 -74
- package/esm2022/lib/forms/form-date/form-date.component.mjs +69 -69
- package/esm2022/lib/forms/form-datetime/form-datetime.component.mjs +67 -67
- package/esm2022/lib/forms/form-empty/form-empty.component.mjs +29 -29
- package/esm2022/lib/forms/form-error/form-error.component.mjs +41 -41
- package/esm2022/lib/forms/form-file/form-file.component.loc.mjs +21 -21
- package/esm2022/lib/forms/form-file/form-file.component.mjs +175 -175
- package/esm2022/lib/forms/form-info/form-info.component.mjs +41 -41
- package/esm2022/lib/forms/form-input/form-input.component.mjs +83 -83
- package/esm2022/lib/forms/form-multiselect/form-multiselect.component.loc.mjs +22 -22
- package/esm2022/lib/forms/form-multiselect/form-multiselect.component.mjs +163 -163
- package/esm2022/lib/forms/form-select/form-select.component.loc.mjs +20 -20
- package/esm2022/lib/forms/form-select/form-select.component.mjs +165 -165
- package/esm2022/lib/forms/form-template/form-template.component.mjs +76 -76
- package/esm2022/lib/forms/form-textarea/form-textarea.component.mjs +57 -57
- package/esm2022/lib/forms/form-time/form-time.component.mjs +115 -115
- package/esm2022/lib/forms-and-validations.module.mjs +199 -199
- package/esm2022/lib/models/AppFile.mjs +13 -13
- package/esm2022/lib/models/ChangeEvent.mjs +6 -6
- package/esm2022/lib/models/FormsAndValidationsModuleConfig.mjs +5 -5
- package/esm2022/lib/models/dayjs-adapter/dayjs-date-adapter.mjs +89 -89
- package/esm2022/lib/tokens.mjs +7 -7
- package/esm2022/lib/validations/base-validation.loc.mjs +22 -22
- package/esm2022/lib/validations/base-validation.mjs +328 -328
- package/esm2022/lib/validations/customValidators/CustomRequiredDirective.mjs +40 -40
- package/esm2022/lib/validations/validation-autocomplete/validation-autocomplete.component.mjs +147 -147
- package/esm2022/lib/validations/validation-autocomplete-multi/validation-autocomplete-multi.component.mjs +240 -240
- package/esm2022/lib/validations/validation-currency/validation-currency.component.mjs +75 -75
- package/esm2022/lib/validations/validation-date/validation-date.component.mjs +183 -183
- package/esm2022/lib/validations/validation-datetime/validation-datetime.component.mjs +212 -212
- package/esm2022/lib/validations/validation-input/validation-input.component.mjs +222 -222
- package/esm2022/lib/validations/validation-select/validation-select.component.mjs +183 -183
- package/esm2022/lib/validations/validation-text-area/validation-text-area.component.mjs +78 -78
- package/esm2022/public-api.mjs +39 -39
- package/fesm2022/esfaenza-forms-and-validations.mjs +4152 -4152
- package/fesm2022/esfaenza-forms-and-validations.mjs.map +1 -1
- package/index.d.ts +5 -5
- package/lib/forms/base-form-control.d.ts +276 -276
- package/lib/forms/form-adaptive/form-adaptive.component.d.ts +126 -126
- package/lib/forms/form-adaptive/form-adaptive.component.loc.d.ts +14 -14
- package/lib/forms/form-autocomplete/form-autocomplete.component.d.ts +84 -84
- package/lib/forms/form-autocomplete/form-autocomplete.component.loc.d.ts +14 -14
- package/lib/forms/form-checkbox/form-checkbox.component.d.ts +23 -23
- package/lib/forms/form-date/form-date.component.d.ts +21 -21
- package/lib/forms/form-datetime/form-datetime.component.d.ts +23 -23
- package/lib/forms/form-empty/form-empty.component.d.ts +15 -15
- package/lib/forms/form-error/form-error.component.d.ts +19 -19
- package/lib/forms/form-file/form-file.component.d.ts +46 -46
- package/lib/forms/form-file/form-file.component.loc.d.ts +14 -14
- package/lib/forms/form-info/form-info.component.d.ts +19 -19
- package/lib/forms/form-input/form-input.component.d.ts +33 -33
- package/lib/forms/form-multiselect/form-multiselect.component.d.ts +67 -67
- package/lib/forms/form-multiselect/form-multiselect.component.loc.d.ts +14 -14
- package/lib/forms/form-select/form-select.component.d.ts +43 -43
- package/lib/forms/form-select/form-select.component.loc.d.ts +14 -14
- package/lib/forms/form-template/form-template.component.d.ts +38 -38
- package/lib/forms/form-textarea/form-textarea.component.d.ts +18 -18
- package/lib/forms/form-time/form-time.component.d.ts +40 -40
- package/lib/forms-and-validations.module.d.ts +47 -47
- package/lib/models/AppFile.d.ts +21 -21
- package/lib/models/ChangeEvent.d.ts +5 -5
- package/lib/models/FormsAndValidationsModuleConfig.d.ts +11 -11
- package/lib/models/dayjs-adapter/dayjs-date-adapter.d.ts +49 -49
- package/lib/tokens.d.ts +7 -7
- package/lib/validations/base-validation.d.ts +219 -219
- package/lib/validations/base-validation.loc.d.ts +14 -14
- package/lib/validations/customValidators/CustomRequiredDirective.d.ts +24 -24
- package/lib/validations/validation-autocomplete/validation-autocomplete.component.d.ts +58 -58
- package/lib/validations/validation-autocomplete-multi/validation-autocomplete-multi.component.d.ts +88 -88
- package/lib/validations/validation-currency/validation-currency.component.d.ts +28 -28
- package/lib/validations/validation-date/validation-date.component.d.ts +79 -79
- package/lib/validations/validation-datetime/validation-datetime.component.d.ts +109 -109
- package/lib/validations/validation-input/validation-input.component.d.ts +134 -134
- package/lib/validations/validation-select/validation-select.component.d.ts +95 -95
- package/lib/validations/validation-text-area/validation-text-area.component.d.ts +28 -28
- package/package.json +13 -13
- package/public-api.d.ts +31 -31
|
@@ -1,328 +1,328 @@
|
|
|
1
|
-
// Angular
|
|
2
|
-
import { EventEmitter, Input, Output, ViewChild, Directive } from "@angular/core";
|
|
3
|
-
import { RequiredValidator } from "@angular/forms";
|
|
4
|
-
// Direttive, Componenti, Librerie
|
|
5
|
-
import { TooltipDirective } from "ngx-bootstrap/tooltip";
|
|
6
|
-
import { Subject } from "rxjs";
|
|
7
|
-
import { takeUntil } from "rxjs/operators";
|
|
8
|
-
import * as i0 from "@angular/core";
|
|
9
|
-
/**
|
|
10
|
-
* Classe astratta base che contiene le logiche / proprietà in comune a tutti i validatori
|
|
11
|
-
*
|
|
12
|
-
* Nota bene: I tooltip rallentano tantissimo la pagina perché il tizio che ha fatto ngx bootstrap non è capace
|
|
13
|
-
*/
|
|
14
|
-
export class BaseValidation {
|
|
15
|
-
/** @ignore Constructor */
|
|
16
|
-
constructor(cdr) {
|
|
17
|
-
this.cdr = cdr;
|
|
18
|
-
/**
|
|
19
|
-
* Variabile per tenere in memoria il fatto che il componente è forzato a invalido o no
|
|
20
|
-
*/
|
|
21
|
-
this._forceInvalid = false;
|
|
22
|
-
/**
|
|
23
|
-
* Indica se il valore è obbligatorio o opzionale
|
|
24
|
-
*/
|
|
25
|
-
this.required = false;
|
|
26
|
-
/**
|
|
27
|
-
* Indica se di default deve valutare il messaggio di errore in base al validatore che fallisce.
|
|
28
|
-
*
|
|
29
|
-
* Se fallisce il required validator scriverà che l'input è obbligatorio, se invece fallisce
|
|
30
|
-
* un eventuale pattern validator scriverà che il formato dell'input è invalido
|
|
31
|
-
*/
|
|
32
|
-
this.InferErrorMessages = true;
|
|
33
|
-
/**
|
|
34
|
-
* Modalità in cui viene mostrato il campo, 1-1 rispetto alle definizioni di Angular Material
|
|
35
|
-
*/
|
|
36
|
-
this.FieldAppearence = "outline";
|
|
37
|
-
/**
|
|
38
|
-
* Indica se il **Placeholder** dev'essere usato come una floating label di material o solo come un placeholder standard
|
|
39
|
-
*
|
|
40
|
-
* Ignorata lato autocomplete, autocomplete-multi e select in quanto hanno gestioni particolari di placeholder ecc...
|
|
41
|
-
*/
|
|
42
|
-
this.FloatingLabel = true;
|
|
43
|
-
/**
|
|
44
|
-
* Messaggio da mostrare se la validazione fallisce.
|
|
45
|
-
*
|
|
46
|
-
* Se questo è valorizzato, il messaggio non viene valutato in automatico nonstante **InferErrorMessages** sia **true**
|
|
47
|
-
*/
|
|
48
|
-
this.validationFailed = "";
|
|
49
|
-
/**
|
|
50
|
-
* Indica se il componente è in sola lettura
|
|
51
|
-
*/
|
|
52
|
-
this.Readonly = false;
|
|
53
|
-
/**
|
|
54
|
-
* Indica le dimensioni del componente
|
|
55
|
-
*/
|
|
56
|
-
this.widthPx = null;
|
|
57
|
-
/**
|
|
58
|
-
* Indica se il componente è disabilitato o no (più o meno stesso concetto del readonly)
|
|
59
|
-
*/
|
|
60
|
-
this.disabled = false;
|
|
61
|
-
/**
|
|
62
|
-
* Eventuale placeholder da mostrare al posto del valore quando il valore è nullo / vuoto
|
|
63
|
-
*/
|
|
64
|
-
this.placeholder = "";
|
|
65
|
-
/**
|
|
66
|
-
* Classi da applicare al componente
|
|
67
|
-
*/
|
|
68
|
-
this.class = "";
|
|
69
|
-
/**
|
|
70
|
-
* Stili da applicare al componente
|
|
71
|
-
*/
|
|
72
|
-
this.style = "";
|
|
73
|
-
/**
|
|
74
|
-
* Pattern di validazione dell'input
|
|
75
|
-
*/
|
|
76
|
-
this.pattern = "";
|
|
77
|
-
/**
|
|
78
|
-
* Indica di non validare il componente
|
|
79
|
-
*/
|
|
80
|
-
this.noValidate = false;
|
|
81
|
-
/**
|
|
82
|
-
* Indica se abilitare o meno l'autocompletamento di default del browser
|
|
83
|
-
*/
|
|
84
|
-
this.autocomplete = "off";
|
|
85
|
-
/**
|
|
86
|
-
* Id dell'input. È importante impostarlo soprattutto se l'interfaccia generata dev'essere testata
|
|
87
|
-
*/
|
|
88
|
-
this.id = "";
|
|
89
|
-
/**
|
|
90
|
-
* Evento che sostituisce l'ngModelChange facendolo funzionare in maniera un po' più consistente
|
|
91
|
-
*/
|
|
92
|
-
this.inputChange = new EventEmitter();
|
|
93
|
-
/**
|
|
94
|
-
* Evento che indica il focus avvenuto su un controllo
|
|
95
|
-
*/
|
|
96
|
-
this.inputFocus = new EventEmitter();
|
|
97
|
-
/**
|
|
98
|
-
* Evento che indica la finalizzazione del valore avvenuta su un controllo
|
|
99
|
-
*/
|
|
100
|
-
this.inputFinalized = new EventEmitter();
|
|
101
|
-
this.destroyed$ = new Subject();
|
|
102
|
-
/**
|
|
103
|
-
* @ignore
|
|
104
|
-
*/
|
|
105
|
-
this.propagateChange = (_) => { };
|
|
106
|
-
}
|
|
107
|
-
/**
|
|
108
|
-
* Query che raccoglie il tooltip in maniera dinamica (ad ogni change detection)
|
|
109
|
-
*
|
|
110
|
-
* @param {TooltipDirective} comp Elemento HTML a cui è applicata la direttiva del tooltip
|
|
111
|
-
*/
|
|
112
|
-
set tooltip_static(comp) {
|
|
113
|
-
if (comp) {
|
|
114
|
-
this.tooltip = comp;
|
|
115
|
-
}
|
|
116
|
-
}
|
|
117
|
-
;
|
|
118
|
-
/**
|
|
119
|
-
* Query che raccoglie l'input o direttiva che contiene il valore in maniera dinamica (ad ogni change detection)
|
|
120
|
-
*
|
|
121
|
-
* @param {NgModel} comp Elemento HTML associato al ngModel del componente
|
|
122
|
-
*/
|
|
123
|
-
set baseInput_static(comp) {
|
|
124
|
-
if (comp) {
|
|
125
|
-
this.baseInput = comp;
|
|
126
|
-
}
|
|
127
|
-
}
|
|
128
|
-
;
|
|
129
|
-
/**
|
|
130
|
-
* Imposta il componente come "submitted" scatenandone le validazioni ed eventualmente la visualizzazione del tooltip di errore
|
|
131
|
-
*
|
|
132
|
-
* @param {boolean} val **true** se si vuole impostare questo controllo come submitted, **false** altrimenti
|
|
133
|
-
*/
|
|
134
|
-
set submitted(val) {
|
|
135
|
-
this._submitted = val;
|
|
136
|
-
if (!this.baseInput)
|
|
137
|
-
return;
|
|
138
|
-
if (val)
|
|
139
|
-
this.baseInput.control.markAsTouched();
|
|
140
|
-
if (this.baseInput.control.status === "INVALID" && val)
|
|
141
|
-
this.showTooltipWithMessage();
|
|
142
|
-
else
|
|
143
|
-
this.tooltip.hide();
|
|
144
|
-
}
|
|
145
|
-
/**
|
|
146
|
-
* Imposta il componente come "invalid" a prescindere dai validatori
|
|
147
|
-
*/
|
|
148
|
-
set forceInvalid(val) {
|
|
149
|
-
this._forceInvalid = val;
|
|
150
|
-
if (val)
|
|
151
|
-
setTimeout(() => {
|
|
152
|
-
this.baseInput.control.setErrors({ forcedtoinvalid: true });
|
|
153
|
-
this.baseInput.control.markAsTouched();
|
|
154
|
-
this.baseInput.control.markAsDirty();
|
|
155
|
-
this.cdr.detectChanges();
|
|
156
|
-
});
|
|
157
|
-
else
|
|
158
|
-
setTimeout(() => {
|
|
159
|
-
this.baseInput.control.setErrors({ forcedtoinvalid: null });
|
|
160
|
-
this.baseInput.control.updateValueAndValidity();
|
|
161
|
-
});
|
|
162
|
-
}
|
|
163
|
-
ngOnInit() {
|
|
164
|
-
if (this.SetValidationSubject) {
|
|
165
|
-
this.SetValidationSubject.pipe(takeUntil(this.destroyed$)).subscribe(v => {
|
|
166
|
-
if (v.fieldName + "_internal" == this.id) {
|
|
167
|
-
this.forceInvalid = true;
|
|
168
|
-
this.showTooltipWithMessage(v.error);
|
|
169
|
-
}
|
|
170
|
-
});
|
|
171
|
-
}
|
|
172
|
-
}
|
|
173
|
-
checkRequiredness(_validators) {
|
|
174
|
-
if (_validators && _validators.some(elem => elem instanceof RequiredValidator && (elem.required === true || (!elem.required && elem.required !== false))))
|
|
175
|
-
this.required = true;
|
|
176
|
-
}
|
|
177
|
-
ngOnDestroy() {
|
|
178
|
-
this.destroyed$.next();
|
|
179
|
-
this.destroyed$.complete();
|
|
180
|
-
}
|
|
181
|
-
/**
|
|
182
|
-
* Helper che controlla se il tooltip deve essere mostrato o meno,
|
|
183
|
-
* richiamato direttamente dall'HTML dei componenti
|
|
184
|
-
*/
|
|
185
|
-
checkTooltip() {
|
|
186
|
-
if ((this.baseInput.invalid && this.baseInput.touched))
|
|
187
|
-
this.showTooltipWithMessage();
|
|
188
|
-
}
|
|
189
|
-
/**
|
|
190
|
-
* Helper che calcola il messaggio da mostrare nel tooltip che andrà ad aprire
|
|
191
|
-
*/
|
|
192
|
-
showTooltipWithMessage(messageOverride = null) {
|
|
193
|
-
// Aggiorno il messaggio di validazione solo se il valore è diverso dall'ultimo valore ricevuto
|
|
194
|
-
if (this.valueOnLastValidation != this.baseInput.value) {
|
|
195
|
-
this.validationFailedBind = messageOverride || this.validationFailed || (this.InferErrorMessages ? this.inferMessage() : "");
|
|
196
|
-
this.valueOnLastValidation = this.baseInput.value;
|
|
197
|
-
}
|
|
198
|
-
if (this.validationFailedBind)
|
|
199
|
-
this.tooltip.show();
|
|
200
|
-
}
|
|
201
|
-
/**
|
|
202
|
-
* Calcola il messaggio da mostrare in base al valore.
|
|
203
|
-
*
|
|
204
|
-
* Entrare in questa funzione significa che lo stato di validazione è fallito, per questo si comporta semplicemente in maniera esclusiva, e cioè:
|
|
205
|
-
*
|
|
206
|
-
* 1) Se ero required e sono senza valore --> Input richiesto
|
|
207
|
-
*
|
|
208
|
-
* 2) Altrimenti se ho un valore --> Di sicuro il formato è errato
|
|
209
|
-
*/
|
|
210
|
-
inferMessage() {
|
|
211
|
-
if (this.required && !this.baseInput.value)
|
|
212
|
-
return this.lc.loc("Required Input");
|
|
213
|
-
if (this.baseInput.value)
|
|
214
|
-
return this.lc.loc("Invalid Input Format");
|
|
215
|
-
}
|
|
216
|
-
/**
|
|
217
|
-
* Forza la chiusura del tooltip
|
|
218
|
-
*/
|
|
219
|
-
closeTooltip() {
|
|
220
|
-
this.tooltip.hide();
|
|
221
|
-
}
|
|
222
|
-
/**
|
|
223
|
-
* Controlla se il controllo è valido e in caso lo sia chiude il tooltip
|
|
224
|
-
*/
|
|
225
|
-
CheckValidity() {
|
|
226
|
-
if (!this.baseInput.statusChanges)
|
|
227
|
-
return;
|
|
228
|
-
this.baseInput.statusChanges.subscribe(event => {
|
|
229
|
-
if (event === "VALID")
|
|
230
|
-
this.tooltip.hide();
|
|
231
|
-
});
|
|
232
|
-
}
|
|
233
|
-
/**
|
|
234
|
-
* L'emit del focus dell'elemento
|
|
235
|
-
*
|
|
236
|
-
* @param {any} toEmit valore da propagare all'esterno
|
|
237
|
-
*/
|
|
238
|
-
onFocus(toEmit) {
|
|
239
|
-
this.inputFocus.emit(toEmit);
|
|
240
|
-
}
|
|
241
|
-
/**
|
|
242
|
-
* Finalizzazione Input
|
|
243
|
-
*/
|
|
244
|
-
onFinalize() {
|
|
245
|
-
this.inputFinalized.emit();
|
|
246
|
-
}
|
|
247
|
-
/**
|
|
248
|
-
* Registra il Subject per ricevere le richieste di Focus dall'esterno
|
|
249
|
-
*/
|
|
250
|
-
registerFocusRequest() {
|
|
251
|
-
if (!this.FocusSubject)
|
|
252
|
-
return;
|
|
253
|
-
this.observable = this.FocusSubject.subscribe(t => {
|
|
254
|
-
this.htmlInput.nativeElement.focus();
|
|
255
|
-
});
|
|
256
|
-
}
|
|
257
|
-
/**
|
|
258
|
-
* Deregistra il Subject delle richieste di focus
|
|
259
|
-
*/
|
|
260
|
-
deregisterFocusRequest() {
|
|
261
|
-
if (this.observable)
|
|
262
|
-
this.observable.unsubscribe();
|
|
263
|
-
}
|
|
264
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "
|
|
265
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "
|
|
266
|
-
}
|
|
267
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "
|
|
268
|
-
type: Directive
|
|
269
|
-
}], ctorParameters:
|
|
270
|
-
type: ViewChild,
|
|
271
|
-
args: [TooltipDirective, { static: false }]
|
|
272
|
-
}], tooltip_static: [{
|
|
273
|
-
type: ViewChild,
|
|
274
|
-
args: [TooltipDirective, { static: true }]
|
|
275
|
-
}], htmlInput: [{
|
|
276
|
-
type: ViewChild,
|
|
277
|
-
args: ['htmlInput', { static: false }]
|
|
278
|
-
}], baseInput: [{
|
|
279
|
-
type: ViewChild,
|
|
280
|
-
args: ["baseInput", { static: false }]
|
|
281
|
-
}], baseInput_static: [{
|
|
282
|
-
type: ViewChild,
|
|
283
|
-
args: ["baseInput", { static: true }]
|
|
284
|
-
}], FocusSubject: [{
|
|
285
|
-
type: Input
|
|
286
|
-
}], SetValidationSubject: [{
|
|
287
|
-
type: Input
|
|
288
|
-
}], InferErrorMessages: [{
|
|
289
|
-
type: Input
|
|
290
|
-
}], FieldAppearence: [{
|
|
291
|
-
type: Input
|
|
292
|
-
}], FloatingLabel: [{
|
|
293
|
-
type: Input
|
|
294
|
-
}], validationFailed: [{
|
|
295
|
-
type: Input
|
|
296
|
-
}], Readonly: [{
|
|
297
|
-
type: Input
|
|
298
|
-
}], widthPx: [{
|
|
299
|
-
type: Input
|
|
300
|
-
}], disabled: [{
|
|
301
|
-
type: Input
|
|
302
|
-
}], placeholder: [{
|
|
303
|
-
type: Input
|
|
304
|
-
}], class: [{
|
|
305
|
-
type: Input
|
|
306
|
-
}], style: [{
|
|
307
|
-
type: Input
|
|
308
|
-
}], pattern: [{
|
|
309
|
-
type: Input
|
|
310
|
-
}], noValidate: [{
|
|
311
|
-
type: Input
|
|
312
|
-
}], autocomplete: [{
|
|
313
|
-
type: Input
|
|
314
|
-
}], id: [{
|
|
315
|
-
type: Input
|
|
316
|
-
}], inputChange: [{
|
|
317
|
-
type: Output
|
|
318
|
-
}], inputFocus: [{
|
|
319
|
-
type: Output
|
|
320
|
-
}], inputFinalized: [{
|
|
321
|
-
type: Output
|
|
322
|
-
}], submitted: [{
|
|
323
|
-
type: Input,
|
|
324
|
-
args: ["submitted"]
|
|
325
|
-
}], forceInvalid: [{
|
|
326
|
-
type: Input
|
|
327
|
-
}] } });
|
|
328
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYmFzZS12YWxpZGF0aW9uLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvZm9ybXMtYW5kLXZhbGlkYXRpb25zL3NyYy9saWIvdmFsaWRhdGlvbnMvYmFzZS12YWxpZGF0aW9uLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLFVBQVU7QUFDVixPQUFPLEVBQUUsWUFBWSxFQUFFLEtBQUssRUFBRSxNQUFNLEVBQUUsU0FBUyxFQUFFLFNBQVMsRUFBaUMsTUFBTSxlQUFlLENBQUM7QUFDakgsT0FBTyxFQUFXLGlCQUFpQixFQUFhLE1BQU0sZ0JBQWdCLENBQUM7QUFLdkUsa0NBQWtDO0FBQ2xDLE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLHVCQUF1QixDQUFDO0FBQ3pELE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFFL0IsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLGdCQUFnQixDQUFDOztBQUUzQzs7OztHQUlHO0FBRUgsTUFBTSxPQUFnQixjQUFjO0lBRWhDLDBCQUEwQjtJQUMxQixZQUFzQixHQUFzQjtRQUF0QixRQUFHLEdBQUgsR0FBRyxDQUFtQjtRQXNCNUM7O1dBRUc7UUFDTyxrQkFBYSxHQUFZLEtBQUssQ0FBQztRQUV6Qzs7V0FFRztRQUNJLGFBQVEsR0FBWSxLQUFLLENBQUM7UUE2Q2pDOzs7OztXQUtHO1FBQ00sdUJBQWtCLEdBQVksSUFBSSxDQUFDO1FBRTVDOztXQUVHO1FBQ00sb0JBQWUsR0FBK0MsU0FBUyxDQUFDO1FBRWpGOzs7O1dBSUc7UUFDTSxrQkFBYSxHQUFZLElBQUksQ0FBQztRQUV2Qzs7OztXQUlHO1FBQ00scUJBQWdCLEdBQVcsRUFBRSxDQUFDO1FBRXZDOztXQUVHO1FBQ00sYUFBUSxHQUFZLEtBQUssQ0FBQztRQUVuQzs7V0FFRztRQUNNLFlBQU8sR0FBVyxJQUFJLENBQUM7UUFFaEM7O1dBRUc7UUFDTSxhQUFRLEdBQVksS0FBSyxDQUFD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QVE7c0JBQWhCLEtBQUs7Z0JBS0csT0FBTztzQkFBZixLQUFLO2dCQUtHLFFBQVE7c0JBQWhCLEtBQUs7Z0JBS0csV0FBVztzQkFBbkIsS0FBSztnQkFLRyxLQUFLO3NCQUFiLEtBQUs7Z0JBS0csS0FBSztzQkFBYixLQUFLO2dCQUtHLE9BQU87c0JBQWYsS0FBSztnQkFLRyxVQUFVO3NCQUFsQixLQUFLO2dCQUtHLFlBQVk7c0JBQXBCLEtBQUs7Z0JBS0csRUFBRTtzQkFBVixLQUFLO2dCQUtJLFdBQVc7c0JBQXBCLE1BQU07Z0JBS0csVUFBVTtzQkFBbkIsTUFBTTtnQkFLRyxjQUFjO3NCQUF2QixNQUFNO2dCQU9pQixTQUFTO3NCQUFoQyxLQUFLO3VCQUFDLFdBQVc7Z0JBaUJMLFlBQVk7c0JBQXhCLEtBQUsiLCJzb3VyY2VzQ29udGVudCI6WyIvLyBBbmd1bGFyXHJcbmltcG9ydCB7IEV2ZW50RW1pdHRlciwgSW5wdXQsIE91dHB1dCwgVmlld0NoaWxkLCBEaXJlY3RpdmUsIEVsZW1lbnRSZWYsIENoYW5nZURldGVjdG9yUmVmIH0gZnJvbSBcIkBhbmd1bGFyL2NvcmVcIjtcclxuaW1wb3J0IHsgTmdNb2RlbCwgUmVxdWlyZWRWYWxpZGF0b3IsIFZhbGlkYXRvciB9IGZyb20gXCJAYW5ndWxhci9mb3Jtc1wiO1xyXG5cclxuLy8gQ29uZmlndXJhemlvbmlcclxuaW1wb3J0IHsgTG9jYWxpemF0aW9uU2VydmljZSB9IGZyb20gXCJAZXNmYWVuemEvbG9jYWxpemF0aW9uc1wiO1xyXG5cclxuLy8gRGlyZXR0aXZlLCBDb21wb25lbnRpLCBMaWJyZXJpZVxyXG5pbXBvcnQgeyBUb29sdGlwRGlyZWN0aXZlIH0gZnJvbSBcIm5neC1ib290c3RyYXAvdG9vbHRpcFwiO1xyXG5pbXBvcnQgeyBTdWJqZWN0IH0gZnJvbSBcInJ4anNcIjtcclxuaW1wb3J0IHsgQ2hhbmdlRXZlbnQgfSBmcm9tIFwiLi4vbW9kZWxzL0NoYW5nZUV2ZW50XCI7XHJcbmltcG9ydCB7IHRha2VVbnRpbCB9IGZyb20gXCJyeGpzL29wZXJhdG9yc1wiO1xyXG5cclxuLyoqXHJcbiAqIENsYXNzZSBhc3RyYXR0YSBiYXNlIGNoZSBjb250aWVuZSBsZSBsb2dpY2hlIC8gcHJvcHJpZXTDoCBpbiBjb211bmUgYSB0dXR0aSBpIHZhbGlkYXRvcmlcclxuICogXHJcbiAqIE5vdGEgYmVuZTogSSB0b29sdGlwIHJhbGxlbnRhbm8gdGFudGlzc2ltbyBsYSBwYWdpbmEgcGVyY2jDqSBpbCB0aXppbyBjaGUgaGEgZmF0dG8gbmd4IGJvb3RzdHJhcCBub24gw6ggY2FwYWNlXHJcbiAqL1xyXG5ARGlyZWN0aXZlKClcclxuZXhwb3J0IGFic3RyYWN0IGNsYXNzIEJhc2VWYWxpZGF0aW9uIHtcclxuXHJcbiAgICAvKiogQGlnbm9yZSBDb25zdHJ1Y3RvciAqL1xyXG4gICAgY29uc3RydWN0b3IocHJvdGVjdGVkIGNkcjogQ2hhbmdlRGV0ZWN0b3JSZWYpIHsgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogUGVyIG5vbiBzb3ZyYXNjcml2ZXJlIGwnb3JpZ2luYWxlIGNvbiBlcnJvcmkgY2hlIHNwdW50YW5vIGRhIEJFXHJcbiAgICAgKi9cclxuICAgIHB1YmxpYyB2YWxpZGF0aW9uRmFpbGVkQmluZDogc3RyaW5nO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogUGVyIGdlc3RpcmUgaWwgY2FtYmlvIGRpIG1lc3NhZ2dpIGRpIGVycm9yZVxyXG4gICAgICovXHJcbiAgICBwcml2YXRlIHZhbHVlT25MYXN0VmFsaWRhdGlvbjogc3RyaW5nO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogU2Vydml6aW8gZGkgbG9jYWxpenphemlvbmUgZGVsIENvbXBvbmVudGVcclxuICAgICAqL1xyXG4gICAgcHJvdGVjdGVkIGxjOiBMb2NhbGl6YXRpb25TZXJ2aWNlO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogVmFyaWFiaWxlIHBlciB0ZW5lcmUgaW4gbWVtb3JpYSBsbyBzdGF0byBkaSBzdWJtaXQgZGkgcXVlc3RvIGNvbXBvbmVudGVcclxuICAgICAqL1xyXG4gICAgcHJvdGVjdGVkIF9zdWJtaXR0ZWQ6IGJvb2xlYW47XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBWYXJpYWJpbGUgcGVyIHRlbmVyZSBpbiBtZW1vcmlhIGlsIGZhdHRvIGNoZSBpbCBjb21wb25lbnRlIMOoIGZvcnphdG8gYSBpbnZhbGlkbyBvIG5vXHJcbiAgICAgKi9cclxuICAgIHByb3RlY3RlZCBfZm9yY2VJbnZhbGlkOiBib29sZWFuID0gZmFsc2U7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBJbmRpY2Egc2UgaWwgdmFsb3JlIMOoIG9iYmxpZ2F0b3JpbyBvIG9wemlvbmFsZVxyXG4gICAgICovXHJcbiAgICBwdWJsaWMgcmVxdWlyZWQ6IGJvb2xlYW4gPSBmYWxzZTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIFF1ZXJ5IGNoZSByYWNjb2dsaWUgaWwgdG9vbHRpcCBpbiBtYW5pZXJhIHN0YXRpY2EgKHNvbG8gYWxsJ2luaXppbylcclxuICAgICAqL1xyXG4gICAgQFZpZXdDaGlsZChUb29sdGlwRGlyZWN0aXZlLCB7IHN0YXRpYzogZmFsc2UgfSkgcHJvdGVjdGVkIHRvb2x0aXA6IFRvb2x0aXBEaXJlY3RpdmU7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBRdWVyeSBjaGUgcmFjY29nbGllIGlsIHRvb2x0aXAgaW4gbWFuaWVyYSBkaW5hbWljYSAoYWQgb2duaSBjaGFuZ2UgZGV0ZWN0aW9uKVxyXG4gICAgICogXHJcbiAgICAgKiBAcGFyYW0ge1Rvb2x0aXBEaXJlY3RpdmV9IGNvbXAgRWxlbWVudG8gSFRNTCBhIGN1aSDDqCBhcHBsaWNhdGEgbGEgZGlyZXR0aXZhIGRlbCB0b29sdGlwXHJcbiAgICAgKi9cclxuICAgIEBWaWV3Q2hpbGQoVG9vbHRpcERpcmVjdGl2ZSwgeyBzdGF0aWM6IHRydWUgfSkgc2V0IHRvb2x0aXBfc3RhdGljKGNvbXA6IFRvb2x0aXBEaXJlY3RpdmUpIHtcclxuICAgICAgICBpZiAoY29tcCkgeyB0aGlzLnRvb2x0aXAgPSBjb21wOyB9XHJcbiAgICB9O1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogRWxlbWVudG8gSFRNTCByYXBwcmVzZW50YW50ZSBsJ0lucHV0XHJcbiAgICAgKi9cclxuICAgIEBWaWV3Q2hpbGQoJ2h0bWxJbnB1dCcsIHsgc3RhdGljOiBmYWxzZSB9KSBodG1sSW5wdXQ6IEVsZW1lbnRSZWY7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBRdWVyeSBjaGUgcmFjY29nbGllIGwnaW5wdXQgbyBkaXJldHRpdmEgY2hlIGNvbnRpZW5lIGlsIHZhbG9yZSBpbiBtYW5pZXJhIHN0YXRpY2EgKHNvbG8gYWxsJ2luaXppbylcclxuICAgICAqL1xyXG4gICAgQFZpZXdDaGlsZChcImJhc2VJbnB1dFwiLCB7IHN0YXRpYzogZmFsc2UgfSkgYmFzZUlucHV0OiBOZ01vZGVsO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogUXVlcnkgY2hlIHJhY2NvZ2xpZSBsJ2lucHV0IG8gZGlyZXR0aXZhIGNoZSBjb250aWVuZSBpbCB2YWxvcmUgaW4gbWFuaWVyYSBkaW5hbWljYSAoYWQgb2duaSBjaGFuZ2UgZGV0ZWN0aW9uKVxyXG4gICAgICogXHJcbiAgICAgKiBAcGFyYW0ge05nTW9kZWx9IGNvbXAgRWxlbWVudG8gSFRNTCBhc3NvY2lhdG8gYWwgbmdNb2RlbCBkZWwgY29tcG9uZW50ZVxyXG4gICAgICovXHJcbiAgICBAVmlld0NoaWxkKFwiYmFzZUlucHV0XCIsIHsgc3RhdGljOiB0cnVlIH0pIHNldCBiYXNlSW5wdXRfc3RhdGljKGNvbXA6IE5nTW9kZWwpIHtcclxuICAgICAgICBpZiAoY29tcCkgeyB0aGlzLmJhc2VJbnB1dCA9IGNvbXA7IH1cclxuICAgIH07XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBTdWJqZWN0IGEgY3VpIGwnb2dnZXR0byBpbnRlcm5vIHNpIGNvbGxlZ2EgcGVyIGVmZmV0dHVhcmUgaWwgZm9jdXMgZGVsbCdlbGVtZW50byBpbnB1dCBzb3R0b3N0YW50ZVxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBGb2N1c1N1YmplY3Q6IFN1YmplY3Q8dm9pZD47XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBARVhQRVJJTUVOVEFMXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIFNldFZhbGlkYXRpb25TdWJqZWN0OiBTdWJqZWN0PHsgZmllbGROYW1lOiBzdHJpbmcsIGVycm9yOiBzdHJpbmcgfT47XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBJbmRpY2Egc2UgZGkgZGVmYXVsdCBkZXZlIHZhbHV0YXJlIGlsIG1lc3NhZ2dpbyBkaSBlcnJvcmUgaW4gYmFzZSBhbCB2YWxpZGF0b3JlIGNoZSBmYWxsaXNjZS5cclxuICAgICAqIFxyXG4gICAgICogU2UgZmFsbGlzY2UgaWwgcmVxdWlyZWQgdmFsaWRhdG9yIHNjcml2ZXLDoCBjaGUgbCdpbnB1dCDDqCBvYmJsaWdhdG9yaW8sIHNlIGludmVjZSBmYWxsaXNjZSBcclxuICAgICAqIHVuIGV2ZW50dWFsZSBwYXR0ZXJuIHZhbGlkYXRvciBzY3JpdmVyw6AgY2hlIGlsIGZvcm1hdG8gZGVsbCdpbnB1dCDDqCBpbnZhbGlkb1xyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBJbmZlckVycm9yTWVzc2FnZXM6IGJvb2xlYW4gPSB0cnVlO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogTW9kYWxpdMOgIGluIGN1aSB2aWVuZSBtb3N0cmF0byBpbCBjYW1wbywgMS0xIHJpc3BldHRvIGFsbGUgZGVmaW5pemlvbmkgZGkgQW5ndWxhciBNYXRlcmlhbCBcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgRmllbGRBcHBlYXJlbmNlOiBcImxlZ2FjeVwiIHwgXCJzdGFuZGFyZFwiIHwgXCJmaWxsXCIgfCBcIm91dGxpbmVcIiA9IFwib3V0bGluZVwiO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogSW5kaWNhIHNlIGlsICoqUGxhY2Vob2xkZXIqKiBkZXYnZXNzZXJlIHVzYXRvIGNvbWUgdW5hIGZsb2F0aW5nIGxhYmVsIGRpIG1hdGVyaWFsIG8gc29sbyBjb21lIHVuIHBsYWNlaG9sZGVyIHN0YW5kYXJkIFxyXG4gICAgICogXHJcbiAgICAgKiBJZ25vcmF0YSBsYXRvIGF1dG9jb21wbGV0ZSwgYXV0b2NvbXBsZXRlLW11bHRpIGUgc2VsZWN0IGluIHF1YW50byBoYW5ubyBnZXN0aW9uaSBwYXJ0aWNvbGFyaSBkaSBwbGFjZWhvbGRlciBlY2MuLi5cclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgRmxvYXRpbmdMYWJlbDogYm9vbGVhbiA9IHRydWU7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBNZXNzYWdnaW8gZGEgbW9zdHJhcmUgc2UgbGEgdmFsaWRhemlvbmUgZmFsbGlzY2UuIFxyXG4gICAgICogXHJcbiAgICAgKiBTZSBxdWVzdG8gw6ggdmFsb3JpenphdG8sIGlsIG1lc3NhZ2dpbyBub24gdmllbmUgdmFsdXRhdG8gaW4gYXV0b21hdGljbyBub25zdGFudGUgKipJbmZlckVycm9yTWVzc2FnZXMqKiBzaWEgKip0cnVlKipcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgdmFsaWRhdGlvbkZhaWxlZDogc3RyaW5nID0gXCJcIjtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEluZGljYSBzZSBpbCBjb21wb25lbnRlIMOoIGluIHNvbGEgbGV0dHVyYVxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBSZWFkb25seTogYm9vbGVhbiA9IGZhbHNlO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogSW5kaWNhIGxlIGRpbWVuc2lvbmkgZGVsIGNvbXBvbmVudGVcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgd2lkdGhQeDogbnVtYmVyID0gbnVsbDtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEluZGljYSBzZSBpbCBjb21wb25lbnRlIMOoIGRpc2FiaWxpdGF0byBvIG5vIChwacO5IG8gbWVubyBzdGVzc28gY29uY2V0dG8gZGVsIHJlYWRvbmx5KVxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBkaXNhYmxlZDogYm9vbGVhbiA9IGZhbHNlO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogRXZlbnR1YWxlIHBsYWNlaG9sZGVyIGRhIG1vc3RyYXJlIGFsIHBvc3RvIGRlbCB2YWxvcmUgcXVhbmRvIGlsIHZhbG9yZSDDqCBudWxsbyAvIHZ1b3RvXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIHBsYWNlaG9sZGVyOiBzdHJpbmcgPSBcIlwiO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogQ2xhc3NpIGRhIGFwcGxpY2FyZSBhbCBjb21wb25lbnRlXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIGNsYXNzOiBzdHJpbmcgPSBcIlwiO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogU3RpbGkgZGEgYXBwbGljYXJlIGFsIGNvbXBvbmVudGVcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgc3R5bGU6IHN0cmluZyA9IFwiXCI7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBQYXR0ZXJuIGRpIHZhbGlkYXppb25lIGRlbGwnaW5wdXRcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgcGF0dGVybjogc3RyaW5nID0gXCJcIjtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEluZGljYSBkaSBub24gdmFsaWRhcmUgaWwgY29tcG9uZW50ZVxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBub1ZhbGlkYXRlOiBib29sZWFuID0gZmFsc2U7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBJbmRpY2Egc2UgYWJpbGl0YXJlIG8gbWVubyBsJ2F1dG9jb21wbGV0YW1lbnRvIGRpIGRlZmF1bHQgZGVsIGJyb3dzZXJcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgYXV0b2NvbXBsZXRlOiBzdHJpbmcgPSBcIm9mZlwiO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogSWQgZGVsbCdpbnB1dC4gw4ggaW1wb3J0YW50ZSBpbXBvc3RhcmxvIHNvcHJhdHR1dHRvIHNlIGwnaW50ZXJmYWNjaWEgZ2VuZXJhdGEgZGV2J2Vzc2VyZSB0ZXN0YXRhXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIGlkOiBzdHJpbmcgPSBcIlwiO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogRXZlbnRvIGNoZSBzb3N0aXR1aXNjZSBsJ25nTW9kZWxDaGFuZ2UgZmFjZW5kb2xvIGZ1bnppb25hcmUgaW4gbWFuaWVyYSB1biBwbycgcGnDuSBjb25zaXN0ZW50ZVxyXG4gICAgICovXHJcbiAgICBAT3V0cHV0KCkgaW5wdXRDaGFuZ2U6IEV2ZW50RW1pdHRlcjxzdHJpbmc+ID0gbmV3IEV2ZW50RW1pdHRlcjxzdHJpbmc+KCk7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBFdmVudG8gY2hlIGluZGljYSBpbCBmb2N1cyBhdnZlbnV0byBzdSB1biBjb250cm9sbG9cclxuICAgICAqL1xyXG4gICAgQE91dHB1dCgpIGlucHV0Rm9jdXM6IEV2ZW50RW1pdHRlcjxhbnk+ID0gbmV3IEV2ZW50RW1pdHRlcjxhbnk+KCk7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBFdmVudG8gY2hlIGluZGljYSBsYSBmaW5hbGl6emF6aW9uZSBkZWwgdmFsb3JlIGF2dmVudXRhIHN1IHVuIGNvbnRyb2xsb1xyXG4gICAgICovXHJcbiAgICBAT3V0cHV0KCkgaW5wdXRGaW5hbGl6ZWQ6IEV2ZW50RW1pdHRlcjxhbnk+ID0gbmV3IEV2ZW50RW1pdHRlcjxhbnk+KCk7XHJcbiAgICBcclxuICAgIC8qKlxyXG4gICAgICogSW1wb3N0YSBpbCBjb21wb25lbnRlIGNvbWUgXCJzdWJtaXR0ZWRcIiBzY2F0ZW5hbmRvbmUgbGUgdmFsaWRhemlvbmkgZWQgZXZlbnR1YWxtZW50ZSBsYSB2aXN1YWxpenphemlvbmUgZGVsIHRvb2x0aXAgZGkgZXJyb3JlXHJcbiAgICAgKiBcclxuICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gdmFsICoqdHJ1ZSoqIHNlIHNpIHZ1b2xlIGltcG9zdGFyZSBxdWVzdG8gY29udHJvbGxvIGNvbWUgc3VibWl0dGVkLCAqKmZhbHNlKiogYWx0cmltZW50aVxyXG4gICAgICovXHJcbiAgICBASW5wdXQoXCJzdWJtaXR0ZWRcIikgc2V0IHN1Ym1pdHRlZCh2YWw6IGJvb2xlYW4pIHtcclxuICAgICAgICB0aGlzLl9zdWJtaXR0ZWQgPSB2YWw7XHJcbiAgICAgICAgaWYgKCF0aGlzLmJhc2VJbnB1dClcclxuICAgICAgICAgICAgcmV0dXJuO1xyXG5cclxuICAgICAgICBpZiAodmFsKVxyXG4gICAgICAgICAgICB0aGlzLmJhc2VJbnB1dC5jb250cm9sLm1hcmtBc1RvdWNoZWQoKTtcclxuXHJcbiAgICAgICAgaWYgKHRoaXMuYmFzZUlucHV0LmNvbnRyb2wuc3RhdHVzID09PSBcIklOVkFMSURcIiAmJiB2YWwpXHJcbiAgICAgICAgICAgIHRoaXMuc2hvd1Rvb2x0aXBXaXRoTWVzc2FnZSgpO1xyXG4gICAgICAgIGVsc2VcclxuICAgICAgICAgICAgdGhpcy50b29sdGlwLmhpZGUoKTtcclxuICAgIH1cclxuXHJcbiAgICAvKipcclxuICAgICAqIEltcG9zdGEgaWwgY29tcG9uZW50ZSBjb21lIFwiaW52YWxpZFwiIGEgcHJlc2NpbmRlcmUgZGFpIHZhbGlkYXRvcmlcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgc2V0IGZvcmNlSW52YWxpZCh2YWw6IGJvb2xlYW4pIHtcclxuICAgICAgICB0aGlzLl9mb3JjZUludmFsaWQgPSB2YWw7XHJcblxyXG4gICAgICAgIGlmICh2YWwpXHJcbiAgICAgICAgICAgIHNldFRpbWVvdXQoKCkgPT4ge1xyXG4gICAgICAgICAgICAgICAgdGhpcy5iYXNlSW5wdXQuY29udHJvbC5zZXRFcnJvcnMoeyBmb3JjZWR0b2ludmFsaWQ6IHRydWUgfSk7XHJcbiAgICAgICAgICAgICAgICB0aGlzLmJhc2VJbnB1dC5jb250cm9sLm1hcmtBc1RvdWNoZWQoKTtcclxuICAgICAgICAgICAgICAgIHRoaXMuYmFzZUlucHV0LmNvbnRyb2wubWFya0FzRGlydHkoKTtcclxuICAgICAgICAgICAgICAgIHRoaXMuY2RyLmRldGVjdENoYW5nZXMoKTtcclxuICAgICAgICAgICAgfSk7XHJcbiAgICAgICAgZWxzZVxyXG4gICAgICAgICAgICBzZXRUaW1lb3V0KCgpID0+IHtcclxuICAgICAgICAgICAgICAgIHRoaXMuYmFzZUlucHV0LmNvbnRyb2wuc2V0RXJyb3JzKHsgZm9yY2VkdG9pbnZhbGlkOiBudWxsIH0pO1xyXG4gICAgICAgICAgICAgICAgdGhpcy5iYXNlSW5wdXQuY29udHJvbC51cGRhdGVWYWx1ZUFuZFZhbGlkaXR5KCk7XHJcbiAgICAgICAgICAgIH0pO1xyXG4gICAgfVxyXG5cclxuICAgIG5nT25Jbml0KCkge1xyXG4gICAgICAgIGlmICh0aGlzLlNldFZhbGlkYXRpb25TdWJqZWN0KSB7XHJcbiAgICAgICAgICAgIHRoaXMuU2V0VmFsaWRhdGlvblN1YmplY3QucGlwZSh0YWtlVW50aWwodGhpcy5kZXN0cm95ZWQkKSkuc3Vic2NyaWJlKHYgPT4ge1xyXG4gICAgICAgICAgICAgICAgaWYgKHYuZmllbGROYW1lICsgXCJfaW50ZXJuYWxcIiA9PSB0aGlzLmlkKSB7XHJcbiAgICAgICAgICAgICAgICAgICAgdGhpcy5mb3JjZUludmFsaWQgPSB0cnVlO1xyXG4gICAgICAgICAgICAgICAgICAgIHRoaXMuc2hvd1Rvb2x0aXBXaXRoTWVzc2FnZSh2LmVycm9yKTtcclxuICAgICAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgfSlcclxuICAgICAgICB9IFxyXG4gICAgfVxyXG5cclxuICAgIHByb3RlY3RlZCBjaGVja1JlcXVpcmVkbmVzcyhfdmFsaWRhdG9yczogVmFsaWRhdG9yW10pIHtcclxuICAgICAgICBpZiAoX3ZhbGlkYXRvcnMgJiYgX3ZhbGlkYXRvcnMuc29tZShlbGVtID0+IGVsZW0gaW5zdGFuY2VvZiBSZXF1aXJlZFZhbGlkYXRvciAmJiAoZWxlbS5yZXF1aXJlZCA9PT0gdHJ1ZSB8fCAoIWVsZW0ucmVxdWlyZWQgJiYgZWxlbS5yZXF1aXJlZCAhPT0gZmFsc2UpKSkpXHJcbiAgICAgICAgICAgIHRoaXMucmVxdWlyZWQgPSB0cnVlO1xyXG4gICAgfVxyXG5cclxuICAgIGRlc3Ryb3llZCQ6IFN1YmplY3Q8dm9pZD4gPSBuZXcgU3ViamVjdDx2b2lkPigpO1xyXG4gICAgbmdPbkRlc3Ryb3koKXtcclxuICAgICAgICB0aGlzLmRlc3Ryb3llZCQubmV4dCgpO1xyXG4gICAgICAgIHRoaXMuZGVzdHJveWVkJC5jb21wbGV0ZSgpO1xyXG4gICAgfVxyXG4gICAgLyoqXHJcbiAgICAgKiBIZWxwZXIgY2hlIGNvbnRyb2xsYSBzZSBpbCB0b29sdGlwIGRldmUgZXNzZXJlIG1vc3RyYXRvIG8gbWVubywgXHJcbiAgICAgKiByaWNoaWFtYXRvIGRpcmV0dGFtZW50ZSBkYWxsJ0hUTUwgZGVpIGNvbXBvbmVudGlcclxuICAgICAqL1xyXG4gICAgcHVibGljIGNoZWNrVG9vbHRpcCgpIHtcclxuICAgICAgICBpZiAoKHRoaXMuYmFzZUlucHV0LmludmFsaWQgJiYgdGhpcy5iYXNlSW5wdXQudG91Y2hlZCkpXHJcbiAgICAgICAgICAgIHRoaXMuc2hvd1Rvb2x0aXBXaXRoTWVzc2FnZSgpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogSGVscGVyIGNoZSBjYWxjb2xhIGlsIG1lc3NhZ2dpbyBkYSBtb3N0cmFyZSBuZWwgdG9vbHRpcCBjaGUgYW5kcsOgIGFkIGFwcmlyZVxyXG4gICAgICovXHJcbiAgICBwcml2YXRlIHNob3dUb29sdGlwV2l0aE1lc3NhZ2UobWVzc2FnZU92ZXJyaWRlOiBzdHJpbmcgPSBudWxsKSB7XHJcblxyXG4gICAgICAgIC8vIEFnZ2lvcm5vIGlsIG1lc3NhZ2dpbyBkaSB2YWxpZGF6aW9uZSBzb2xvIHNlIGlsIHZhbG9yZSDDqCBkaXZlcnNvIGRhbGwndWx0aW1vIHZhbG9yZSByaWNldnV0b1xyXG4gICAgICAgIGlmICh0aGlzLnZhbHVlT25MYXN0VmFsaWRhdGlvbiAhPSB0aGlzLmJhc2VJbnB1dC52YWx1ZSkge1xyXG4gICAgICAgICAgICB0aGlzLnZhbGlkYXRpb25GYWlsZWRCaW5kID0gbWVzc2FnZU92ZXJyaWRlIHx8IHRoaXMudmFsaWRhdGlvbkZhaWxlZCB8fCAodGhpcy5JbmZlckVycm9yTWVzc2FnZXMgPyB0aGlzLmluZmVyTWVzc2FnZSgpIDogXCJcIik7XHJcbiAgICAgICAgICAgIHRoaXMudmFsdWVPbkxhc3RWYWxpZGF0aW9uID0gdGhpcy5iYXNlSW5wdXQudmFsdWU7XHJcbiAgICAgICAgfVxyXG5cclxuICAgICAgICBpZiAodGhpcy52YWxpZGF0aW9uRmFpbGVkQmluZClcclxuICAgICAgICAgICAgdGhpcy50b29sdGlwLnNob3coKTtcclxuICAgIH1cclxuXHJcbiAgICAvKipcclxuICAgICAqIENhbGNvbGEgaWwgbWVzc2FnZ2lvIGRhIG1vc3RyYXJlIGluIGJhc2UgYWwgdmFsb3JlLlxyXG4gICAgICogXHJcbiAgICAgKiBFbnRyYXJlIGluIHF1ZXN0YSBmdW56aW9uZSBzaWduaWZpY2EgY2hlIGxvIHN0YXRvIGRpIHZhbGlkYXppb25lIMOoIGZhbGxpdG8sIHBlciBxdWVzdG8gc2kgY29tcG9ydGEgc2VtcGxpY2VtZW50ZSBpbiBtYW5pZXJhIGVzY2x1c2l2YSwgZSBjaW/DqDpcclxuICAgICAqIFxyXG4gICAgICogMSkgU2UgZXJvIHJlcXVpcmVkIGUgc29ubyBzZW56YSB2YWxvcmUgLS0+IElucHV0IHJpY2hpZXN0b1xyXG4gICAgICogXHJcbiAgICAgKiAyKSBBbHRyaW1lbnRpIHNlIGhvIHVuIHZhbG9yZSAtLT4gRGkgc2ljdXJvIGlsIGZvcm1hdG8gw6ggZXJyYXRvXHJcbiAgICAgKi9cclxuICAgIHByaXZhdGUgaW5mZXJNZXNzYWdlKCk6IHN0cmluZyB7XHJcbiAgICAgICAgaWYgKHRoaXMucmVxdWlyZWQgJiYgIXRoaXMuYmFzZUlucHV0LnZhbHVlKVxyXG4gICAgICAgICAgICByZXR1cm4gdGhpcy5sYy5sb2MoXCJSZXF1aXJlZCBJbnB1dFwiKVxyXG5cclxuICAgICAgICBpZiAodGhpcy5iYXNlSW5wdXQudmFsdWUpXHJcbiAgICAgICAgICAgIHJldHVybiB0aGlzLmxjLmxvYyhcIkludmFsaWQgSW5wdXQgRm9ybWF0XCIpXHJcbiAgICB9XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBGb3J6YSBsYSBjaGl1c3VyYSBkZWwgdG9vbHRpcFxyXG4gICAgICovXHJcbiAgICBjbG9zZVRvb2x0aXAoKSB7XHJcbiAgICAgICAgdGhpcy50b29sdGlwLmhpZGUoKTtcclxuICAgIH1cclxuXHJcbiAgICAvKipcclxuICAgICAqIENvbnRyb2xsYSBzZSBpbCBjb250cm9sbG8gw6ggdmFsaWRvIGUgaW4gY2FzbyBsbyBzaWEgY2hpdWRlIGlsIHRvb2x0aXBcclxuICAgICAqL1xyXG4gICAgcHJvdGVjdGVkIENoZWNrVmFsaWRpdHkoKSB7XHJcbiAgICAgICAgaWYgKCF0aGlzLmJhc2VJbnB1dC5zdGF0dXNDaGFuZ2VzKVxyXG4gICAgICAgICAgICByZXR1cm47XHJcblxyXG4gICAgICAgIHRoaXMuYmFzZUlucHV0LnN0YXR1c0NoYW5nZXMuc3Vic2NyaWJlKGV2ZW50ID0+IHtcclxuICAgICAgICAgICAgaWYgKGV2ZW50ID09PSBcIlZBTElEXCIpXHJcbiAgICAgICAgICAgICAgICB0aGlzLnRvb2x0aXAuaGlkZSgpO1xyXG4gICAgICAgIH0pO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogQGlnbm9yZVxyXG4gICAgICovXHJcbiAgICBwcm90ZWN0ZWQgcHJvcGFnYXRlQ2hhbmdlID0gKF86IGFueSkgPT4geyB9O1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogTCdlbWl0IGRlbCBmb2N1cyBkZWxsJ2VsZW1lbnRvXHJcbiAgICAgKiBcclxuICAgICAqIEBwYXJhbSB7YW55fSB0b0VtaXQgdmFsb3JlIGRhIHByb3BhZ2FyZSBhbGwnZXN0ZXJub1xyXG4gICAgICovXHJcbiAgICBvbkZvY3VzKHRvRW1pdCkge1xyXG4gICAgICAgIHRoaXMuaW5wdXRGb2N1cy5lbWl0KHRvRW1pdCk7XHJcbiAgICB9XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBGaW5hbGl6emF6aW9uZSBJbnB1dFxyXG4gICAgICovXHJcbiAgICBvbkZpbmFsaXplKCkge1xyXG4gICAgICAgIHRoaXMuaW5wdXRGaW5hbGl6ZWQuZW1pdCgpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogU3Vic2NyaXB0aW9uIGFsbGUgcmljaGllc3RlIGRpIGZvY3VzXHJcbiAgICAgKi9cclxuICAgIG9ic2VydmFibGU6IGFueTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIFJlZ2lzdHJhIGlsIFN1YmplY3QgcGVyIHJpY2V2ZXJlIGxlIHJpY2hpZXN0ZSBkaSBGb2N1cyBkYWxsJ2VzdGVybm9cclxuICAgICAqL1xyXG4gICAgcmVnaXN0ZXJGb2N1c1JlcXVlc3QoKTogYW55IHtcclxuICAgICAgICBpZighdGhpcy5Gb2N1c1N1YmplY3QpXHJcbiAgICAgICAgICAgIHJldHVybjtcclxuICAgICAgICB0aGlzLm9ic2VydmFibGUgPSB0aGlzLkZvY3VzU3ViamVjdC5zdWJzY3JpYmUodCA9PiB7XHJcbiAgICAgICAgICAgIHRoaXMuaHRtbElucHV0Lm5hdGl2ZUVsZW1lbnQuZm9jdXMoKTtcclxuICAgICAgICB9KTtcclxuICAgIH1cclxuXHJcbiAgICAvKipcclxuICAgICAqIERlcmVnaXN0cmEgaWwgU3ViamVjdCBkZWxsZSByaWNoaWVzdGUgZGkgZm9jdXNcclxuICAgICAqL1xyXG4gICAgZGVyZWdpc3RlckZvY3VzUmVxdWVzdCgpIHtcclxuICAgICAgICBpZiAodGhpcy5vYnNlcnZhYmxlKVxyXG4gICAgICAgICAgICB0aGlzLm9ic2VydmFibGUudW5zdWJzY3JpYmUoKTtcclxuICAgIH1cclxufSJdfQ==
|
|
1
|
+
// Angular
|
|
2
|
+
import { EventEmitter, Input, Output, ViewChild, Directive } from "@angular/core";
|
|
3
|
+
import { RequiredValidator } from "@angular/forms";
|
|
4
|
+
// Direttive, Componenti, Librerie
|
|
5
|
+
import { TooltipDirective } from "ngx-bootstrap/tooltip";
|
|
6
|
+
import { Subject } from "rxjs";
|
|
7
|
+
import { takeUntil } from "rxjs/operators";
|
|
8
|
+
import * as i0 from "@angular/core";
|
|
9
|
+
/**
|
|
10
|
+
* Classe astratta base che contiene le logiche / proprietà in comune a tutti i validatori
|
|
11
|
+
*
|
|
12
|
+
* Nota bene: I tooltip rallentano tantissimo la pagina perché il tizio che ha fatto ngx bootstrap non è capace
|
|
13
|
+
*/
|
|
14
|
+
export class BaseValidation {
|
|
15
|
+
/** @ignore Constructor */
|
|
16
|
+
constructor(cdr) {
|
|
17
|
+
this.cdr = cdr;
|
|
18
|
+
/**
|
|
19
|
+
* Variabile per tenere in memoria il fatto che il componente è forzato a invalido o no
|
|
20
|
+
*/
|
|
21
|
+
this._forceInvalid = false;
|
|
22
|
+
/**
|
|
23
|
+
* Indica se il valore è obbligatorio o opzionale
|
|
24
|
+
*/
|
|
25
|
+
this.required = false;
|
|
26
|
+
/**
|
|
27
|
+
* Indica se di default deve valutare il messaggio di errore in base al validatore che fallisce.
|
|
28
|
+
*
|
|
29
|
+
* Se fallisce il required validator scriverà che l'input è obbligatorio, se invece fallisce
|
|
30
|
+
* un eventuale pattern validator scriverà che il formato dell'input è invalido
|
|
31
|
+
*/
|
|
32
|
+
this.InferErrorMessages = true;
|
|
33
|
+
/**
|
|
34
|
+
* Modalità in cui viene mostrato il campo, 1-1 rispetto alle definizioni di Angular Material
|
|
35
|
+
*/
|
|
36
|
+
this.FieldAppearence = "outline";
|
|
37
|
+
/**
|
|
38
|
+
* Indica se il **Placeholder** dev'essere usato come una floating label di material o solo come un placeholder standard
|
|
39
|
+
*
|
|
40
|
+
* Ignorata lato autocomplete, autocomplete-multi e select in quanto hanno gestioni particolari di placeholder ecc...
|
|
41
|
+
*/
|
|
42
|
+
this.FloatingLabel = true;
|
|
43
|
+
/**
|
|
44
|
+
* Messaggio da mostrare se la validazione fallisce.
|
|
45
|
+
*
|
|
46
|
+
* Se questo è valorizzato, il messaggio non viene valutato in automatico nonstante **InferErrorMessages** sia **true**
|
|
47
|
+
*/
|
|
48
|
+
this.validationFailed = "";
|
|
49
|
+
/**
|
|
50
|
+
* Indica se il componente è in sola lettura
|
|
51
|
+
*/
|
|
52
|
+
this.Readonly = false;
|
|
53
|
+
/**
|
|
54
|
+
* Indica le dimensioni del componente
|
|
55
|
+
*/
|
|
56
|
+
this.widthPx = null;
|
|
57
|
+
/**
|
|
58
|
+
* Indica se il componente è disabilitato o no (più o meno stesso concetto del readonly)
|
|
59
|
+
*/
|
|
60
|
+
this.disabled = false;
|
|
61
|
+
/**
|
|
62
|
+
* Eventuale placeholder da mostrare al posto del valore quando il valore è nullo / vuoto
|
|
63
|
+
*/
|
|
64
|
+
this.placeholder = "";
|
|
65
|
+
/**
|
|
66
|
+
* Classi da applicare al componente
|
|
67
|
+
*/
|
|
68
|
+
this.class = "";
|
|
69
|
+
/**
|
|
70
|
+
* Stili da applicare al componente
|
|
71
|
+
*/
|
|
72
|
+
this.style = "";
|
|
73
|
+
/**
|
|
74
|
+
* Pattern di validazione dell'input
|
|
75
|
+
*/
|
|
76
|
+
this.pattern = "";
|
|
77
|
+
/**
|
|
78
|
+
* Indica di non validare il componente
|
|
79
|
+
*/
|
|
80
|
+
this.noValidate = false;
|
|
81
|
+
/**
|
|
82
|
+
* Indica se abilitare o meno l'autocompletamento di default del browser
|
|
83
|
+
*/
|
|
84
|
+
this.autocomplete = "off";
|
|
85
|
+
/**
|
|
86
|
+
* Id dell'input. È importante impostarlo soprattutto se l'interfaccia generata dev'essere testata
|
|
87
|
+
*/
|
|
88
|
+
this.id = "";
|
|
89
|
+
/**
|
|
90
|
+
* Evento che sostituisce l'ngModelChange facendolo funzionare in maniera un po' più consistente
|
|
91
|
+
*/
|
|
92
|
+
this.inputChange = new EventEmitter();
|
|
93
|
+
/**
|
|
94
|
+
* Evento che indica il focus avvenuto su un controllo
|
|
95
|
+
*/
|
|
96
|
+
this.inputFocus = new EventEmitter();
|
|
97
|
+
/**
|
|
98
|
+
* Evento che indica la finalizzazione del valore avvenuta su un controllo
|
|
99
|
+
*/
|
|
100
|
+
this.inputFinalized = new EventEmitter();
|
|
101
|
+
this.destroyed$ = new Subject();
|
|
102
|
+
/**
|
|
103
|
+
* @ignore
|
|
104
|
+
*/
|
|
105
|
+
this.propagateChange = (_) => { };
|
|
106
|
+
}
|
|
107
|
+
/**
|
|
108
|
+
* Query che raccoglie il tooltip in maniera dinamica (ad ogni change detection)
|
|
109
|
+
*
|
|
110
|
+
* @param {TooltipDirective} comp Elemento HTML a cui è applicata la direttiva del tooltip
|
|
111
|
+
*/
|
|
112
|
+
set tooltip_static(comp) {
|
|
113
|
+
if (comp) {
|
|
114
|
+
this.tooltip = comp;
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
;
|
|
118
|
+
/**
|
|
119
|
+
* Query che raccoglie l'input o direttiva che contiene il valore in maniera dinamica (ad ogni change detection)
|
|
120
|
+
*
|
|
121
|
+
* @param {NgModel} comp Elemento HTML associato al ngModel del componente
|
|
122
|
+
*/
|
|
123
|
+
set baseInput_static(comp) {
|
|
124
|
+
if (comp) {
|
|
125
|
+
this.baseInput = comp;
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
;
|
|
129
|
+
/**
|
|
130
|
+
* Imposta il componente come "submitted" scatenandone le validazioni ed eventualmente la visualizzazione del tooltip di errore
|
|
131
|
+
*
|
|
132
|
+
* @param {boolean} val **true** se si vuole impostare questo controllo come submitted, **false** altrimenti
|
|
133
|
+
*/
|
|
134
|
+
set submitted(val) {
|
|
135
|
+
this._submitted = val;
|
|
136
|
+
if (!this.baseInput)
|
|
137
|
+
return;
|
|
138
|
+
if (val)
|
|
139
|
+
this.baseInput.control.markAsTouched();
|
|
140
|
+
if (this.baseInput.control.status === "INVALID" && val)
|
|
141
|
+
this.showTooltipWithMessage();
|
|
142
|
+
else
|
|
143
|
+
this.tooltip.hide();
|
|
144
|
+
}
|
|
145
|
+
/**
|
|
146
|
+
* Imposta il componente come "invalid" a prescindere dai validatori
|
|
147
|
+
*/
|
|
148
|
+
set forceInvalid(val) {
|
|
149
|
+
this._forceInvalid = val;
|
|
150
|
+
if (val)
|
|
151
|
+
setTimeout(() => {
|
|
152
|
+
this.baseInput.control.setErrors({ forcedtoinvalid: true });
|
|
153
|
+
this.baseInput.control.markAsTouched();
|
|
154
|
+
this.baseInput.control.markAsDirty();
|
|
155
|
+
this.cdr.detectChanges();
|
|
156
|
+
});
|
|
157
|
+
else
|
|
158
|
+
setTimeout(() => {
|
|
159
|
+
this.baseInput.control.setErrors({ forcedtoinvalid: null });
|
|
160
|
+
this.baseInput.control.updateValueAndValidity();
|
|
161
|
+
});
|
|
162
|
+
}
|
|
163
|
+
ngOnInit() {
|
|
164
|
+
if (this.SetValidationSubject) {
|
|
165
|
+
this.SetValidationSubject.pipe(takeUntil(this.destroyed$)).subscribe(v => {
|
|
166
|
+
if (v.fieldName + "_internal" == this.id) {
|
|
167
|
+
this.forceInvalid = true;
|
|
168
|
+
this.showTooltipWithMessage(v.error);
|
|
169
|
+
}
|
|
170
|
+
});
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
checkRequiredness(_validators) {
|
|
174
|
+
if (_validators && _validators.some(elem => elem instanceof RequiredValidator && (elem.required === true || (!elem.required && elem.required !== false))))
|
|
175
|
+
this.required = true;
|
|
176
|
+
}
|
|
177
|
+
ngOnDestroy() {
|
|
178
|
+
this.destroyed$.next();
|
|
179
|
+
this.destroyed$.complete();
|
|
180
|
+
}
|
|
181
|
+
/**
|
|
182
|
+
* Helper che controlla se il tooltip deve essere mostrato o meno,
|
|
183
|
+
* richiamato direttamente dall'HTML dei componenti
|
|
184
|
+
*/
|
|
185
|
+
checkTooltip() {
|
|
186
|
+
if ((this.baseInput.invalid && this.baseInput.touched))
|
|
187
|
+
this.showTooltipWithMessage();
|
|
188
|
+
}
|
|
189
|
+
/**
|
|
190
|
+
* Helper che calcola il messaggio da mostrare nel tooltip che andrà ad aprire
|
|
191
|
+
*/
|
|
192
|
+
showTooltipWithMessage(messageOverride = null) {
|
|
193
|
+
// Aggiorno il messaggio di validazione solo se il valore è diverso dall'ultimo valore ricevuto
|
|
194
|
+
if (this.valueOnLastValidation != this.baseInput.value) {
|
|
195
|
+
this.validationFailedBind = messageOverride || this.validationFailed || (this.InferErrorMessages ? this.inferMessage() : "");
|
|
196
|
+
this.valueOnLastValidation = this.baseInput.value;
|
|
197
|
+
}
|
|
198
|
+
if (this.validationFailedBind)
|
|
199
|
+
this.tooltip.show();
|
|
200
|
+
}
|
|
201
|
+
/**
|
|
202
|
+
* Calcola il messaggio da mostrare in base al valore.
|
|
203
|
+
*
|
|
204
|
+
* Entrare in questa funzione significa che lo stato di validazione è fallito, per questo si comporta semplicemente in maniera esclusiva, e cioè:
|
|
205
|
+
*
|
|
206
|
+
* 1) Se ero required e sono senza valore --> Input richiesto
|
|
207
|
+
*
|
|
208
|
+
* 2) Altrimenti se ho un valore --> Di sicuro il formato è errato
|
|
209
|
+
*/
|
|
210
|
+
inferMessage() {
|
|
211
|
+
if (this.required && !this.baseInput.value)
|
|
212
|
+
return this.lc.loc("Required Input");
|
|
213
|
+
if (this.baseInput.value)
|
|
214
|
+
return this.lc.loc("Invalid Input Format");
|
|
215
|
+
}
|
|
216
|
+
/**
|
|
217
|
+
* Forza la chiusura del tooltip
|
|
218
|
+
*/
|
|
219
|
+
closeTooltip() {
|
|
220
|
+
this.tooltip.hide();
|
|
221
|
+
}
|
|
222
|
+
/**
|
|
223
|
+
* Controlla se il controllo è valido e in caso lo sia chiude il tooltip
|
|
224
|
+
*/
|
|
225
|
+
CheckValidity() {
|
|
226
|
+
if (!this.baseInput.statusChanges)
|
|
227
|
+
return;
|
|
228
|
+
this.baseInput.statusChanges.subscribe(event => {
|
|
229
|
+
if (event === "VALID")
|
|
230
|
+
this.tooltip.hide();
|
|
231
|
+
});
|
|
232
|
+
}
|
|
233
|
+
/**
|
|
234
|
+
* L'emit del focus dell'elemento
|
|
235
|
+
*
|
|
236
|
+
* @param {any} toEmit valore da propagare all'esterno
|
|
237
|
+
*/
|
|
238
|
+
onFocus(toEmit) {
|
|
239
|
+
this.inputFocus.emit(toEmit);
|
|
240
|
+
}
|
|
241
|
+
/**
|
|
242
|
+
* Finalizzazione Input
|
|
243
|
+
*/
|
|
244
|
+
onFinalize() {
|
|
245
|
+
this.inputFinalized.emit();
|
|
246
|
+
}
|
|
247
|
+
/**
|
|
248
|
+
* Registra il Subject per ricevere le richieste di Focus dall'esterno
|
|
249
|
+
*/
|
|
250
|
+
registerFocusRequest() {
|
|
251
|
+
if (!this.FocusSubject)
|
|
252
|
+
return;
|
|
253
|
+
this.observable = this.FocusSubject.subscribe(t => {
|
|
254
|
+
this.htmlInput.nativeElement.focus();
|
|
255
|
+
});
|
|
256
|
+
}
|
|
257
|
+
/**
|
|
258
|
+
* Deregistra il Subject delle richieste di focus
|
|
259
|
+
*/
|
|
260
|
+
deregisterFocusRequest() {
|
|
261
|
+
if (this.observable)
|
|
262
|
+
this.observable.unsubscribe();
|
|
263
|
+
}
|
|
264
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: BaseValidation, deps: [{ token: i0.ChangeDetectorRef }], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
265
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "17.3.12", type: BaseValidation, inputs: { FocusSubject: "FocusSubject", SetValidationSubject: "SetValidationSubject", InferErrorMessages: "InferErrorMessages", FieldAppearence: "FieldAppearence", FloatingLabel: "FloatingLabel", validationFailed: "validationFailed", Readonly: "Readonly", widthPx: "widthPx", disabled: "disabled", placeholder: "placeholder", class: "class", style: "style", pattern: "pattern", noValidate: "noValidate", autocomplete: "autocomplete", id: "id", submitted: "submitted", forceInvalid: "forceInvalid" }, outputs: { inputChange: "inputChange", inputFocus: "inputFocus", inputFinalized: "inputFinalized" }, viewQueries: [{ propertyName: "tooltip", first: true, predicate: TooltipDirective, descendants: true }, { propertyName: "tooltip_static", first: true, predicate: TooltipDirective, descendants: true, static: true }, { propertyName: "htmlInput", first: true, predicate: ["htmlInput"], descendants: true }, { propertyName: "baseInput", first: true, predicate: ["baseInput"], descendants: true }, { propertyName: "baseInput_static", first: true, predicate: ["baseInput"], descendants: true, static: true }], ngImport: i0 }); }
|
|
266
|
+
}
|
|
267
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: BaseValidation, decorators: [{
|
|
268
|
+
type: Directive
|
|
269
|
+
}], ctorParameters: () => [{ type: i0.ChangeDetectorRef }], propDecorators: { tooltip: [{
|
|
270
|
+
type: ViewChild,
|
|
271
|
+
args: [TooltipDirective, { static: false }]
|
|
272
|
+
}], tooltip_static: [{
|
|
273
|
+
type: ViewChild,
|
|
274
|
+
args: [TooltipDirective, { static: true }]
|
|
275
|
+
}], htmlInput: [{
|
|
276
|
+
type: ViewChild,
|
|
277
|
+
args: ['htmlInput', { static: false }]
|
|
278
|
+
}], baseInput: [{
|
|
279
|
+
type: ViewChild,
|
|
280
|
+
args: ["baseInput", { static: false }]
|
|
281
|
+
}], baseInput_static: [{
|
|
282
|
+
type: ViewChild,
|
|
283
|
+
args: ["baseInput", { static: true }]
|
|
284
|
+
}], FocusSubject: [{
|
|
285
|
+
type: Input
|
|
286
|
+
}], SetValidationSubject: [{
|
|
287
|
+
type: Input
|
|
288
|
+
}], InferErrorMessages: [{
|
|
289
|
+
type: Input
|
|
290
|
+
}], FieldAppearence: [{
|
|
291
|
+
type: Input
|
|
292
|
+
}], FloatingLabel: [{
|
|
293
|
+
type: Input
|
|
294
|
+
}], validationFailed: [{
|
|
295
|
+
type: Input
|
|
296
|
+
}], Readonly: [{
|
|
297
|
+
type: Input
|
|
298
|
+
}], widthPx: [{
|
|
299
|
+
type: Input
|
|
300
|
+
}], disabled: [{
|
|
301
|
+
type: Input
|
|
302
|
+
}], placeholder: [{
|
|
303
|
+
type: Input
|
|
304
|
+
}], class: [{
|
|
305
|
+
type: Input
|
|
306
|
+
}], style: [{
|
|
307
|
+
type: Input
|
|
308
|
+
}], pattern: [{
|
|
309
|
+
type: Input
|
|
310
|
+
}], noValidate: [{
|
|
311
|
+
type: Input
|
|
312
|
+
}], autocomplete: [{
|
|
313
|
+
type: Input
|
|
314
|
+
}], id: [{
|
|
315
|
+
type: Input
|
|
316
|
+
}], inputChange: [{
|
|
317
|
+
type: Output
|
|
318
|
+
}], inputFocus: [{
|
|
319
|
+
type: Output
|
|
320
|
+
}], inputFinalized: [{
|
|
321
|
+
type: Output
|
|
322
|
+
}], submitted: [{
|
|
323
|
+
type: Input,
|
|
324
|
+
args: ["submitted"]
|
|
325
|
+
}], forceInvalid: [{
|
|
326
|
+
type: Input
|
|
327
|
+
}] } });
|
|
328
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYmFzZS12YWxpZGF0aW9uLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvZm9ybXMtYW5kLXZhbGlkYXRpb25zL3NyYy9saWIvdmFsaWRhdGlvbnMvYmFzZS12YWxpZGF0aW9uLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLFVBQVU7QUFDVixPQUFPLEVBQUUsWUFBWSxFQUFFLEtBQUssRUFBRSxNQUFNLEVBQUUsU0FBUyxFQUFFLFNBQVMsRUFBaUMsTUFBTSxlQUFlLENBQUM7QUFDakgsT0FBTyxFQUFXLGlCQUFpQixFQUFhLE1BQU0sZ0JBQWdCLENBQUM7QUFLdkUsa0NBQWtDO0FBQ2xDLE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLHVCQUF1QixDQUFDO0FBQ3pELE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFFL0IsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLGdCQUFnQixDQUFDOztBQUUzQzs7OztHQUlHO0FBRUgsTUFBTSxPQUFnQixjQUFjO0lBRWhDLDBCQUEwQjtJQUMxQixZQUFzQixHQUFzQjtRQUF0QixRQUFHLEdBQUgsR0FBRyxDQUFtQjtRQXNCNUM7O1dBRUc7UUFDTyxrQkFBYSxHQUFZLEtBQUssQ0FBQztRQUV6Qzs7V0FFRztRQUNJLGFBQVEsR0FBWSxLQUFLLENBQUM7UUE2Q2pDOzs7OztXQUtHO1FBQ00sdUJBQWtCLEdBQVksSUFBSSxDQUFDO1FBRTVDOztXQUVHO1FBQ00sb0JBQWUsR0FBK0MsU0FBUyxDQUFDO1FBRWpGOzs7O1dBSUc7UUFDTSxrQkFBYSxHQUFZLElBQUksQ0FBQztRQUV2Qzs7OztXQUlHO1FBQ00scUJBQWdCLEdBQVcsRUFBRSxDQUFDO1FBRXZDOztXQUVHO1FBQ00sYUFBUSxHQUFZLEtBQUssQ0FBQztRQUVuQzs7V0FFRztRQUNNLFlBQU8sR0FBVyxJQUFJLENBQUM7UUFFaEM7O1dBRUc7UUFDTSxhQUFRLEdBQVksS0FBSyxDQUFD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YUFBYTtzQkFBckIsS0FBSztnQkFPRyxnQkFBZ0I7c0JBQXhCLEtBQUs7Z0JBS0csUUFBUTtzQkFBaEIsS0FBSztnQkFLRyxPQUFPO3NCQUFmLEtBQUs7Z0JBS0csUUFBUTtzQkFBaEIsS0FBSztnQkFLRyxXQUFXO3NCQUFuQixLQUFLO2dCQUtHLEtBQUs7c0JBQWIsS0FBSztnQkFLRyxLQUFLO3NCQUFiLEtBQUs7Z0JBS0csT0FBTztzQkFBZixLQUFLO2dCQUtHLFVBQVU7c0JBQWxCLEtBQUs7Z0JBS0csWUFBWTtzQkFBcEIsS0FBSztnQkFLRyxFQUFFO3NCQUFWLEtBQUs7Z0JBS0ksV0FBVztzQkFBcEIsTUFBTTtnQkFLRyxVQUFVO3NCQUFuQixNQUFNO2dCQUtHLGNBQWM7c0JBQXZCLE1BQU07Z0JBT2lCLFNBQVM7c0JBQWhDLEtBQUs7dUJBQUMsV0FBVztnQkFpQkwsWUFBWTtzQkFBeEIsS0FBSyIsInNvdXJjZXNDb250ZW50IjpbIi8vIEFuZ3VsYXJcclxuaW1wb3J0IHsgRXZlbnRFbWl0dGVyLCBJbnB1dCwgT3V0cHV0LCBWaWV3Q2hpbGQsIERpcmVjdGl2ZSwgRWxlbWVudFJlZiwgQ2hhbmdlRGV0ZWN0b3JSZWYgfSBmcm9tIFwiQGFuZ3VsYXIvY29yZVwiO1xyXG5pbXBvcnQgeyBOZ01vZGVsLCBSZXF1aXJlZFZhbGlkYXRvciwgVmFsaWRhdG9yIH0gZnJvbSBcIkBhbmd1bGFyL2Zvcm1zXCI7XHJcblxyXG4vLyBDb25maWd1cmF6aW9uaVxyXG5pbXBvcnQgeyBMb2NhbGl6YXRpb25TZXJ2aWNlIH0gZnJvbSBcIkBlc2ZhZW56YS9sb2NhbGl6YXRpb25zXCI7XHJcblxyXG4vLyBEaXJldHRpdmUsIENvbXBvbmVudGksIExpYnJlcmllXHJcbmltcG9ydCB7IFRvb2x0aXBEaXJlY3RpdmUgfSBmcm9tIFwibmd4LWJvb3RzdHJhcC90b29sdGlwXCI7XHJcbmltcG9ydCB7IFN1YmplY3QgfSBmcm9tIFwicnhqc1wiO1xyXG5pbXBvcnQgeyBDaGFuZ2VFdmVudCB9IGZyb20gXCIuLi9tb2RlbHMvQ2hhbmdlRXZlbnRcIjtcclxuaW1wb3J0IHsgdGFrZVVudGlsIH0gZnJvbSBcInJ4anMvb3BlcmF0b3JzXCI7XHJcblxyXG4vKipcclxuICogQ2xhc3NlIGFzdHJhdHRhIGJhc2UgY2hlIGNvbnRpZW5lIGxlIGxvZ2ljaGUgLyBwcm9wcmlldMOgIGluIGNvbXVuZSBhIHR1dHRpIGkgdmFsaWRhdG9yaVxyXG4gKiBcclxuICogTm90YSBiZW5lOiBJIHRvb2x0aXAgcmFsbGVudGFubyB0YW50aXNzaW1vIGxhIHBhZ2luYSBwZXJjaMOpIGlsIHRpemlvIGNoZSBoYSBmYXR0byBuZ3ggYm9vdHN0cmFwIG5vbiDDqCBjYXBhY2VcclxuICovXHJcbkBEaXJlY3RpdmUoKVxyXG5leHBvcnQgYWJzdHJhY3QgY2xhc3MgQmFzZVZhbGlkYXRpb24ge1xyXG5cclxuICAgIC8qKiBAaWdub3JlIENvbnN0cnVjdG9yICovXHJcbiAgICBjb25zdHJ1Y3Rvcihwcm90ZWN0ZWQgY2RyOiBDaGFuZ2VEZXRlY3RvclJlZikgeyB9XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBQZXIgbm9uIHNvdnJhc2NyaXZlcmUgbCdvcmlnaW5hbGUgY29uIGVycm9yaSBjaGUgc3B1bnRhbm8gZGEgQkVcclxuICAgICAqL1xyXG4gICAgcHVibGljIHZhbGlkYXRpb25GYWlsZWRCaW5kOiBzdHJpbmc7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBQZXIgZ2VzdGlyZSBpbCBjYW1iaW8gZGkgbWVzc2FnZ2kgZGkgZXJyb3JlXHJcbiAgICAgKi9cclxuICAgIHByaXZhdGUgdmFsdWVPbkxhc3RWYWxpZGF0aW9uOiBzdHJpbmc7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBTZXJ2aXppbyBkaSBsb2NhbGl6emF6aW9uZSBkZWwgQ29tcG9uZW50ZVxyXG4gICAgICovXHJcbiAgICBwcm90ZWN0ZWQgbGM6IExvY2FsaXphdGlvblNlcnZpY2U7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBWYXJpYWJpbGUgcGVyIHRlbmVyZSBpbiBtZW1vcmlhIGxvIHN0YXRvIGRpIHN1Ym1pdCBkaSBxdWVzdG8gY29tcG9uZW50ZVxyXG4gICAgICovXHJcbiAgICBwcm90ZWN0ZWQgX3N1Ym1pdHRlZDogYm9vbGVhbjtcclxuXHJcbiAgICAvKipcclxuICAgICAqIFZhcmlhYmlsZSBwZXIgdGVuZXJlIGluIG1lbW9yaWEgaWwgZmF0dG8gY2hlIGlsIGNvbXBvbmVudGUgw6ggZm9yemF0byBhIGludmFsaWRvIG8gbm9cclxuICAgICAqL1xyXG4gICAgcHJvdGVjdGVkIF9mb3JjZUludmFsaWQ6IGJvb2xlYW4gPSBmYWxzZTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEluZGljYSBzZSBpbCB2YWxvcmUgw6ggb2JibGlnYXRvcmlvIG8gb3B6aW9uYWxlXHJcbiAgICAgKi9cclxuICAgIHB1YmxpYyByZXF1aXJlZDogYm9vbGVhbiA9IGZhbHNlO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogUXVlcnkgY2hlIHJhY2NvZ2xpZSBpbCB0b29sdGlwIGluIG1hbmllcmEgc3RhdGljYSAoc29sbyBhbGwnaW5pemlvKVxyXG4gICAgICovXHJcbiAgICBAVmlld0NoaWxkKFRvb2x0aXBEaXJlY3RpdmUsIHsgc3RhdGljOiBmYWxzZSB9KSBwcm90ZWN0ZWQgdG9vbHRpcDogVG9vbHRpcERpcmVjdGl2ZTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIFF1ZXJ5IGNoZSByYWNjb2dsaWUgaWwgdG9vbHRpcCBpbiBtYW5pZXJhIGRpbmFtaWNhIChhZCBvZ25pIGNoYW5nZSBkZXRlY3Rpb24pXHJcbiAgICAgKiBcclxuICAgICAqIEBwYXJhbSB7VG9vbHRpcERpcmVjdGl2ZX0gY29tcCBFbGVtZW50byBIVE1MIGEgY3VpIMOoIGFwcGxpY2F0YSBsYSBkaXJldHRpdmEgZGVsIHRvb2x0aXBcclxuICAgICAqL1xyXG4gICAgQFZpZXdDaGlsZChUb29sdGlwRGlyZWN0aXZlLCB7IHN0YXRpYzogdHJ1ZSB9KSBzZXQgdG9vbHRpcF9zdGF0aWMoY29tcDogVG9vbHRpcERpcmVjdGl2ZSkge1xyXG4gICAgICAgIGlmIChjb21wKSB7IHRoaXMudG9vbHRpcCA9IGNvbXA7IH1cclxuICAgIH07XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBFbGVtZW50byBIVE1MIHJhcHByZXNlbnRhbnRlIGwnSW5wdXRcclxuICAgICAqL1xyXG4gICAgQFZpZXdDaGlsZCgnaHRtbElucHV0JywgeyBzdGF0aWM6IGZhbHNlIH0pIGh0bWxJbnB1dDogRWxlbWVudFJlZjtcclxuXHJcbiAgICAvKipcclxuICAgICAqIFF1ZXJ5IGNoZSByYWNjb2dsaWUgbCdpbnB1dCBvIGRpcmV0dGl2YSBjaGUgY29udGllbmUgaWwgdmFsb3JlIGluIG1hbmllcmEgc3RhdGljYSAoc29sbyBhbGwnaW5pemlvKVxyXG4gICAgICovXHJcbiAgICBAVmlld0NoaWxkKFwiYmFzZUlucHV0XCIsIHsgc3RhdGljOiBmYWxzZSB9KSBiYXNlSW5wdXQ6IE5nTW9kZWw7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBRdWVyeSBjaGUgcmFjY29nbGllIGwnaW5wdXQgbyBkaXJldHRpdmEgY2hlIGNvbnRpZW5lIGlsIHZhbG9yZSBpbiBtYW5pZXJhIGRpbmFtaWNhIChhZCBvZ25pIGNoYW5nZSBkZXRlY3Rpb24pXHJcbiAgICAgKiBcclxuICAgICAqIEBwYXJhbSB7TmdNb2RlbH0gY29tcCBFbGVtZW50byBIVE1MIGFzc29jaWF0byBhbCBuZ01vZGVsIGRlbCBjb21wb25lbnRlXHJcbiAgICAgKi9cclxuICAgIEBWaWV3Q2hpbGQoXCJiYXNlSW5wdXRcIiwgeyBzdGF0aWM6IHRydWUgfSkgc2V0IGJhc2VJbnB1dF9zdGF0aWMoY29tcDogTmdNb2RlbCkge1xyXG4gICAgICAgIGlmIChjb21wKSB7IHRoaXMuYmFzZUlucHV0ID0gY29tcDsgfVxyXG4gICAgfTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIFN1YmplY3QgYSBjdWkgbCdvZ2dldHRvIGludGVybm8gc2kgY29sbGVnYSBwZXIgZWZmZXR0dWFyZSBpbCBmb2N1cyBkZWxsJ2VsZW1lbnRvIGlucHV0IHNvdHRvc3RhbnRlXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIEZvY3VzU3ViamVjdDogU3ViamVjdDx2b2lkPjtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEBFWFBFUklNRU5UQUxcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgU2V0VmFsaWRhdGlvblN1YmplY3Q6IFN1YmplY3Q8eyBmaWVsZE5hbWU6IHN0cmluZywgZXJyb3I6IHN0cmluZyB9PjtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEluZGljYSBzZSBkaSBkZWZhdWx0IGRldmUgdmFsdXRhcmUgaWwgbWVzc2FnZ2lvIGRpIGVycm9yZSBpbiBiYXNlIGFsIHZhbGlkYXRvcmUgY2hlIGZhbGxpc2NlLlxyXG4gICAgICogXHJcbiAgICAgKiBTZSBmYWxsaXNjZSBpbCByZXF1aXJlZCB2YWxpZGF0b3Igc2NyaXZlcsOgIGNoZSBsJ2lucHV0IMOoIG9iYmxpZ2F0b3Jpbywgc2UgaW52ZWNlIGZhbGxpc2NlIFxyXG4gICAgICogdW4gZXZlbnR1YWxlIHBhdHRlcm4gdmFsaWRhdG9yIHNjcml2ZXLDoCBjaGUgaWwgZm9ybWF0byBkZWxsJ2lucHV0IMOoIGludmFsaWRvXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIEluZmVyRXJyb3JNZXNzYWdlczogYm9vbGVhbiA9IHRydWU7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBNb2RhbGl0w6AgaW4gY3VpIHZpZW5lIG1vc3RyYXRvIGlsIGNhbXBvLCAxLTEgcmlzcGV0dG8gYWxsZSBkZWZpbml6aW9uaSBkaSBBbmd1bGFyIE1hdGVyaWFsIFxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBGaWVsZEFwcGVhcmVuY2U6IFwibGVnYWN5XCIgfCBcInN0YW5kYXJkXCIgfCBcImZpbGxcIiB8IFwib3V0bGluZVwiID0gXCJvdXRsaW5lXCI7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBJbmRpY2Egc2UgaWwgKipQbGFjZWhvbGRlcioqIGRldidlc3NlcmUgdXNhdG8gY29tZSB1bmEgZmxvYXRpbmcgbGFiZWwgZGkgbWF0ZXJpYWwgbyBzb2xvIGNvbWUgdW4gcGxhY2Vob2xkZXIgc3RhbmRhcmQgXHJcbiAgICAgKiBcclxuICAgICAqIElnbm9yYXRhIGxhdG8gYXV0b2NvbXBsZXRlLCBhdXRvY29tcGxldGUtbXVsdGkgZSBzZWxlY3QgaW4gcXVhbnRvIGhhbm5vIGdlc3Rpb25pIHBhcnRpY29sYXJpIGRpIHBsYWNlaG9sZGVyIGVjYy4uLlxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBGbG9hdGluZ0xhYmVsOiBib29sZWFuID0gdHJ1ZTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIE1lc3NhZ2dpbyBkYSBtb3N0cmFyZSBzZSBsYSB2YWxpZGF6aW9uZSBmYWxsaXNjZS4gXHJcbiAgICAgKiBcclxuICAgICAqIFNlIHF1ZXN0byDDqCB2YWxvcml6emF0bywgaWwgbWVzc2FnZ2lvIG5vbiB2aWVuZSB2YWx1dGF0byBpbiBhdXRvbWF0aWNvIG5vbnN0YW50ZSAqKkluZmVyRXJyb3JNZXNzYWdlcyoqIHNpYSAqKnRydWUqKlxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSB2YWxpZGF0aW9uRmFpbGVkOiBzdHJpbmcgPSBcIlwiO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogSW5kaWNhIHNlIGlsIGNvbXBvbmVudGUgw6ggaW4gc29sYSBsZXR0dXJhXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIFJlYWRvbmx5OiBib29sZWFuID0gZmFsc2U7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBJbmRpY2EgbGUgZGltZW5zaW9uaSBkZWwgY29tcG9uZW50ZVxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSB3aWR0aFB4OiBudW1iZXIgPSBudWxsO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogSW5kaWNhIHNlIGlsIGNvbXBvbmVudGUgw6ggZGlzYWJpbGl0YXRvIG8gbm8gKHBpw7kgbyBtZW5vIHN0ZXNzbyBjb25jZXR0byBkZWwgcmVhZG9ubHkpXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIGRpc2FibGVkOiBib29sZWFuID0gZmFsc2U7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBFdmVudHVhbGUgcGxhY2Vob2xkZXIgZGEgbW9zdHJhcmUgYWwgcG9zdG8gZGVsIHZhbG9yZSBxdWFuZG8gaWwgdmFsb3JlIMOoIG51bGxvIC8gdnVvdG9cclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgcGxhY2Vob2xkZXI6IHN0cmluZyA9IFwiXCI7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBDbGFzc2kgZGEgYXBwbGljYXJlIGFsIGNvbXBvbmVudGVcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgY2xhc3M6IHN0cmluZyA9IFwiXCI7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBTdGlsaSBkYSBhcHBsaWNhcmUgYWwgY29tcG9uZW50ZVxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBzdHlsZTogc3RyaW5nID0gXCJcIjtcclxuXHJcbiAgICAvKipcclxuICAgICAqIFBhdHRlcm4gZGkgdmFsaWRhemlvbmUgZGVsbCdpbnB1dFxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBwYXR0ZXJuOiBzdHJpbmcgPSBcIlwiO1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogSW5kaWNhIGRpIG5vbiB2YWxpZGFyZSBpbCBjb21wb25lbnRlXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dCgpIG5vVmFsaWRhdGU6IGJvb2xlYW4gPSBmYWxzZTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEluZGljYSBzZSBhYmlsaXRhcmUgbyBtZW5vIGwnYXV0b2NvbXBsZXRhbWVudG8gZGkgZGVmYXVsdCBkZWwgYnJvd3NlclxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBhdXRvY29tcGxldGU6IHN0cmluZyA9IFwib2ZmXCI7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBJZCBkZWxsJ2lucHV0LiDDiCBpbXBvcnRhbnRlIGltcG9zdGFybG8gc29wcmF0dHV0dG8gc2UgbCdpbnRlcmZhY2NpYSBnZW5lcmF0YSBkZXYnZXNzZXJlIHRlc3RhdGFcclxuICAgICAqL1xyXG4gICAgQElucHV0KCkgaWQ6IHN0cmluZyA9IFwiXCI7XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBFdmVudG8gY2hlIHNvc3RpdHVpc2NlIGwnbmdNb2RlbENoYW5nZSBmYWNlbmRvbG8gZnVuemlvbmFyZSBpbiBtYW5pZXJhIHVuIHBvJyBwacO5IGNvbnNpc3RlbnRlXHJcbiAgICAgKi9cclxuICAgIEBPdXRwdXQoKSBpbnB1dENoYW5nZTogRXZlbnRFbWl0dGVyPHN0cmluZz4gPSBuZXcgRXZlbnRFbWl0dGVyPHN0cmluZz4oKTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEV2ZW50byBjaGUgaW5kaWNhIGlsIGZvY3VzIGF2dmVudXRvIHN1IHVuIGNvbnRyb2xsb1xyXG4gICAgICovXHJcbiAgICBAT3V0cHV0KCkgaW5wdXRGb2N1czogRXZlbnRFbWl0dGVyPGFueT4gPSBuZXcgRXZlbnRFbWl0dGVyPGFueT4oKTtcclxuXHJcbiAgICAvKipcclxuICAgICAqIEV2ZW50byBjaGUgaW5kaWNhIGxhIGZpbmFsaXp6YXppb25lIGRlbCB2YWxvcmUgYXZ2ZW51dGEgc3UgdW4gY29udHJvbGxvXHJcbiAgICAgKi9cclxuICAgIEBPdXRwdXQoKSBpbnB1dEZpbmFsaXplZDogRXZlbnRFbWl0dGVyPGFueT4gPSBuZXcgRXZlbnRFbWl0dGVyPGFueT4oKTtcclxuICAgIFxyXG4gICAgLyoqXHJcbiAgICAgKiBJbXBvc3RhIGlsIGNvbXBvbmVudGUgY29tZSBcInN1Ym1pdHRlZFwiIHNjYXRlbmFuZG9uZSBsZSB2YWxpZGF6aW9uaSBlZCBldmVudHVhbG1lbnRlIGxhIHZpc3VhbGl6emF6aW9uZSBkZWwgdG9vbHRpcCBkaSBlcnJvcmVcclxuICAgICAqIFxyXG4gICAgICogQHBhcmFtIHtib29sZWFufSB2YWwgKip0cnVlKiogc2Ugc2kgdnVvbGUgaW1wb3N0YXJlIHF1ZXN0byBjb250cm9sbG8gY29tZSBzdWJtaXR0ZWQsICoqZmFsc2UqKiBhbHRyaW1lbnRpXHJcbiAgICAgKi9cclxuICAgIEBJbnB1dChcInN1Ym1pdHRlZFwiKSBzZXQgc3VibWl0dGVkKHZhbDogYm9vbGVhbikge1xyXG4gICAgICAgIHRoaXMuX3N1Ym1pdHRlZCA9IHZhbDtcclxuICAgICAgICBpZiAoIXRoaXMuYmFzZUlucHV0KVxyXG4gICAgICAgICAgICByZXR1cm47XHJcblxyXG4gICAgICAgIGlmICh2YWwpXHJcbiAgICAgICAgICAgIHRoaXMuYmFzZUlucHV0LmNvbnRyb2wubWFya0FzVG91Y2hlZCgpO1xyXG5cclxuICAgICAgICBpZiAodGhpcy5iYXNlSW5wdXQuY29udHJvbC5zdGF0dXMgPT09IFwiSU5WQUxJRFwiICYmIHZhbClcclxuICAgICAgICAgICAgdGhpcy5zaG93VG9vbHRpcFdpdGhNZXNzYWdlKCk7XHJcbiAgICAgICAgZWxzZVxyXG4gICAgICAgICAgICB0aGlzLnRvb2x0aXAuaGlkZSgpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogSW1wb3N0YSBpbCBjb21wb25lbnRlIGNvbWUgXCJpbnZhbGlkXCIgYSBwcmVzY2luZGVyZSBkYWkgdmFsaWRhdG9yaVxyXG4gICAgICovXHJcbiAgICBASW5wdXQoKSBzZXQgZm9yY2VJbnZhbGlkKHZhbDogYm9vbGVhbikge1xyXG4gICAgICAgIHRoaXMuX2ZvcmNlSW52YWxpZCA9IHZhbDtcclxuXHJcbiAgICAgICAgaWYgKHZhbClcclxuICAgICAgICAgICAgc2V0VGltZW91dCgoKSA9PiB7XHJcbiAgICAgICAgICAgICAgICB0aGlzLmJhc2VJbnB1dC5jb250cm9sLnNldEVycm9ycyh7IGZvcmNlZHRvaW52YWxpZDogdHJ1ZSB9KTtcclxuICAgICAgICAgICAgICAgIHRoaXMuYmFzZUlucHV0LmNvbnRyb2wubWFya0FzVG91Y2hlZCgpO1xyXG4gICAgICAgICAgICAgICAgdGhpcy5iYXNlSW5wdXQuY29udHJvbC5tYXJrQXNEaXJ0eSgpO1xyXG4gICAgICAgICAgICAgICAgdGhpcy5jZHIuZGV0ZWN0Q2hhbmdlcygpO1xyXG4gICAgICAgICAgICB9KTtcclxuICAgICAgICBlbHNlXHJcbiAgICAgICAgICAgIHNldFRpbWVvdXQoKCkgPT4ge1xyXG4gICAgICAgICAgICAgICAgdGhpcy5iYXNlSW5wdXQuY29udHJvbC5zZXRFcnJvcnMoeyBmb3JjZWR0b2ludmFsaWQ6IG51bGwgfSk7XHJcbiAgICAgICAgICAgICAgICB0aGlzLmJhc2VJbnB1dC5jb250cm9sLnVwZGF0ZVZhbHVlQW5kVmFsaWRpdHkoKTtcclxuICAgICAgICAgICAgfSk7XHJcbiAgICB9XHJcblxyXG4gICAgbmdPbkluaXQoKSB7XHJcbiAgICAgICAgaWYgKHRoaXMuU2V0VmFsaWRhdGlvblN1YmplY3QpIHtcclxuICAgICAgICAgICAgdGhpcy5TZXRWYWxpZGF0aW9uU3ViamVjdC5waXBlKHRha2VVbnRpbCh0aGlzLmRlc3Ryb3llZCQpKS5zdWJzY3JpYmUodiA9PiB7XHJcbiAgICAgICAgICAgICAgICBpZiAodi5maWVsZE5hbWUgKyBcIl9pbnRlcm5hbFwiID09IHRoaXMuaWQpIHtcclxuICAgICAgICAgICAgICAgICAgICB0aGlzLmZvcmNlSW52YWxpZCA9IHRydWU7XHJcbiAgICAgICAgICAgICAgICAgICAgdGhpcy5zaG93VG9vbHRpcFdpdGhNZXNzYWdlKHYuZXJyb3IpO1xyXG4gICAgICAgICAgICAgICAgfVxyXG4gICAgICAgICAgICB9KVxyXG4gICAgICAgIH0gXHJcbiAgICB9XHJcblxyXG4gICAgcHJvdGVjdGVkIGNoZWNrUmVxdWlyZWRuZXNzKF92YWxpZGF0b3JzOiBWYWxpZGF0b3JbXSkge1xyXG4gICAgICAgIGlmIChfdmFsaWRhdG9ycyAmJiBfdmFsaWRhdG9ycy5zb21lKGVsZW0gPT4gZWxlbSBpbnN0YW5jZW9mIFJlcXVpcmVkVmFsaWRhdG9yICYmIChlbGVtLnJlcXVpcmVkID09PSB0cnVlIHx8ICghZWxlbS5yZXF1aXJlZCAmJiBlbGVtLnJlcXVpcmVkICE9PSBmYWxzZSkpKSlcclxuICAgICAgICAgICAgdGhpcy5yZXF1aXJlZCA9IHRydWU7XHJcbiAgICB9XHJcblxyXG4gICAgZGVzdHJveWVkJDogU3ViamVjdDx2b2lkPiA9IG5ldyBTdWJqZWN0PHZvaWQ+KCk7XHJcbiAgICBuZ09uRGVzdHJveSgpe1xyXG4gICAgICAgIHRoaXMuZGVzdHJveWVkJC5uZXh0KCk7XHJcbiAgICAgICAgdGhpcy5kZXN0cm95ZWQkLmNvbXBsZXRlKCk7XHJcbiAgICB9XHJcbiAgICAvKipcclxuICAgICAqIEhlbHBlciBjaGUgY29udHJvbGxhIHNlIGlsIHRvb2x0aXAgZGV2ZSBlc3NlcmUgbW9zdHJhdG8gbyBtZW5vLCBcclxuICAgICAqIHJpY2hpYW1hdG8gZGlyZXR0YW1lbnRlIGRhbGwnSFRNTCBkZWkgY29tcG9uZW50aVxyXG4gICAgICovXHJcbiAgICBwdWJsaWMgY2hlY2tUb29sdGlwKCkge1xyXG4gICAgICAgIGlmICgodGhpcy5iYXNlSW5wdXQuaW52YWxpZCAmJiB0aGlzLmJhc2VJbnB1dC50b3VjaGVkKSlcclxuICAgICAgICAgICAgdGhpcy5zaG93VG9vbHRpcFdpdGhNZXNzYWdlKCk7XHJcbiAgICB9XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBIZWxwZXIgY2hlIGNhbGNvbGEgaWwgbWVzc2FnZ2lvIGRhIG1vc3RyYXJlIG5lbCB0b29sdGlwIGNoZSBhbmRyw6AgYWQgYXByaXJlXHJcbiAgICAgKi9cclxuICAgIHByaXZhdGUgc2hvd1Rvb2x0aXBXaXRoTWVzc2FnZShtZXNzYWdlT3ZlcnJpZGU6IHN0cmluZyA9IG51bGwpIHtcclxuXHJcbiAgICAgICAgLy8gQWdnaW9ybm8gaWwgbWVzc2FnZ2lvIGRpIHZhbGlkYXppb25lIHNvbG8gc2UgaWwgdmFsb3JlIMOoIGRpdmVyc28gZGFsbCd1bHRpbW8gdmFsb3JlIHJpY2V2dXRvXHJcbiAgICAgICAgaWYgKHRoaXMudmFsdWVPbkxhc3RWYWxpZGF0aW9uICE9IHRoaXMuYmFzZUlucHV0LnZhbHVlKSB7XHJcbiAgICAgICAgICAgIHRoaXMudmFsaWRhdGlvbkZhaWxlZEJpbmQgPSBtZXNzYWdlT3ZlcnJpZGUgfHwgdGhpcy52YWxpZGF0aW9uRmFpbGVkIHx8ICh0aGlzLkluZmVyRXJyb3JNZXNzYWdlcyA/IHRoaXMuaW5mZXJNZXNzYWdlKCkgOiBcIlwiKTtcclxuICAgICAgICAgICAgdGhpcy52YWx1ZU9uTGFzdFZhbGlkYXRpb24gPSB0aGlzLmJhc2VJbnB1dC52YWx1ZTtcclxuICAgICAgICB9XHJcblxyXG4gICAgICAgIGlmICh0aGlzLnZhbGlkYXRpb25GYWlsZWRCaW5kKVxyXG4gICAgICAgICAgICB0aGlzLnRvb2x0aXAuc2hvdygpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogQ2FsY29sYSBpbCBtZXNzYWdnaW8gZGEgbW9zdHJhcmUgaW4gYmFzZSBhbCB2YWxvcmUuXHJcbiAgICAgKiBcclxuICAgICAqIEVudHJhcmUgaW4gcXVlc3RhIGZ1bnppb25lIHNpZ25pZmljYSBjaGUgbG8gc3RhdG8gZGkgdmFsaWRhemlvbmUgw6ggZmFsbGl0bywgcGVyIHF1ZXN0byBzaSBjb21wb3J0YSBzZW1wbGljZW1lbnRlIGluIG1hbmllcmEgZXNjbHVzaXZhLCBlIGNpb8OoOlxyXG4gICAgICogXHJcbiAgICAgKiAxKSBTZSBlcm8gcmVxdWlyZWQgZSBzb25vIHNlbnphIHZhbG9yZSAtLT4gSW5wdXQgcmljaGllc3RvXHJcbiAgICAgKiBcclxuICAgICAqIDIpIEFsdHJpbWVudGkgc2UgaG8gdW4gdmFsb3JlIC0tPiBEaSBzaWN1cm8gaWwgZm9ybWF0byDDqCBlcnJhdG9cclxuICAgICAqL1xyXG4gICAgcHJpdmF0ZSBpbmZlck1lc3NhZ2UoKTogc3RyaW5nIHtcclxuICAgICAgICBpZiAodGhpcy5yZXF1aXJlZCAmJiAhdGhpcy5iYXNlSW5wdXQudmFsdWUpXHJcbiAgICAgICAgICAgIHJldHVybiB0aGlzLmxjLmxvYyhcIlJlcXVpcmVkIElucHV0XCIpXHJcblxyXG4gICAgICAgIGlmICh0aGlzLmJhc2VJbnB1dC52YWx1ZSlcclxuICAgICAgICAgICAgcmV0dXJuIHRoaXMubGMubG9jKFwiSW52YWxpZCBJbnB1dCBGb3JtYXRcIilcclxuICAgIH1cclxuXHJcbiAgICAvKipcclxuICAgICAqIEZvcnphIGxhIGNoaXVzdXJhIGRlbCB0b29sdGlwXHJcbiAgICAgKi9cclxuICAgIGNsb3NlVG9vbHRpcCgpIHtcclxuICAgICAgICB0aGlzLnRvb2x0aXAuaGlkZSgpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogQ29udHJvbGxhIHNlIGlsIGNvbnRyb2xsbyDDqCB2YWxpZG8gZSBpbiBjYXNvIGxvIHNpYSBjaGl1ZGUgaWwgdG9vbHRpcFxyXG4gICAgICovXHJcbiAgICBwcm90ZWN0ZWQgQ2hlY2tWYWxpZGl0eSgpIHtcclxuICAgICAgICBpZiAoIXRoaXMuYmFzZUlucHV0LnN0YXR1c0NoYW5nZXMpXHJcbiAgICAgICAgICAgIHJldHVybjtcclxuXHJcbiAgICAgICAgdGhpcy5iYXNlSW5wdXQuc3RhdHVzQ2hhbmdlcy5zdWJzY3JpYmUoZXZlbnQgPT4ge1xyXG4gICAgICAgICAgICBpZiAoZXZlbnQgPT09IFwiVkFMSURcIilcclxuICAgICAgICAgICAgICAgIHRoaXMudG9vbHRpcC5oaWRlKCk7XHJcbiAgICAgICAgfSk7XHJcbiAgICB9XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBAaWdub3JlXHJcbiAgICAgKi9cclxuICAgIHByb3RlY3RlZCBwcm9wYWdhdGVDaGFuZ2UgPSAoXzogYW55KSA9PiB7IH07XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBMJ2VtaXQgZGVsIGZvY3VzIGRlbGwnZWxlbWVudG9cclxuICAgICAqIFxyXG4gICAgICogQHBhcmFtIHthbnl9IHRvRW1pdCB2YWxvcmUgZGEgcHJvcGFnYXJlIGFsbCdlc3Rlcm5vXHJcbiAgICAgKi9cclxuICAgIG9uRm9jdXModG9FbWl0KSB7XHJcbiAgICAgICAgdGhpcy5pbnB1dEZvY3VzLmVtaXQodG9FbWl0KTtcclxuICAgIH1cclxuXHJcbiAgICAvKipcclxuICAgICAqIEZpbmFsaXp6YXppb25lIElucHV0XHJcbiAgICAgKi9cclxuICAgIG9uRmluYWxpemUoKSB7XHJcbiAgICAgICAgdGhpcy5pbnB1dEZpbmFsaXplZC5lbWl0KCk7XHJcbiAgICB9XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBTdWJzY3JpcHRpb24gYWxsZSByaWNoaWVzdGUgZGkgZm9jdXNcclxuICAgICAqL1xyXG4gICAgb2JzZXJ2YWJsZTogYW55O1xyXG5cclxuICAgIC8qKlxyXG4gICAgICogUmVnaXN0cmEgaWwgU3ViamVjdCBwZXIgcmljZXZlcmUgbGUgcmljaGllc3RlIGRpIEZvY3VzIGRhbGwnZXN0ZXJub1xyXG4gICAgICovXHJcbiAgICByZWdpc3RlckZvY3VzUmVxdWVzdCgpOiBhbnkge1xyXG4gICAgICAgIGlmKCF0aGlzLkZvY3VzU3ViamVjdClcclxuICAgICAgICAgICAgcmV0dXJuO1xyXG4gICAgICAgIHRoaXMub2JzZXJ2YWJsZSA9IHRoaXMuRm9jdXNTdWJqZWN0LnN1YnNjcmliZSh0ID0+IHtcclxuICAgICAgICAgICAgdGhpcy5odG1sSW5wdXQubmF0aXZlRWxlbWVudC5mb2N1cygpO1xyXG4gICAgICAgIH0pO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogRGVyZWdpc3RyYSBpbCBTdWJqZWN0IGRlbGxlIHJpY2hpZXN0ZSBkaSBmb2N1c1xyXG4gICAgICovXHJcbiAgICBkZXJlZ2lzdGVyRm9jdXNSZXF1ZXN0KCkge1xyXG4gICAgICAgIGlmICh0aGlzLm9ic2VydmFibGUpXHJcbiAgICAgICAgICAgIHRoaXMub2JzZXJ2YWJsZS51bnN1YnNjcmliZSgpO1xyXG4gICAgfVxyXG59Il19
|