Initial Commit - NG UI
[osm/NG-UI.git] / src / app / roles / roles-create-edit / RolesCreateEditComponent.ts
1 /*
2  Copyright 2020 TATA ELXSI
3
4  Licensed under the Apache License, Version 2.0 (the 'License');
5  you may not use this file except in compliance with the License.
6  You may obtain a copy of the License at
7
8   http://www.apache.org/licenses/LICENSE-2.0
9
10  Unless required by applicable law or agreed to in writing, software
11  distributed under the License is distributed on an "AS IS" BASIS,
12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  See the License for the specific language governing permissions and
14  limitations under the License.
15
16  Author: KUMARAN M (kumaran.m@tataelxsi.co.in), RAJESH S (rajesh.s@tataelxsi.co.in), BARATH KUMAR R (barath.r@tataelxsi.co.in)
17 */
18 /**
19  * @file Roles Create and Edit Component
20  */
21 import { HttpClient, HttpHeaders } from '@angular/common/http';
22 import { Component, Injector, Input, OnInit } from '@angular/core';
23 import { FormBuilder, FormGroup, Validators } from '@angular/forms';
24 import { ActivatedRoute, Router } from '@angular/router';
25 import { TranslateService } from '@ngx-translate/core';
26 import { NotifierService } from 'angular-notifier';
27 import { APIURLHEADER, ERRORDATA } from 'CommonModel';
28 import { environment } from 'environment';
29 import * as jsonpath from 'jsonpath';
30 import { RestService } from 'RestService';
31 import { Permission, PermissionGroup, RoleConfig, RoleData } from 'RolesModel';
32 import { SharedService } from 'SharedService';
33 import { isNullOrUndefined } from 'util';
34
35 /**
36  * Creating component
37  * @Component takes RolesCreateEditComponent.html as template url
38  */
39 @Component({
40   selector: 'app-roles-create-edit',
41   templateUrl: './RolesCreateEditComponent.html',
42   styleUrls: ['./RolesCreateEditComponent.scss']
43 })
44 /** Exporting a class @exports RolesCreateEditComponent */
45 export class RolesCreateEditComponent implements OnInit {
46   /** To inject services @public */
47   public injector: Injector;
48
49   /** contains role permissions from config file @public */
50   public rolePermissions: {}[];
51
52   /** contains role form group information @public */
53   public roleForm: FormGroup;
54
55   /** Instance of the rest service @public */
56   public restService: RestService;
57
58   /** Check the loading results for loader status @public */
59   public isLoadingResults: boolean = false;
60
61   /** Give the message for the loading @public */
62   public message: string = 'PLEASEWAIT';
63
64   /** Instance to check role form submitted status @public */
65   public submitted: boolean = false;
66
67   /** Contains role create or edit value @public */
68   public getRoleType: string;
69
70   /** Contains view selection value either text or preview @public */
71   public viewMode: string = 'text';
72
73   /** Contains role id value @private */
74   private roleRef: string;
75
76   /** Notifier service to popup notification @private */
77   private notifierService: NotifierService;
78
79   /** Contains tranlsate instance @private */
80   private translateService: TranslateService;
81
82   /** contians form builder module @private */
83   private formBuilder: FormBuilder;
84
85   /** Contains all methods related to shared @private */
86   private sharedService: SharedService;
87
88   /** Controls the header form @private */
89   private headers: HttpHeaders;
90
91   /** Varaibles to hold http client @private */
92   private httpClient: HttpClient;
93
94   /** Holds the instance of activatedRoute of router service @private */
95   private activatedRoute: ActivatedRoute;
96
97   /** Holds the instance of roter service @private */
98   private router: Router;
99
100   constructor(injector: Injector) {
101     this.injector = injector;
102     this.restService = this.injector.get(RestService);
103     this.notifierService = this.injector.get(NotifierService);
104     this.translateService = this.injector.get(TranslateService);
105     this.formBuilder = this.injector.get(FormBuilder);
106     this.sharedService = this.injector.get(SharedService);
107     this.httpClient = this.injector.get(HttpClient);
108     this.activatedRoute = this.injector.get(ActivatedRoute);
109     this.router = this.injector.get(Router);
110   }
111
112   /** Lifecyle Hooks the trigger before component is instantiate @public */
113   public ngOnInit(): void {
114     this.headers = new HttpHeaders({
115       'Content-Type': 'application/json',
116       Accept: 'application/json',
117       'Cache-Control': 'no-cache, no-store, must-revalidate, max-age=0'
118     });
119     this.roleForm = this.formBuilder.group({
120       roleName: ['', [Validators.required]],
121       permissions: ['']
122     });
123     this.getRolePermissions();
124   }
125
126   /** Get role permission information based on action @public */
127   public getRolePermissions(): void {
128     this.isLoadingResults = true;
129     this.loadPermissions().then((response: RoleConfig) => {
130       this.rolePermissions = response.rolePermissions;
131       if (this.activatedRoute.snapshot.url[0].path === 'create') {
132         this.getRoleType = 'Add';
133         this.isLoadingResults = false;
134       } else {
135         this.getRoleType = 'Edit';
136         this.getRoleData();
137       }
138     }).catch(() => {
139       // Empty Block
140     });
141   }
142
143   /** Check Role Create or Edit and proceed action @public */
144   public roleCheck(): void {
145     this.submitted = true;
146     if (!this.roleForm.valid) {
147       const errorIp: Element = document.querySelector('.ng-invalid[formControlName]');
148       if (errorIp) {
149         errorIp.scrollIntoView({ behavior: 'smooth', block: 'center' });
150       }
151     } else {
152       if (this.getRoleType === 'Add') {
153         this.createRole();
154       } else {
155         this.editRole();
156       }
157     }
158   }
159
160   /** Convenience getter for easy access to form fields */
161   get f(): FormGroup['controls'] { return this.roleForm.controls; }
162
163   /** Create role @private  */
164   public createRole(): void {
165     const apiURLHeader: APIURLHEADER = {
166       url: environment.ROLES_URL,
167       httpOptions: { headers: this.headers }
168     };
169     let permissionData: Object = {};
170     this.sharedService.cleanForm(this.roleForm);
171     if (!this.roleForm.invalid) {
172       if (this.viewMode === 'preview') {
173         this.isLoadingResults = true;
174         permissionData = this.generatePermissions();
175         this.roleCreateAPI(apiURLHeader, permissionData);
176       } else {
177         if (this.checkPermission()) {
178           this.isLoadingResults = true;
179           permissionData = this.roleForm.value.permissions !== '' ? JSON.parse(this.roleForm.value.permissions) : {};
180           this.roleCreateAPI(apiURLHeader, permissionData);
181         }
182       }
183     }
184   }
185
186   /** Method to handle role create API call @public */
187   public roleCreateAPI(apiURLHeader: APIURLHEADER, permissionData: {}): void {
188     const postData: {} = {
189       name: this.roleForm.value.roleName,
190       permissions: !isNullOrUndefined(permissionData) ? permissionData : {}
191     };
192     this.restService.postResource(apiURLHeader, postData).subscribe(() => {
193       this.notifierService.notify('success', this.translateService.instant('PAGE.ROLES.CREATEDSUCCESSFULLY'));
194       this.router.navigate(['/roles/details']).catch();
195     }, (error: ERRORDATA) => {
196       this.isLoadingResults = false;
197       this.restService.handleError(error, 'post');
198     });
199   }
200
201   /** Edit role  @private  */
202   public editRole(): void {
203     const apiURLHeader: APIURLHEADER = {
204       url: environment.ROLES_URL + '/' + this.roleRef,
205       httpOptions: { headers: this.headers }
206     };
207     let permissionData: Object = {};
208     this.sharedService.cleanForm(this.roleForm);
209     if (!this.roleForm.invalid) {
210       if (this.viewMode === 'preview') {
211         this.isLoadingResults = true;
212         permissionData = this.generatePermissions();
213         this.roleEditAPI(apiURLHeader, permissionData);
214       } else {
215         if (this.checkPermission()) {
216           this.isLoadingResults = true;
217           permissionData = this.roleForm.value.permissions !== '' ? JSON.parse(this.roleForm.value.permissions) : {};
218           this.roleEditAPI(apiURLHeader, permissionData);
219         }
220       }
221     }
222   }
223
224   /** Method to handle role edit API call */
225   public roleEditAPI(apiURLHeader: APIURLHEADER, permissionData: {}): void {
226     const postData: {} = {
227       name: this.roleForm.value.roleName,
228       permissions: !isNullOrUndefined(permissionData) ? permissionData : {}
229     };
230     this.restService.patchResource(apiURLHeader, postData).subscribe(() => {
231       this.notifierService.notify('success', this.translateService.instant('PAGE.ROLES.UPDATEDSUCCESSFULLY'));
232       this.router.navigate(['/roles/details']).catch();
233     }, (error: ERRORDATA) => {
234       this.isLoadingResults = false;
235       this.restService.handleError(error, 'patch');
236     });
237   }
238
239   /** Method to handle toggle role view selection @public */
240   public viewSelection(): void {
241     if (this.viewMode === 'text' && this.checkPermission()) {
242       this.loadPermissions().then((response: RoleConfig) => {
243         this.rolePermissions = response.rolePermissions;
244         const permissions: {} = this.roleForm.value.permissions !== '' ? JSON.parse(this.roleForm.value.permissions) : {};
245         this.filterRoleData(permissions);
246         this.viewMode = 'preview';
247       }).catch(() => {
248         // Empty Block
249       });
250     } else {
251       const rolePermission: {} = this.generatePermissions();
252       if (Object.keys(rolePermission).length !== 0) {
253         this.roleForm.patchValue({ permissions: JSON.stringify(rolePermission, null, '\t') });
254       }
255       this.viewMode = 'text';
256     }
257
258   }
259
260   /** Generate role permission post data @private */
261   private generatePermissions(): Object {
262     const permissions: Object = {};
263     this.rolePermissions.forEach((permissionGroup: PermissionGroup) => {
264       if (!isNullOrUndefined(permissionGroup)) {
265         permissionGroup.permissions.forEach((permission: Permission) => {
266           if (!isNullOrUndefined(permission.value) && permission.value !== 'NA') {
267             permissions[permission.operation] = permission.value;
268           }
269         });
270       }
271     });
272     return permissions;
273   }
274
275   /** Validation method for check permission json string @private */
276   private checkPermission(): boolean {
277     if (this.roleForm.value.permissions) {
278       if (!this.sharedService.checkJson(this.roleForm.value.permissions)) {
279         this.notifierService.notify('error', this.translateService.instant('PAGE.ROLES.ROLEJSONERROR'));
280         return false;
281       } else {
282         this.roleForm.value.permissions = this.roleForm.value.permissions.replace(/'/g, '"');
283         const rolePermission: {} = JSON.parse(this.roleForm.value.permissions);
284         for (const key of Object.keys(rolePermission)) {
285           if (typeof rolePermission[key] !== 'boolean') {
286             this.notifierService.notify('error', this.translateService.instant('PAGE.ROLES.ROLEKEYERROR', { roleKey: key }));
287             return false;
288           }
289         }
290       }
291     }
292     return true;
293   }
294
295   /** Get role data from NBI based on ID and apply filter @private */
296   private getRoleData(): void {
297     // tslint:disable-next-line: no-backbone-get-set-outside-model
298     this.roleRef = this.activatedRoute.snapshot.paramMap.get('id');
299     if (!isNullOrUndefined(this.roleRef)) {
300       this.restService.getResource(environment.ROLES_URL + '/' + this.roleRef).subscribe((data: RoleData) => {
301         this.roleForm.setValue({ roleName: data.name, permissions: JSON.stringify(data.permissions, null, '\t') });
302         this.filterRoleData(data.permissions);
303         this.isLoadingResults = false;
304       }, (error: ERRORDATA) => {
305         this.router.navigate(['/roles/details']).catch();
306         this.restService.handleError(error, 'get');
307       });
308     }
309   }
310
311   /** Method to filter role data @private */
312   private filterRoleData(permissions: {}): void {
313     Object.keys(permissions).forEach((permission: string) => {
314       jsonpath.apply(this.rolePermissions, '$..permissions[?(@.operation == "' + permission + '")]', (response: Permission) => {
315         if (response.operation === permission) {
316           response.value = permissions[permission];
317         }
318         return response;
319       });
320     });
321   }
322
323   /** Method to load the role permission Json file @private */
324   private async loadPermissions(): Promise<Object> {
325     const jsonFile: string = environment.PERMISSIONS_CONFIG_FILE + '?cb=' + new Date().getTime();
326     return new Promise<Object>((resolve: Function, reject: Function): void => {
327       this.httpClient.get(jsonFile).subscribe((response: Response) => {
328         resolve(response);
329       }, (error: {}) => {
330         reject();
331       });
332     });
333   }
334
335 }