diff options
Diffstat (limited to 'ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin')
46 files changed, 4181 insertions, 0 deletions
diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin-routing.module.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin-routing.module.ts new file mode 100644 index 00000000..87d01fa2 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin-routing.module.ts @@ -0,0 +1,30 @@ +import {NgModule} from '@angular/core'; +import {RouterModule, Routes} from '@angular/router'; +import {RoleFunctionsComponent} from './role-functions/role-functions.component'; +import {UsageComponent} from './usage/usage.component'; +import {CacheAdminComponent} from './cache-admin/cache-admin.component'; +import {RolesComponent} from './roles/roles.component'; +import {MenusComponent} from './menus/menus.component'; +import {AdminComponent} from './admin.component'; + +const routes: Routes = [ + { + path: '', + component: AdminComponent, + children: [ + {path: 'role_function_list', component: RoleFunctionsComponent}, + {path: 'usage_list', component: UsageComponent}, + {path: 'cache_admin', component: CacheAdminComponent}, + {path: 'admin', component: RolesComponent}, + {path: 'admin_menu_edit', component: MenusComponent}, + ] + } +]; + +@NgModule({ + imports: [RouterModule.forChild(routes)], + exports: [RouterModule] +}) +export class AdminRouting { + +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.html new file mode 100644 index 00000000..0680b43f --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.html @@ -0,0 +1 @@ +<router-outlet></router-outlet> diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.scss new file mode 100644 index 00000000..e69de29b --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.scss diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.spec.ts new file mode 100644 index 00000000..e93ac925 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.spec.ts @@ -0,0 +1,27 @@ +import { async, ComponentFixture, TestBed } from '@angular/core/testing'; + +import { AdminComponent } from './admin.component'; +import { RouterTestingModule } from '@angular/router/testing'; + +describe('AdminComponent', () => { + let component: AdminComponent; + let fixture: ComponentFixture<AdminComponent>; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + declarations: [ AdminComponent ], + imports: [ RouterTestingModule ] + }) + .compileComponents(); + })); + + beforeEach(() => { + fixture = TestBed.createComponent(AdminComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.ts new file mode 100644 index 00000000..ad5498c6 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.component.ts @@ -0,0 +1,13 @@ +import { Component, OnInit } from '@angular/core'; + +@Component({ + selector: 'app-admin', + templateUrl: './admin.component.html', + styleUrls: ['./admin.component.scss'] +}) +export class AdminComponent implements OnInit { + constructor() { } + ngOnInit() { + } + +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.module.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.module.ts new file mode 100644 index 00000000..ba546647 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.module.ts @@ -0,0 +1,46 @@ +import { NgModule } from '@angular/core'; +import { CommonModule } from '@angular/common'; +import { AdminComponent } from './admin.component'; +import {CacheAdminComponent} from './cache-admin/cache-admin.component'; +import {MenusModule} from './menus/menus.module'; +import {UsageModule} from './usage/usage.module'; +import {FormsModule} from '@angular/forms'; +import { + MatExpansionModule, + MatFormFieldModule, + MatPaginatorModule, + MatRadioModule, + MatSlideToggleModule, + MatTableModule, + MatInputModule +} from '@angular/material'; +import {RdpModule} from 'portalsdk-tag-lib'; +import {AdminRouting} from './admin-routing.module'; +import {RoleFunctionsComponent} from './role-functions/role-functions.component'; +import {RolesComponent} from './roles/roles.component'; +import {NewRoleComponent} from './roles/new-role/new-role.component' +import { UserService } from '../shared/services/user/user.service'; + +@NgModule({ + declarations: [AdminComponent, CacheAdminComponent, RoleFunctionsComponent, RolesComponent, NewRoleComponent], + imports: [ + CommonModule, + MenusModule, + UsageModule, + FormsModule, + MatRadioModule, + RdpModule, + AdminRouting, + MatExpansionModule, + MatFormFieldModule, + MatTableModule, + MatSlideToggleModule, + MatPaginatorModule, + MatInputModule + ], + entryComponents: [NewRoleComponent], + exports: [ + ], + providers: [UserService] +}) +export class AdminModule { } diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.service.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.service.spec.ts new file mode 100644 index 00000000..d23489be --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.service.spec.ts @@ -0,0 +1,130 @@ +import { TestBed, async } from '@angular/core/testing'; +import { AdminService } from './admin.service'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; +import { environment } from 'src/environments/environment'; + +describe('AdminService', () => { + + let service:AdminService; + + beforeEach(() =>{ + TestBed.configureTestingModule({ + imports:[HttpClientTestingModule], + providers: [AdminService] + }) + service = TestBed.get(AdminService); + }); + + it('should be created', () => { + const service: AdminService = TestBed.get(AdminService); + expect(service).toBeTruthy(); + }); + + it('should get getUserPagination', () => { + service.getRoleFunctionList().subscribe((resp) => { + expect(resp).toBe(environment.roleFunctionList); + }); + }) + + it('should test saveRoleFunction',()=>{ + service.saveRoleFunction("roleData").subscribe((resp)=>{ + expect(resp).toBe(environment.addRoleFunction); + }) + }) + + it('should test getUsageList',()=>{ + service.getUsageList().subscribe((resp) => { + expect(resp).toBe(environment.usageList); + }) + }) + + it('should test getCacheRegions',()=>{ + service.getCacheRegions().subscribe((resp) => { + expect(resp).toBe(environment.cachedRegions); + }) + }) + + it('should test getRole',()=>{ + service.getRole(1).subscribe((resp) => { + expect(resp).toBe(environment.cachedRegions); + }) + }) + + it('should test getRole',()=>{ + service.getRole(1).subscribe((resp) => { + expect(resp).toBe(environment.getRole); + }) + }) + + it('should test getFnMenuItems',()=>{ + service.getFnMenuItems().subscribe((resp) => { + expect(resp).toBe(environment.getFnMenuItems); + }) + }) + + it('should test updateFnMenuItem',()=>{ + let menuObj: any + service.updateFnMenuItem(menuObj).subscribe((resp) => { + expect(resp).toBe(environment.updateFnMenuItem); + }) + }) + + it('should test getFunctionCdList',()=>{ + service.getFunctionCdList().subscribe((resp) => { + expect(resp).toBe(environment.getFunctionCdList); + }) + }) + + + it('should test getParentData',()=>{ + service.getParentData().subscribe((resp) => { + expect(resp).toBe(environment.getParentList); + }) + }) + + it('should test deleteRole',()=>{ + let roleData: any + service.deleteRole(roleData).subscribe((resp) => { + expect(resp).toBe(environment.deleteRole); + }) + }) + + it('should test deleteRoleFunction',()=>{ + let roleData: any + service.deleteRoleFunction(roleData).subscribe((resp) => { + expect(resp).toBe(environment.deleteRoleFunction); + }) + }) + + it('should test removeRoleFunction',()=>{ + let roleFunc:any; + let roleId:any; + service.removeRoleFunction(roleFunc,roleId).subscribe((resp) => { + expect(resp).toBe(environment.removeRoleFunction+roleId); + }) + }) + + it('should test saveRole',()=>{ + let roleObj:any; + let roleId:any; + service.saveRole(roleObj,roleId).subscribe((resp) => { + expect(resp).toBe(environment.saveRole+roleId); + }) + }) + + it('should test deleteMenu',()=>{ + let fnMenuItem: any + service.deleteMenu(fnMenuItem).subscribe((resp) => { + expect(resp).toBe(environment.deleteMenu); + }) + }) + + + it('should test getCacheRegionDetails',()=>{ + let cacheName:any + service.getCacheRegionDetails(cacheName).subscribe((resp) => { + expect(resp).toBe(environment.getRegion); + }) + }) + +}); diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.service.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.service.ts new file mode 100644 index 00000000..2a7135ad --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/admin.service.ts @@ -0,0 +1,124 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { Injectable } from '@angular/core'; +import { HttpClient, HttpHeaders, HttpParams } from '@angular/common/http'; +import { JsonPipe } from '@angular/common'; +import { environment } from '../../environments/environment'; +import { Observable } from 'rxjs'; + +@Injectable({ + providedIn: 'root' +}) + +export class AdminService { + + constructor(private http:HttpClient) { } + + getRoleFunctionList(){ + return this.http.get(environment.roleFunctionList); + } + + saveRoleFunction(roleData:string){ + return this.http.post(environment.addRoleFunction,roleData); + } + + getUsageList() + { + return this.http.get(environment.usageList); + + } + + getCacheRegions(){ + return this.http.get(environment.cachedRegions); + + } + + getRole(roleId){ + return this.http.get(environment.getRole+'?role_id=' + roleId); + + } + getFnMenuItems() + { + return this.http.get(environment.getFnMenuItems); + } + + updateFnMenuItem(menuObj: any): Observable<any> { + let updateMenuURL = environment.updateFnMenuItem; + return this.http.post(updateMenuURL, menuObj) + } + + getFunctionCdList(): Observable<any>{ + let getFunctionCdListURL = environment.getFunctionCdList; + return this.http.get(getFunctionCdListURL); + } + + getParentData(): Observable<any>{ + let getParentDataURL = environment.getParentList; + return this.http.get(getParentDataURL); + } + + deleteRole(roleData:any){ + return this.http.post(environment.deleteRole,JSON.stringify({role: roleData})); + } + + deleteRoleFunction(roleFunc:any) + { + return this.http.post(environment.deleteRoleFunction,roleFunc); + + } + + removeRoleFunction(roleFunc:any, roleId:any){ + let removeRoleFunctionURL = environment.removeRoleFunction+roleId; + return this.http.post(removeRoleFunctionURL,JSON.stringify({roleFunction:roleFunc})); + } + + saveRole(roleObj:any, roleId:any){ + let saveRoleURL = environment.saveRole+roleId; + return this.http.post(saveRoleURL,JSON.stringify(roleObj)); + } + + deleteMenu(fnMenuItem:any){ + return this.http.post(environment.deleteMenu,JSON.stringify({fnMenuItem: fnMenuItem})); + } + + getCacheRegionDetails(cacheName:any){ + return this.http.get(environment.getRegion+'?cacheName='+cacheName); + + } +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.html new file mode 100644 index 00000000..8aba64c9 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.html @@ -0,0 +1,50 @@ +<div id="page-content" style=" width: 100%"> + + <div> + <h1 class="heading-page" id="CacheRegions">Cache Regions</h1> + </div> + + <div style="margin-right:20px; text-align:justify; text-align-last:auto;"> + <p> + These are the regions which are currently defined in the cache. 'Items' and 'Bytes' refer to the elements currently in memory (not spooled). + You can clear all items for a region by clicking on the Clear icon next to the desired region below. You can also <a href="admin#/jcs_admin" ng-click="clearAllFuncPopUp();">clear all regions</a> + which empties the entire cache.</p> + </div> + + + + <mat-accordion displayMode="flat" multi class="mat-table"> + <section matSort class="mat-header-row"> + <span class="mat-header-cell" >Cache Name</span> + <span class="mat-header-cell" ># of Items</span> + <span class="mat-header-cell" >Bytes</span> + <span class="mat-header-cell" >Status</span> + <span class="mat-header-cell" >Memory Hits</span> + <span class="mat-header-cell">Aux Hits</span> + <span class="mat-header-cell" >Not Expired MissesFound Misses</span> + <span class="mat-header-cell" >Expired Misses</span> + <span class="mat-header-cell" >Clear?</span> + <span class="mat-header-cell" >Items</span> + + </section> + + <mat-expansion-panel *ngFor="let item of regions"> + <mat-expansion-panel-header > + <span class="mat-cell"><a href="javascript:;" (click)="showRegionDetails(item.cacheName)">{{item.cacheName}}</a></span> + <span class="mat-cell">{{item.byteCount}}</span> + <span class="mat-cell">{{item.status}}</span> + <span class="mat-cell">{{item.hitCountRam}}</span> + <span class="mat-cell">{{item.hitCountAux}}</span> + <span class="mat-cell">{{item.missCountNotFound}}</span> + <span class="mat-cell">{{item.missCountExpired}}</span> + <span class="mat-cell">{{item.hitCountRam}}</span> + <span class="mat-cell">clear</span> + <span class="mat-cell">delete</span> + + </mat-expansion-panel-header> + <div><pre>{{item.items | json }}</pre></div> + </mat-expansion-panel> + + </mat-accordion> + +
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.scss new file mode 100644 index 00000000..39ba7164 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.scss @@ -0,0 +1,68 @@ +table { + width: 100%; +} + +.mat-form-field { + font-size: 14px; + width: 100%; +} + +td, th { + width: 25%; +} + + +.mat-accordion .mat-header-row { + padding-left: 1.5rem; + padding-right: 2rem; + border-bottom: none; +} + + +//copied from https://github.com/angular/material2/blob/master/src/lib/table/table.scss +$mat-header-row-height: 56px; +$mat-row-height: 48px; +$mat-row-horizontal-padding: 24px; + + +.mat-header-row { + min-height: $mat-header-row-height; +} + +.mat-row { + min-height: $mat-row-height; +} + +.mat-row, .mat-header-row { + display: flex; + border-bottom-width: 1px; + border-bottom-style: solid; + align-items: center; + padding: 0 $mat-row-horizontal-padding; + box-sizing: border-box; + + // Workaround for https://goo.gl/pFmjJD in IE 11. Adds a pseudo + // element that will stretch the row the correct height. See: + // https://connect.microsoft.com/IE/feedback/details/802625 + &::after { + display: inline-block; + min-height: inherit; + content: ''; + } +} + +:host::ng-deep .mat-cell, .mat-header-cell { + flex: 1; + overflow: hidden; + word-wrap: break-word; + font-weight: bold; + font-size: 14px; + color: #343a40; +} + +.mat-expansion-panel { + margin: 0; + border-radius: 4px; + overflow: hidden; + transition: margin 225ms cubic-bezier(.4,0,.2,1),box-shadow 280ms cubic-bezier(.4,0,.2,1); +}
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.spec.ts new file mode 100644 index 00000000..01ec7a92 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.spec.ts @@ -0,0 +1,73 @@ +import { async, ComponentFixture, TestBed } from '@angular/core/testing'; +import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/core'; +import { CacheAdminComponent } from './cache-admin.component'; +import { MatExpansionModule } from '@angular/material'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; +import { AdminService } from '../admin.service'; +import { Observable } from 'rxjs/Observable'; +import 'rxjs/add/observable/of'; +import { CookieService } from 'ngx-cookie-service'; +import { BrowserDynamicTestingModule } from '@angular/platform-browser-dynamic/testing'; +import { NgbModule } from '@ng-bootstrap/ng-bootstrap'; +import { SuccessModalComponent } from '../../modals/success-modal/success-modal.component'; + + +describe('CacheAdminComponent', () => { + let component: CacheAdminComponent; + let fixture: ComponentFixture<CacheAdminComponent>; + let adminService:AdminService; + + var stubData1={"data":'{"data":"cachedRegions"}'}; + var stubData2={"data":"stubData2"}; + + beforeEach(async(() => { + + TestBed.configureTestingModule({ + declarations: [ + CacheAdminComponent, + SuccessModalComponent, + ], + schemas: [CUSTOM_ELEMENTS_SCHEMA], + imports:[ + MatExpansionModule, + HttpClientTestingModule, + NgbModule.forRoot() + ], + providers:[CookieService,AdminService], + }) + TestBed.overrideModule(BrowserDynamicTestingModule,{ + set:{ + entryComponents:[SuccessModalComponent] + } + }) + .compileComponents(); + })); + + beforeEach(() => { + fixture = TestBed.createComponent(CacheAdminComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + adminService=TestBed.get(AdminService); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); + + + describe('it should test ngOnInit method',()=>{ + it('should test ngOnInit',()=>{ + let spy=spyOn(adminService,'getCacheRegions').and.returnValue(Observable.of(stubData1)); + component.ngOnInit(); + expect(spy).toHaveBeenCalled(); + }) + }) + + it('it should test showRegionDetails method',()=>{ + let spy=spyOn(adminService,'getCacheRegionDetails').and.returnValue(Observable.of(stubData2)); + component.showRegionDetails("string"); + expect(spy).toHaveBeenCalled(); + }) + +}); + diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.ts new file mode 100644 index 00000000..d9f5ca80 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/cache-admin/cache-admin.component.ts @@ -0,0 +1,65 @@ +import {Component, OnInit, ViewChild} from '@angular/core'; +import { AdminService } from '../admin.service'; +import { NgbModal } from '@ng-bootstrap/ng-bootstrap'; +import { SuccessModalComponent } from 'src/app/modals/success-modal/success-modal.component'; + + +@Component({ + selector: 'app-cache-admin', + templateUrl: './cache-admin.component.html', + styleUrls: ['./cache-admin.component.scss'] +}) +export class CacheAdminComponent implements OnInit { + + constructor(public adminService:AdminService,private ngModal: NgbModal) { + + } + + response: any; + regions:any; + message;any; + + ngOnInit() { + + let result = this.adminService.getCacheRegions(); + result.subscribe(data => { + this.response = data; + this.regions = JSON.parse(this.response.data); + }); + + } + + + showRegionDetails(item: any) { + let response; + + this.adminService.getCacheRegionDetails(item).subscribe(data => { + response = data; + + + let message = response.data; + let msgParsed = JSON.stringify(message); + + + + if(message!=null && message!=''){ + var status = response.status; + var htmlstring = message.toString(); + var htmlStrReplace = htmlstring.replace(/['"]+/g, ''); + var htmlStrReplaceSplit = htmlStrReplace.split('\n'); + var dataStr = htmlStrReplace.replace(/\\n/g, "\n"); + this.message = dataStr; + + } + + + + }); + const modalRef = this.ngModal.open(SuccessModalComponent); + modalRef.componentInstance.message = this.message; + + + } + +} + diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.html new file mode 100644 index 00000000..25ae9665 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.html @@ -0,0 +1,48 @@ +<!-- + ============LICENSE_START========================================== + ONAP Portal SDK + =================================================================== + Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + =================================================================== + + Unless otherwise specified, all software contained herein is licensed + under the Apache License, Version 2.0 (the "License"); + you may not use this software except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + Unless otherwise specified, all documentation contained herein is licensed + under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + you may not use this documentation except in compliance with the License. + You may obtain a copy of the License at + + https://creativecommons.org/licenses/by/4.0/ + + Unless required by applicable law or agreed to in writing, documentation + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + ============LICENSE_END============================================ + +--> +<div class="main-container"> + <div id="page-content"> + <div class="ecomp-main-view-title"> + <h3 class="heading-page">Admin Menu Items</h3> + </div> + <div ng-show="showLoader" class="span loader-container"> + <i class="icon-primary-spinner" role="img" aria-label="Please wait while we load your content"></i> + </div> + <span class="ecomp-spinner" *ngIf="showSpinner"></span> + <rdp-data-table [data]="tableData" [settings]="settings"></rdp-data-table> + </div> +</div>
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.scss new file mode 100644 index 00000000..4e88eeb8 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.scss @@ -0,0 +1,70 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + + table { + width: 100%; +} + +.mat-form-field { + font-size: 14px; + width: 100%; +} + +td, th { + width: 25%; +} + +td[_ngcontent-c4], th[_ngcontent-c4] { + width: 7%; +} + +::ng-deep .mat-form-field[_ngcontent-c4][_ngcontent-c4] { + font-size: 14px; + width: 20%; + float: left; +} + +rdp-data-table{ + overflow-x : scroll; +} + +:host::ng-deep .mat-header-cell{ + font-weight: bold; + font-size: 14px; + color: #343a40; +}
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.spec.ts new file mode 100644 index 00000000..49fee828 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.spec.ts @@ -0,0 +1,74 @@ +import { async, ComponentFixture, TestBed, inject } from '@angular/core/testing'; +import { MatTableModule } from '@angular/material/table'; +import { MatPaginatorModule } from '@angular/material/paginator'; +import { MatSortModule } from '@angular/material/sort'; +import { NoopAnimationsModule } from '@angular/platform-browser/animations'; +import { BrowserDynamicTestingModule } from '@angular/platform-browser-dynamic/testing'; +import { NgbModule, NgbModal } from '@ng-bootstrap/ng-bootstrap'; + +import { MenusComponent } from './menus.component'; +import { AdminService } from '../admin.service'; +import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/core'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; +import { MenusService } from './menus.service'; +import { CookieService } from 'ngx-cookie-service'; +import { MockBackend } from '@angular/http/testing'; +import { BaseRequestOptions, Http } from '@angular/http'; +import 'rxjs/add/observable/of'; +import { Observable } from 'rxjs/Observable'; +import { InformationModalComponent } from '../../modals/information-modal/information-modal.component'; + +describe('MenusComponent', () => { + let component: MenusComponent; + let fixture: ComponentFixture<MenusComponent>; + let modalService: any; + let adminService:any; + var stubData={"data":'{"fnMenuItems":{"tableData":{"element":{"active":1}}}}'}; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + schemas:[CUSTOM_ELEMENTS_SCHEMA], + declarations: [ MenusComponent, + InformationModalComponent ], + imports: [ MatTableModule, + MatPaginatorModule, + MatSortModule, + HttpClientTestingModule, + NoopAnimationsModule, + NgbModule.forRoot() + ], + providers:[MenusService,CookieService] + }) + .compileComponents(); + })); + + beforeEach(async() => { + fixture = TestBed.createComponent(MenusComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + modalService = TestBed.get(NgbModal); + adminService=TestBed.get(AdminService); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); + + describe('test getMenus',()=>{ + it('should test getMenus',()=>{ + let spy=spyOn(adminService,'getParentData').and.returnValue(Observable.of('you object')) + component.getParentData(); + expect(spy).toHaveBeenCalled(); + }) + }) + + describe('testing getFunctionCDselectData',()=>{ + it('should test getFunctionCDselectData',()=>{ + let spy=spyOn(adminService,'getFunctionCdList').and.returnValue(Observable.of(1,1)); + component.getFunctionCDselectData(); + expect(spy).toHaveBeenCalled(); + }) + }) + + +}); diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.ts new file mode 100644 index 00000000..c6fbc8c4 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.component.ts @@ -0,0 +1,203 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { Component, OnInit, ViewChild } from '@angular/core'; +import { MatTableDataSource } from '@angular/material/table'; +import { MatPaginator } from '@angular/material/paginator'; +import { MatSort } from '@angular/material/sort'; +import { AdminService } from '../admin.service'; +import { NgbModal, ModalDismissReasons, NgbActiveModal } from '@ng-bootstrap/ng-bootstrap'; +import { InformationModalComponent } from 'src/app/modals/information-modal/information-modal.component'; +import { NewMenuComponent } from './new-menu/new-menu.component'; +import { Column, DataTableSettings, RdpCrudInterface , ColumnTypes} from 'portalsdk-tag-lib'; +import { element } from '@angular/core/src/render3'; +import { MenusService } from './menus.service'; + +@Component({ + selector: 'app-menus', + templateUrl: './menus.component.html', + styleUrls: ['./menus.component.scss'] +}) +export class MenusComponent implements OnInit { + + constructor(public adminService: AdminService, private ngModal: NgbModal, public menuService : MenusService) { } + + // menuHeaders = ["menuId", "label", "paretId", "sortOrder", "action", "functionCd", "active", "servlet", "queryString", "externalUrl", "target", "menuSetCode", "separator", "imageSrc", "Edit", "Delete"]; + + response: any; + result: any; + functionalMenuRes: any; + tableData; + dataSource: MatTableDataSource<[]>; + closeResult: string; + isEditMode: boolean; + showSpinner: boolean; + + public settings; + public columns: any = []; + + activeStatusOptions = [ + {id: '0', name: 'Y'}, + {id: '1', name: 'N'} + ]; + separatorStatusOptions = [ + {id: '0', name: 'Y'}, + {id: '1', name: 'N'} + ]; + functionCDselectData = []; + parentListSelectData = []; + parentList = []; + + @ViewChild(MatPaginator, {}) paginator: MatPaginator; + @ViewChild(MatSort, {}) sort: MatSort; + + ngOnInit() { + this.showSpinner = false; + this.getParentData(); + this.getFunctionCDselectData(); + this.getMenus(); + } + + getMenus() { + console.log(">>>>>>>>>>>>>>> GetMenus calles >>>>>>>>>>>>>>") + this.showSpinner = true; + let response; + this.response = this.adminService.getFnMenuItems(); + this.response.subscribe(data => { + response = data; + + this.functionalMenuRes = JSON.parse(response.data); + this.tableData = this.functionalMenuRes.fnMenuItems; + this.tableData.forEach(element => { + if (element.active) { element.active = "Y"; } + else { element.active = "N"; } + if (element.separator) { element.separator = "Y"; } + else { element.separator = "N"; } + }); + + //rdp table data + let menuIdColumn = new Column("id", "Menu ID", ColumnTypes.TEXT, true, null); + menuIdColumn.isColumnDisabled = true; + this.columns.push(menuIdColumn); + + let label = new Column("label", "Label", ColumnTypes.TEXT, true, null); + label.setIsColumnMandatory = true; + this.columns.push(label); + + let parent = new Column("parentId", "ParentId", ColumnTypes.DROPDOWN, true, this.parentList); + parent.setIsColumnMandatory = true; + this.columns.push(parent); + + let sortOrder = new Column("sortOrder", "Sort Order", ColumnTypes.TEXT, true, null); + sortOrder.setIsColumnMandatory = true; + this.columns.push(sortOrder); + + let action = new Column("action", "Action", ColumnTypes.TEXT, true, null); + action.setIsColumnMandatory = true; + this.columns.push(action); + + let functionCd = new Column("functionCd", "Function", ColumnTypes.DROPDOWN, true, this.functionCDselectData); + functionCd.setIsColumnMandatory = true; + this.columns.push(functionCd); + + let active = new Column("active", "Active", ColumnTypes.DROPDOWN, true, this.activeStatusOptions); + active.setIsColumnMandatory = true; + this.columns.push(active); + + this.columns.push(new Column("servlet", "Servlet", ColumnTypes.TEXT, true, null)); + this.columns.push(new Column("queryString", " Query String", ColumnTypes.TEXT, true, null)); + this.columns.push(new Column("externalUrl", "External URL", ColumnTypes.TEXT, true, null)); + this.columns.push(new Column("target", "Target", ColumnTypes.TEXT, true, null)); + + let menuSetCode = new Column("menuSetCode", "Menu Set Code", ColumnTypes.TEXT, false, null); + menuSetCode.setIsColumnMandatory = true; + this.columns.push(menuSetCode); + + let separator = new Column("separator", "Separator", ColumnTypes.DROPDOWN, false, this.separatorStatusOptions); + separator.setIsColumnMandatory = true; + this.columns.push(separator); + this.columns.push(new Column("imageSrc", "Image Source", ColumnTypes.TEXT, true, null)); + + this.settings = new DataTableSettings() + this.settings.columns = this.columns; + this.settings.isPaginationEnabled = true; + this.settings.paginationsSize = "5"; + this.settings.isReadOnly = false; + this.settings.isTableSearchEnabled = true; + this.settings.applicationService = this.menuService; + + this.showSpinner = false; + + }); + } + + getFunctionCDselectData = function () { + this.adminService.getFunctionCdList() + .subscribe(_data => { + this.result = _data; + if (_data) { + + for(let i = 0; i< _data.length; i++){ + this.functionCDselectData.push({id: i, name: _data[i]}); + } + } + }, error => { + this.showSpinner = false; + console.log(error); + this.openConfirmationModal("", "Function Code Data not available !"); + }); + } + + getParentData() { + this.adminService.getParentData() + .subscribe(_data => { + this.result = _data; + if (_data) { + for(let i = 0; i< _data.length; i++){ + this.parentList.push({id: _data[i][0], name: _data[i][1]}); + } + console.log("Actual parent list : ", this.parentList); + this.menuService.getParentList(this.parentList); + } + }, error => { + this.showSpinner = false; + console.log(error); + }); + } + +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.module.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.module.ts new file mode 100644 index 00000000..99268e9f --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.module.ts @@ -0,0 +1,56 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { NgModule } from '@angular/core'; +import { CommonModule } from '@angular/common'; +import { MenusComponent } from './menus.component'; +import { MaterialModule } from 'src/app/material-module'; +import { FormsModule, ReactiveFormsModule } from '@angular/forms'; +import { MatFormFieldModule } from '@angular/material/form-field'; +import { NewMenuComponent } from './new-menu/new-menu.component'; +import {RdpModule} from 'portalsdk-tag-lib'; + +@NgModule({ + declarations: [MenusComponent, NewMenuComponent], + imports: [ + CommonModule, FormsModule, ReactiveFormsModule, MatFormFieldModule, RdpModule + ], + exports: [MenusComponent], + bootstrap: [MenusComponent] +}) +export class MenusModule { } diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.service.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.service.ts new file mode 100644 index 00000000..912b65bb --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/menus.service.ts @@ -0,0 +1,198 @@ + +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { Injectable } from '@angular/core'; +import { HttpClient } from '@angular/common/http'; +import { RdpCrudInterface } from 'portalsdk-tag-lib'; +import { environment } from 'src/environments/environment'; +import { AdminService } from '../admin.service'; +import { BehaviorSubject } from 'rxjs'; + +@Injectable({ + providedIn: 'root' +}) +export class MenusService implements RdpCrudInterface { + + public statusResponse = new BehaviorSubject(""); + public updatedData = new BehaviorSubject<any>({}); + + loadTableData(filter: any, sortActive: any, sortDirection: any, pageIndex: any, pageSize: any): import("rxjs").Observable<any[]> { + throw new Error("Method not implemented."); + } + getTotalRowCount() { + throw new Error("Method not implemented."); + } + + parentDataList: any; + constructor(private http: HttpClient, private adminService: AdminService) { + + } + + + menu = { + action: null, + active: false, + activeAsString: "false", + auditTrail: null, + auditUserId: null, + childMenus: [], + created: null, + createdId: null, + externalUrl: null, + functionCd: null, + id: null, + imageSrc: null, + label: null, + menuLevel: null, + menuSetCode: null, + modified: null, + modifiedId: null, + parentId: null, + parentIdAsString: null, + parentMenu: null, + queryString: null, + rowNum: null, + separator: false, + separatorAsString: false, + servlet: null, + sortOrder: null, + target: null + }; + + add(data: any) { + console.log("Add method is getting called from AppServie data:: ", data); + } + + + update(data: any) { + data.active = this.updateStatus(data.active); + data.separator = this.updateStatus(data.separator); + let keys = Object.keys(data); + let menuCache = this.menu; + keys.forEach(element => { + if (data[element] != null || data[element] != undefined) { + if (element == 'parentId') { + if (isNaN(data[element])) { + menuCache[element] = this.updateParentNameToID(data[element]); + } else{ + menuCache[element] = data[element]; + } + console.log("Parent Id to update : ", menuCache[element]); + } else { + menuCache[element] = data[element]; + } + } + }); + let result = { availableFnMenuItem: menuCache }; + let postData = JSON.stringify(result); + console.log("postData >>>>>>", postData); + this.adminService.updateFnMenuItem(postData) + .subscribe(_data => { + console.log("Response : ", _data); + this.statusResponse.next("200"); + menuCache = this.menu; + }, error => { + console.log("Error : ", error); + menuCache = this.menu; + }); + + } + + delete(data: any) { + console.log("Delete method is getting called from AppServie data::>> " + JSON.stringify(data)); + console.log(data.active); + data.active = this.updateStatus(data.active); + data.separator = this.updateStatus(data.separator); + this.adminService.deleteMenu(data).subscribe(response => { + console.log("Response ", response); + this.statusResponse.next("200"); + }, error => { + console.log("Error : ", error); + }) + } + + private updateStatus(data) { + if (data == 'N') { + return false; + } else { + return true; + } + } + + private updateBooleanValue(data) { + if (data) { + return 'Y'; + } else { + return 'N'; + } + } + + parentList: any; + + getParentList(list) { + this.parentList = list; + } + + private updateParentNameToID(data) { + let val; + this.parentList.forEach(ele => { + if (ele['name'] == data) { + val = ele['id']; + } + }); + console.log("ParentId value ", val); + return val; + } + + get() { + console.log("get method is getting called from MenuServie data:: "); + let response = this.adminService.getFnMenuItems(); + let resp; + response.subscribe(res => { + resp = res; + let responseData = JSON.parse(resp.data).fnMenuItems; + responseData.forEach(element => { + element.active = this.updateBooleanValue(element.active); + element.separator = this.updateBooleanValue(element.separator); + }) + this.updatedData.next(responseData); + }) + } + +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.html new file mode 100644 index 00000000..6a5426a8 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.html @@ -0,0 +1,137 @@ +<!-- + ============LICENSE_START========================================== + ONAP Portal SDK + =================================================================== + Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + =================================================================== + + Unless otherwise specified, all software contained herein is licensed + under the Apache License, Version 2.0 (the "License"); + you may not use this software except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + Unless otherwise specified, all documentation contained herein is licensed + under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + you may not use this documentation except in compliance with the License. + You may obtain a copy of the License at + + https://creativecommons.org/licenses/by/4.0/ + + Unless required by applicable law or agreed to in writing, documentation + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + ============LICENSE_END============================================ + +--> + +<div class="container"> + <!--Modal Headers--> + <div class="modal-header"> + <h4 class="modal-title">{{(isEditMode) ? 'Edit Menu Item' : 'Add New Menu Item'}}</h4> + <button type="button" class="close" aria-label="Close" (click)="activeModal.dismiss('Cross')"> + <span aria-hidden="true">×</span> + </button> + </div> + + <!--Modal Body goes here--> + <div class="modal-body"> + <div class="elementsContainer"> + <div class="groupItem"> + <label class="item-label">*Label:</label><br> + <input [(ngModel)]="menu.label" type="text" name="label" id="label"> + </div> + <div class="groupItem"> + <label class="item-label">*Parent:</label><br> + <!-- <input [(ngModel)]="menu.parentId" type="text" name="parentId" id="parent"> --> + <select class="form-field" name="parentSelect" id="parentSelect" [(ngModel)]="menu.parentId"> + <option>{{getParentLabel(menu.parentId, parentListSelectData)}}</option> + <option *ngFor="let option of parentListSelectData" value="{{option[0]}}">{{option[1]}}</option> + </select> + </div> + <div class="groupItem"> + <label class="item-label">*Sort Order</label><br> + <input [(ngModel)]="menu.sortOrder" type="text" name="sortOrder" id="sortOrder"> + </div> + <div class="groupItem"> + <label class="item-label">*Action</label><br> + <input [(ngModel)]="menu.action" type="text" name="action" id="action"> + </div> + </div> + + <br> + + <div class="elementsContainer"> + <div class="groupItem"> + <label class="item-label"><b>*</b>Function:</label><br> + <select class="form-field" name="repeatSelect" id="repeatSelect" [(ngModel)]="menu.functionCd"> + <option>{{menu.functionCd}}</option> + <option *ngFor="let item of functionCDselectData" value="{{item}}" >{{item}}</option> + </select> + </div> + <div class="groupItem"> + <label class="item-label"><b>*</b>Active:</label><br> + <select class="form-field" name="selectActive" ng-model="menu.active"> + <option *ngFor="let active of activeStatusOptions" value="{{active.value}}">{{active.title}}</option> + </select> + </div> + <div class="groupItem"> + <label class="item-label">Servlet:</label><br> + <input [(ngModel)]="menu.servlet" type="text" name="servlet" id="servlet"> + </div> + <div class="groupItem"> + <label class="item-label">Query String:</label><br> + <input [(ngModel)]="menu.queryString" type="text" name="queryString" id="queryString"> + </div> + </div> + + <br> + + <div class="elementsContainer"> + <div class="groupItem"> + <label class="item-label">External URL:</label><br> + <input [(ngModel)]="menu.externalUrl" type="text" name="externalURL" id="externalURL"> + </div> + <div class="groupItem"> + <label class="item-label">Target:</label><br> + <input [(ngModel)]="menu.target" type="text" name="target" id="target"> + </div> + <div class="groupItem"> + <label class="item-label"><b>*</b>Menu Set Code:</label><br> + <input [(ngModel)]="menu.menuSetCode" type="text" name="menuSetCode" id="menuSetCode"> + </div> + <div class="groupItem"> + <label class="item-label"><b>*</b>Separator:</label><br> + <select class="form-field" name="select" ng-model="menu.separator"> + <option *ngFor="let separator of separatorStatusOptions" value="{{separator.value}}">{{separator.title}}</option> + </select> + </div> + </div> + + <br> + + <div class="elementsContainer"> + <div class="groupItem"> + <label class="item-label">Image Source:</label><br> + <input [(ngModel)]="menu.imageSrc" type="text" name="imageSource" id="imageSource"> + </div> + </div> + + </div> + <!--Modal Footer goes Here--> + <div class="modal-footer"> + <button type="button" class="btn btn-primary" (click)="updateFnMenu()">Save</button> + <button type="button" class="btn btn-primary" (click)="activeModal.close('Close')">Cancel</button> + </div> +</div> +
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.scss new file mode 100644 index 00000000..a8b5f966 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.scss @@ -0,0 +1,71 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +::ng-deep .modal-dialog { + max-width: 1200px; + width: 883px; + overflow-x: auto; + overflow-y: auto; +} + +table { + width: 100%; +} + +body { + font-family: Roboto, Arial, sans-serif; + margin: 0; +} + +.elementsContainer{ + display: inline-flex; +} + +.groupItem{ + margin-right: 11px; + margin-bottom: 10px; +} + +.form-field{ + height: 30px; + width: 198px +} + +.item-label{ + margin-bottom: 1px; +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.spec.ts new file mode 100644 index 00000000..650f09a6 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.spec.ts @@ -0,0 +1,165 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * * Modification Copyright © 2020 IBM. + * =================================================================== + + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + */ + +import { async, ComponentFixture, TestBed } from '@angular/core/testing'; +import {FormsModule} from '@angular/forms'; +import { NewMenuComponent } from './new-menu.component'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; +import { NgbActiveModal, NgbModalModule } from '@ng-bootstrap/ng-bootstrap'; +import { RouterTestingModule } from '@angular/router/testing'; +import { CookieService } from 'ngx-cookie-service'; +import { AdminService } from '../../admin.service'; +import 'rxjs/add/operator/toPromise'; +import { ConfirmationModalComponent } from 'src/app/modals/confirmation-modal/confirmation-modal.component'; +import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; +import 'rxjs/add/observable/of'; +import { Observable } from 'rxjs/Observable'; +import 'rxjs/add/operator/catch'; +import 'rxjs/add/observable/throw'; +import { BrowserDynamicTestingModule } from '@angular/platform-browser-dynamic/testing'; + + +describe('NewMenuComponent', () => { + let component: NewMenuComponent; + let fixture: ComponentFixture<NewMenuComponent>; + let adminService:AdminService; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + declarations: [ NewMenuComponent,ConfirmationModalComponent ], + imports:[ + FormsModule, + HttpClientTestingModule, + RouterTestingModule, + NgbModalModule, + BrowserAnimationsModule + ], + providers:[ + AdminService, + NgbActiveModal, + CookieService + ], + }) + TestBed.overrideModule(BrowserDynamicTestingModule,{ + set:{ + entryComponents:[ConfirmationModalComponent ] + } + }) + .compileComponents(); + + })); + + beforeEach(() => { + fixture = TestBed.createComponent(NewMenuComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + adminService=TestBed.get(AdminService); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); + + it('testing ngOnInit method for if condition',()=>{ + component.selectedMenu=1; + component.ngOnInit(); + expect(component.menu).toEqual(component.selectedMenu); + }) + + it('testing ngOnInit method for else condition',()=>{ + component.selectedMenu=0; + component.ngOnInit(); + expect(component.menu.menuSetCode).toEqual('APP'); + }) + + it('testing sortItems method',()=>{ + let prop: any; + component.sortItems(prop); + + }) + + it('testing getParentLabel method',()=>{ + component.getParentLabel(1,"data"); + }) + + + it('should test getParentData method1 ',()=>{ + const children="children"; + let spy=spyOn(adminService,'getParentData').and.returnValue(Observable.of('you object')); + component.getParentData(); + expect(spy).toHaveBeenCalled(); + }) + + it('should test getParentData method2 error part ',()=>{ + const children="children"; + let spy=spyOn(adminService,'getParentData').and.returnValue(Observable.throw({status:404})); + component.getParentData(); + expect(spy).toHaveBeenCalled(); + }) + + describe('should test getLeftMenuItems',()=>{ + it('testing getLeftMenuItems',()=>{ + component.getLeftMenuItems(); + }) + }) + + it('testing getFunctionCDselectData method1',()=>{ + let spy=spyOn(adminService,'getFunctionCdList').and.returnValue(Observable.of('your object')); + component.getFunctionCDselectData(); + expect(spy).toHaveBeenCalled(); + expect(component.result).toEqual('your object'); + expect(component.functionCDselectData).toEqual('your object'); + }) + + describe('should test getFunctionCDselectData method2',()=>{ + it('testing getFunctionCDselectData',()=>{ + let spy= spyOn(adminService,'getFunctionCdList').and.returnValue(Observable.throw({status:404})) + component.getFunctionCDselectData(); + expect(spy).toHaveBeenCalled(); + expect(component.showSpinner).toEqual(false); + }) + }) + + it('should test updateFnMenu method',()=>{ + component.menu.label!=null; + component.updateFnMenu(); + }) + +}); diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.ts new file mode 100644 index 00000000..6e5b0c1a --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/menus/new-menu/new-menu.component.ts @@ -0,0 +1,267 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { Component, OnInit, Input, Output, EventEmitter } from '@angular/core'; +import { NgbActiveModal, NgbModal } from '@ng-bootstrap/ng-bootstrap'; +import { AdminService } from '../../admin.service'; +import { SidebarComponent } from 'src/app/layout/components/sidebar/sidebar.component'; +import { Router } from '@angular/router'; +import { SidebarService } from 'src/app/shared/services'; +import { ConfirmationModalComponent } from 'src/app/modals/confirmation-modal/confirmation-modal.component'; +import { CookieService } from 'ngx-cookie-service'; + +@Component({ + selector: 'app-new-menu', + templateUrl: './new-menu.component.html', + styleUrls: ['./new-menu.component.scss'] +}) +export class NewMenuComponent implements OnInit { + + menu = { + action: null, + active: false, + activeAsString: "false", + auditTrail: null, + auditUserId: null, + childMenus: [], + created: null, + createdId: null, + externalUrl: null, + functionCd: null, + id: null, + imageSrc: null, + label: null, + menuLevel: null, + menuSetCode: null, + modified: null, + modifiedId: null, + parentId: null, + parentIdAsString: null, + parentMenu: null, + queryString: null, + rowNum: null, + separator: false, + separatorAsString: false, + servlet: null, + sortOrder: null, + target: null + } + showSpinner: boolean; + result: any; + //menu: any; + @Input() selectedMenu: any; + @Input() isEditMode: boolean; + @Output() passEntry: EventEmitter<any> = new EventEmitter(); + + statusOptions = [ + {index: 0, value: 'true', title: 'Y'}, + {index: 1, value: 'false', title: 'N'} + ]; + selectedValue = this.statusOptions[0]; + separator = { + availableOptions:[ + {value: 'true', name: 'Y'}, + {value: 'false', name: 'N'} + ], + selectedOption: {value: 'true', name: 'Y'} + } + + activeStatusOptions = [ + {index: 0, value: 'true', title: 'Y'}, + {index: 1, value: 'false', title: 'N'} + ]; + activeSelectedValue = this.activeStatusOptions[0]; + + separatorStatusOptions = [ + {index: 0, value: 'true', title: 'Y'}, + {index: 1, value: 'false', title: 'N'} + ]; + separatorSelectedValue = this.separatorStatusOptions[1]; + + active = { + availableOptions:[ + {value: 'true', name: 'Y'}, + {value: 'false', name: 'N'} + ], + selectedOption: {value: 'true', name: 'Y'} + }; + + functionCDselectData = []; + parentListSelectData = []; + childListSelectData = []; + + constructor(public adminService: AdminService, public activeModal: NgbActiveModal, + public ngmodel: NgbModal, public router: Router, public sidebarService: SidebarService,public cookieService:CookieService) { } + + ngOnInit() { + if(this.selectedMenu){ + this.menu = this.selectedMenu; + }else{ + this.menu.menuSetCode='APP'; + } + this.getFunctionCDselectData(); + this.getParentData(); + } + + getParentData(){ + this.showSpinner = true; + this.adminService.getParentData() + .subscribe( _data => { + this.result = _data; + if(_data){ + this.parentListSelectData= _data; // data from server + let menuItems = this.parentListSelectData; + var heirarchicalMenuItems = []; + var children = []; + for ( var i=0; i<menuItems.length; i++){ + for(var j=0; j<menuItems.length; j++){ + if(menuItems[j][2]==menuItems[i][0]) + children.push( + { + menuId: menuItems[j][0], + label: menuItems[j][1] + } + ); + } + if(children.length!=0){ + heirarchicalMenuItems.push( + { + menuId: menuItems[i][0], + label: menuItems[i][1], + children: children.sort(this.sortItems("label")) + } + + ); + } + children = []; + } + heirarchicalMenuItems.sort(this.sortItems("label")); + this.childListSelectData = heirarchicalMenuItems; + } + }, error => { + this.showSpinner = false; + console.log(error); + }); + } + + sortItems(prop){ + return function(a, b) { + if (a[prop] > b[prop]) { + return 1; + } else if (a[prop] < b[prop]) { + return -1; + } + return 0; + } + } + + getParentLabel(parentId, parentListSelectData){ + var element; + element = parentListSelectData[0]; + for (var i=0; i<parentListSelectData.length; i++){ + element = parentListSelectData[i]; + if (element[0] == parentId) + return element[1]; + else "---"; + } + } + + updateFnMenu(){ + this.showSpinner = true; + if( this.menu && this.menu.imageSrc == "" ) this.menu.imageSrc = "N/A"; + if( this.menu && this.menu.target == "" ) this.menu.target = "N/A"; + if( this.menu && this.menu.externalUrl == "" ) this.menu.externalUrl = "N/A"; + if( this.menu && this.menu.queryString == "" ) this.menu.queryString = "N/A"; + if( this.menu && this.menu.servlet == "" ) this.menu.servlet = "N/A"; + + let validationRule = /^\S{3,}$/; + let selectedFunction = this.menu.functionCd; + var selectedFunctionText = this.menu.functionCd; //selectedFunction.options[selectedFunction.selectedIndex].text; + + if((this.menu.label == null || this.menu.label == "" || (this.menu.label && this.menu.label.trim().length == 0) ) || + this.menu.parentId == null || this.menu.parentId == "" || this.menu.action == null || this.menu.action == "" || + selectedFunctionText == null || selectedFunctionText == "" || this.menu.sortOrder == null || this.menu.sortOrder == "" || + this.menu.menuSetCode == null ||this.menu.menuSetCode == ""){ + + this.openConfirmationModal('','Please provide all the mandatory (*) fields inputs !'); + return; + }else{ + this.menu.parentId=parseFloat(this.menu.parentId); + let data ={availableFnMenuItem: this.menu}; + let postData = JSON.stringify(data); + this.adminService.updateFnMenuItem(postData) + .subscribe( _data => { + this.result = _data; + this.passEntry.emit(this.result); + this.ngmodel.dismissAll(); + }, error => { + this.showSpinner = false; + console.log(error); + this.openConfirmationModal("Error",error); + }); + this.getLeftMenuItems(); + } + + } + + getLeftMenuItems(){ + let sidebarComponent = new SidebarComponent(this.router, this.sidebarService,this.cookieService); + sidebarComponent.ngOnInit(); + } + + getFunctionCDselectData = function(){ + this.adminService.getFunctionCdList() + .subscribe( _data => { + this.result = _data; + if(_data){ + this.functionCDselectData = _data; + } + }, error => { + this.showSpinner = false; + console.log(error); + this.openConfirmationModal("","Function Code Data not available !"); + }); + } + + openConfirmationModal(_title: string, _message: string) { + const modalInfoRef = this.ngmodel.open(ConfirmationModalComponent); + modalInfoRef.componentInstance.title = _title; + modalInfoRef.componentInstance.message = _message; + } + +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.html new file mode 100644 index 00000000..888deca8 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.html @@ -0,0 +1,101 @@ +<!-- + ============LICENSE_START========================================== + ONAP Portal- SDK + =================================================================== + Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + =================================================================== + + Unless otherwise specified, all software contained herein is licensed + under the Apache License, Version 2.0 (the "License"); + you may not use this software except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + Unless otherwise specified, all documentation contained herein is licensed + under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + you may not use this documentation except in compliance with the License. + You may obtain a copy of the License at + + https://creativecommons.org/licenses/by/4.0/ + + Unless required by applicable law or agreed to in writing, documentation + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + ============LICENSE_END============================================ + + + --> + + <div class="container"> + <div class="modal-header"> + <h4 class="modal-title">{{title}}</h4> + <button type="button" class="close" aria-label="Close" (click)="activeModal.dismiss('Cross')"> + <span aria-hidden="true">×</span> + </button> + </div> + <div class="modal-body"> + <span class="ecomp-spinner" *ngIf="showSpinner"></span> + <form> + <fieldset class="form-group"> + <div class="row"> + <legend class="col-form-label col-sm-2 pt-0">Type</legend> + <div class="col-sm-10"> + <div class="form-check"> + {{selectedType}} + <mat-radio-group aria-labelledby="example-radio-group-label" class="example-radio-group" + [(ngModel)]="selectedType" name="type"> + <mat-radio-button class="example-radio-button" [disabled]="editDisable" *ngFor="let type of typeOptions" [value]="type"> + {{type}} + </mat-radio-button> + </mat-radio-group> + </div> + </div> + </div> + </fieldset> + <div *ngIf="selectedType === 'other'" class="form-group row"> + <label for="inputOtherType" class="col-sm-2 col-form-label"></label> + <div class="col-sm-10"> + <input type="text" class="form-control" [disabled]="editDisable" [(ngModel)]="otherTypeValue" name="type2" id="inputOtherType" + placeholder="Type"> + </div> + </div> + <div class="form-group row"> + <label for="inputInstance" class="col-sm-2 col-form-label">Instance</label> + <div class="col-sm-10"> + <input type="text" class="form-control" [disabled]="editDisable" [(ngModel)]="roleFunction.code" name="code" id="inputInstance" + placeholder="Instance"> + </div> + </div> + <div class="form-group row"> + <label for="inputAction" class="col-sm-2 col-form-label">Action</label> + <div class="col-sm-10"> + <input type="text" class="form-control" [disabled]="editDisable" [(ngModel)]="roleFunction.action" name="action" id="inputAction" + placeholder="Action"> + </div> + </div> + <div class="form-group row"> + <label for="inputName" class="col-sm-2 col-form-label">Name</label> + <div class="col-sm-10"> + <input type="text" class="form-control" [(ngModel)]="roleFunction.name" name="name" id="inputName" + placeholder="Name"> + </div> + </div> + </form> + </div> + <div class="modal-footer"> + <button type="button" class="btn btn-primary" + [disabled]="(selectedType === 'other' && otherTypeValue.length === 0 ) || (roleFunction.code.length === 0 || roleFunction.action.length === 0 || roleFunction.name.length === 0)" + (click)="saveRoleFunction()">Save</button> + <button type="button" class="btn btn-primary" (click)="activeModal.close('Close')">Cancel</button> + </div> + </div>
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.scss new file mode 100644 index 00000000..56cb1aa3 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.scss @@ -0,0 +1,40 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal - SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + .ecomp-spinner{ + z-index: 9999; +}
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.spec.ts new file mode 100644 index 00000000..ecc0947d --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.spec.ts @@ -0,0 +1,69 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ +import { async, ComponentFixture, TestBed } from '@angular/core/testing'; + +import { NewRoleFunctionComponent } from './new-role-function.component'; +import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/core'; +import { FormsModule } from '@angular/forms'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; +import { NgbActiveModal } from '@ng-bootstrap/ng-bootstrap'; + +describe('NewRoleFunctionComponent', () => { + let component: NewRoleFunctionComponent; + let fixture: ComponentFixture<NewRoleFunctionComponent>; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + schemas:[CUSTOM_ELEMENTS_SCHEMA], + declarations: [ NewRoleFunctionComponent ], + imports:[FormsModule,HttpClientTestingModule], + providers:[NgbActiveModal] + }) + .compileComponents(); + })); + + beforeEach(() => { + fixture = TestBed.createComponent(NewRoleFunctionComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + // it('should create', () => { + // expect(component).toBeTruthy(); + // }); +}); diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.ts new file mode 100644 index 00000000..d0be5145 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/new-role-function/new-role-function.component.ts @@ -0,0 +1,174 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ +import { Component, OnInit, Input, Output, EventEmitter } from '@angular/core'; +import { NgbActiveModal, NgbModal } from '@ng-bootstrap/ng-bootstrap'; +import { InformationModalComponent } from 'src/app/modals/information-modal/information-modal.component'; +import { RoleFunction } from '../role-function'; +import { HttpClient } from '@angular/common/http'; +import { AdminService } from '../../admin.service'; +import { ConfirmationModalComponent } from 'src/app/modals/confirmation-modal/confirmation-modal.component'; + +@Component({ + selector: 'app-new-role-function', + templateUrl: './new-role-function.component.html', + styleUrls: ['./new-role-function.component.scss'] +}) +export class NewRoleFunctionComponent implements OnInit { + + @Input() title: string; + @Input() appId: any; + @Input() dialogState: number; + @Input() currentRoleFunctions: any; + @Input() editRoleFunction: RoleFunction; + @Output() passBackRoleFunctionPopup: EventEmitter<any> = new EventEmitter(); + roleFunction: RoleFunction; + otherTypeValue: string; + typeOptions: string[] = ['menu', 'url', 'other']; + api = ''; + isEditing: any; + editDisable: boolean; + showSpinner: boolean; + selectedType: string; + createOrUpdate: string; + constructor(public adminService: AdminService, public activeModal: NgbActiveModal, public ngbModal: NgbModal, public http: HttpClient) { } + + ngOnInit() { + this.createOrUpdate = 'create'; + this.selectedType = 'menu'; + this.roleFunction = new RoleFunction(this.selectedType, '', '*', ''); + this.otherTypeValue = ''; + if (this.editRoleFunction) { + this.createOrUpdate = 'update'; + this.editDisable = true; + if (this.editRoleFunction.type !== 'menu' && this.editRoleFunction.type !== 'url') { + this.selectedType = 'other'; + this.otherTypeValue = this.editRoleFunction.type; + }else{ + this.selectedType = this.editRoleFunction.type; + } + this.roleFunction = new RoleFunction(this.editRoleFunction.type, this.editRoleFunction.code, this.editRoleFunction.action, this.editRoleFunction.name); + } + } + + saveRoleFunction() { + if (/[^a-zA-Z0-9\-\.\_]/.test(this.roleFunction.type)) { + this.openConfirmationModal('Confirmation', 'Type can only contain alphanumeric characters, dots(.) and underscores(_)'); + return; + } + if (this.roleFunction.action !== '*' && /[^a-zA-Z0-9\-\.\_]/.test(this.roleFunction.action)) { + this.openConfirmationModal('Confirmation', 'Action can only contain alphanumeric characters, hyphens(-), dots(.) and underscores(_) and single asterisk character(*)'); + return; + } + if (/[^a-zA-Z0-9\-\:\_\./*]/.test(this.roleFunction.code)) { + this.openConfirmationModal('Confirmation', 'Instance can only contain alphanumeric characters, hyphens(-), dots(.), colons(:), forwardSlash(/) , asterisk(*) and underscores(_)'); + return; + } + const modalInfoRef = this.ngbModal.open(InformationModalComponent); + modalInfoRef.componentInstance.title = 'Confirmation'; + modalInfoRef.componentInstance.message = 'You are about to ' + this.createOrUpdate + ' the role function ' + this.roleFunction.name + '. Do you want to continue?'; + modalInfoRef.result.then((_res) => { + if (_res === 'Ok') { + this.showSpinner = true; + var exists = false, x; + for (x in this.currentRoleFunctions) { + if (this.currentRoleFunctions[x].type == this.roleFunction.type + && this.currentRoleFunctions[x].code == this.roleFunction.code + && this.currentRoleFunctions[x].action == this.roleFunction.action + && this.currentRoleFunctions[x].name == this.roleFunction.name) { + this.openConfirmationModal('Confirmation', "Role Function already exist."); + exists = true; + this.showSpinner = false; + break; + } + if (!this.editDisable) { + if (this.currentRoleFunctions[x].type == this.roleFunction.type + && this.currentRoleFunctions[x].code == this.roleFunction.code + && this.currentRoleFunctions[x].action == this.roleFunction.action + ) { + this.openConfirmationModal('Confirmation', "Please make sure code, type and action is unique. Please create a role function with a different code or type or action to proceed."); + exists = true; + this.showSpinner = false; + break; + } + } + } + + if (this.selectedType === 'other'){ + this.roleFunction.type = this.otherTypeValue; + }else{ + this.roleFunction.type = this.selectedType; + } + + if (!exists && this.roleFunction.name.trim() != '' && this.roleFunction.code.trim() != '') { + var postData = this.roleFunction; + //console.log("saveRoleFunction post data :: ",postData); + this.adminService.saveRoleFunction(JSON.stringify(postData)) + .subscribe(_data => { + this.showSpinner = false; + //console.log("saveRoleFunction response",_data); + if (this.editRoleFunction) { + this.editRoleFunction.name = this.roleFunction.name; + this.passBackRoleFunctionPopup.emit(this.editRoleFunction); + } else{ + this.passBackRoleFunctionPopup.emit(this.roleFunction); + } + if (this.editRoleFunction) { + this.openConfirmationModal('Success', "Role function updated successfully."); + }else{ + this.openConfirmationModal('Success', "Role function created successfully."); + } + }, error =>{ + //console.log(error); + this.showSpinner = false; + this.openConfirmationModal('Error', error.message); + }); + } + } + }, (_dismiss) => { + + }) + } + + + openConfirmationModal(_title: string, _message: string) { + const modalInfoRef = this.ngbModal.open(ConfirmationModalComponent); + modalInfoRef.componentInstance.title = _title; + modalInfoRef.componentInstance.message = _message; + } + +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-function.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-function.ts new file mode 100644 index 00000000..9a00995b --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-function.ts @@ -0,0 +1,52 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +export class RoleFunction { + type: string; + code: string; + action: string; + name: string; + + //constructor + constructor(type: string, code: string, action: string, name: string) { + this.type = type; + this.code = code; + this.action = action; + this.name = name; + } +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.html new file mode 100644 index 00000000..460f69b3 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.html @@ -0,0 +1,48 @@ +<!-- + ============LICENSE_START========================================== + ONAP Portal SDK + =================================================================== + Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + =================================================================== + + Unless otherwise specified, all software contained herein is licensed + under the Apache License, Version 2.0 (the "License"); + you may not use this software except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + Unless otherwise specified, all documentation contained herein is licensed + under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + you may not use this documentation except in compliance with the License. + You may obtain a copy of the License at + + https://creativecommons.org/licenses/by/4.0/ + + Unless required by applicable law or agreed to in writing, documentation + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + ============LICENSE_END============================================ + + --> + + +<div class="main-container"> + <div class="role-function-title"> + <h3 class="heading-page" id="roleFunction"> Role Functions </h3> + <span class= "heading-small" *ngIf="isAppCentralized=='true'"><b>Please go to portal to Manage Role Function.</b></span> + </div> + <span class="ecomp-spinner" *ngIf="showSpinner"></span> + + <rdp-data-table [data]="tableData" [settings]="settings"></rdp-data-table> +</div> +
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.scss new file mode 100644 index 00000000..ec7b2cac --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.scss @@ -0,0 +1,63 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + table { + width: 100%; +} + +td, th { + width: 25%; +} + +td[_ngcontent-c4], th[_ngcontent-c4] { + width: 15%; +} + +.icon-trash{ + cursor: pointer; +} + +::ng-deep .mat-form-field-infix { + width: 250px; + margin-left: 10px; +} + +:host::ng-deep .mat-header-cell{ + font-weight: bold; + font-size: 14px; + color: #343a40; +}
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.spec.ts new file mode 100644 index 00000000..dab6af2b --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.spec.ts @@ -0,0 +1,99 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * Modification Copyright © 2020 IBM. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ +import { async, ComponentFixture, TestBed, inject } from '@angular/core/testing'; + +import { RoleFunctionsComponent } from './role-functions.component'; +import { CUSTOM_ELEMENTS_SCHEMA} from '@angular/core'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; +import { RdpModule } from 'portalsdk-tag-lib'; +import { FormsModule} from '@angular/forms'; +import { AdminService } from '../admin.service'; +import { MatSelectModule} from '@angular/material'; +import { Observable } from 'rxjs'; +import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; +import { UserService } from '../../shared/services/user/user.service'; + +describe('RoleFunctionsComponent', () => { + let component: RoleFunctionsComponent; + let fixture: ComponentFixture<RoleFunctionsComponent>; + let userService:UserService; + let adminService:AdminService; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + schemas: [CUSTOM_ELEMENTS_SCHEMA], + declarations: [ RoleFunctionsComponent ], + imports: [HttpClientTestingModule,BrowserAnimationsModule, + RdpModule, + FormsModule, + ], + providers:[MatSelectModule] + }) + .compileComponents(); + })); + + beforeEach(() => { + TestBed.configureTestingModule({ + providers:[AdminService] + }) + fixture = TestBed.createComponent(RoleFunctionsComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + userService=TestBed.get(UserService); + adminService=TestBed.get(AdminService); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); + + describe('test for subscribe in ngOnInit',()=>{ + it('should test ngOnInit method',()=>{ + let spy=spyOn(userService,'getFunctionalMenuStaticDetailSession').and.returnValue(Observable.of('you object')); + component.ngOnInit(); + expect(spy).toHaveBeenCalled(); + }) + }) + it('Admin service injection check', inject([AdminService],(injectService:AdminService) =>{ + expect(injectService).toBe(adminService); + })); + + +}); diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.ts new file mode 100644 index 00000000..3b97be51 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.component.ts @@ -0,0 +1,126 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { Component, OnInit, Directive, Input, Output, EventEmitter, ViewChildren, QueryList, PipeTransform, ViewChild } from '@angular/core'; +import { AdminService } from '../admin.service'; +import {UserService} from '../../shared/services/user/user.service' +import { User } from 'src/app/shared/services/user/user'; +import { of, Observable } from 'rxjs'; +import { RoleFunction } from './role-function'; +import { MatTableDataSource } from '@angular/material/table'; +import { MatPaginator } from '@angular/material/paginator'; +import { MatSort } from '@angular/material/sort'; +import { InformationModalComponent } from 'src/app/modals/information-modal/information-modal.component'; +import { NgbModal, ModalDismissReasons } from '@ng-bootstrap/ng-bootstrap'; +import { NewRoleFunctionComponent } from './new-role-function/new-role-function.component'; +import { Column, DataTableSettings, ColumnTypes } from 'portalsdk-tag-lib'; +import { RoleFunctionsService } from './role-functions.service'; + +@Component({ + selector: 'app-role-functions', + templateUrl: './role-functions.component.html', + styleUrls: ['./role-functions.component.scss'] +}) +export class RoleFunctionsComponent implements OnInit { + + tableData: Array<RoleFunction> = []; + response: any; + result: any; + function: RoleFunction; + isEditMode: boolean = false; + availableRoleFunctions: any; + showSpinner: boolean; + + isAppCentralized: any; + user: User; + closeResult: string; + + roleFunctionHeaders = ["name", "code", "type", "action", "edit", "delete"]; + dataSource: MatTableDataSource<RoleFunction>; + + constructor(public adminService: AdminService, + public userService: UserService, + private ngModal: NgbModal, + private roleFunctionService: RoleFunctionsService) { } + + @ViewChild(MatPaginator, {}) paginator: MatPaginator; + @ViewChild(MatSort, {}) sort: MatSort; + + public settings; + public columns: any = []; + typeOptions: string[] = ['menu', 'url', 'other']; + + ngOnInit() { + this.showSpinner = false; + this.availableRoleFunctions = []; + this.getRoleFunctions(); + let result = this.userService.getFunctionalMenuStaticDetailSession(); + result.subscribe(user => { + this.user = user; + this.isAppCentralized = this.user.isAppCentralized; + }); + } + + getRoleFunctions() { + this.showSpinner = true; + let response; + this.response = this.adminService.getRoleFunctionList(); + this.response.subscribe(data => { + response = data; + this.result = JSON.parse(response.data); + this.availableRoleFunctions = this.result.availableRoleFunctions; + this.tableData = JSON.parse(this.result.availableRoleFunctions); + //console.log("Table data : ", this.tableData); + this.columns.push(new Column("name", "Name", ColumnTypes.TEXT, true, null)); + this.columns.push(new Column("code", "Code", ColumnTypes.TEXT, true, null)); + this.columns.push(new Column("type", "Type", ColumnTypes.RADIO, true, this.typeOptions)); + this.columns.push(new Column("action", "Action", ColumnTypes.TEXT, true, null)); + + this.settings = new DataTableSettings() + this.settings.columns = this.columns; + this.settings.isPaginationEnabled = true; + this.settings.paginationsSize = "5"; + this.settings.isReadOnly = false; + this.settings.isTableSearchEnabled = true; + this.settings.applicationService = this.roleFunctionService; + this.showSpinner = false; + + }); + + } +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.service.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.service.ts new file mode 100644 index 00000000..bd44a63d --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/role-functions/role-functions.service.ts @@ -0,0 +1,57 @@ +import { Injectable } from '@angular/core'; +import { RdpCrudInterface } from 'portalsdk-tag-lib'; +import { AdminService } from '../admin.service'; +import { BehaviorSubject } from 'rxjs'; + +@Injectable({ + providedIn: 'root' +}) +export class RoleFunctionsService implements RdpCrudInterface { + + public statusResponse = new BehaviorSubject(""); + public updatedData = new BehaviorSubject<any>({}); + + loadTableData(filter: any, sortActive: any, sortDirection: any, pageIndex: any, pageSize: any): import("rxjs").Observable<any[]> { + throw new Error("Method not implemented."); + } + getTotalRowCount() { + throw new Error("Method not implemented."); + } + + constructor(private adminService: AdminService) { } + + add(data: any) { + //console.log("Add method is getting called from RoleFunctionService data:: ", data); + } + + + update(data: any): any { + console.log("Update method is getting called from RoleFunctionService data:: ", data); + return this.adminService.saveRoleFunction(data).subscribe(response => { + //console.log("Success Response ", response); + this.statusResponse.next("200"); + }, error => { + console.log("Error ", error); + }) + } + + delete(data: any) { + //console.log("Delete method is getting called from RoleFunctionService data::>> " + JSON.stringify(data)); + this.adminService.deleteRoleFunction(data).subscribe(response => { + //console.log("Repsonse : ", response); + this.statusResponse.next("200"); + + }) + } + + get() { + let response = this.adminService.getRoleFunctionList(); + let editedData; + response.subscribe(res => { + editedData = res; + let data = JSON.parse(JSON.parse(editedData.data).availableRoleFunctions); + //console.log("Get Method called : ", data); + this.updatedData.next(data); + }) + } +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.html new file mode 100644 index 00000000..f3a7f8ea --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.html @@ -0,0 +1,106 @@ +<!-- + ============LICENSE_START========================================== + ONAP Portal SDK + =================================================================== + Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + =================================================================== + + Unless otherwise specified, all software contained herein is licensed + under the Apache License, Version 2.0 (the "License"); + you may not use this software except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + Unless otherwise specified, all documentation contained herein is licensed + under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + you may not use this documentation except in compliance with the License. + You may obtain a copy of the License at + + https://creativecommons.org/licenses/by/4.0/ + + Unless required by applicable law or agreed to in writing, documentation + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + ============LICENSE_END============================================ + + --> +<div class="container"> + <!--Modal Headers--> + <div class="modal-header"> + <h4 class="modal-title">Role</h4> + <button type="button" class="close" aria-label="Close" (click)="activeModal.dismiss('Cross')"> + <span aria-hidden="true">×</span> + </button> + </div> + + <!--Modal Body goes here--> + <div class="modal-body"> + <span class="ecomp-spinner" *ngIf="showSpinner"></span> + <div class="role-properties-main"> + <form id="role-details-form" name="roleDetails" novalidate autocomplete="off" method="post"> + <div class="elementsDiv"> + <div class="item required role-name"> + <div class="item-label">Name :</div> + <input id="role-details-input-name" class="table-search-field" + type="text" name="rolename" + [(ngModel)]="role.name" + ng-pattern="/^[\w -]*$/" maxlength="100" required /> + </div> + <div> + <div class="item-label">Priority :</div> + <input id="role-details-input-priority" class="table-search-field" + type="text" + ng-change="accountAddDetails.updateUsername()" name="priority" + [(ngModel)]="role.priority"/> + </div> + </div> + </form> + </div> + + <!-- Role Functions List--> + <div *ngIf="isEditMode" class="role-functions-title">Role Functions</div> + <div *ngIf="isEditMode" class="rolefunctionTable"> + <table mat-table [dataSource]="roleFunctionDataSource"> + <ng-container matColumnDef="roleFunctionName"> + <th mat-header-cell *matHeaderCellDef id="heading1">Function Name</th> + <td mat-cell *matCellDef="let rowData"> {{rowData.name}} </td> + </ng-container> + + <!--<ng-container matColumnDef="remove"> + <th mat-header-cell *matHeaderCellDef id="heading1">Remove</th> + <td id="rowheader_t1_{{i}}" mat-cell *matCellDef="let rowData; let i=index;"> + <span class="icon-trash" id="{{i}}-button-role-remove" (click)="delRoleFunctionConfirmPopUp(rowData,role.id)"> + <i class="icon ion-md-trash"></i> + </span> + </td> + </ng-container>--> + + <!-- Active Column --> + <ng-container matColumnDef="active"> + <th id="col3" mat-header-cell *matHeaderCellDef>Active ?</th> + <td id="rowheader_t1_{{i}}-userId" mat-cell *matCellDef="let element; let i=index;"> + <mat-slide-toggle [(ngModel)]="element.selected" (change)="toggleRoleFunction(element)"></mat-slide-toggle> + </td> + </ng-container> + + <tr mat-header-row *matHeaderRowDef="roleFunctionTableHeaders"></tr> + <tr mat-row *matRowDef="let rowData; columns: roleFunctionTableHeaders;"> + </table> + </div> + </div> + <!--Modal Footer goes Here--> + <div class="modal-footer"> + <button type="button" class="btn btn-primary" (click)="saveChanges()">Save</button> + <button type="button" class="btn btn-primary" (click)="activeModal.close('Close')">Cancel</button> + </div> +</div> diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.scss new file mode 100644 index 00000000..972094c7 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.scss @@ -0,0 +1,74 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + + ::ng-deep .modal-dialog { + max-width: 700px; + width: 700px; + overflow-x: auto; + overflow-y: auto; +} + +::ng-deep .mat-column-roleFunctionName { + width: 38em !important; +} + + +.role-properties-main input[type="text"] { + width: 18em; +} + +.role-properties-main .role-name{ + margin-right: 35px; +} + +.elementsDiv{ + display: inline-flex; +} + +.role-functions-title{ + margin-top: 2em; +} + +.manageRoleFunction{ + margin-top: 2em; +} + +.rolefunctionTable{ + overflow-y: auto; + height: 440px; +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.spec.ts new file mode 100644 index 00000000..4eca8263 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.spec.ts @@ -0,0 +1,132 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * Modification Copyright © 2020 IBM. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { async, ComponentFixture, TestBed } from '@angular/core/testing'; +import {FormsModule} from '@angular/forms'; +import { NewRoleComponent } from './new-role.component'; +import { MatTableModule } from '@angular/material' +import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/core'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; +import { NgbActiveModal, NgbModule } from '@ng-bootstrap/ng-bootstrap'; +import { ConfirmationModalComponent } from 'src/app/modals/confirmation-modal/confirmation-modal.component'; +import { BrowserDynamicTestingModule } from '@angular/platform-browser-dynamic/testing'; +import { AdminService } from '../../admin.service'; +import { Observable } from 'rxjs'; +import { InformationModalComponent } from 'src/app/modals/information-modal/information-modal.component'; + +describe('NewRoleComponent', () => { + let component: NewRoleComponent; + let fixture: ComponentFixture<NewRoleComponent>; + let role1 = ""; + let adminService:AdminService; + var _element={ + "selected":false, + "code":"code", + "type":"type", + "action":"action" + }; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + providers: [NgbActiveModal,AdminService], + schemas: [CUSTOM_ELEMENTS_SCHEMA] , + declarations: [ + NewRoleComponent, + ConfirmationModalComponent, + InformationModalComponent + ], + imports: [ + FormsModule, + MatTableModule, + HttpClientTestingModule, + NgbModule.forRoot() + ] + }) + TestBed.overrideModule(BrowserDynamicTestingModule,{ + set:{ + entryComponents:[ConfirmationModalComponent,InformationModalComponent] + } + }) + .compileComponents(); + })); + + beforeEach(() => { + fixture = TestBed.createComponent(NewRoleComponent); + component = fixture.componentInstance; + component.role = role1; + fixture.detectChanges(); + adminService=TestBed.get(AdminService); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); + + it('should test delRoleFunctionConfirmPopUp method',()=>{ + component.delRoleFunctionConfirmPopUp("abc","def"); + }) + + it('should test else condition in saveChanges method',()=>{ + spyOn(adminService,'saveRole').and.returnValue(Observable.of('your object')); + component.saveChanges() + }) + + it('should test toggleRoleFunction method',()=>{ + component.finalSelectedRoleFunctions="Indrijeet kuma"; + component.ociavailableRoleFunctions="i"; + component.finalSelectedRoleFunctions="k"; + component.toggleRoleFunction(_element) + }) + + it('should test populateTableData method',()=>{ + component.populateTableData("populateTableData"); + expect(component.roleFunctionDataSource.sort).toEqual(component.sort); + expect(component.roleFunctionDataSource.paginator).toEqual(component.paginator) + }) + + it('should test isRoleAlreadyExist method',()=>{ + component.availableRoles={"name":["currentRoleName"]}; + component.isRoleAlreadyExist("currentRoleName") + }) + + it('it should test openConfirmationModal method',()=>{ + component.openConfirmationModal("test","value"); + }) +});
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.ts new file mode 100644 index 00000000..6b1470fa --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/new-role/new-role.component.ts @@ -0,0 +1,250 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { Component, OnInit, Input, Output, EventEmitter, ViewChild } from '@angular/core'; +import { NgbActiveModal, NgbModal } from '@ng-bootstrap/ng-bootstrap'; +import { AdminService } from '../../admin.service'; +import { UserService } from 'src/app/shared/services/user/user.service'; +import { MatSort } from '@angular/material/sort'; +import { MatPaginator } from '@angular/material/paginator'; +import { MatTableDataSource } from '@angular/material'; +import { InformationModalComponent } from 'src/app/modals/information-modal/information-modal.component'; +import { ConfirmationModalComponent } from 'src/app/modals/confirmation-modal/confirmation-modal.component'; + + +@Component({ + selector: 'app-new-role', + templateUrl: './new-role.component.html', + styleUrls: ['./new-role.component.scss'] +}) +export class NewRoleComponent implements OnInit { + + showSpinner: boolean; + result: any; + @Input() role: any; + @Input() isEditMode: boolean; + @Input() availableRoles : any; + @Input() ociavailableRoleFunctions: any; + roleFunctionTableHeaders: Array<string> = []; + roleFunctions: Array<Object> = []; + roleFunctionsLenght: any; + finalSelectedRoleFunctions: any; + availableRoleFunctions: any; + @Output() passEntry: EventEmitter<any> = new EventEmitter(); + @ViewChild(MatPaginator, {}) paginator: MatPaginator; + @ViewChild(MatSort, {}) sort: MatSort; + roleFunctionDataSource = new MatTableDataSource(this.roleFunctions); + + constructor(public adminService:AdminService, public userService: UserService, public activeModal: NgbActiveModal, public ngbModal: NgbModal) { } + + ngOnInit() { + this.roleFunctionTableHeaders = ["roleFunctionName","active"]; + this.finalSelectedRoleFunctions = []; + this.availableRoleFunctions = []; + if(this.isEditMode && this.ociavailableRoleFunctions && this.ociavailableRoleFunctions.length > 0){ + this.availableRoleFunctions = this.setSelectedRoleFucntions(this.ociavailableRoleFunctions); + this.populateTableData(this.availableRoleFunctions) + } + } + + setSelectedRoleFucntions(ociavailableRoleFunctions: any) { + for (var i = 0; i < this.ociavailableRoleFunctions.length; i++) { + var availableRoleFunction = this.ociavailableRoleFunctions[i]; + availableRoleFunction['selected'] = false; + for (var j = 0; j < this.role.roleFunctions.length; j++) { + if (availableRoleFunction.code === this.role.roleFunctions[j].code + && availableRoleFunction.type === this.role.roleFunctions[j].type + && availableRoleFunction.action === this.role.roleFunctions[j].action) { + availableRoleFunction.selected = true; + } + } + this.availableRoleFunctions.push(availableRoleFunction); + } + return this.availableRoleFunctions; + } + + + toggleRoleFunction(_element) { + if (this.ociavailableRoleFunctions) { + for (var i = 0; i < this.ociavailableRoleFunctions.length; i++) { + var availableRoleFunction = this.ociavailableRoleFunctions[i]; + if (availableRoleFunction.selected && !this.finalSelectedRoleFunctions.includes(availableRoleFunction)) { + this.finalSelectedRoleFunctions.push(availableRoleFunction); + } + } + } + if (!_element.selected) { + for (var i = 0; i < this.finalSelectedRoleFunctions.length; i++) { + var availableRoleFunction = this.finalSelectedRoleFunctions[i]; + if (availableRoleFunction.code == _element.code + && availableRoleFunction.type == _element.type + && availableRoleFunction.action == _element.action) { + this.finalSelectedRoleFunctions.splice(i, 1); + } + } + } + } + + delRoleFunctionConfirmPopUp(roleFunction: any, roleId: any){ + const modalRef = this.ngbModal.open(InformationModalComponent); + modalRef.componentInstance.title = "Confirmation"; + modalRef.componentInstance.message = 'You are about to delete this Role Function : ' + roleFunction.name+ '. Click OK to continue.'; + modalRef.result.then((result) => { + if (result === 'Ok') { + let temproleFunctions = this.role.roleFunctions; + let index = 0; + for(let i=0; i<temproleFunctions.length; i++){ + if(temproleFunctions[i].code == roleFunction.code){ + break; + } + index = index + 1; + }; + temproleFunctions.splice(index,1); + this.populateTableData(temproleFunctions); + this.adminService.removeRoleFunction(roleFunction , roleId) + .subscribe(_data => { + this.result = _data + this.passEntry.emit(this.result); + }, error =>{ + this.openConfirmationModal('Error', error.message); + }); + } + }, (resut) => { + this.openConfirmationModal('Error', resut); + return; + }) + } + + populateTableData(roleFunctionsList: any){ + this.roleFunctionDataSource = new MatTableDataSource(roleFunctionsList); + this.roleFunctionDataSource.sort = this.sort; + this.roleFunctionDataSource.paginator = this.paginator; + } + + //Add Or Update Account. + saveChanges(){ + if(this.isEditMode){ + if (this.role.priority && this.role.priority != '' && isNaN(parseInt(this.role.priority))) { + let errorMsg = 'Priority must be an integer.'; + this.openConfirmationModal('Error', errorMsg); + } + //update the role object + this.showSpinner = true + this.role.roleFunctions = this.finalSelectedRoleFunctions; + let postData={ + role: this.role, + childRoles: this.role.childRoles, + roleFunctions : this.role.roleFunctions + }; + this.adminService.saveRole(postData, this.role.id) + .subscribe(_data => { + this.showSpinner = false; + this.result = _data + this.passEntry.emit(this.result); + this.ngbModal.dismissAll(); + }, error =>{ + this.openConfirmationModal('Error', error.message); + }); + }else{ + //create new Role Object + if (this.role.priority && this.role.priority != '' && isNaN(parseInt(this.role.priority))) { + let errorMsg = 'Priority must be an integer.'; + this.openConfirmationModal('Error', errorMsg); + } + let newRoleObj = { + 'id':null, + 'created':null, + 'modified':null, + 'createdId':null, + 'modifiedId':null, + 'rowNum':null, + 'auditUserId':null, + 'auditTrail':null, + 'name':this.role.name, + 'active':true, + 'priority':this.role.priority, + 'roleFunctions':null, + 'childRoles':null, + 'toggleActiveAltText':"Click to Activate Role ", + 'toggleActiveImage':" / static fusion images inactive.png ", + 'editUrl':" role.htm ? role_id = null", + }; + if(this.isRoleAlreadyExist(this.role.name)){ + //msg Role already exit + let errorMsg = "Role Name " + this.role.name +" is already present." + this.openConfirmationModal('Error', errorMsg); + }else{ + this.showSpinner = true + newRoleObj.childRoles = []; + newRoleObj.roleFunctions = []; + let postData={ + role: newRoleObj, + childRoles: newRoleObj.childRoles, + roleFunctions : newRoleObj.roleFunctions + }; + this.adminService.saveRole(postData, newRoleObj.id) + .subscribe(_data => { + this.showSpinner = false; + this.result = _data + this.passEntry.emit(this.result); + this.ngbModal.dismissAll(); + }, error =>{ + this.openConfirmationModal('Error', error.message); + }); + } + } + } + + isRoleAlreadyExist(currentRoleName: any){ + let roles = this.availableRoles; + if(roles && roles.length > 0){ + for(let i=0; i<roles.length; i++){ + if(roles[i].name === currentRoleName){ + return true; + } + } + } + return false; + } + + openConfirmationModal(_title: string, _message: string) { + const modalInfoRef = this.ngbModal.open(ConfirmationModalComponent); + modalInfoRef.componentInstance.title = _title; + modalInfoRef.componentInstance.message = _message; + } +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.html new file mode 100644 index 00000000..7d845fee --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.html @@ -0,0 +1,104 @@ +<!-- + ============LICENSE_START========================================== + ONAP Portal SDK + =================================================================== + Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + =================================================================== + + Unless otherwise specified, all software contained herein is licensed + under the Apache License, Version 2.0 (the "License"); + you may not use this software except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + Unless otherwise specified, all documentation contained herein is licensed + under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + you may not use this documentation except in compliance with the License. + You may obtain a copy of the License at + + https://creativecommons.org/licenses/by/4.0/ + + Unless required by applicable law or agreed to in writing, documentation + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + ============LICENSE_END============================================ + + --> + + <div class="main-container"> + <div id="page-content"> + <div class="ecomp-main-view-title"> + <h3 class="heading-page">Roles</h3> + <span class= "heading-small" *ngIf="isAppCentralized=='true'"><b>Please go to portal to Manage Roles.</b></span> + </div> + + <span class="ecomp-spinner" *ngIf="showSpinner"></span> + + <div class="table-search-div"> + <mat-form-field> + <input matInput type="text" (keyup)="applyFilter($event.target.value)" placeholder="Search in entire table"> + </mat-form-field> + + <button type="button" *ngIf="isAppCentralized=='false'" class="btn btn-primary new-role-button" (click)="openAddNewRoleModal('')"> + <i class="icon ion-md-person-add"></i>Add New Role + </button> + </div> + + <table mat-table [dataSource]="dataSource" matSort> + <ng-container matColumnDef="name"> + <th mat-header-cell *matHeaderCellDef mat-sort-header id="heading1"> Name</th> + <td mat-cell *matCellDef="let rowData"> {{rowData.name}} </td> + </ng-container> + + <ng-container matColumnDef="priority"> + <th mat-header-cell *matHeaderCellDef id="heading2"> Priority</th> + <td mat-cell *matCellDef="let rowData"> {{rowData.priority}} </td> + </ng-container> + + <ng-container matColumnDef="Edit"> + <th mat-header-cell *matHeaderCellDef id="heading3">{{roleHeaders[2]}} </th> + <td id="rowheader_t1_{{i}}" mat-cell *matCellDef="let rowData; let i=index;"> + <span class="icon-trash" id="{{i}}-button-role-edit" + (click)="openAddNewRoleModal(rowData)"> + <i class="ion ion-md-create"></i> + </span> + </td> + </ng-container> + + <ng-container matColumnDef="Active?"> + <th mat-header-cell *matHeaderCellDef id="heading4"> {{roleHeaders[3]}} </th> + <td mat-cell *matCellDef="let rowData"> + <mat-slide-toggle [(ngModel)]="rowData.active" (change)="toggleRole(rowData)"></mat-slide-toggle> + </td> + </ng-container> + + <ng-container matColumnDef="Delete?"> + <th mat-header-cell *matHeaderCellDef id="heading6"> {{roleHeaders[4]}} </th> + <td id="rowheader_t1_{{i}}" mat-cell *matCellDef="let rowData; let i=index;"> + <span class="icon-trash" id="{{i}}-button-role-remove" + (click)="delRoleConfirmPopUp(rowData)"> + <i class="icon ion-md-trash"></i> + </span> + </td> + </ng-container> + <tr mat-header-row *matHeaderRowDef="roleHeaders"></tr> + <tr mat-row *matRowDef="let rowData; columns: roleHeaders;"> + </table> + <mat-paginator [pageSizeOptions]="[5, 10, 25, 100]"></mat-paginator> + <span class="ecomp-spinner" *ngIf="showSpinner"></span> + <div> + <a (click)="getFunctions()" id="functions-link">Manage Role Functions</a><br><br> + </div> + </div> + </div> +
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.scss new file mode 100644 index 00000000..1a4d76ae --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.scss @@ -0,0 +1,120 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + + @import '~@angular/material/prebuilt-themes/deeppurple-amber.css'; +table { + width: 100%; +} + +.mat-form-field { + font-size: 14px; + width: 100%; +} + +td, th { + width: 25%; +} +.mat-form-field[_ngcontent-c4] { + font-size: 14px; + width: 20%; + float: right; +} + +td[_ngcontent-c4], th[_ngcontent-c4] { + width: 15%; +} + +.example-h2 { + margin: 10px; +} + +.example-section { + display: flex; + align-content: center; + align-items: center; + height: 60px; +} + +.example-margin { + margin: 10px; +} +body { + font-family: Roboto, Arial, sans-serif; + margin: 0; +} + +.basic-container { + padding: 30px; +} + +.version-info { + font-size: 8pt; + float: right; +} + +.icon-trash{ + cursor: pointer; +} + +.new-role-button{ + margin-left: 15px; + float: right; +} +#functions-link{ + cursor: pointer; text-decoration: underline; color: #007bff; +} + +:host::ng-deep .mat-form-field-wrapper{ + width: 28%; + float: right; + padding-top: 14px; +} + +.table-search-div{ + display: flex; +} + +.new-role-button{ + height: 38px; +} + +:host::ng-deep .mat-header-cell{ + font-weight: bold; + font-size: 14px; + color: #343a40; +}
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.spec.ts new file mode 100644 index 00000000..ab27b353 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.spec.ts @@ -0,0 +1,99 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Modification Copyright © 2020 IBM. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { async, ComponentFixture, TestBed } from '@angular/core/testing'; + +import { RolesComponent } from './roles.component'; +import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/core'; +import { MatTableModule } from '@angular/material'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; +import { Observable } from 'rxjs'; +import { NgbModule } from '@ng-bootstrap/ng-bootstrap'; +import { BrowserDynamicTestingModule } from '@angular/platform-browser-dynamic/testing'; +import { RouterTestingModule } from '@angular/router/testing'; +import { UserService } from '../../shared/services/user/user.service'; +import { InformationModalComponent } from '../../modals/information-modal/information-modal.component'; + +describe('RolesComponent', () => { + let component: RolesComponent; + let fixture: ComponentFixture<RolesComponent>; + let userService: UserService; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + schemas: [CUSTOM_ELEMENTS_SCHEMA], + declarations: [ + RolesComponent, + InformationModalComponent, + ], + imports:[ + MatTableModule, + HttpClientTestingModule, + NgbModule.forRoot(), + RouterTestingModule + ] + }) + TestBed.overrideModule(BrowserDynamicTestingModule,{ + set:{ + entryComponents:[InformationModalComponent] + } + }) + .compileComponents(); + })); + + beforeEach(() => { + fixture = TestBed.createComponent(RolesComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + userService=TestBed.get(UserService); + }); + + it('should test subscribe inside ngOnInit method',()=>{ + let spy=spyOn(userService,'getFunctionalMenuStaticDetailSession').and.returnValue(Observable.of('your data')) + component.ngOnInit(); + expect(spy).toHaveBeenCalled(); + }) + + it('should test delRoleConfirmPopUp method',()=>{ + component.delRoleConfirmPopUp('dummyargument'); + + }) +}); diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.ts new file mode 100644 index 00000000..8032aa18 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.component.ts @@ -0,0 +1,216 @@ +/*- + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ +import { Component, OnInit, ViewChild } from '@angular/core'; +import { AdminService } from '../admin.service'; +import { MatTableDataSource } from '@angular/material/table'; +import { MatSort } from '@angular/material/sort'; +import { MatPaginator } from '@angular/material/paginator'; +import { User } from 'src/app/shared/services/user/user'; +import { UserService } from 'src/app/shared/services/user/user.service'; +import { NgbModal, ModalDismissReasons } from '@ng-bootstrap/ng-bootstrap'; +import { InformationModalComponent } from 'src/app/modals/information-modal/information-modal.component'; +import { NewRoleComponent } from './new-role/new-role.component'; +import { Router } from '@angular/router'; + + +@Component({ + selector: 'app-roles', + templateUrl: './roles.component.html', + styleUrls: ['./roles.component.scss'] +}) +export class RolesComponent implements OnInit { + tableData: Array<object> = []; + roleHeaders: Array<string> = []; + constructor(public adminService:AdminService,public userService: UserService,private ngbModal: NgbModal,private _router: Router) { } + roleId; + response:any; + result:any; + roleInfo:any; + roleData:any; + ociavailableRoleFunctions; + availableRoleFunctions; + availableRoles; + dataSource: MatTableDataSource<[]>; + user:User; + isAppCentralized; + closeResult: string; + isEditMode: boolean = false; + showSpinner:boolean; + + @ViewChild(MatPaginator, {}) paginator: MatPaginator; + @ViewChild(MatSort, {}) sort: MatSort; + + + ngOnInit() { + this.roleHeaders = ["name","priority","Edit","Active?","Delete?"]; + this.showSpinner = false; + this.roleId=undefined; + this.getRole(this.roleId); + let result = this.userService.getFunctionalMenuStaticDetailSession(); + let user; + result.subscribe(user => { + this.user = user; + this.isAppCentralized = this.user.isAppCentralized; + }); + } + + getRole(roleId:any){ + this.showSpinner = true; + this.response = this.adminService.getRole(roleId); + this.response.subscribe(data => { + this.result = data; + this.roleInfo = JSON.parse(this.result.data); + this.roleData =JSON.parse(this.roleInfo.role); + this.ociavailableRoleFunctions =JSON.parse(this.roleInfo.availableRoleFunctions); + this.availableRoleFunctions=[]; + for( let availableFun of this.ociavailableRoleFunctions){ + let availableRoleFunction = availableFun; + availableRoleFunction.selected = false; + for( let availableFunc of this.roleData.roleFunctions){ + if(availableFun.code === availableFunc.code){ + availableRoleFunction.selected = true; + } + } + this.availableRoleFunctions.push(availableRoleFunction); + } + this.availableRoles=JSON.parse(this.roleInfo.availableRoles); + this.dataSource = new MatTableDataSource(this.availableRoles); + this.dataSource.paginator = this.paginator; + this.dataSource.sort = this.sort; + this.showSpinner = false; + }); + } + + delRoleConfirmPopUp(item: any) { + const modalRef = this.ngbModal.open(InformationModalComponent); + modalRef.componentInstance.title = 'Confirmation'; + let response; + modalRef.componentInstance.message = `Are you sure you want to delete ${item.name} ?`; + modalRef.result.then((result) => { + if (result === 'Ok') { + this.adminService.deleteRole(item).subscribe(data => { + this.showSpinner = true; + response = data; + this.availableRoles = response.availableRoles; + this.dataSource = new MatTableDataSource(this.availableRoles); + this.dataSource.paginator = this.paginator; + this.dataSource.sort = this.sort; + this.showSpinner = false; + }) + } + }, (reason) => { + this.closeResult = `Dismissed ${this.getDismissReason(reason)}`; + }); + } + + private getDismissReason(reason: any): string { + if (reason === ModalDismissReasons.ESC) { + return 'by pressing ESC'; + } else if (reason === ModalDismissReasons.BACKDROP_CLICK) { + return 'by clicking on a backdrop'; + } else { + return `with: ${reason}`; + } + + } + + /** + * openAddNewRoleModal + * @param rowData + */ + openAddNewRoleModal(rowData: any){ + const modalRef = this.ngbModal.open(NewRoleComponent, { size: 'lg' }); + modalRef.componentInstance.title = 'Role Details'; + modalRef.componentInstance.availableRoles = this.availableRoles; + modalRef.componentInstance.ociavailableRoleFunctions = this.ociavailableRoleFunctions; + if(rowData != 'undefined' && rowData){ + modalRef.componentInstance.role = rowData; + this.isEditMode = true; + modalRef.componentInstance.isEditMode = true; + }else{ + modalRef.componentInstance.role = {}; + this.isEditMode = false; + modalRef.componentInstance.isEditMode = false; + } + modalRef.componentInstance.passEntry.subscribe((receivedEntry: any) => { + if(receivedEntry){ + this.availableRoles = []; + this.getRole(this.roleId); + } + }); + } + + toggleRole(_element) { + let activeOrInactive = (_element.active) ? 'activate' : 'inactivate'; + const modalInfoRef = this.ngbModal.open(InformationModalComponent); + modalInfoRef.componentInstance.title = 'Confirmation'; + modalInfoRef.componentInstance.message = 'You are about to ' + activeOrInactive + ' the role ' + _element.name + '. Do you want to continue?'; + modalInfoRef.result.then((_res) => { + if (_res === 'Ok') { + this.showSpinner = true; + let postData={ + role: _element, + childRoles: _element.childRoles, + roleFunctions : _element.roleFunctions + }; + this.adminService.saveRole(postData, _element.id) + .subscribe( _data => { + this.showSpinner = false; + }, (response) => { + _element.active = !_element.active; + const modalErrorRef = this.ngbModal.open(InformationModalComponent); + modalErrorRef.componentInstance.title = 'Error'; + modalErrorRef.componentInstance.message = 'Error while saving. ' + response.restCallStatus; + }); + } else { + _element.active = !_element.active; + } + + }, (result) => { + + }) + } + + applyFilter(filterValue: string) { + this.dataSource.filter = filterValue.trim().toLowerCase(); + } + + getFunctions() { + this._router.navigate(['v2/admin/role_function_list']); +} +}
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.module.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.module.ts new file mode 100644 index 00000000..5986e863 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/roles/roles.module.ts @@ -0,0 +1,19 @@ +import { NgModule } from '@angular/core'; +import { CommonModule } from '@angular/common'; +import { RolesComponent } from './roles.component'; +import {NewRoleComponent} from './new-role/new-role.component'; +import {MatFormFieldModule, MatPaginatorModule, MatSlideToggleModule, MatTableModule} from '@angular/material'; +import {FormsModule} from '@angular/forms'; + +@NgModule({ + declarations: [RolesComponent, NewRoleComponent], + imports: [ + CommonModule, + MatTableModule, + MatFormFieldModule, + MatSlideToggleModule, + MatPaginatorModule, + FormsModule + ] +}) +export class RolesModule { } diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.html b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.html new file mode 100644 index 00000000..ac56a13f --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.html @@ -0,0 +1,49 @@ +<!-- + ============LICENSE_START========================================== + ONAP Portal SDK + =================================================================== + Copyright (C) 2019 AT&T Intellectual Property. All rights reserved. + =================================================================== + + Unless otherwise specified, all software contained herein is licensed + under the Apache License, Version 2.0 (the "License"); + you may not use this software except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + Unless otherwise specified, all documentation contained herein is licensed + under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + you may not use this documentation except in compliance with the License. + You may obtain a copy of the License at + + https://creativecommons.org/licenses/by/4.0/ + + Unless required by applicable law or agreed to in writing, documentation + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + + ============LICENSE_END============================================ + +--> + +<div class="main-container"> + <div id="page-content"> + <div> + <h3 class="heading-page" id="Usage">Current Usage</h3> + </div> + <p class="heading-small"> + The following table shows all current user sessions. Click the icon to end a user's session. + </p> + <!-- RDP datatable --> + <rdp-data-table [data]="users" [settings]="settings"></rdp-data-table> + </div> +</div>
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.scss b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.scss new file mode 100644 index 00000000..8712b3b2 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.scss @@ -0,0 +1,64 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + + table { + width: 100%; +} + +.mat-form-field { + font-size: 14px; + width: 100%; +} + +td, th { + width: 25%; +} +.mat-form-field[_ngcontent-c4] { + font-size: 14px; + width: 20%; + float: right; +} +td[_ngcontent-c4], th[_ngcontent-c4] { +width: 15%; +} + +:host::ng-deep .mat-header-cell{ + font-weight: bold; + font-size: 14px; + color: #343a40; +}
\ No newline at end of file diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.spec.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.spec.ts new file mode 100644 index 00000000..01f31669 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.spec.ts @@ -0,0 +1,70 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Modification Copyright © 2020 IBM. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { async, ComponentFixture, TestBed } from '@angular/core/testing'; + +import { UsageComponent } from './usage.component'; +import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/core'; +import { HttpClientTestingModule } from '@angular/common/http/testing'; + +describe('UsageComponent', () => { + let component: UsageComponent; + let fixture: ComponentFixture<UsageComponent>; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + declarations: [ UsageComponent ], + schemas:[CUSTOM_ELEMENTS_SCHEMA], + imports:[HttpClientTestingModule] + }) + .compileComponents(); + })); + + beforeEach(() => { + fixture = TestBed.createComponent(UsageComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.ts new file mode 100644 index 00000000..d5121909 --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.component.ts @@ -0,0 +1,82 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { Component, OnInit } from '@angular/core'; +import { AdminService } from '../admin.service'; +import { Column, DataTableSettings, ColumnTypes } from 'portalsdk-tag-lib'; + +@Component({ + selector: 'app-usage', + templateUrl: './usage.component.html', + styleUrls: ['./usage.component.scss'] +}) +export class UsageComponent implements OnInit { + + response: any; + result: any; + users: any; + public settings; + public columns: any = []; + + constructor(public adminService: AdminService) { } + + ngOnInit() { + this.adminService.getUsageList() + .subscribe(data => { + this.response = data; + this.users = JSON.parse(this.response.data); + //adding Current Session property to each users + this.users.forEach(element => { + Object.assign(element, {"currentSession":"Current Session"}); + }); + this.columns.push(new Column("id", "User Id", ColumnTypes.TEXT, false, null)); + this.columns.push(new Column("lastName", "User Name",ColumnTypes.TEXT, false, null)); + this.columns.push(new Column("email", "Email", ColumnTypes.TEXT, false, null)); + this.columns.push(new Column("lastAccess", " Last Access Time (minutes)", ColumnTypes.TEXT, false, null)); + this.columns.push(new Column("remaining", "Time Remaining (minutes)", ColumnTypes.TEXT, false, null)); + this.columns.push(new Column("currentSession", "Expire User Session?", ColumnTypes.TEXT, false, null)); + + this.settings = new DataTableSettings() + this.settings.columns = this.columns; + this.settings.isPaginationEnabled = false; + this.settings.isReadOnly = true; + this.settings.isTableSearchEnabled = false; + }); + } + +} diff --git a/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.module.ts b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.module.ts new file mode 100644 index 00000000..6043d5df --- /dev/null +++ b/ecomp-sdk/epsdk-app-overlay/src/main/webapp/ngapp/src/app/admin/usage/usage.module.ts @@ -0,0 +1,51 @@ +/* + * ============LICENSE_START========================================== + * ONAP Portal SDK + * =================================================================== + * Copyright © 2019 AT&T Intellectual Property. All rights reserved. + * =================================================================== + * + * Unless otherwise specified, all software contained herein is licensed + * under the Apache License, Version 2.0 (the "License"); + * you may not use this software except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Unless otherwise specified, all documentation contained herein is licensed + * under the Creative Commons License, Attribution 4.0 Intl. (the "License"); + * you may not use this documentation except in compliance with the License. + * You may obtain a copy of the License at + * + * https://creativecommons.org/licenses/by/4.0/ + * + * Unless required by applicable law or agreed to in writing, documentation + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * ============LICENSE_END============================================ + * + * + */ + +import { NgModule } from '@angular/core'; +import { CommonModule } from '@angular/common'; +import { UsageComponent } from './usage.component'; +import { RdpModule } from 'portalsdk-tag-lib'; + +@NgModule({ + declarations: [UsageComponent], + imports: [ + CommonModule, + RdpModule + ] +}) +export class UsageModule { } |