]> git.proxmox.com Git - ceph.git/blob - ceph/src/pybind/mgr/dashboard/frontend/src/app/ceph/cluster/configuration/configuration-form/configuration-form.component.ts
e99ff3cee971f7bb2709f3eb4d785d3774d24851
[ceph.git] / ceph / src / pybind / mgr / dashboard / frontend / src / app / ceph / cluster / configuration / configuration-form / configuration-form.component.ts
1 import { Component, OnInit } from '@angular/core';
2 import { FormControl, FormGroup, ValidatorFn } from '@angular/forms';
3 import { ActivatedRoute, Router } from '@angular/router';
4
5 import { I18n } from '@ngx-translate/i18n-polyfill';
6 import * as _ from 'lodash';
7
8 import { ConfigurationService } from '../../../../shared/api/configuration.service';
9 import { ConfigFormModel } from '../../../../shared/components/config-option/config-option.model';
10 import { ConfigOptionTypes } from '../../../../shared/components/config-option/config-option.types';
11 import { NotificationType } from '../../../../shared/enum/notification-type.enum';
12 import { CdFormGroup } from '../../../../shared/forms/cd-form-group';
13 import { NotificationService } from '../../../../shared/services/notification.service';
14 import { ConfigFormCreateRequestModel } from './configuration-form-create-request.model';
15
16 @Component({
17 selector: 'cd-configuration-form',
18 templateUrl: './configuration-form.component.html',
19 styleUrls: ['./configuration-form.component.scss']
20 })
21 export class ConfigurationFormComponent implements OnInit {
22 configForm: CdFormGroup;
23 response: ConfigFormModel;
24 type: string;
25 inputType: string;
26 humanReadableType: string;
27 minValue: number;
28 maxValue: number;
29 patternHelpText: string;
30 availSections = ['global', 'mon', 'mgr', 'osd', 'mds', 'client'];
31
32 constructor(
33 private route: ActivatedRoute,
34 private router: Router,
35 private configService: ConfigurationService,
36 private notificationService: NotificationService,
37 private i18n: I18n
38 ) {
39 this.createForm();
40 }
41
42 createForm() {
43 const formControls = {
44 name: new FormControl({ value: null }),
45 desc: new FormControl({ value: null }),
46 long_desc: new FormControl({ value: null }),
47 values: new FormGroup({}),
48 default: new FormControl({ value: null }),
49 daemon_default: new FormControl({ value: null }),
50 services: new FormControl([])
51 };
52
53 this.availSections.forEach((section) => {
54 formControls.values.addControl(section, new FormControl(null));
55 });
56
57 this.configForm = new CdFormGroup(formControls);
58 }
59
60 ngOnInit() {
61 this.route.params.subscribe((params: { name: string }) => {
62 const configName = params.name;
63 this.configService.get(configName).subscribe((resp: ConfigFormModel) => {
64 this.setResponse(resp);
65 });
66 });
67 }
68
69 getValidators(configOption: any): ValidatorFn[] {
70 const typeValidators = ConfigOptionTypes.getTypeValidators(configOption);
71 if (typeValidators) {
72 this.patternHelpText = typeValidators.patternHelpText;
73
74 if ('max' in typeValidators && typeValidators.max !== '') {
75 this.maxValue = typeValidators.max;
76 }
77
78 if ('min' in typeValidators && typeValidators.min !== '') {
79 this.minValue = typeValidators.min;
80 }
81
82 return typeValidators.validators;
83 }
84
85 return undefined;
86 }
87
88 getStep(type: string, value: number): number | undefined {
89 return ConfigOptionTypes.getTypeStep(type, value);
90 }
91
92 setResponse(response: ConfigFormModel) {
93 this.response = response;
94 const validators = this.getValidators(response);
95
96 this.configForm.get('name').setValue(response.name);
97 this.configForm.get('desc').setValue(response.desc);
98 this.configForm.get('long_desc').setValue(response.long_desc);
99 this.configForm.get('default').setValue(response.default);
100 this.configForm.get('daemon_default').setValue(response.daemon_default);
101 this.configForm.get('services').setValue(response.services);
102
103 if (this.response.value) {
104 this.response.value.forEach((value) => {
105 // Check value type. If it's a boolean value we need to convert it because otherwise we
106 // would use the string representation. That would cause issues for e.g. checkboxes.
107 let sectionValue = null;
108 if (value.value === 'true') {
109 sectionValue = true;
110 } else if (value.value === 'false') {
111 sectionValue = false;
112 } else {
113 sectionValue = value.value;
114 }
115 this.configForm
116 .get('values')
117 .get(value.section)
118 .setValue(sectionValue);
119 });
120 }
121
122 this.availSections.forEach((section) => {
123 this.configForm
124 .get('values')
125 .get(section)
126 .setValidators(validators);
127 });
128
129 const currentType = ConfigOptionTypes.getType(response.type);
130 this.type = currentType.name;
131 this.inputType = currentType.inputType;
132 this.humanReadableType = currentType.humanReadable;
133 }
134
135 createRequest(): ConfigFormCreateRequestModel | null {
136 const values: any[] = [];
137
138 this.availSections.forEach((section) => {
139 const sectionValue = this.configForm.getValue(section);
140 if (sectionValue !== null && sectionValue !== '') {
141 values.push({ section: section, value: sectionValue });
142 }
143 });
144
145 if (!_.isEqual(this.response.value, values)) {
146 const request = new ConfigFormCreateRequestModel();
147 request.name = this.configForm.getValue('name');
148 request.value = values;
149 return request;
150 }
151
152 return null;
153 }
154
155 submit() {
156 const request = this.createRequest();
157
158 if (request) {
159 this.configService.create(request).subscribe(
160 () => {
161 this.notificationService.show(
162 NotificationType.success,
163 this.i18n('Updated config option {{name}}', { name: request.name })
164 );
165 this.router.navigate(['/configuration']);
166 },
167 () => {
168 this.configForm.setErrors({ cdSubmitButton: true });
169 }
170 );
171 }
172
173 this.router.navigate(['/configuration']);
174 }
175 }