aboutsummaryrefslogtreecommitdiffhomepage
path: root/client/src/app/shared
diff options
context:
space:
mode:
Diffstat (limited to 'client/src/app/shared')
-rw-r--r--client/src/app/shared/forms/form-reactive.ts52
-rw-r--r--client/src/app/shared/forms/form-validators/form-validator.service.ts65
-rw-r--r--client/src/app/shared/forms/form-validators/index.ts1
-rw-r--r--client/src/app/shared/forms/form-validators/login.ts18
-rw-r--r--client/src/app/shared/forms/form-validators/reset-password.ts10
-rw-r--r--client/src/app/shared/shared.module.ts2
6 files changed, 126 insertions, 22 deletions
diff --git a/client/src/app/shared/forms/form-reactive.ts b/client/src/app/shared/forms/form-reactive.ts
index e7764d069..441ec8203 100644
--- a/client/src/app/shared/forms/form-reactive.ts
+++ b/client/src/app/shared/forms/form-reactive.ts
@@ -1,40 +1,48 @@
1import { FormGroup } from '@angular/forms' 1import { FormGroup } from '@angular/forms'
2import { BuildFormArgument, BuildFormDefaultValues, FormValidatorService } from '@app/shared/forms/form-validators/form-validator.service'
3
4export type FormReactiveErrors = { [ id: string ]: string }
5export type FormReactiveValidationMessages = {
6 [ id: string ]: {
7 [ name: string ]: string
8 }
9}
2 10
3export abstract class FormReactive { 11export abstract class FormReactive {
4 abstract form: FormGroup 12 protected abstract formValidatorService: FormValidatorService
5 abstract formErrors: Object
6 abstract validationMessages: Object
7 13
8 abstract buildForm (): void 14 form: FormGroup
15 formErrors: FormReactiveErrors
16 validationMessages: FormReactiveValidationMessages
9 17
10 protected onValueChanged (data?: any) { 18 buildForm (obj: BuildFormArgument, defaultValues: BuildFormDefaultValues = {}) {
11 for (const field in this.formErrors) { 19 const { formErrors, validationMessages, form } = this.formValidatorService.buildForm(obj, defaultValues)
12 // clear previous error message (if any)
13 this.formErrors[field] = ''
14 const control = this.form.get(field)
15 20
16 if (control && control.dirty && !control.valid) { 21 this.form = form
17 const messages = this.validationMessages[field] 22 this.formErrors = formErrors
18 for (const key in control.errors) { 23 this.validationMessages = validationMessages
19 this.formErrors[field] += messages[key] + ' ' 24
20 } 25 this.form.valueChanges.subscribe(data => this.onValueChanged(false))
21 }
22 }
23 } 26 }
24 27
25 // Same as onValueChanged but force checking even if the field is not dirty 28 protected onValueChanged (forceCheck = false) {
26 protected forceCheck () {
27 for (const field in this.formErrors) { 29 for (const field in this.formErrors) {
28 // clear previous error message (if any) 30 // clear previous error message (if any)
29 this.formErrors[field] = '' 31 this.formErrors[ field ] = ''
30 const control = this.form.get(field) 32 const control = this.form.get(field)
31 33
32 if (control && !control.valid) { 34 // Don't care if dirty on force check
33 const messages = this.validationMessages[field] 35 const isDirty = control.dirty || forceCheck === true
36 if (control && isDirty && !control.valid) {
37 const messages = this.validationMessages[ field ]
34 for (const key in control.errors) { 38 for (const key in control.errors) {
35 this.formErrors[field] += messages[key] + ' ' 39 this.formErrors[ field ] += messages[ key ] + ' '
36 } 40 }
37 } 41 }
38 } 42 }
39 } 43 }
44
45 protected forceCheck () {
46 return this.onValueChanged(true)
47 }
40} 48}
diff --git a/client/src/app/shared/forms/form-validators/form-validator.service.ts b/client/src/app/shared/forms/form-validators/form-validator.service.ts
new file mode 100644
index 000000000..5c3d3e4bd
--- /dev/null
+++ b/client/src/app/shared/forms/form-validators/form-validator.service.ts
@@ -0,0 +1,65 @@
1import { FormBuilder, FormControl, FormGroup, ValidatorFn } from '@angular/forms'
2import { Injectable } from '@angular/core'
3import { FormReactiveErrors, FormReactiveValidationMessages } from '@app/shared/forms/form-reactive'
4import { I18n } from '@ngx-translate/i18n-polyfill'
5
6export type BuildFormArgument = {
7 [ id: string ]: {
8 VALIDATORS: ValidatorFn[],
9 MESSAGES: { [ name: string ]: string }
10 }
11}
12export type BuildFormDefaultValues = {
13 [ name: string ]: string | string[]
14}
15
16@Injectable()
17export class FormValidatorService {
18
19 constructor (
20 private formBuilder: FormBuilder,
21 private i18n: I18n
22 ) {}
23
24 buildForm (obj: BuildFormArgument, defaultValues: BuildFormDefaultValues = {}) {
25 const formErrors: FormReactiveErrors = {}
26 const validationMessages: FormReactiveValidationMessages = {}
27 const group: { [key: string]: any } = {}
28
29 for (const name of Object.keys(obj)) {
30 formErrors[name] = ''
31
32 const field = obj[name]
33 if (field && field.MESSAGES) validationMessages[name] = field.MESSAGES
34
35 const defaultValue = defaultValues[name] || ''
36
37 if (field && field.VALIDATORS) group[name] = [ defaultValue, field.VALIDATORS ]
38 else group[name] = [ defaultValue ]
39 }
40
41 const form = this.formBuilder.group(group)
42 return { form, formErrors, validationMessages }
43 }
44
45 updateForm (
46 form: FormGroup,
47 formErrors: FormReactiveErrors,
48 validationMessages: FormReactiveValidationMessages,
49 obj: BuildFormArgument,
50 defaultValues: BuildFormDefaultValues = {}
51 ) {
52 for (const name of Object.keys(obj)) {
53 formErrors[name] = ''
54
55 const field = obj[name]
56 if (field && field.MESSAGES) validationMessages[name] = field.MESSAGES
57
58 const defaultValue = defaultValues[name] || ''
59
60 if (field && field.VALIDATORS) form.addControl(name, new FormControl(defaultValue, field.VALIDATORS))
61 else form.addControl(name, new FormControl(defaultValue))
62 }
63 }
64
65}
diff --git a/client/src/app/shared/forms/form-validators/index.ts b/client/src/app/shared/forms/form-validators/index.ts
index 09ae86f8a..cf544b2a9 100644
--- a/client/src/app/shared/forms/form-validators/index.ts
+++ b/client/src/app/shared/forms/form-validators/index.ts
@@ -1,3 +1,4 @@
1export * from './form-validator.service'
1export * from './host' 2export * from './host'
2export * from './user' 3export * from './user'
3export * from './video-abuse' 4export * from './video-abuse'
diff --git a/client/src/app/shared/forms/form-validators/login.ts b/client/src/app/shared/forms/form-validators/login.ts
new file mode 100644
index 000000000..f37f8d285
--- /dev/null
+++ b/client/src/app/shared/forms/form-validators/login.ts
@@ -0,0 +1,18 @@
1import { Validators } from '@angular/forms'
2
3export const LOGIN_USERNAME = {
4 VALIDATORS: [
5 Validators.required
6 ],
7 MESSAGES: {
8 'required': 'Username is required.'
9 }
10}
11export const LOGIN_PASSWORD = {
12 VALIDATORS: [
13 Validators.required
14 ],
15 MESSAGES: {
16 'required': 'Password is required.'
17 }
18}
diff --git a/client/src/app/shared/forms/form-validators/reset-password.ts b/client/src/app/shared/forms/form-validators/reset-password.ts
new file mode 100644
index 000000000..7dafdef9a
--- /dev/null
+++ b/client/src/app/shared/forms/form-validators/reset-password.ts
@@ -0,0 +1,10 @@
1import { Validators } from '@angular/forms'
2
3export const RESET_PASSWORD_CONFIRM = {
4 VALIDATORS: [
5 Validators.required
6 ],
7 MESSAGES: {
8 'required': 'Confirmation of the password is required.'
9 }
10}
diff --git a/client/src/app/shared/shared.module.ts b/client/src/app/shared/shared.module.ts
index fba099401..91d905ec7 100644
--- a/client/src/app/shared/shared.module.ts
+++ b/client/src/app/shared/shared.module.ts
@@ -34,6 +34,7 @@ import { VideoService } from './video/video.service'
34import { AccountService } from '@app/shared/account/account.service' 34import { AccountService } from '@app/shared/account/account.service'
35import { VideoChannelService } from '@app/shared/video-channel/video-channel.service' 35import { VideoChannelService } from '@app/shared/video-channel/video-channel.service'
36import { I18n } from '@ngx-translate/i18n-polyfill' 36import { I18n } from '@ngx-translate/i18n-polyfill'
37import { FormValidatorService } from '@app/shared/forms/form-validators/form-validator.service'
37 38
38@NgModule({ 39@NgModule({
39 imports: [ 40 imports: [
@@ -110,6 +111,7 @@ import { I18n } from '@ngx-translate/i18n-polyfill'
110 AccountService, 111 AccountService,
111 MarkdownService, 112 MarkdownService,
112 VideoChannelService, 113 VideoChannelService,
114 FormValidatorService,
113 I18n 115 I18n
114 ] 116 ]
115}) 117})