summaryrefslogtreecommitdiffstats
path: root/vid-webpack-master/src/app/shared
diff options
context:
space:
mode:
authorMateusz Gołuchowski <mateusz.goluchowski@nokia.com>2020-11-05 10:11:08 +0100
committerIkram Ikramullah <ikram@research.att.com>2020-11-12 14:21:25 +0000
commitd74f6cc4a47f4ebe94c6143f5ffb12b7f47c8fb6 (patch)
tree659d245c2d60edd94c19f06683916e0d37a9c79b /vid-webpack-master/src/app/shared
parent182d036de5a7d64250fc5058f3cf361b9d823282 (diff)
Extend Modern UI for pnf usecase
Implemented functionalities to manage PNFs in modern UI: - Adding, removing, editing PNFs - PNF default generation based on 'min_instances' property - FE sends proper instantiation request to BE This is still impossible to deploy service with PNFs as VID's BE logic must be adjusted to generate proper request to SO as described in VID-695. Issue-ID: VID-694 Signed-off-by: Mateusz Goluchowski <mateusz.goluchowski@nokia.com> Change-Id: I5285ac2ab5e95665244ca29c6549249d9330b1ed
Diffstat (limited to 'vid-webpack-master/src/app/shared')
-rw-r--r--vid-webpack-master/src/app/shared/components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator.spec.ts175
-rw-r--r--vid-webpack-master/src/app/shared/components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator.ts87
-rw-r--r--vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.spec.ts351
-rw-r--r--vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.ts49
-rw-r--r--vid-webpack-master/src/app/shared/models/pnfInstance.ts1
-rw-r--r--vid-webpack-master/src/app/shared/models/pnfModel.ts5
-rw-r--r--vid-webpack-master/src/app/shared/models/serviceInstance.ts4
-rw-r--r--vid-webpack-master/src/app/shared/services/aaiService/aai.service.spec.ts37
-rw-r--r--vid-webpack-master/src/app/shared/services/aaiService/aai.service.ts10
-rw-r--r--vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.spec.ts234
-rw-r--r--vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.ts86
-rw-r--r--vid-webpack-master/src/app/shared/shared.module.ts4
-rw-r--r--vid-webpack-master/src/app/shared/storeUtil/utils/main.reducer.ts4
-rw-r--r--vid-webpack-master/src/app/shared/storeUtil/utils/network/network.reducers.ts2
-rw-r--r--vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.actions.ts88
-rw-r--r--vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.reducers.spec.ts172
-rw-r--r--vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.reducers.ts87
-rw-r--r--vid-webpack-master/src/app/shared/storeUtil/utils/reducersHelper.ts24
-rw-r--r--vid-webpack-master/src/app/shared/storeUtil/utils/vnf/vnf.reducers.ts27
-rw-r--r--vid-webpack-master/src/app/shared/storeUtil/utils/vrf/vrf.reducer.ts2
20 files changed, 1374 insertions, 75 deletions
diff --git a/vid-webpack-master/src/app/shared/components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator.spec.ts b/vid-webpack-master/src/app/shared/components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator.spec.ts
new file mode 100644
index 000000000..e510eaad2
--- /dev/null
+++ b/vid-webpack-master/src/app/shared/components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator.spec.ts
@@ -0,0 +1,175 @@
+import {getTestBed, TestBed} from '@angular/core/testing';
+import {HttpClientTestingModule, HttpTestingController} from '@angular/common/http/testing';
+import {NgRedux} from '@angular-redux/store';
+import {FormControlNames} from "../service.control.generator";
+import {ControlGeneratorUtil} from "../control.generator.util.service";
+import {AaiService} from "../../../../services/aaiService/aai.service";
+import {GenericFormService} from "../../generic-form.service";
+import {FormBuilder} from "@angular/forms";
+import {FormControlModel} from "../../../../models/formControlModels/formControl.model";
+import {LogService} from "../../../../utils/log/log.service";
+import {FeatureFlagsService} from "../../../../services/featureFlag/feature-flags.service";
+import {SharedControllersService} from "../sharedControlles/shared.controllers.service";
+import {PnfControlGenerator} from "./pnf.control.generator";
+import {MockNgRedux} from "@angular-redux/store/testing";
+
+class MockFeatureFlagsService {
+}
+
+class MockAppStore<T> {
+ getState() {
+ return {
+ global: {
+ flags: {
+ "FLAG_NETWORK_TO_ASYNC_INSTANTIATION": false,
+ "FLAG_SHOW_ASSIGNMENTS": true,
+ "FLAG_FABRIC_CONFIGURATION_ASSIGNMENTS": true,
+ "FLAG_SHOW_VERIFY_SERVICE": false,
+ "FLAG_SERVICE_MODEL_CACHE": true,
+ "FLAG_ADD_MSO_TESTAPI_FIELD": true
+ }
+ },
+ service: {
+ serviceHierarchy: {
+ 'serviceId': {
+ 'pnfs': {
+ 'pnfName': {}
+ }
+ }
+ },
+ serviceInstance: {
+ 'serviceId': {
+ 'pnfs': {
+ 'pnfName': {}
+ }
+ }
+ }
+ }
+ }
+ }
+}
+
+describe('PNF Control Generator', () => {
+ let injector;
+ let service: PnfControlGenerator;
+ let httpMock: HttpTestingController;
+
+ beforeAll(done => (async () => {
+ TestBed.configureTestingModule({
+ imports: [HttpClientTestingModule],
+ providers: [
+ MockNgRedux,
+ PnfControlGenerator,
+ GenericFormService,
+ ControlGeneratorUtil,
+ SharedControllersService,
+ AaiService,
+ FormBuilder,
+ LogService,
+ {provide: FeatureFlagsService, useClass: MockFeatureFlagsService},
+ {provide: NgRedux, useClass: MockAppStore}]
+ });
+ await TestBed.compileComponents();
+
+ injector = getTestBed();
+ service = injector.get(PnfControlGenerator);
+ httpMock = injector.get(HttpTestingController);
+
+ })().then(done).catch(done.fail));
+
+ test('getMacroFormControls check for mandatory controls', () => {
+ const serviceId = "serviceId";
+ const pnfName = "pnfName";
+ const pnfStoreKey = "pnfStoreKey";
+ const mandatoryControls: string[] = [
+ FormControlNames.INSTANCE_NAME,
+ FormControlNames.PRODUCT_FAMILY_ID
+ ];
+
+ const controls: FormControlModel[] = service.getMacroFormControls(serviceId, pnfStoreKey, pnfName, []);
+
+ for (let i = 0; i < mandatoryControls.length; i++) {
+ let requiredExist = controls.find(ctrl => ctrl.controlName === mandatoryControls[i]).validations.find(item => item.validatorName === 'required');
+ expect(requiredExist).toBeDefined();
+ }
+ });
+
+ test('should provide empty array on getMacroFormControls when serviceId, pnfName and pnfStoreKey equals to null', () => {
+ let pnfStoreKey = null;
+ const serviceId = null;
+ const pnfName: string = null;
+
+ const controls: FormControlModel[] = service.getMacroFormControls(serviceId, pnfStoreKey, pnfName, []);
+
+ expect(controls).toEqual([]);
+ });
+
+ test('getAlacartFormControls check for mandatory controls', () => {
+ const serviceId = "serviceId";
+ const pnfName = "pnfName";
+ const pnfStoreKey = "pnfStoreKey";
+ const mandatoryControls: string[] = [
+ FormControlNames.INSTANCE_NAME,
+ 'platformName',
+ 'lineOfBusiness',
+ 'rollbackOnFailure'
+ ];
+
+ const controls: FormControlModel[] = service.getAlaCarteFormControls(serviceId, pnfStoreKey, pnfName, []);
+
+ for (let i = 0; i < mandatoryControls.length; i++) {
+ let requiredExist = controls.find(ctrl => ctrl.controlName === mandatoryControls[i]).validations.find(item => item.validatorName === 'required');
+ expect(requiredExist).toBeDefined();
+ }
+ });
+
+ test('should provide empty array on getAlaCarteFormControls when serviceId, pnfName and pnfStoreKey equals to null', () => {
+ let pnfStoreKey = null;
+ const serviceId = null;
+ const pnfName: string = null;
+
+ const result: FormControlModel[] = service.getAlaCarteFormControls(serviceId, pnfStoreKey, pnfName, []);
+
+ expect(result).toEqual([]);
+ });
+
+
+ test('getMacroFormControls should return the correct order of controls', () => {
+ const serviceId = "serviceId";
+ const pnfName = "pnfName";
+ const pnfStoreKey = "pnfStoreKey";
+ const controls: FormControlModel[] = service.getMacroFormControls(serviceId, pnfStoreKey, pnfName, []);
+
+ const controlsOrderNames = [
+ FormControlNames.INSTANCE_NAME,
+ FormControlNames.PRODUCT_FAMILY_ID,
+ 'platformName',
+ 'lineOfBusiness'];
+
+ expect(controls.length).toEqual(4);
+ for (let i = 0; i < controls.length; i++) {
+ expect(controls[i].controlName).toEqual(controlsOrderNames[i]);
+ }
+ });
+
+ test('getAlacarteFormControls should return the correct order of controls', () => {
+ const serviceId = "serviceId";
+ const pnfName = "pnfName";
+ const pnfStoreKey = "pnfStoreKey";
+ const controls: FormControlModel[] = service.getAlaCarteFormControls(serviceId, pnfStoreKey, pnfName, []);
+
+ const controlsOrderNames = [
+ FormControlNames.INSTANCE_NAME,
+ FormControlNames.PRODUCT_FAMILY_ID,
+ 'platformName',
+ 'lineOfBusiness',
+ 'rollbackOnFailure'
+ ];
+
+ expect(controls.length).toEqual(5);
+ for (let i = 0; i < controls.length; i++) {
+ expect(controls[i].controlName).toEqual(controlsOrderNames[i]);
+ }
+ });
+});
+
diff --git a/vid-webpack-master/src/app/shared/components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator.ts b/vid-webpack-master/src/app/shared/components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator.ts
new file mode 100644
index 000000000..7e3381701
--- /dev/null
+++ b/vid-webpack-master/src/app/shared/components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator.ts
@@ -0,0 +1,87 @@
+import {Injectable} from "@angular/core";
+import {GenericFormService} from "../../generic-form.service";
+import {AaiService} from "../../../../services/aaiService/aai.service";
+import {NgRedux} from "@angular-redux/store";
+import {HttpClient} from "@angular/common/http";
+import {ControlGeneratorUtil} from "../control.generator.util.service";
+import {FormControlModel} from "../../../../models/formControlModels/formControl.model";
+import {LogService} from "../../../../utils/log/log.service";
+import {PNFModel} from "../../../../models/pnfModel";
+import {AppState} from "../../../../store/reducers";
+import * as _ from 'lodash';
+import {SharedControllersService} from "../sharedControlles/shared.controllers.service";
+
+@Injectable()
+export class PnfControlGenerator {
+ aaiService: AaiService;
+ constructor(private genericFormService: GenericFormService,
+ private _basicControlGenerator: ControlGeneratorUtil,
+ private _sharedControllersService : SharedControllersService,
+ private store: NgRedux<AppState>,
+ private http: HttpClient,
+ private _aaiService: AaiService,
+ private _logService: LogService) {
+ this.aaiService = _aaiService;
+ }
+
+ getPnfInstance = (serviceId: string, pnfStoreKey: string): any => {
+ let pnfInstance = null;
+ if (this.store.getState().service.serviceInstance[serviceId] && _.has(this.store.getState().service.serviceInstance[serviceId].pnfs, pnfStoreKey)) {
+ pnfInstance = Object.assign({}, this.store.getState().service.serviceInstance[serviceId].pnfs[pnfStoreKey]);
+ }
+ return pnfInstance;
+ };
+
+ getMacroFormControls(serviceId: string, pnfStoreKey: string, pnfName: string, dynamicInputs?: any[]): FormControlModel[] {
+ pnfStoreKey = _.isNil(pnfStoreKey) ? pnfName : pnfStoreKey;
+
+ if (_.isNil(serviceId) || _.isNil(pnfStoreKey) || _.isNil(pnfName)) {
+ this._logService.error('should provide serviceId, pnfName, pnfStoreKey', serviceId);
+ return [];
+ }
+ const pnfInstance = this._basicControlGenerator.retrieveInstanceIfUpdateMode(this.store,this.getPnfInstance(serviceId, pnfStoreKey));
+ const pnfModel = new PNFModel(this.store.getState().service.serviceHierarchy[serviceId].pnfs[pnfName]);
+ let result: FormControlModel[] = [];
+ const flags = this.store.getState().global.flags;
+
+ if (!_.isNil(pnfModel)) {
+ const isPlatformMultiSelected = flags['FLAG_2002_PNF_PLATFORM_MULTI_SELECT'];
+ const isLobMultiSelected = flags['FLAG_2006_PNF_LOB_MULTI_SELECT'];
+
+ result.push(this.getInstanceName(pnfInstance, serviceId, pnfName, pnfModel.isEcompGeneratedNaming));
+ result.push(this._sharedControllersService.getProductFamilyControl(pnfInstance, result, true));
+ result.push(this._sharedControllersService.getPlatformMultiselectControl(pnfInstance, result, isPlatformMultiSelected));
+ result.push(this._sharedControllersService.getLobMultiselectControl(pnfInstance, isLobMultiSelected));
+ }
+ return result;
+ }
+
+ getAlaCarteFormControls(serviceId: string, pnfStoreKey: string, pnfName: string, dynamicInputs?: any[]): FormControlModel[] {
+ pnfStoreKey = _.isNil(pnfStoreKey) ? pnfName : pnfStoreKey;
+ if (_.isNil(serviceId) || _.isNil(pnfStoreKey) || _.isNil(pnfName)) {
+ this._logService.error('should provide serviceId, pnfName, pnfStoreKey', serviceId);
+ return [];
+ }
+
+ let result: FormControlModel[] = [];
+ const pnfInstance = this._basicControlGenerator.retrieveInstanceIfUpdateMode(this.store,this.getPnfInstance(serviceId, pnfStoreKey));
+ const pnfModel = new PNFModel(this.store.getState().service.serviceHierarchy[serviceId].pnfs[pnfName]);
+ const flags = this.store.getState().global.flags;
+
+ if (!_.isNil(pnfModel)) {
+ const isPlatformMultiSelected = flags['FLAG_2002_VNF_PLATFORM_MULTI_SELECT'];
+ const isLobMultiSelected = flags['FLAG_2006_VNF_LOB_MULTI_SELECT'];
+ result.push(this.getInstanceName(pnfInstance, serviceId, pnfName, pnfModel.isEcompGeneratedNaming));
+ result.push(this._sharedControllersService.getProductFamilyControl(pnfInstance, result, true));
+ result.push(this._sharedControllersService.getPlatformMultiselectControl(pnfInstance, result, isPlatformMultiSelected));
+ result.push(this._sharedControllersService.getLobMultiselectControl(pnfInstance,isLobMultiSelected));
+ result.push(this._sharedControllersService.getRollbackOnFailureControl(pnfInstance));
+ }
+ return result;
+ }
+
+ getInstanceName(instance : any, serviceId : string, pnfName : string, isEcompGeneratedNaming: boolean): FormControlModel {
+ const pnfModel : PNFModel = this.store.getState().service.serviceHierarchy[serviceId].pnfs[pnfName];
+ return this._sharedControllersService.getInstanceNameController(instance, serviceId, isEcompGeneratedNaming, pnfModel);
+ }
+}
diff --git a/vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.spec.ts b/vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.spec.ts
new file mode 100644
index 000000000..bae5aee61
--- /dev/null
+++ b/vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.spec.ts
@@ -0,0 +1,351 @@
+import {DefaultDataGeneratorService} from "../../../../services/defaultDataServiceGenerator/default.data.generator.service";
+import {NgRedux} from "@angular-redux/store";
+import {IframeService} from "../../../../utils/iframe.service";
+import {VfModulePopupService} from "../vfModule/vfModule.popup.service";
+import {FormBuilder} from "@angular/forms";
+import {GenericFormService} from "../../../genericForm/generic-form.service";
+import {BasicPopupService} from "../basic.popup.service";
+import {AaiService} from "../../../../services/aaiService/aai.service";
+import {LogService} from "../../../../utils/log/log.service";
+import {HttpClient} from "@angular/common/http";
+import {ControlGeneratorUtil} from "../../../genericForm/formControlsServices/control.generator.util.service";
+import {PnfControlGenerator} from "../../../genericForm/formControlsServices/pnfGenerator/pnf.control.generator";
+import {UUIDData} from "../../generic-form-popup.component";
+import {FeatureFlagsService} from "../../../../services/featureFlag/feature-flags.service";
+import {getTestBed, TestBed} from "@angular/core/testing";
+import {VfModuleUpgradePopupService} from "../vfModuleUpgrade/vfModule.upgrade.popuop.service";
+import {SharedControllersService} from "../../../genericForm/formControlsServices/sharedControlles/shared.controllers.service";
+import {PnfPopupService} from "../pnf/pnf.popup.service";
+import {AppState} from "../../../../store/reducers";
+
+class MockAppStore<T> {
+}
+
+class MockReduxStore<T> {
+ dispatch() {}
+ getState() {
+ return {
+ "global": {
+ "flags": {
+ "FLAG_NETWORK_TO_ASYNC_INSTANTIATION": false,
+ "FLAG_SHOW_ASSIGNMENTS": true,
+ "FLAG_FABRIC_CONFIGURATION_ASSIGNMENTS": true,
+ "FLAG_SHOW_VERIFY_SERVICE": false,
+ "FLAG_SERVICE_MODEL_CACHE": true,
+ "FLAG_ADD_MSO_TESTAPI_FIELD": true
+ }
+ },
+ "service": {
+ "serviceHierarchy": {
+ "serviceId": {
+ "service": {
+ "uuid": "6e59c5de-f052-46fa-aa7e-2fca9d674c44",
+ "invariantUuid": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "name": "action-data",
+ "version": "1.0",
+ "toscaModelURL": null,
+ "category": "Emanuel",
+ "serviceType": "",
+ "serviceRole": "",
+ "description": "action-data",
+ "serviceEcompNaming": "false",
+ "instantiationType": "Macro",
+ "vidNotions": {
+ "instantiationType": "Macro"
+ },
+ },
+ "globalSubscriberId": "subscriberId",
+ "pnfs": {
+ "pnfInstanceV1": {
+ "name": "pnfName",
+ "pnfStoreKey": "pnfInstanceV1",
+ "version": "1.0",
+ "description": "PNF description",
+ "uuid": "0903e1c0-8e03-4936-b5c2-260653b96413",
+ "invariantUuid": "00beb8f9-6d39-452f-816d-c709b9cbb87d"
+ },
+ "pnfInstanceV2": {
+ "name": "pnfName2",
+ "pnfStoreKey": "pnfInstanceV2"
+ }
+ },
+ "modelInfo": {
+ "modelInvariantId": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "modelVersionId": "6b528779-44a3-4472-bdff-9cd15ec93450",
+ "modelName": "action-data",
+ "modelVersion": "1.0",
+ "uuid": "6b528779-44a3-4472-bdff-9cd15ec93450"
+ },
+ "instanceName": "InstanceName",
+ "owningEntityId": "d61e6f2d-12fa-4cc2-91df-7c244011d6fc",
+ "productFamilyId": "17cc1042-527b-11e6-beb8-9e71128cae77",
+ "lcpCloudRegionId": "AAIAIC25",
+ "tenantId": "092eb9e8e4b7412e8787dd091bc58e86",
+ "aicZoneId": "JAG1",
+ "projectName": null,
+ "rollbackOnFailure": "true",
+ "aicZoneName": "YUDFJULP-JAG1",
+ "owningEntityName": "WayneHolland",
+ "testApi": "GR_API",
+ "tenantName": "USP-SIP-IC-24335-T-01",
+ "bulkSize": 1,
+ "isALaCarte": false,
+ "name": "action-data",
+ "version": "1.0",
+ "description": "",
+ "category": "",
+ "uuid": "6b528779-44a3-4472-bdff-9cd15ec93450",
+ "invariantUuid": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "serviceType": "",
+ "serviceRole": "",
+ "isMultiStepDesign": false
+ }
+ },
+ "serviceInstance": {
+ "serviceId": {
+ "globalSubscriberId": "subscriberId",
+ "pnfs": {
+ "pnfInstanceV1": {
+ "name": "pnfName",
+ "pnfStoreKey": "pnfInstanceV1"
+ },
+ "pnfInstanceV2": {
+ "name": "pnfName2",
+ "pnfStoreKey": "pnfInstanceV2"
+ }
+ },
+ "modelInfo": {
+ "modelInvariantId": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "modelVersionId": "6b528779-44a3-4472-bdff-9cd15ec93450",
+ "modelName": "action-data",
+ "modelVersion": "1.0",
+ "uuid": "6b528779-44a3-4472-bdff-9cd15ec93450"
+ },
+ "instanceName": "InstanceName",
+ "owningEntityId": "d61e6f2d-12fa-4cc2-91df-7c244011d6fc",
+ "productFamilyId": "17cc1042-527b-11e6-beb8-9e71128cae77",
+ "lcpCloudRegionId": "AAIAIC25",
+ "tenantId": "092eb9e8e4b7412e8787dd091bc58e86",
+ "aicZoneId": "JAG1",
+ "projectName": null,
+ "rollbackOnFailure": "true",
+ "aicZoneName": "YUDFJULP-JAG1",
+ "owningEntityName": "WayneHolland",
+ "testApi": "GR_API",
+ "tenantName": "USP-SIP-IC-24335-T-01",
+ "bulkSize": 1,
+ "isALaCarte": false,
+ "name": "action-data",
+ "version": "1.0",
+ "description": "",
+ "category": "",
+ "uuid": "6b528779-44a3-4472-bdff-9cd15ec93450",
+ "invariantUuid": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "serviceType": "",
+ "serviceRole": "",
+ "isMultiStepDesign": false
+ }
+ },
+ "subscribers": [
+ {
+ "id": "someSubscriberId",
+ "name": "someSubscriberName",
+ "isPermitted": true
+ },
+ {
+ "id": "subscriberId",
+ "name": "subscriberName",
+ "isPermitted": true
+ },
+ {
+ "id": "subscriberId2",
+ "name": "subscriberName2",
+ "isPermitted": true
+ }
+ ]
+ }
+ }
+ }
+}
+
+class MockFeatureFlagsService {
+}
+
+describe('pnf new popup service', () => {
+ let injector;
+ let service: PnfPopupService;
+ let store: NgRedux<AppState>;
+
+
+ beforeAll(done => (async () => {
+ TestBed.configureTestingModule({
+ providers: [
+ PnfPopupService,
+ DefaultDataGeneratorService,
+ GenericFormService,
+ FormBuilder,
+ IframeService,
+ {provide: FeatureFlagsService, useClass: MockFeatureFlagsService},
+ AaiService,
+ LogService,
+ BasicPopupService,
+ VfModulePopupService,
+ VfModuleUpgradePopupService,
+ ControlGeneratorUtil,
+ SharedControllersService,
+ PnfControlGenerator,
+ {provide: NgRedux, useClass: MockReduxStore},
+ {provide: HttpClient, useClass: MockAppStore},
+ ]
+ });
+ await TestBed.compileComponents();
+
+ injector = getTestBed();
+ store = injector.get(NgRedux);
+ service = injector.get(PnfPopupService);
+
+ })().then(done).catch(done.fail));
+
+ test('getGenericFormPopupDetails returns the FormPopupDetails object', () => {
+ const serviceId: string = 'serviceId';
+ const pnfModelName: string = 'pnfInstanceV2';
+ const pnfStoreKey: string = 'pnfInstanceV2';
+ let uuidData: UUIDData = <any>{
+ serviceId: "serviceId",
+ modelName: "pnfInstanceV2",
+ pnfStoreKey: "pnfInstanceV2"
+ };
+
+ const formPopupDetailsObject = service.getGenericFormPopupDetails(serviceId, pnfModelName, pnfStoreKey, null, uuidData, true);
+
+ expect(formPopupDetailsObject).toBeDefined();
+ }
+ );
+
+ test('getInstance with empty storekey should be created', () => {
+ const serviceId: string = 'serviceId';
+ const pnfModelName: string = 'pnfInstanceV1';
+
+ const newInstance = service.getInstance(serviceId, pnfModelName, null);
+
+ expect(newInstance).toBeDefined();
+ expect(newInstance.pnfStoreKey).toBeNull();
+ });
+
+ test('getInstance with not empty storekey should return existing instance with the same model name as store key', () => {
+ const serviceId: string = 'serviceId';
+ const pnfModelName: string = 'pnfInstanceV1';
+ const pnfStoreKey: string = 'pnfInstanceV2';
+
+ const newInstance = service.getInstance(serviceId, pnfModelName, pnfStoreKey);
+
+ expect(newInstance).toBeDefined();
+ expect(newInstance.pnfStoreKey).toEqual('pnfInstanceV2');
+ });
+
+ test('getModelInformation pnf should update modelInformations', () => {
+ const serviceId: string = 'serviceId';
+ const pnfModelName: string = 'pnfInstanceV1';
+
+ service.getModelInformation(serviceId, pnfModelName);
+
+ expect(service.modelInformations.length).toEqual(14);
+
+ expect(service.modelInformations[0].label).toEqual("Subscriber Name");
+ expect(service.modelInformations[0].values).toEqual(['subscriberName']);
+
+ expect(service.modelInformations[1].label).toEqual("Service Name");
+ expect(service.modelInformations[1].values).toEqual(['action-data']);
+
+ expect(service.modelInformations[2].label).toEqual("Service Instance Name");
+ expect(service.modelInformations[2].values).toEqual(['InstanceName']);
+
+ expect(service.modelInformations[3].label).toEqual("Model Name");
+ expect(service.modelInformations[3].values).toEqual(['pnfName']);
+
+ expect(service.modelInformations[4].label).toEqual("Model version");
+ expect(service.modelInformations[4].values).toEqual(['1.0']);
+
+ expect(service.modelInformations[5].label).toEqual("Description");
+ expect(service.modelInformations[5].values).toEqual(['PNF description']);
+
+ expect(service.modelInformations[6].label).toEqual("Category");
+ expect(service.modelInformations[6].values).toEqual([undefined]);
+
+ expect(service.modelInformations[7].label).toEqual("Sub Category");
+ expect(service.modelInformations[7].values).toEqual([undefined]);
+
+ expect(service.modelInformations[8].label).toEqual("UUID");
+ expect(service.modelInformations[8].values).toEqual(['0903e1c0-8e03-4936-b5c2-260653b96413']);
+
+ expect(service.modelInformations[9].label).toEqual("Invariant UUID");
+ expect(service.modelInformations[9].values).toEqual(['00beb8f9-6d39-452f-816d-c709b9cbb87d']);
+
+ expect(service.modelInformations[10].label).toEqual("Service type");
+ expect(service.modelInformations[10].values).toEqual(['']);
+
+ expect(service.modelInformations[11].label).toEqual("Service role");
+ expect(service.modelInformations[11].values).toEqual(['']);
+
+ expect(service.modelInformations[12].label).toEqual("Minimum to instantiate");
+ expect(service.modelInformations[12].values).toEqual(['0']);
+
+ expect(service.modelInformations[13].label).toEqual("Maximum to instantiate");
+ expect(service.modelInformations[13].values).toEqual(['1']);
+ });
+
+ test('getSubLeftTitle new pnf popup should return service model name', () => {
+ service.uuidData = {
+ serviceId: 'serviceId',
+ modelName: 'pnfInstanceV1'
+ };
+ expect(service.getSubLeftTitle()).toBe("PNF MODEL: pnfName");
+ });
+
+ test('storePNF should dispatch createPNFInstance action when isUpdateMode is false', () => {
+ let mockedPopupService = getMockedPopupService(false);
+
+ spyOn(store, 'dispatch');
+ service.storePNF(mockedPopupService, {});
+
+ expect(store.dispatch).toHaveBeenCalledWith(jasmine.objectContaining({
+ type: "CREATE_PNF_INSTANCE",
+ }));
+ });
+
+ test('storePNF should dispatch updatePNFInstance action when isUpdateMode is true', () => {
+ let mockedPopupService = getMockedPopupService(true);
+
+ spyOn(mockedPopupService._store, 'dispatch');
+ service.storePNF(mockedPopupService, {});
+
+ expect(mockedPopupService._store.dispatch).toHaveBeenCalledWith(jasmine.objectContaining({
+ type: "UPDATE_PNF_INSTANCE",
+ }));
+ });
+
+ function getMockedPopupService(isUpdateMode: boolean) {
+ return <any>{
+ model: {},
+ isUpdateMode: isUpdateMode,
+ _store: {
+ dispatch: () => {
+ }
+ },
+ uuidData: {
+ serviceId: "serviceId"
+ }
+ };
+ }
+
+ test('getTitle pnf should return the correct title for edit and create mode', () => {
+ expect(service.getTitle(false)).toBe('Set a new PNF');
+ expect(service.getTitle(true)).toBe('Edit PNF instance');
+ });
+
+ test('extractSubscriberNameBySubscriberId should extract proper subscriber by id', () => {
+ expect(service.extractSubscriberNameBySubscriberId("subscriberId", store))
+ .toBe('subscriberName');
+ });
+
+});
diff --git a/vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.ts b/vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.ts
index c4f1b2eea..70fcc16db 100644
--- a/vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.ts
+++ b/vid-webpack-master/src/app/shared/components/genericFormPopup/genericFormServices/pnf/pnf.popup.service.ts
@@ -7,6 +7,7 @@ import {ModelInformationItem} from "../../../model-information/model-information
import {ServiceModel} from "../../../../models/serviceModel";
import {Subject} from "rxjs/Subject";
import {ControlGeneratorUtil} from "../../../genericForm/formControlsServices/control.generator.util.service";
+import {PnfControlGenerator} from "../../../genericForm/formControlsServices/pnfGenerator/pnf.control.generator";
import {IframeService} from "../../../../utils/iframe.service";
import {DefaultDataGeneratorService} from "../../../../services/defaultDataServiceGenerator/default.data.generator.service";
import {AaiService} from "../../../../services/aaiService/aai.service";
@@ -16,14 +17,17 @@ import {AppState} from "../../../../store/reducers";
import {Subscriber} from "../../../../models/subscriber";
import {Constants} from "../../../../utils/constants";
import {PnfInstance} from "../../../../models/pnfInstance";
+import {ModelInfo} from "../../../../models/modelInfo";
+import {changeInstanceCounter} from "../../../../storeUtil/utils/general/general.actions";
+import {createPNFInstance, updatePNFInstance} from "../../../../storeUtil/utils/pnf/pnf.actions";
import * as _ from 'lodash';
@Injectable()
-export class PnfPopupService implements GenericPopupInterface{
+export class PnfPopupService implements GenericPopupInterface {
dynamicInputs: any;
instance: any;
- model:any;
- serviceModel:ServiceModel;
+ model: any;
+ serviceModel: ServiceModel;
modelInformations: ModelInformationItem[] = [];
uuidData: Object;
closeDialogEvent: Subject<any> = new Subject<any>();
@@ -31,6 +35,7 @@ export class PnfPopupService implements GenericPopupInterface{
constructor(
private _basicControlGenerator: ControlGeneratorUtil,
+ private _pnfControlGenerator: PnfControlGenerator,
private _iframeService: IframeService,
private _defaultDataGeneratorService: DefaultDataGeneratorService,
private _aaiService: AaiService,
@@ -53,17 +58,25 @@ export class PnfPopupService implements GenericPopupInterface{
this.getControls(serviceId, modelName, pnfStoreKey),
this._basicPopupService.getDynamicInputs(serviceId, modelName, pnfStoreKey, 'pnfs'),
this.modelInformations,
- (that, form: FormGroup) => {that.onSubmit(that, form);},
- (that: any, form: FormGroup) => {that.onCancel(that, form); }
- )
+ (that, form: FormGroup) => {
+ that.onSubmit(that, form);
+ },
+ (that: any, form: FormGroup) => {
+ that.onCancel(that, form);
+ }
+ )
}
- getControls(serviceId: string, modelName: string, pnfStoreKey: string){
- return [];
+ getControls(serviceId: string, modelName: string, pnfStoreKey: string) {
+ if (this._store.getState().service.serviceHierarchy[serviceId].service.vidNotions.instantiationType === 'Macro') {
+ return this._pnfControlGenerator.getMacroFormControls(serviceId, pnfStoreKey, modelName);
+ } else {
+ return this._pnfControlGenerator.getAlaCarteFormControls(serviceId, pnfStoreKey, modelName);
+ }
}
getInstance(serviceId: string, modelName: string, pnfStoreKey: string): any {
- if(_.isNil(pnfStoreKey)){
+ if (_.isNil(pnfStoreKey)) {
return new PnfInstance();
}
return this._store.getState().service.serviceInstance[serviceId].pnfs[pnfStoreKey];
@@ -89,7 +102,7 @@ export class PnfPopupService implements GenericPopupInterface{
new ModelInformationItem("Service role", "serviceRole", [this.serviceModel.serviceRole]),
new ModelInformationItem("Minimum to instantiate", "min", [!_.isNil(this.model.min) ? this.model.min.toString() : '0'], "", false),
this._basicPopupService.createMaximumToInstantiateModelInformationItem(this.model)
- ];
+ ];
})
}
@@ -101,10 +114,20 @@ export class PnfPopupService implements GenericPopupInterface{
return "PNF Instance Details";
}
- storePNF = (that, formValues: any): void => {};
+ storePNF = (that, formValues: any): void => {
+ formValues.modelInfo = new ModelInfo(that.model);
+ formValues.uuid = formValues.modelInfo.uuid;
+ formValues.isMissingData = false;
+ if (!that.isUpdateMode) {
+ that._store.dispatch(changeInstanceCounter(formValues.modelInfo.modelUniqueId, that.uuidData.serviceId, 1, <any>{data: {type: 'PNF'}}));
+ this._store.dispatch(createPNFInstance(formValues, that.uuidData['modelName'], that.uuidData['serviceId'], that.uuidData['modelName']));
+ } else {
+ that._store.dispatch(updatePNFInstance(formValues, that.uuidData.modelName, that.uuidData.serviceId, that.uuidData.pnfStoreKey))
+ }
+ };
getTitle(isUpdateMode: boolean): string {
- return isUpdateMode ? "Edit PNF instance": "Set a new PNF" ;
+ return isUpdateMode ? "Edit PNF instance" : "Set a new PNF";
}
onCancel(that, form): void {
@@ -116,7 +139,7 @@ export class PnfPopupService implements GenericPopupInterface{
onSubmit(that, form: FormGroup, ...args): void {
form.value['instanceParams'] = form.value['instanceParams'] && [form.value['instanceParams']];
that.storePNF(that, form.value);
- window.parent.postMessage( {
+ window.parent.postMessage({
eventId: 'submitIframe',
data: {
serviceModelId: that.uuidData.serviceId
diff --git a/vid-webpack-master/src/app/shared/models/pnfInstance.ts b/vid-webpack-master/src/app/shared/models/pnfInstance.ts
index ba3679646..ff855bc8c 100644
--- a/vid-webpack-master/src/app/shared/models/pnfInstance.ts
+++ b/vid-webpack-master/src/app/shared/models/pnfInstance.ts
@@ -5,6 +5,7 @@ export class PnfInstance extends Level1Instance {
pnfStoreKey : string;
statusMessage?: string;
+ position: number;
constructor() {
super();
diff --git a/vid-webpack-master/src/app/shared/models/pnfModel.ts b/vid-webpack-master/src/app/shared/models/pnfModel.ts
index 14e6588d2..8f9e0d1de 100644
--- a/vid-webpack-master/src/app/shared/models/pnfModel.ts
+++ b/vid-webpack-master/src/app/shared/models/pnfModel.ts
@@ -3,6 +3,8 @@ import {
Level1ModelProperties,
Level1ModelResponseInterface
} from "./nodeModel";
+import {VNFModelResponseInterface} from "./vnfModel";
+import {Utils} from "../utils/utils";
@@ -18,10 +20,11 @@ export class PNFModel extends Level1Model{
roles: string[] = [];
properties: PnfProperties;
- constructor(pnfJson?: PNFModelResponseInterface) {
+ constructor(pnfJson?: PNFModelResponseInterface, flags?: { [key: string]: boolean }) {
super(pnfJson);
if (pnfJson && pnfJson.properties) {
this.properties = pnfJson.properties;
+ this.max = Utils.getMaxFirstLevel(this.properties, flags);
}
}
diff --git a/vid-webpack-master/src/app/shared/models/serviceInstance.ts b/vid-webpack-master/src/app/shared/models/serviceInstance.ts
index 1f111d14b..67b8806a8 100644
--- a/vid-webpack-master/src/app/shared/models/serviceInstance.ts
+++ b/vid-webpack-master/src/app/shared/models/serviceInstance.ts
@@ -23,8 +23,8 @@ export class ServiceInstance extends NodeInstance{
latestAvailableVersion: Number;
pause: boolean;
bulkSize: number;
- pnfs: { [pnf_module_model_name: string]: PnfInstance; };
vnfs: { [vnf_module_model_name: string]: VnfInstance; };
+ pnfs: { [pnf_module_model_name: string]: PnfInstance; };
vrfs: { [vrf_model_name: string]: VrfInstance; };
vnfGroups : {[vnf_module_model_name: string]: VnfGroupInstance; };
networks: { [vnf_module_model_name: string]: NetworkInstance; };
@@ -36,8 +36,8 @@ export class ServiceInstance extends NodeInstance{
validationCounter: number;
existingNames: {[key: string] : any};
modelInavariantId?: string;
- existingPNFCounterMap : { [pnf_module_model_name: string]: number; };
existingVNFCounterMap : { [vnf_module_model_name: string]: number; };
+ existingPNFCounterMap : { [pnf_module_model_name: string]: number; };
existingVRFCounterMap : { [vrf_module_model_name: string]: number; };
existingVnfGroupCounterMap : { [vnf_group_module_model_name: string]: number; };
existingNetworksCounterMap : { [network_module_model_name: string]: number; };
diff --git a/vid-webpack-master/src/app/shared/services/aaiService/aai.service.spec.ts b/vid-webpack-master/src/app/shared/services/aaiService/aai.service.spec.ts
index f563cbc75..ad934cf79 100644
--- a/vid-webpack-master/src/app/shared/services/aaiService/aai.service.spec.ts
+++ b/vid-webpack-master/src/app/shared/services/aaiService/aai.service.spec.ts
@@ -22,7 +22,7 @@ describe("AaiService", () => {
let httpMock: HttpTestingController;
let aaiService: AaiService;
let mockFeatureFlagsService: FeatureFlagsService = mock(FeatureFlagsService);
- let store : NgRedux<AppState>;
+ let store: NgRedux<AppState>;
beforeAll(done => (async () => {
TestBed.configureTestingModule({
@@ -42,8 +42,6 @@ describe("AaiService", () => {
})().then(done).catch(done.fail));
-
-
describe('#resolve tests', () => {
test('aai service resolve should return the right object', () => {
let serviceInstance = new ServiceInstance();
@@ -173,8 +171,37 @@ describe("AaiService", () => {
});
});
+ describe('#Pnf modelCustomizationName initialization tests', () => {
+
+ test('initializePnfModelCustomizationName should not reinitialize modelCustomizationName when it exists', () => {
+ let serviceHierarchy = {
+ "pnfs": {
+ "pnfInstance": {
+ "modelCustomizationName": "existingName"
+ }
+ }
+ }
+
+ aaiService.initializePnfModelCustomizationName(serviceHierarchy);
+
+ expect(serviceHierarchy.pnfs["pnfInstance"].modelCustomizationName).toBe("existingName");
+ });
+
+ test('initializePnfModelCustomizationName should initialize modelCustomizationName when it doesnt exist', () => {
+ let serviceHierarchy = {
+ "pnfs": {
+ "pnfInstance": {}
+ }
+ }
+
+ aaiService.initializePnfModelCustomizationName(serviceHierarchy);
+
+ expect((serviceHierarchy.pnfs["pnfInstance"] as any).modelCustomizationName).toBe("pnfInstance");
+ });
+ });
+
function getTopology() {
- return {
+ return {
"vnfs": {
"2017-388_PASQUALE-vPE 0": {
"vfModules": {},
@@ -398,7 +425,7 @@ describe("AaiService", () => {
}
}
- function getMockActiveNetworks(){
+ function getMockActiveNetworks() {
return [
{
networkInstanceName: "networkInstanceName",
diff --git a/vid-webpack-master/src/app/shared/services/aaiService/aai.service.ts b/vid-webpack-master/src/app/shared/services/aaiService/aai.service.ts
index adb7017be..2829a8981 100644
--- a/vid-webpack-master/src/app/shared/services/aaiService/aai.service.ts
+++ b/vid-webpack-master/src/app/shared/services/aaiService/aai.service.ts
@@ -58,6 +58,7 @@ export class AaiService {
getServiceModelById = (serviceModelId: string): Observable<any> => {
if (_.has(this.store.getState().service.serviceHierarchy, serviceModelId)) {
+ this.initializePnfModelCustomizationName(this.store.getState().service.serviceHierarchy[serviceModelId]);
return of(<any> JSON.parse(JSON.stringify(this.store.getState().service.serviceHierarchy[serviceModelId])));
}
let pathQuery: string = Constants.Path.SERVICES_PATH + serviceModelId;
@@ -321,6 +322,15 @@ export class AaiService {
return result;
}
+ initializePnfModelCustomizationName(serviceHierarchy) : void {
+ let pnfs = serviceHierarchy.pnfs;
+ for (let pnf in pnfs) {
+ if (!pnfs[pnf].modelCustomizationName){
+ pnfs[pnf].modelCustomizationName = pnf;
+ }
+ }
+ }
+
loadMockMembers(): any {
return [
{
diff --git a/vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.spec.ts b/vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.spec.ts
index 56f49e75c..4abffabcb 100644
--- a/vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.spec.ts
+++ b/vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.spec.ts
@@ -4,25 +4,176 @@ import {NgRedux} from '@angular-redux/store';
import {DefaultDataGeneratorService} from './default.data.generator.service';
import {ServiceNodeTypes} from "../../models/ServiceNodeTypes";
import {VNFModel} from "../../models/vnfModel";
+import {AppState} from "../../store/reducers";
-class MockAppStore<T> {}
+class MockAppStore<T> {
+ dispatch() {
+
+ }
+
+ getState() {
+ return {
+ "global": {
+ "flags": {
+ "FLAG_NETWORK_TO_ASYNC_INSTANTIATION": false,
+ "FLAG_SHOW_ASSIGNMENTS": true,
+ "FLAG_FABRIC_CONFIGURATION_ASSIGNMENTS": true,
+ "FLAG_SHOW_VERIFY_SERVICE": false,
+ "FLAG_SERVICE_MODEL_CACHE": true,
+ "FLAG_ADD_MSO_TESTAPI_FIELD": true
+ }
+ },
+ "service": {
+ "serviceHierarchy": {
+ "serviceId": {
+ "service": {
+ "uuid": "6e59c5de-f052-46fa-aa7e-2fca9d674c44",
+ "invariantUuid": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "name": "action-data",
+ "version": "1.0",
+ "toscaModelURL": null,
+ "category": "Emanuel",
+ "serviceType": "",
+ "serviceRole": "",
+ "description": "action-data",
+ "serviceEcompNaming": "false",
+ "instantiationType": "Macro",
+ "vidNotions": {
+ "instantiationType": "Macro"
+ },
+ },
+ "globalSubscriberId": "subscriberId",
+ "pnfs": {
+ "pnfInstanceV1": {
+ "name": "pnfName",
+ "pnfStoreKey": "pnfInstanceV1",
+ "version": "1.0",
+ "description": "PNF description",
+ "uuid": "0903e1c0-8e03-4936-b5c2-260653b96413",
+ "invariantUuid": "00beb8f9-6d39-452f-816d-c709b9cbb87d",
+ "properties": {
+ "min_instances": "1",
+ "ecomp_generated_naming": "true"
+ }
+ }
+ },
+ "modelInfo": {
+ "modelInvariantId": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "modelVersionId": "6b528779-44a3-4472-bdff-9cd15ec93450",
+ "modelName": "action-data",
+ "modelVersion": "1.0",
+ "uuid": "6b528779-44a3-4472-bdff-9cd15ec93450"
+ },
+ "instanceName": "InstanceName",
+ "owningEntityId": "d61e6f2d-12fa-4cc2-91df-7c244011d6fc",
+ "productFamilyId": "17cc1042-527b-11e6-beb8-9e71128cae77",
+ "lcpCloudRegionId": "AAIAIC25",
+ "tenantId": "092eb9e8e4b7412e8787dd091bc58e86",
+ "aicZoneId": "JAG1",
+ "projectName": null,
+ "rollbackOnFailure": "true",
+ "aicZoneName": "YUDFJULP-JAG1",
+ "owningEntityName": "WayneHolland",
+ "testApi": "GR_API",
+ "tenantName": "USP-SIP-IC-24335-T-01",
+ "bulkSize": 1,
+ "isALaCarte": false,
+ "name": "action-data",
+ "version": "1.0",
+ "description": "",
+ "category": "",
+ "uuid": "6b528779-44a3-4472-bdff-9cd15ec93450",
+ "invariantUuid": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "serviceType": "",
+ "serviceRole": "",
+ "isMultiStepDesign": false
+ }
+ },
+ "serviceInstance": {
+ "serviceId": {
+ "globalSubscriberId": "subscriberId",
+ "pnfs": {
+ "pnfInstanceV1": {
+ "name": "pnfName",
+ "pnfStoreKey": "pnfInstanceV1"
+ },
+ "pnfInstanceV2": {
+ "name": "pnfName2",
+ "pnfStoreKey": "pnfInstanceV2"
+ }
+ },
+ "modelInfo": {
+ "modelInvariantId": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "modelVersionId": "6b528779-44a3-4472-bdff-9cd15ec93450",
+ "modelName": "action-data",
+ "modelVersion": "1.0",
+ "uuid": "6b528779-44a3-4472-bdff-9cd15ec93450"
+ },
+ "instanceName": "InstanceName",
+ "owningEntityId": "d61e6f2d-12fa-4cc2-91df-7c244011d6fc",
+ "productFamilyId": "17cc1042-527b-11e6-beb8-9e71128cae77",
+ "lcpCloudRegionId": "AAIAIC25",
+ "tenantId": "092eb9e8e4b7412e8787dd091bc58e86",
+ "aicZoneId": "JAG1",
+ "projectName": null,
+ "rollbackOnFailure": "true",
+ "aicZoneName": "YUDFJULP-JAG1",
+ "owningEntityName": "WayneHolland",
+ "testApi": "GR_API",
+ "tenantName": "USP-SIP-IC-24335-T-01",
+ "bulkSize": 1,
+ "isALaCarte": false,
+ "name": "action-data",
+ "version": "1.0",
+ "description": "",
+ "category": "",
+ "uuid": "6b528779-44a3-4472-bdff-9cd15ec93450",
+ "invariantUuid": "e49fbd11-e60c-4a8e-b4bf-30fbe8f4fcc0",
+ "serviceType": "",
+ "serviceRole": "",
+ "isMultiStepDesign": false
+ }
+ },
+ "subscribers": [
+ {
+ "id": "someSubscriberId",
+ "name": "someSubscriberName",
+ "isPermitted": true
+ },
+ {
+ "id": "subscriberId",
+ "name": "subscriberName",
+ "isPermitted": true
+ },
+ {
+ "id": "subscriberId2",
+ "name": "subscriberName2",
+ "isPermitted": true
+ }
+ ]
+ }
+ }
+ }
+}
describe('Default Data Generator Service', () => {
let injector;
let service: DefaultDataGeneratorService;
+ let store: NgRedux<AppState>;
let httpMock: HttpTestingController;
beforeAll(done => (async () => {
TestBed.configureTestingModule({
imports: [HttpClientTestingModule],
- providers: [DefaultDataGeneratorService,
- {provide: NgRedux, useClass: MockAppStore}]
+ providers: [DefaultDataGeneratorService,
+ {provide: NgRedux, useClass: MockAppStore}]
});
await TestBed.compileComponents();
injector = getTestBed();
service = injector.get(DefaultDataGeneratorService);
httpMock = injector.get(HttpTestingController);
+ store = injector.get(NgRedux);
})().then(done).catch(done.fail));
test('generateVFModule aLaCarte vf module object should missed data', () => {
@@ -124,7 +275,7 @@ describe('Default Data Generator Service', () => {
"modelVersion": "1"
},
volumeGroupName: "",
- isMissingData : false,
+ isMissingData: false,
trackById: Math.random().toString()
}, vfModuleModel, vnfModuleUUID, false, [], "");
expect(newVfModule.name).toEqual('&lt;Automatically Assigned&gt;');
@@ -147,7 +298,7 @@ describe('Default Data Generator Service', () => {
"modelVersion": "1"
},
volumeGroupName: "",
- isMissingData : false,
+ isMissingData: false,
trackById: Math.random().toString()
}, vfModuleModel, vnfModuleUUID, true, [], "");
expect(newVfModule.name).toEqual('&lt;Automatically Assigned&gt;');
@@ -159,7 +310,7 @@ describe('Default Data Generator Service', () => {
test('createNewVnfTreeNode with isEcompGeneratedNaming instance name not filled - missing data true', () => {
const vnfModel = generateServiceHierarchy().vnfs['VF_vGeraldine 0'];
const newVnf = service.createNewTreeNode({
- uuid : '',
+ uuid: '',
instanceName: "",
productFamilyId: "productFamilyId",
lcpCloudRegionId: "lcpCloudRegionId",
@@ -168,7 +319,7 @@ describe('Default Data Generator Service', () => {
platformName: "platformName",
lineOfBusiness: "lineOfBusiness",
rollbackOnFailure: "rollbackOnFailure",
- originalName : null,
+ originalName: null,
vfModules: {},
modelInfo: {
"modelCustomizationName": "VF_vGeraldine 0",
@@ -182,7 +333,7 @@ describe('Default Data Generator Service', () => {
isMissingData: false,
trackById: Math.random().toString(),
vnfStoreKey: "abc"
- }, new VNFModel(vnfModel),'VF_vGeraldine 0', 'vnfs');
+ }, new VNFModel(vnfModel), 'VF_vGeraldine 0', 'vnfs');
expect(newVnf.name).toEqual('VF_vGeraldine 0');
expect(newVnf.missingData).toEqual(true);
});
@@ -190,7 +341,7 @@ describe('Default Data Generator Service', () => {
test('createNewVnfTreeNode with isEcompGeneratedNaming instance name filled - missing data false', () => {
const vnfModel = generateServiceHierarchy().vnfs['VF_vGeraldine 0'];
const newVnf = service.createNewTreeNode({
- uuid : '',
+ uuid: '',
instanceName: "instanceName",
productFamilyId: "productFamilyId",
lcpCloudRegionId: "lcpCloudRegionId",
@@ -199,7 +350,7 @@ describe('Default Data Generator Service', () => {
platformName: "platformName",
lineOfBusiness: "lineOfBusiness",
rollbackOnFailure: "rollbackOnFailure",
- originalName : null,
+ originalName: null,
vfModules: {},
modelInfo: {
"modelCustomizationName": "VF_vGeraldine 0",
@@ -213,12 +364,73 @@ describe('Default Data Generator Service', () => {
isMissingData: false,
trackById: Math.random().toString(),
vnfStoreKey: "abc"
- }, vnfModel,'VF_vGeraldine 0', 'vnfs');
+ }, vnfModel, 'VF_vGeraldine 0', 'vnfs');
expect(newVnf.name).toEqual("instanceName");
expect(newVnf.missingData).toEqual(false);
});
});
+ describe('#updatePnfsOnFirstSet tests', () => {
+
+ test('updatePnfsOnFirstSet should call createPNFInstanceReduxIfNotExist when pnfs exists and extended pnf flag is on', () => {
+ jest.spyOn(service, 'isExtendedMacroPnfConfigOn').mockReturnValue(true);
+ spyOn(service, 'createPNFInstanceReduxIfNotExist');
+
+ service.updatePnfsOnFirstSet("serviceId", {})
+
+ expect(service.createPNFInstanceReduxIfNotExist).toHaveBeenCalled();
+ });
+
+ test('updatePnfsOnFirstSet should not call createPNFInstanceReduxIfNotExist when pnfs exists and extended pnf flag is off', () => {
+ jest.spyOn(service, 'isExtendedMacroPnfConfigOn').mockReturnValue(false);
+ spyOn(service, 'createPNFInstanceReduxIfNotExist');
+
+ service.updatePnfsOnFirstSet("serviceId", {})
+
+ expect(service.createPNFInstanceReduxIfNotExist).not.toHaveBeenCalled();
+ });
+
+ test('updatePnfsOnFirstSet should not call createPNFInstanceReduxIfNotExist when min_instances == 0 and extended pnf flag is on', () => {
+ jest.spyOn(service, 'isExtendedMacroPnfConfigOn').mockReturnValue(true);
+ jest.spyOn(service, 'isMinInstancesGreaterThanZero').mockReturnValue(false);
+ spyOn(service, 'createPNFInstanceReduxIfNotExist');
+
+ service.updatePnfsOnFirstSet("serviceId", {})
+
+ expect(service.createPNFInstanceReduxIfNotExist).not.toHaveBeenCalled();
+ });
+
+ test('createPNFInstanceReduxIfNotExist should dispatch proper actions when pnf doesnt exist', () => {
+ let pnfData = {
+ modelInfo: {
+ modelCustomizationName: "pnfName"
+ }
+ };
+ spyOn(store, 'dispatch');
+
+ service.createPNFInstanceReduxIfNotExist("serviceId", pnfData);
+
+ expect(store.dispatch).toHaveBeenCalledWith(jasmine.objectContaining({
+ type: "CREATE_PNF_INSTANCE",
+ }));
+ expect(store.dispatch).toHaveBeenCalledWith(jasmine.objectContaining({
+ type: "CHANGE_INSTANCE_COUNTER",
+ }));
+ });
+
+ test('createPNFInstanceReduxIfNotExist should not dispatch anything when pnf exists', () => {
+ let pnfData = {
+ modelInfo: {
+ modelCustomizationName: "pnfInstanceV1"
+ }
+ };
+ spyOn(store, 'dispatch');
+
+ service.createPNFInstanceReduxIfNotExist("serviceId", pnfData);
+
+ expect(store.dispatch).not.toHaveBeenCalled();
+ });
+ });
});
diff --git a/vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.ts b/vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.ts
index e00b259a0..1bf698463 100644
--- a/vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.ts
+++ b/vid-webpack-master/src/app/shared/services/defaultDataServiceGenerator/default.data.generator.service.ts
@@ -1,6 +1,5 @@
import {Injectable} from '@angular/core';
import * as _ from 'lodash';
-
import {NgRedux} from '@angular-redux/store';
import {AppState} from '../../store/reducers';
import {VnfTreeNode} from "../../models/vnfTreeNode";
@@ -21,12 +20,15 @@ import {VnfGroupTreeNode} from "../../models/vnfGroupTreeNode";
import {ModelInfo} from "../../models/modelInfo";
import {ServiceInstanceActions} from "../../models/serviceInstanceActions";
import Parameter = Constants.Parameter;
+import {createPNFInstance} from "../../storeUtil/utils/pnf/pnf.actions";
+import {FeatureFlagsService, Features} from "../featureFlag/feature-flags.service";
@Injectable()
export class DefaultDataGeneratorService {
static controlsFieldsStatus = {};
public requiredFields = {
VF: [InputType.LCP_REGION, InputType.TENANT, InputType.PLATFORM],
+ PNF: [InputType.PLATFORM],
Network: [InputType.LCP_REGION, InputType.TENANT, InputType.PLATFORM],
VL: [InputType.LCP_REGION, InputType.TENANT, InputType.PLATFORM],
VFmodule: [],
@@ -65,11 +67,10 @@ export class DefaultDataGeneratorService {
break;
}
if (Utils.hasContents(inputs[key][Parameter.CONSTRAINTS])
- && ( inputs[key][Parameter.CONSTRAINTS].length > 0 )) {
+ && (inputs[key][Parameter.CONSTRAINTS].length > 0)) {
let constraintsArray = inputs[key][Parameter.CONSTRAINTS];
this.addConstraintParameters(parameterList, constraintsArray, key, inputs, parameter);
- }
- else {
+ } else {
parameterList.push(parameter);
}
@@ -97,8 +98,8 @@ export class DefaultDataGeneratorService {
name: constraintsArray[i][Parameter.VALID_VALUES][j],
isDefault: false
};
- if ((Utils.hasContents(inputs[key][Parameter.DEFAULT]) )
- && (inputs[key][Parameter.DEFAULT] === constraintsArray[i][Parameter.VALID_VALUES][j] )) {
+ if ((Utils.hasContents(inputs[key][Parameter.DEFAULT]))
+ && (inputs[key][Parameter.DEFAULT] === constraintsArray[i][Parameter.VALID_VALUES][j])) {
option = {
name: constraintsArray[i][Parameter.VALID_VALUES][j],
isDefault: true
@@ -180,14 +181,13 @@ export class DefaultDataGeneratorService {
return _.isEmpty(displayInputs) ? [] : this.getArbitraryInputs(displayInputs);
}
- updateNetworksOnFirstSet(serviceId: string, formServiceValues: any){
+ updateNetworksOnFirstSet(serviceId: string, formServiceValues: any) {
const serviceHierarchy = this.store.getState().service.serviceHierarchy[serviceId];
if (serviceHierarchy && !_.isEmpty(serviceHierarchy.networks)) {
for (let networkUUID in serviceHierarchy.networks) {
const isEcompGeneratedNaming = this.getIsEcompGeneratedNaming(serviceHierarchy.networks[networkUUID]);
let min_vnf_instances_greater_than_0 = serviceHierarchy.networks[networkUUID].properties['min_instances'] && serviceHierarchy.networks[networkUUID].properties['min_instances'] > 0;
- if(min_vnf_instances_greater_than_0)
- {
+ if (min_vnf_instances_greater_than_0) {
this.createNetworkInstanceReduxIfNotExist(
serviceId,
this.generateNetworkData(serviceHierarchy, networkUUID, formServiceValues, isEcompGeneratedNaming)
@@ -197,14 +197,13 @@ export class DefaultDataGeneratorService {
}
}
- updateVnfGroupsOnFirstSet(serviceId: string, formServiceValues: any){
+ updateVnfGroupsOnFirstSet(serviceId: string, formServiceValues: any) {
const serviceHierarchy = this.store.getState().service.serviceHierarchy[serviceId];
if (serviceHierarchy && !_.isEmpty(serviceHierarchy.vnfGroups)) {
for (let vnfGroupUUID in serviceHierarchy.vnfGroups) {
const isEcompGeneratedNaming = this.getIsEcompGeneratedNaming(serviceHierarchy.vnfGroups[vnfGroupUUID]);
let min_vnf_group_instances_greater_than_0 = serviceHierarchy.vnfGroups[vnfGroupUUID].properties['min_instances'] && serviceHierarchy.vnfGroups[vnfGroupUUID].properties['min_instances'] > 0;
- if(min_vnf_group_instances_greater_than_0)
- {
+ if (min_vnf_group_instances_greater_than_0) {
this.createVnfGroupInstanceReduxIfNotExist(
serviceId,
this.generateVnfGroupData(serviceHierarchy, vnfGroupUUID, formServiceValues, isEcompGeneratedNaming)
@@ -214,9 +213,38 @@ export class DefaultDataGeneratorService {
}
}
+ updatePnfsOnFirstSet(serviceId: string, formServiceValues: any) {
+ const serviceHierarchy = this.store.getState().service.serviceHierarchy[serviceId];
+ if (serviceHierarchy && !_.isEmpty(serviceHierarchy.pnfs)) {
+ for (let pnfUUID in serviceHierarchy.pnfs) {
+ if (this.isMinInstancesGreaterThanZero(serviceHierarchy, pnfUUID) && this.isExtendedMacroPnfConfigOn()) {
+ this.createPNFInstanceReduxIfNotExist(
+ serviceId,
+ this.generatePNFData(
+ serviceHierarchy,
+ pnfUUID,
+ formServiceValues,
+ this.getIsEcompGeneratedNaming(serviceHierarchy.pnfs[pnfUUID])
+ )
+ );
+ }
+ }
+ }
+ }
+
+ isExtendedMacroPnfConfigOn(): boolean {
+ return FeatureFlagsService.getFlagState(Features.FLAG_EXTENDED_MACRO_PNF_CONFIG, this.store)
+ }
+
+ isMinInstancesGreaterThanZero(serviceHierarchy, pnfUUID): boolean {
+ return serviceHierarchy.pnfs[pnfUUID].properties['min_instances']
+ && serviceHierarchy.pnfs[pnfUUID].properties['min_instances'] > 0;
+ }
+
updateReduxOnFirstSet(serviceId: string, formServiceValues: any): void {
this.updateNetworksOnFirstSet(serviceId, formServiceValues);
this.updateVnfGroupsOnFirstSet(serviceId, formServiceValues);
+ this.updatePnfsOnFirstSet(serviceId, formServiceValues);
const serviceHierarchy = this.store.getState().service.serviceHierarchy[serviceId];
if (serviceHierarchy && !_.isEmpty(serviceHierarchy.vnfs)) {
for (let vnfUUID in serviceHierarchy.vnfs) {
@@ -245,8 +273,7 @@ export class DefaultDataGeneratorService {
}
let min_vnf_instances_greater_than_0 = serviceHierarchy.vnfs[vnfUUID].properties['min_instances'] && serviceHierarchy.vnfs[vnfUUID].properties['min_instances'] > 0;
- if(min_vnf_instances_greater_than_0)
- {
+ if (min_vnf_instances_greater_than_0) {
this.createVNFInstanceReduxIfNotExist(
serviceId,
this.generateVNFData(serviceHierarchy, vnfUUID, formServiceValues, isEcompGeneratedNaming)
@@ -256,7 +283,6 @@ export class DefaultDataGeneratorService {
}
}
-
private getIsEcompGeneratedNaming(vnfJson) {
const ecompGeneratedNaming = vnfJson.properties.ecomp_generated_naming;
return ecompGeneratedNaming === "true";
@@ -269,6 +295,13 @@ export class DefaultDataGeneratorService {
}
}
+ createPNFInstanceReduxIfNotExist(serviceId: string, pnfData: any): void {
+ if(!this.store.getState().service.serviceInstance[serviceId].pnfs[pnfData.modelInfo.modelCustomizationName]){
+ this.store.dispatch(createPNFInstance(pnfData, pnfData.modelInfo.modelCustomizationName, serviceId));
+ this.store.dispatch(changeInstanceCounter(pnfData.modelInfo.modelUniqueId, serviceId, 1, <any> {data : {type : 'PNF'}}));
+ }
+ }
+
createNetworkInstanceReduxIfNotExist(serviceId: string, networkData: any): void {
if(!this.store.getState().service.serviceInstance[serviceId].vnfs[networkData.modelInfo.modelCustomizationName]){
this.store.dispatch(createNetworkInstance(networkData, networkData.modelInfo.modelCustomizationName, serviceId));
@@ -378,6 +411,29 @@ export class DefaultDataGeneratorService {
}
}
+ generatePNFData(serviceHierarchy: any, pnfName: string, formValues: any, isEcompGeneratedNaming) {
+ return {
+ 'uuid' : serviceHierarchy.pnfs[pnfName].uuid,
+ 'isMissingData' :this.setIsMissingData(ServiceNodeTypes.PNF, [], isEcompGeneratedNaming),
+ 'productFamilyId': formValues.productFamilyId,
+ 'lcpCloudRegionId': null,
+ 'tenantId': null,
+ 'lineOfBusiness': null,
+ 'platformName': null,
+ 'modelInfo': {
+ 'modelType': 'PNF',
+ 'modelInvariantId': serviceHierarchy.pnfs[pnfName].invariantUuid,
+ 'modelVersionId': serviceHierarchy.pnfs[pnfName].uuid,
+ 'modelName': serviceHierarchy.pnfs[pnfName].name,
+ 'modelVersion': serviceHierarchy.pnfs[pnfName].version,
+ 'modelCustomizationId': serviceHierarchy.pnfs[pnfName].customizationUuid,
+ 'modelCustomizationName': serviceHierarchy.pnfs[pnfName].modelCustomizationName,
+ 'modelUniqueId' : serviceHierarchy.pnfs[pnfName].customizationUuid || serviceHierarchy.pnfs[pnfName].uuid,
+ },
+ 'trackById': DefaultDataGeneratorService.createRandomTrackById(),
+ }
+ }
+
generateNetworkData(serviceHierarchy: any, networkName: string, formValues: any, isEcompGeneratedNaming) {
return {
'uuid' : serviceHierarchy.network[networkName].uuid,
diff --git a/vid-webpack-master/src/app/shared/shared.module.ts b/vid-webpack-master/src/app/shared/shared.module.ts
index f228389aa..e4238e079 100644
--- a/vid-webpack-master/src/app/shared/shared.module.ts
+++ b/vid-webpack-master/src/app/shared/shared.module.ts
@@ -99,6 +99,9 @@ import {MessageModal} from "./components/messageModal/message-modal.service";
import {SpaceToUnderscorePipe} from "./pipes/spaceToUnderscore/space-to-underscore.pipe";
import {ResizableModule} from 'angular-resizable-element';
import {PnfPopupService} from "./components/genericFormPopup/genericFormServices/pnf/pnf.popup.service";
+import {PnfControlGenerator} from "./components/genericForm/formControlsServices/pnfGenerator/pnf.control.generator";
+
+
@NgModule({
imports: [
@@ -235,6 +238,7 @@ import {PnfPopupService} from "./components/genericFormPopup/genericFormServices
ServiceControlGenerator,
ServicePopupService,
VnfControlGenerator,
+ PnfControlGenerator,
VfModuleControlGenerator,
ControlGeneratorUtil,
SharedControllersService,
diff --git a/vid-webpack-master/src/app/shared/storeUtil/utils/main.reducer.ts b/vid-webpack-master/src/app/shared/storeUtil/utils/main.reducer.ts
index a135563eb..faf4aae4e 100644
--- a/vid-webpack-master/src/app/shared/storeUtil/utils/main.reducer.ts
+++ b/vid-webpack-master/src/app/shared/storeUtil/utils/main.reducer.ts
@@ -26,6 +26,8 @@ import {CrActions} from "./cr/cr.actions";
import {crReducer} from "./cr/cr.reducer";
import {NcfActions} from "./ncf/ncf.actions";
import {ncfReducer} from "./ncf/ncf.reducer";
+import {PNFActions} from "./pnf/pnf.actions";
+import {pnfReducer} from "./pnf/pnf.reducers";
export let initialState: ServiceState = {
serviceHierarchy: {},
@@ -64,6 +66,8 @@ export const MainReducer = function (state: ServiceState = initialState, action:
return vfModuleReducer(state, action);
}else if (Object.values(VNFActions).includes(action.type)){
return vnfReducer(state, action);
+ }else if (Object.values(PNFActions).includes(action.type)){
+ return pnfReducer(state, action);
}else if (Object.values(VnfGroupActions).includes(action.type)){
return vnfGroupReducer(state, action);
}else if(Object.values(RelatedVnfActions).includes(action.type)){
diff --git a/vid-webpack-master/src/app/shared/storeUtil/utils/network/network.reducers.ts b/vid-webpack-master/src/app/shared/storeUtil/utils/network/network.reducers.ts
index a8154e856..9c4421317 100644
--- a/vid-webpack-master/src/app/shared/storeUtil/utils/network/network.reducers.ts
+++ b/vid-webpack-master/src/app/shared/storeUtil/utils/network/network.reducers.ts
@@ -8,7 +8,7 @@ import {
UpdateNetworkInstanceAction
} from "./network.actions";
import {ServiceInstance} from "../../../models/serviceInstance";
-import {calculateNextUniqueModelName} from "../vnf/vnf.reducers";
+import {calculateNextUniqueModelName} from "../reducersHelper";
import {ServiceState} from "../main.reducer";
import {ServiceInstanceActions} from "../../../models/serviceInstanceActions";
import {deleteFirstLevel, updateServiceValidationCounter} from "../reducersHelper";
diff --git a/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.actions.ts b/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.actions.ts
new file mode 100644
index 000000000..82ab59fb5
--- /dev/null
+++ b/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.actions.ts
@@ -0,0 +1,88 @@
+import {Action, ActionCreator} from "redux";
+import {PnfInstance} from "../../../models/pnfInstance";
+import {ActionOnFirstLevel} from "../firstLevel/firstLevel.actions";
+
+export enum PNFActions {
+ CREATE_PNF_INSTANCE = "CREATE_PNF_INSTANCE",
+ UPDATE_PNF_INSTANCE = "UPDATE_PNF_INSTANCE",
+ REMOVE_PNF_INSTANCE = "REMOVE_PNF_INSTANCE",
+ DELETE_ACTION_PNF_INSTANCE = "DELETE_PNF_INSTANCE",
+ UNDO_DELETE_ACTION_PNF_INSTANCE = "UNDO_DELETE_PNF_INSTANCE",
+ UPDATE_PNF_POSITION = "UPDATE_PNF_POISTION"
+}
+
+export enum PNFMethods{
+ UPGRADE = "upgrade",
+ UNDO_UPGRADE = "undoUpgrade"
+}
+
+
+export interface CreatePnfInstanceAction extends Action {
+ pnfInstance?: PnfInstance;
+ pnfModelName?: string;
+ serviceUuid?: string;
+ pnfStoreKey?:string;
+}
+
+export interface UpdatePnfPosition extends Action {
+ node: any,
+ instanceId : string,
+ pnfStoreKey?: string;
+}
+
+export interface UpdatePnfInstanceAction extends Action {
+ pnfInstance?: PnfInstance;
+ pnfModelName?: string;
+ serviceUuid?: string;
+ pnfStoreKey?:string;
+}
+
+export interface RemovePnfInstanceAction extends Action {
+ pnfStoreKey: string;
+ serviceId?: string;
+}
+
+export const createPNFInstance: ActionCreator<CreatePnfInstanceAction> = (pnfInstance, pnfModelName, serviceUuid, pnfStoreKey) => ({
+ type: PNFActions.CREATE_PNF_INSTANCE,
+ pnfInstance: pnfInstance,
+ pnfModelName: pnfModelName,
+ serviceUuid: serviceUuid,
+ pnfStoreKey : pnfStoreKey
+});
+
+
+export const updatePNFInstance: ActionCreator<UpdatePnfInstanceAction> = (pnfInstance, pnfModelName, serviceUuid, pnfStoreKey) => ({
+ type: PNFActions.UPDATE_PNF_INSTANCE,
+ pnfInstance: pnfInstance,
+ pnfModelName: pnfModelName,
+ serviceUuid: serviceUuid,
+ pnfStoreKey : pnfStoreKey
+});
+
+
+export const deleteActionPnfInstance: ActionCreator<ActionOnFirstLevel> = (pnfStoreKey, serviceId) => ({
+ type: PNFActions.DELETE_ACTION_PNF_INSTANCE,
+ firstLevelName: 'pnfs',
+ storeKey: pnfStoreKey,
+ serviceId: serviceId
+});
+
+export const undoDeleteActionPnfInstance: ActionCreator<ActionOnFirstLevel> = (pnfStoreKey, serviceId) => ({
+ type: PNFActions.UNDO_DELETE_ACTION_PNF_INSTANCE,
+ firstLevelName: 'pnfs',
+ storeKey: pnfStoreKey,
+ serviceId: serviceId
+});
+
+export const removePnfInstance: ActionCreator<RemovePnfInstanceAction> = (pnfStoreKey, serviceId) => ({
+ type: PNFActions.REMOVE_PNF_INSTANCE,
+ pnfStoreKey: pnfStoreKey,
+ serviceId: serviceId
+});
+
+export const updatePnfPosition: ActionCreator<UpdatePnfPosition> = (node, instanceId, pnfStoreKey) => ({
+ type: PNFActions.UPDATE_PNF_POSITION,
+ node: node,
+ instanceId: instanceId,
+ pnfStoreKey : pnfStoreKey
+});
diff --git a/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.reducers.spec.ts b/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.reducers.spec.ts
new file mode 100644
index 000000000..b92495773
--- /dev/null
+++ b/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.reducers.spec.ts
@@ -0,0 +1,172 @@
+import {
+ CreatePnfInstanceAction,
+ RemovePnfInstanceAction,
+ UpdatePnfPosition,
+ UpdatePnfInstanceAction,
+ PNFActions
+} from "./pnf.actions";
+import {pnfReducer} from "./pnf.reducers";
+import {ServiceInstanceActions} from "../../../models/serviceInstanceActions";
+import {ActionOnFirstLevel} from "../firstLevel/firstLevel.actions";
+import {PnfInstance} from "../../../models/pnfInstance";
+
+describe('pnfReducer', () => {
+
+ test('#CREATE_PNF_INSTANCE', () => {
+ let pnfInstance: PnfInstance = new PnfInstance();
+ pnfInstance.isMissingData = false;
+ pnfInstance.instanceName = 'instanceName';
+ let pnfState = pnfReducer(<any>{
+ serviceInstance: {
+ 'serviceModelId': {
+ pnfs: {}
+ }
+ }
+ },
+ <CreatePnfInstanceAction>{
+ type: PNFActions.CREATE_PNF_INSTANCE,
+ pnfInstance: pnfInstance,
+ pnfStoreKey: null,
+ pnfModelName: 'pnfModelName',
+ serviceUuid: 'serviceModelId'
+ }).serviceInstance['serviceModelId'].pnfs['pnfModelName'];
+
+ expect(pnfState).toBeDefined();
+ expect(pnfState.isMissingData).toBeFalsy();
+ });
+
+ test('#UPDATE_PNF_INSTANCE_NAME', () => {
+ let newInstanceName: string = "newInstanceName"
+ let pnfInstance: PnfInstance = new PnfInstance();
+ pnfInstance.isMissingData = false;
+ pnfInstance.instanceName = newInstanceName;
+
+ let pnfState = pnfReducer(<any>{
+ serviceInstance: {
+ 'serviceModelId': {
+ pnfs: {
+ "pnfStoreKey": {
+ instanceName: 'oldInstanceName'
+ }
+ },
+ existingNames: {
+ 'oldinstancename': {}
+ }
+ }
+ }
+ },
+ <UpdatePnfInstanceAction>{
+ type: PNFActions.UPDATE_PNF_INSTANCE,
+ pnfInstance: pnfInstance,
+ pnfStoreKey: 'pnfStoreKey',
+ pnfModelName: 'pnfModelName',
+ serviceUuid: 'serviceModelId'
+ }).serviceInstance['serviceModelId'];
+
+ expect(pnfState).toBeDefined();
+ expect(pnfState.pnfs['pnfStoreKey'].instanceName).toEqual(newInstanceName);
+ expect(newInstanceName.toLowerCase() in pnfState.existingNames).toBeTruthy();
+ });
+
+ test('#DELETE_ACTION_PNF_INSTANCE', () => {
+ let pnfState = pnfReducer(<any>{
+ serviceInstance: {
+ 'serviceModelId': {
+ pnfs: {
+ 'pnfStoreKey': {
+ isMissingData: true,
+ action: 'None'
+ }
+ }
+ }
+ }
+ },
+ <ActionOnFirstLevel>{
+ type: PNFActions.DELETE_ACTION_PNF_INSTANCE,
+ firstLevelName: 'pnfs',
+ storeKey: 'pnfStoreKey',
+ serviceId: 'serviceModelId'
+ }).serviceInstance['serviceModelId'].pnfs['pnfStoreKey'];
+
+ expect(pnfState).toBeDefined();
+ expect(pnfState.action).toEqual(ServiceInstanceActions.None_Delete);
+ });
+
+ test('#UNDO_DELETE_ACTION_PNF_INSTANCE', () => {
+ let pnfState = pnfReducer(<any>{
+ serviceInstance: {
+ 'serviceModelId': {
+ pnfs: {
+ 'pnfStoreKey': {
+ isMissingData: true,
+ action: 'Update_Delete'
+ }
+ }
+ }
+ }
+ },
+ <ActionOnFirstLevel>{
+ type: PNFActions.UNDO_DELETE_ACTION_PNF_INSTANCE,
+ storeKey: 'pnfStoreKey',
+ firstLevelName: 'pnfs',
+ serviceId: 'serviceModelId'
+ }).serviceInstance['serviceModelId'].pnfs['pnfStoreKey'];
+
+ expect(pnfState).toBeDefined();
+ expect(pnfState.action).toEqual(ServiceInstanceActions.Update);
+ });
+
+ test('#REMOVE_PNF_INSTANCE', () => {
+ let pnfs = pnfReducer(<any>{
+ serviceInstance: {
+ 'serviceModelId': {
+ pnfs: {
+ 'pnfStoreKey': {
+ isMissingData: true,
+ action: 'Update_Delete'
+ },
+ 'pnfStoreKey_1': {
+ isMissingData: true,
+ action: 'Update_Delete'
+ }
+ }
+ }
+ }
+ },
+ <RemovePnfInstanceAction>{
+ type: PNFActions.REMOVE_PNF_INSTANCE,
+ pnfStoreKey: 'pnfStoreKey',
+ serviceId: 'serviceModelId'
+ }).serviceInstance['serviceModelId'].pnfs;
+
+ expect(pnfs).toBeDefined();
+ expect(pnfs['pnfStoreKey']).toBeUndefined();
+ expect(pnfs['pnfStoreKey_1']).toBeDefined();
+ });
+
+ test('#UPDATE_PNF_POSITION', () => {
+ let pnfInstance: PnfInstance = new PnfInstance();
+ pnfInstance.isMissingData = false;
+ pnfInstance.instanceName = 'instanceName';
+ let pnfState = pnfReducer(<any>{
+ serviceInstance: {
+ 'serviceModelId': {
+ pnfs: {
+ "pnfStoreKey": {}
+ }
+ }
+ }
+ },
+ <UpdatePnfPosition>{
+ type: PNFActions.UPDATE_PNF_POSITION,
+ node: <any>{
+ position: 2
+ },
+ pnfStoreKey: 'pnfStoreKey',
+ instanceId: 'serviceModelId'
+ }).serviceInstance['serviceModelId'].pnfs['pnfStoreKey'];
+
+ expect(pnfState).toBeDefined();
+ expect(pnfState.position).toEqual(2);
+ });
+});
diff --git a/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.reducers.ts b/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.reducers.ts
new file mode 100644
index 000000000..aeeae4d4e
--- /dev/null
+++ b/vid-webpack-master/src/app/shared/storeUtil/utils/pnf/pnf.reducers.ts
@@ -0,0 +1,87 @@
+import {Action} from "redux";
+import {PnfInstance} from "../../../models/pnfInstance";
+import {
+ CreatePnfInstanceAction,
+ RemovePnfInstanceAction,
+ UpdatePnfInstanceAction, UpdatePnfPosition,
+ PNFActions
+} from "./pnf.actions";
+import * as _ from "lodash";
+import {ServiceState} from "../main.reducer";
+import {ServiceInstanceActions} from "../../../models/serviceInstanceActions";
+import {deleteFirstLevel, updateServiceValidationCounter, calculateNextUniqueModelName, updateUniqueNames} from "../reducersHelper";
+import {ActionOnFirstLevel} from "../firstLevel/firstLevel.actions";
+
+export function pnfReducer(state: ServiceState, action: Action): ServiceState {
+ switch (action.type) {
+ case PNFActions.CREATE_PNF_INSTANCE: {
+ const updatePnfInstanceAction = <CreatePnfInstanceAction>action;
+ const serviceUuid = updatePnfInstanceAction.serviceUuid;
+ let pnfModelName = updatePnfInstanceAction.pnfModelName;
+ let newState = _.cloneDeep(state);
+
+ updatePnfInstanceAction.pnfInstance.originalName = pnfModelName;
+ updatePnfInstanceAction.pnfModelName = calculateNextUniqueModelName(pnfModelName, serviceUuid, newState, 'pnfs');
+
+ let pnfInstance: PnfInstance = newState.serviceInstance[serviceUuid].pnfs[pnfModelName];
+ pnfInstance = new PnfInstance();
+ updatePnfInstanceAction.pnfInstance.pnfStoreKey = updatePnfInstanceAction.pnfModelName;
+ updatePnfInstanceAction.pnfInstance.originalName = pnfModelName;
+ pnfInstance.originalName = updatePnfInstanceAction.pnfInstance.originalName;
+ pnfInstance.pnfStoreKey = updatePnfInstanceAction.pnfInstance.pnfStoreKey;
+ updateServiceValidationCounter(newState, pnfInstance['isMissingData'], updatePnfInstanceAction.pnfInstance['isMissingData'], serviceUuid);
+
+ newState.serviceInstance[serviceUuid].pnfs[updatePnfInstanceAction.pnfModelName] = Object.assign(pnfInstance, updatePnfInstanceAction.pnfInstance);
+ return newState;
+ }
+
+ case PNFActions.UPDATE_PNF_INSTANCE: {
+ const updatePnfInstanceAction = <UpdatePnfInstanceAction>action;
+ const serviceUuid = updatePnfInstanceAction.serviceUuid;
+ let pnfStoreKey = updatePnfInstanceAction.pnfStoreKey;
+
+ let newState = _.cloneDeep(state);
+ let pnfInstance: PnfInstance = newState.serviceInstance[serviceUuid].pnfs[pnfStoreKey];
+ let oldInstanceName = pnfInstance ? pnfInstance.instanceName : null;
+ updateUniqueNames(oldInstanceName, updatePnfInstanceAction.pnfInstance.instanceName, newState.serviceInstance[serviceUuid]);
+
+ pnfInstance = pnfInstance || new PnfInstance();
+ updateServiceValidationCounter(newState, pnfInstance['isMissingData'], updatePnfInstanceAction.pnfInstance['isMissingData'], serviceUuid);
+
+ newState.serviceInstance[serviceUuid].pnfs[pnfStoreKey] = Object.assign(pnfInstance, updatePnfInstanceAction.pnfInstance);
+ return newState;
+ }
+
+ case PNFActions.DELETE_ACTION_PNF_INSTANCE : {
+ return deleteFirstLevel(state, <ActionOnFirstLevel>action,true);
+ }
+
+ case PNFActions.UNDO_DELETE_ACTION_PNF_INSTANCE : {
+ let newState = _.cloneDeep(state);
+ let pnf = newState.serviceInstance[(<ActionOnFirstLevel>action).serviceId].pnfs[(<ActionOnFirstLevel>action).storeKey];
+ let oldState = pnf.action;
+ newState.serviceInstance[(<ActionOnFirstLevel>action).serviceId].pnfs[(<ActionOnFirstLevel>action).storeKey].action = (oldState.split('_')[0]) as ServiceInstanceActions;
+ updateServiceValidationCounter(newState, pnf['isMissingData'], false, (<ActionOnFirstLevel>action).serviceId);
+ return newState;
+ }
+
+ case PNFActions.REMOVE_PNF_INSTANCE : {
+ let newState = _.cloneDeep(state);
+ let pnfInstance = newState.serviceInstance[(<RemovePnfInstanceAction>action).serviceId].pnfs[(<RemovePnfInstanceAction>action).pnfStoreKey];
+ updateServiceValidationCounter(newState, pnfInstance['isMissingData'], false, (<RemovePnfInstanceAction>action).serviceId);
+ delete newState.serviceInstance[(<RemovePnfInstanceAction>action).serviceId].pnfs[(<RemovePnfInstanceAction>action).pnfStoreKey];
+ return newState;
+ }
+
+ case PNFActions.UPDATE_PNF_POSITION : {
+ let newState = _.cloneDeep(state);
+ newState.serviceInstance[(<UpdatePnfPosition>action).instanceId]
+ .pnfs[(<UpdatePnfPosition>action).pnfStoreKey]
+ .position = (<UpdatePnfPosition>action).node.position;
+ return newState;
+ }
+ }
+}
+
+
+
diff --git a/vid-webpack-master/src/app/shared/storeUtil/utils/reducersHelper.ts b/vid-webpack-master/src/app/shared/storeUtil/utils/reducersHelper.ts
index c192ece48..0291a3b5c 100644
--- a/vid-webpack-master/src/app/shared/storeUtil/utils/reducersHelper.ts
+++ b/vid-webpack-master/src/app/shared/storeUtil/utils/reducersHelper.ts
@@ -2,6 +2,7 @@ import * as _ from "lodash";
import {ActionOnFirstLevel} from "./firstLevel/firstLevel.actions";
import {ServiceInstanceActions} from "../../models/serviceInstanceActions";
import {ServiceState} from "./main.reducer";
+import {ServiceInstance} from "../../models/serviceInstance";
export function deleteFirstLevel(state: ServiceState, action: ActionOnFirstLevel,shouldUpdateServiceValidationCounter: boolean){
let newState = _.cloneDeep(state);
@@ -28,3 +29,26 @@ function resetUpgradeStatus(newState: any, serviceUuid: string){
newState.serviceInstance[serviceUuid].upgradedVFMSonsCounter = 0;
newState.serviceInstance[serviceUuid].isUpgraded = false;
}
+
+export const updateUniqueNames = (oldName: string, newName: string, serviceInstance: ServiceInstance): void => {
+ let existingNames = serviceInstance.existingNames;
+ if (!_.isNil(oldName) && oldName.toLowerCase() in existingNames) {
+ delete existingNames[oldName.toLowerCase()];
+ }
+ if (!_.isNil(newName)) {
+ existingNames[newName.toLowerCase()] = "";
+ }
+};
+
+
+export const calculateNextUniqueModelName = (nfModelName: string, serviceId: string, state: any, levelName: string): string => {
+ let counter: number = null;
+ while (true) {
+ let pattern = !_.isNil(counter) ? ("_" + counter) : "";
+ if (!_.isNil(state.serviceInstance[serviceId][levelName][nfModelName + pattern])) {
+ counter = counter ? (counter + 1) : 1;
+ } else {
+ return nfModelName + pattern;
+ }
+ }
+};
diff --git a/vid-webpack-master/src/app/shared/storeUtil/utils/vnf/vnf.reducers.ts b/vid-webpack-master/src/app/shared/storeUtil/utils/vnf/vnf.reducers.ts
index c5cd88aa7..b5bcec955 100644
--- a/vid-webpack-master/src/app/shared/storeUtil/utils/vnf/vnf.reducers.ts
+++ b/vid-webpack-master/src/app/shared/storeUtil/utils/vnf/vnf.reducers.ts
@@ -7,10 +7,9 @@ import {
VNFActions
} from "./vnf.actions";
import * as _ from "lodash";
-import {ServiceInstance} from "../../../models/serviceInstance";
import {ServiceState} from "../main.reducer";
import {ServiceInstanceActions} from "../../../models/serviceInstanceActions";
-import {deleteFirstLevel, updateServiceValidationCounter} from "../reducersHelper";
+import {deleteFirstLevel, updateServiceValidationCounter, calculateNextUniqueModelName, updateUniqueNames} from "../reducersHelper";
import {ActionOnFirstLevel} from "../firstLevel/firstLevel.actions";
export function vnfReducer(state: ServiceState, action: Action): ServiceState {
@@ -126,27 +125,3 @@ export function vnfReducer(state: ServiceState, action: Action): ServiceState {
}
}
-
-
-const updateUniqueNames = (oldName: string, newName: string, serviceInstance: ServiceInstance): void => {
- let existingNames = serviceInstance.existingNames;
- if (!_.isNil(oldName) && oldName.toLowerCase() in existingNames) {
- delete existingNames[oldName.toLowerCase()];
- }
- if (!_.isNil(newName)) {
- existingNames[newName.toLowerCase()] = "";
- }
-};
-
-
-export const calculateNextUniqueModelName = (vnfModelName: string, serviceId: string, state: any, levelName: string): string => {
- let counter: number = null;
- while (true) {
- let pattern = !_.isNil(counter) ? ("_" + counter) : "";
- if (!_.isNil(state.serviceInstance[serviceId][levelName][vnfModelName + pattern])) {
- counter = counter ? (counter + 1) : 1;
- } else {
- return vnfModelName + pattern;
- }
- }
-};
diff --git a/vid-webpack-master/src/app/shared/storeUtil/utils/vrf/vrf.reducer.ts b/vid-webpack-master/src/app/shared/storeUtil/utils/vrf/vrf.reducer.ts
index f3d81209e..33992ddfe 100644
--- a/vid-webpack-master/src/app/shared/storeUtil/utils/vrf/vrf.reducer.ts
+++ b/vid-webpack-master/src/app/shared/storeUtil/utils/vrf/vrf.reducer.ts
@@ -7,7 +7,7 @@ import {
CreateVRFInstanceAction, DeleteActionVrfInstanceAction, UndoDeleteActionVrfInstanceAction,
VrfActions
} from "./vrf.actions";
-import {calculateNextUniqueModelName} from "../vnf/vnf.reducers";
+import {calculateNextUniqueModelName} from "../reducersHelper";
import {ServiceInstanceActions} from "../../../models/serviceInstanceActions";
export function vrfReducer(state: ServiceState, action: Action): ServiceState {