Merge "Extract getSupplementaryFile out of VFM controller"
[vid.git] / vid-webpack-master / src / app / shared / components / genericForm / formControlsServices / vfModuleGenerator / vfModule.control.generator.ts
1 import {Injectable} from "@angular/core";
2 import {GenericFormService} from "../../generic-form.service";
3 import {AaiService} from "../../../../services/aaiService/aai.service";
4 import {NgRedux} from "@angular-redux/store";
5 import {HttpClient} from "@angular/common/http";
6 import {BasicControlGenerator} from "../basic.control.generator";
7 import * as _ from 'lodash';
8 import {Observable, of} from "rxjs";
9
10 import {
11   CustomValidatorOptions,
12   FormControlModel,
13   ValidatorModel,
14   ValidatorOptions
15 } from "../../../../models/formControlModels/formControl.model";
16 import {LogService} from "../../../../utils/log/log.service";
17 import {AppState} from "../../../../store/reducers";
18 import {FormGroup} from "@angular/forms";
19 import {DropdownFormControl} from "../../../../models/formControlModels/dropdownFormControl.model";
20 import {FormControlType} from "../../../../models/formControlModels/formControlTypes.enum";
21 import {InputFormControl} from "../../../../models/formControlModels/inputFormControl.model";
22 import {SelectOption} from "../../../../models/selectOption";
23 import {VfModuleInstance} from "../../../../models/vfModuleInstance";
24 import {VfModule} from "../../../../models/vfModule";
25 import {VNFModel} from "../../../../models/vnfModel";
26 import {VnfInstance} from "../../../../models/vnfInstance";
27 import {FileFormControl} from "../../../../models/formControlModels/fileFormControl.model";
28 import {CheckboxFormControl} from "../../../../models/formControlModels/checkboxFormControl.model";
29 import {FileUnit} from "../../../formControls/component/file/fileUnit.enum";
30 import {Constants} from "../../../../utils/constants";
31
32
33 export enum FormControlNames {
34   INSTANCE_NAME = 'instanceName',
35   VOLUME_GROUP_NAME = 'volumeGroupName',
36   LCPCLOUD_REGION_ID = 'lcpCloudRegionId',
37   LEGACY_REGION = 'legacyRegion',
38   TENANT_ID = 'tenantId',
39   ROLLBACK_ON_FAILURE = 'rollbackOnFailure',
40   SDN_C_PRE_LOAD = 'sdncPreLoad',
41 }
42
43
44 @Injectable()
45 export class VfModuleControlGenerator {
46   aaiService: AaiService;
47   vfModuleModel: VfModule;
48   isUpdateMode : boolean;
49
50   constructor(private genericFormService: GenericFormService,
51               private _basicControlGenerator: BasicControlGenerator,
52               private store: NgRedux<AppState>,
53               private http: HttpClient,
54               private _aaiService: AaiService,
55               private _logService: LogService) {
56     this.aaiService = _aaiService;
57   }
58
59   setVFModuleStoreKey = (serviceId: string, vfModuleUuid: string) => {
60       const vfModules = this.store.getState().service.serviceHierarchy[serviceId].vfModules;
61       const vfModulesKeys = Object.keys(vfModules);
62       for(let key of  vfModulesKeys){
63         if(vfModules[key].uuid === vfModuleUuid){
64           return;
65         }
66       }
67   };
68
69
70   getVfModuleInstance = (serviceId: string, vnfStoreKey: string, UUIDData: Object, isUpdateMode: boolean): VfModuleInstance => {
71     let vfModuleInstance: VfModuleInstance = null;
72     if (isUpdateMode && this.store.getState().service.serviceInstance[serviceId] &&
73       _.has(this.store.getState().service.serviceInstance[serviceId].vnfs, vnfStoreKey) &&
74       _.has(this.store.getState().service.serviceInstance[serviceId].vnfs[vnfStoreKey].vfModules, UUIDData['modelName'])) {
75        vfModuleInstance = Object.assign({},this.store.getState().service.serviceInstance[serviceId].vnfs[vnfStoreKey].vfModules[UUIDData['modelName']][UUIDData['vFModuleStoreKey']]);
76     }
77     return vfModuleInstance;
78   };
79
80   extractVfAccordingToVfModuleUuid(serviceId: string, UUIDData: Object): VfModule {
81     const vfModule = this.store.getState().service.serviceHierarchy[serviceId].vfModules[UUIDData['modelName']];
82     this.vfModuleModel = vfModule;
83     return vfModule;
84   }
85
86   getMacroFormControls(serviceId: string, vnfStoreKey: string, vfModuleStoreKey: string, uuidData : Object, isUpdateMode: boolean): FormControlModel[] {
87     this.isUpdateMode = isUpdateMode;
88     this.extractVfAccordingToVfModuleUuid(serviceId, uuidData);
89     if (_.isNil(serviceId) || _.isNil(vnfStoreKey) || _.isNil(vfModuleStoreKey)) {
90       if(isUpdateMode){
91         this._logService.error('should provide serviceId, vfModuleStoreKey, vnfStoreKey', serviceId);
92         return [];
93       }
94     }
95
96     const vfModuleInstance = this.getVfModuleInstance(serviceId, vnfStoreKey, uuidData, isUpdateMode);
97     const vfModuleModel = this.vfModuleModel;
98     const vnf: VnfInstance = this.store.getState().service.serviceInstance[serviceId].vnfs[vnfStoreKey];
99     const vnfModelName: string = vnf.originalName;
100     const vnfModel = new VNFModel(this.store.getState().service.serviceHierarchy[serviceId].vnfs[vnfModelName]);
101
102     let result: FormControlModel[] = [];
103
104     if (!_.isNil(vfModuleModel)) {
105       result = this.pushInstanceAndVGToForm(result, vfModuleInstance, serviceId, vnfModel, false);
106     }
107     if(this.store.getState().global.flags['FLAG_SUPPLEMENTARY_FILE']) {
108       let suppFileInput:FileFormControl = <FileFormControl>(this._basicControlGenerator.getSupplementaryFile(vfModuleInstance));
109       result.push(suppFileInput);
110       result = result.concat(suppFileInput.hiddenFile);
111     }
112     return result;
113   }
114
115   pushInstanceAndVGToForm(result: FormControlModel[], vfModuleElement: any, serviceId: string, vnfModel: any, isALaCarte: boolean) :FormControlModel[]{
116     result.push(this.getInstanceName(vfModuleElement, serviceId, vnfModel.isEcompGeneratedNaming));
117     if (this.vfModuleModel.volumeGroupAllowed) {
118       result.push(this.getVolumeGroupData(vfModuleElement, serviceId, vnfModel.isEcompGeneratedNaming, isALaCarte));
119     }
120     return result;
121   }
122
123   getAlaCarteFormControls(serviceId: string, vnfStoreKey: string, vfModuleStoreKey: string, uuidData : Object, isUpdateMode: boolean): FormControlModel[] {
124     this.isUpdateMode = isUpdateMode;
125     this.extractVfAccordingToVfModuleUuid(serviceId, uuidData);
126     if (_.isNil(serviceId) || _.isNil(vnfStoreKey) || _.isNil(vfModuleStoreKey)) {
127       if(isUpdateMode){
128         this._logService.error('should provide serviceId, vfModuleStoreKey, vnfStoreKey', serviceId);
129         return [];
130       }
131     }
132     const vnf: VnfInstance = this.store.getState().service.serviceInstance[serviceId].vnfs[vnfStoreKey];
133     const vnfModelName: string = vnf.originalName;
134     const vnfModel = new VNFModel(this.store.getState().service.serviceHierarchy[serviceId].vnfs[vnfModelName]);
135
136     const vfModuleInstance = this.getVfModuleInstance(serviceId, vnfStoreKey, uuidData, isUpdateMode);
137     let result: FormControlModel[] = [];
138     this.pushInstanceAndVGToForm(result, vfModuleInstance, serviceId, vnfModel, true);
139     result.push(this.getLcpRegionControl(serviceId, vfModuleInstance, result));
140     result.push(this._basicControlGenerator.getLegacyRegion(vfModuleInstance));
141     result.push(this.getTenantControl(serviceId, vfModuleInstance, result));
142     result.push(this.getRollbackOnFailureControl(vfModuleInstance, result));
143     result.push(this.getSDNCControl(vfModuleInstance, result));
144     if(this.store.getState().global.flags['FLAG_SUPPLEMENTARY_FILE']) {
145       let suppFileInput:FileFormControl = <FileFormControl>(this._basicControlGenerator.getSupplementaryFile(vfModuleInstance));
146       result.push(suppFileInput);
147       result = result.concat(suppFileInput.hiddenFile);
148     }
149     return result;
150
151   }
152
153   getInstanceName(instance: any, serviceId: string, isEcompGeneratedNaming: boolean): FormControlModel {
154     let formControlModel:FormControlModel = this._basicControlGenerator.getInstanceNameController(instance, serviceId, isEcompGeneratedNaming, this.vfModuleModel);
155     formControlModel.onBlur = (event, form : FormGroup) => {
156         if(!_.isNil(form.controls['volumeGroupName'])&& event.target.value.length > 0){
157           form.controls['volumeGroupName'].setValue(event.target.value + "_vol");
158         }
159       };
160
161     return formControlModel;
162   }
163
164   getDefaultVolumeGroupName(instance: any, isEcompGeneratedNaming: boolean): string {
165     if ((!_.isNil(instance) && instance.volumeGroupName))  {
166       return instance.volumeGroupName;
167     }
168     if (isEcompGeneratedNaming) {
169       return null;
170     }
171     return this._basicControlGenerator.getDefaultInstanceName(instance, this.vfModuleModel) + "_vol";
172   }
173
174   getVolumeGroupData(instance: any, serviceId: string, isEcompGeneratedNaming: boolean, isALaCarte: boolean): FormControlModel {
175     let validations: ValidatorModel[] = [
176       new ValidatorModel(ValidatorOptions.pattern, 'Instance name may include only alphanumeric characters and underscore.', BasicControlGenerator.INSTANCE_NAME_REG_EX),
177       new ValidatorModel(CustomValidatorOptions.uniqueInstanceNameValidator, 'Volume Group instance name is already in use, please pick another name', [this.store, serviceId, instance && instance.volumeGroupName])
178     ];
179     // comment out because if not provided vid won't create VG
180     // if (!isEcompGeneratedNaming)  {
181     //   validations.push(new ValidatorModel(ValidatorOptions.required, 'is required'));
182     // }
183     return new InputFormControl({
184       controlName: 'volumeGroupName',
185       displayName: 'Volume Group Name',
186       dataTestId: 'volumeGroupName',
187       // placeHolder: (!isEcompGeneratedNaming) ? 'Volume Group Name' : 'Automatically generated when not provided',
188       validations: validations,
189       tooltip : 'When filled, VID will create a Volume Group by this name and associate with this module.\n' +
190                 'When empty, the module is created without a Volume Group.',
191       isVisible: this.shouldVGNameBeVisible(isEcompGeneratedNaming,isALaCarte),
192       value: this.getDefaultVolumeGroupName(instance, isEcompGeneratedNaming),
193       onKeypress: (event) => {
194         const pattern:RegExp = BasicControlGenerator.INSTANCE_NAME_REG_EX;
195         if (pattern) {
196           if (!pattern.test(event['key'])) {
197             event.preventDefault();
198           }
199         }
200         return event;
201       }
202     });
203   }
204
205   private shouldVGNameBeVisible(isEcompGeneratedNaming: boolean, isALaCarte: boolean) {
206     if((!isALaCarte && !isEcompGeneratedNaming) || isALaCarte){
207       return true;
208     }
209     return false;
210
211   }
212
213   getTenantControl = (serviceId: string, instance: any, controls: FormControlModel[]): DropdownFormControl => {
214     const service = this.store.getState().service.serviceInstance[serviceId];
215     const globalCustomerId: string = service.globalSubscriberId;
216     const serviceType: string = service.subscriptionServiceType;
217     return new DropdownFormControl({
218       type: FormControlType.DROPDOWN,
219       controlName: FormControlNames.TENANT_ID,
220       displayName: 'Tenant',
221       dataTestId: 'tenant',
222       placeHolder: 'Select Tenant',
223       name: "tenant",
224       isDisabled: _.isNil(instance) || _.isNil(instance.lcpCloudRegionId),
225       onInitSelectedField: instance ? ['lcpRegionsTenantsMap', instance.lcpCloudRegionId] : null,
226       value: instance ? instance.tenantId : null,
227       validations: [new ValidatorModel(ValidatorOptions.required, 'is required')],
228       onInit: instance ? this._basicControlGenerator.getSubscribeInitResult.bind(
229         this._aaiService,
230         this.aaiService.getLcpRegionsAndTenants.bind(this, globalCustomerId, serviceType)) : () => {
231       },
232     })
233   };
234
235   getLcpRegionControl = (serviceId: string, instance: any, controls: FormControlModel[]): DropdownFormControl => {
236     const service = this.store.getState().service.serviceInstance[serviceId];
237     const globalCustomerId: string = service.globalSubscriberId;
238     const serviceType: string = service.subscriptionServiceType;
239     return new DropdownFormControl({
240       type: FormControlType.DROPDOWN,
241       controlName: 'lcpCloudRegionId',
242       displayName: 'LCP region',
243       dataTestId: 'lcpRegion',
244       placeHolder: 'Select LCP Region',
245       name: "lcpRegion",
246       isDisabled: false,
247       value: instance ? instance.lcpCloudRegionId : null,
248       validations: [new ValidatorModel(ValidatorOptions.required, 'is required')],
249       onInitSelectedField: ['lcpRegionList'],
250       onInit: this._basicControlGenerator.getSubscribeInitResult.bind(
251         this._aaiService,
252         this._aaiService.getLcpRegionsAndTenants.bind(this, globalCustomerId, serviceType)),
253       onChange: (param: string, form: FormGroup) => {
254         form.controls[FormControlNames.TENANT_ID].enable();
255         form.controls[FormControlNames.TENANT_ID].reset();
256         if (!_.isNil(globalCustomerId) && !_.isNil(serviceType)) {
257           this._basicControlGenerator.getSubscribeResult.bind(this, this._aaiService.getLcpRegionsAndTenants(globalCustomerId, serviceType).subscribe(res => {
258             controls.find(item => item.controlName === FormControlNames.TENANT_ID)['options$'] = res.lcpRegionsTenantsMap[param];
259             if (res.lcpRegionsTenantsMap[param]) {
260               controls.find(item => item.controlName === FormControlNames.TENANT_ID)['hasEmptyOptions'] = res.lcpRegionsTenantsMap[param].length === 0;
261             }
262           }));
263         }
264
265         if (Constants.LegacyRegion.MEGA_REGION.indexOf(param) !== -1) {
266           form.controls['legacyRegion'].enable();
267           controls.find(item => item.controlName === 'legacyRegion').isVisible = true;
268
269         } else {
270           controls.find(item => item.controlName === 'legacyRegion').isVisible = false;
271           form.controls['legacyRegion'].setValue(null);
272           form.controls['legacyRegion'].reset();
273           form.controls['legacyRegion'].disable();
274         }
275       }
276     })
277   };
278
279   getSDNCControl = (instance: any, controls: FormControlModel[]): CheckboxFormControl => {
280     return new CheckboxFormControl({
281       type: FormControlType.CHECKBOX,
282       controlName: 'sdncPreLoad',
283       displayName: 'SDN-C pre-load',
284       dataTestId: 'sdncPreLoad',
285       value: instance ? instance.sdncPreLoad : false,
286       validations: [new ValidatorModel(ValidatorOptions.required, 'is required')]
287     })
288   };
289
290   getRollbackOnFailureControl = (instance: any, controls: FormControlModel[]): DropdownFormControl => {
291     return new DropdownFormControl({
292       type: FormControlType.DROPDOWN,
293       controlName: FormControlNames.ROLLBACK_ON_FAILURE,
294       displayName: 'Rollback on failure',
295       dataTestId: 'rollback',
296       isDisabled: false,
297       validations: [new ValidatorModel(ValidatorOptions.required, 'is required')],
298       value: instance ? instance.rollbackOnFailure : 'true',
299       onInit: this._basicControlGenerator.getSubscribeInitResult.bind(null, this.getRollBackOnFailureOptions)
300     })
301   };
302
303   getRollBackOnFailureOptions = (): Observable<SelectOption[]> => {
304     return of([
305       new SelectOption({id: 'true', name: 'Rollback'}),
306       new SelectOption({id: 'false', name: 'Don\'t Rollback'})
307     ]);
308   };
309 }