Skip to content

Commit 0eebe9c

Browse files
authored
Merge pull request #30 from OpenTOSCA/feature/multipleBuildPlans
Feature/multiple build plans
2 parents a718c89 + 9087a91 commit 0eebe9c

17 files changed

Lines changed: 1625 additions & 1340 deletions

package-lock.json

Lines changed: 1339 additions & 1148 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,8 @@
1414
"@angular-redux/form": "~9.0.1",
1515
"@angular-redux/router": "~9.0.0",
1616
"@angular-redux/store": "~9.0.0",
17-
"@angular/animations": "~7.2.0",
17+
"@angular/animations": "~7.2.10",
18+
"@angular/cdk": "~7.3.0",
1819
"@angular/common": "~7.2.0",
1920
"@angular/compiler": "~7.2.0",
2021
"@angular/core": "~7.2.0",
@@ -24,13 +25,13 @@
2425
"@angular/platform-browser-dynamic": "~7.2.0",
2526
"@angular/router": "~7.2.0",
2627
"@fortawesome/fontawesome-free": "^5.6.3",
27-
"core-js": "^2.6.2",
28-
"fuse.js": "^3.3.0",
28+
"core-js": "^2.6.5",
29+
"fuse.js": "^3.4.4",
2930
"lodash": "^4.17.11",
3031
"ng-spin-kit": "^5.1.1",
3132
"primeflex": "^1.0.0-rc.1",
3233
"primeicons": "^1.0.0",
33-
"primeng": "7.0.0-beta.1",
34+
"primeng": "^7.1.0",
3435
"redux": "^4.0.1",
3536
"redux-localstorage": "^0.4.1",
3637
"redux-logger": "^3.0.6",
@@ -40,9 +41,9 @@
4041
"zone.js": "~0.8.27"
4142
},
4243
"devDependencies": {
43-
"@angular-devkit/build-angular": "~0.12.1",
44+
"@angular-devkit/build-angular": "^0.13.6",
4445
"@angular/cli": "~7.2.1",
45-
"@angular/compiler-cli": "~7.2.0",
46+
"@angular/compiler-cli": "^7.2.10",
4647
"@angular/language-service": "~7.2.0",
4748
"@types/jasmine": "~3.3.5",
4849
"@types/jasminewd2": "~2.0.6",

src/app/application-management/application-detail/application-detail-resolver.service.ts

Lines changed: 26 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -18,32 +18,39 @@ import { LoggerService } from '../../core/service/logger.service';
1818
import { Csar } from '../../core/model/csar.model';
1919
import { forkJoin, Observable, of } from 'rxjs';
2020
import { catchError, mergeMap } from 'rxjs/operators';
21-
import { Plan } from '../../core/model/plan.model';
21+
import { Interface } from '../../core/model/interface.model';
22+
import { PlanTypes } from '../../core/model/plan-types.model';
2223

2324
@Injectable()
24-
export class ApplicationDetailResolverService implements Resolve<{ csar: Csar, buildPlan: Plan, terminationPlan: Plan }> {
25+
export class ApplicationDetailResolverService implements Resolve<{ csar: Csar, interfaces: Interface[] }> {
2526

26-
constructor(private applicationService: ApplicationManagementService, private logger: LoggerService) {
27+
constructor(private applicationService: ApplicationManagementService, private logger: LoggerService,) {
2728
}
2829

29-
resolve(route: ActivatedRouteSnapshot): Observable<{ csar: Csar, buildPlan: Plan, terminationPlan: Plan }> {
30+
resolve(route: ActivatedRouteSnapshot): Observable<{ csar: Csar, buildPlanAvailable: boolean, terminationPlanAvailable: boolean, interfaces: Interface[] }> {
3031
return forkJoin(
3132
this.applicationService.getCsar(route.params['id']),
32-
this.applicationService.getBuildPlan(route.params['id'])
33-
.pipe(
34-
catchError(() => of(null))
35-
),
36-
this.applicationService.getTerminationPlan(route.params['id'])
37-
.pipe(
38-
catchError(() => of(null))
39-
)
33+
this.applicationService.getInterfaces(route.params['id']),
4034
)
41-
.pipe(
42-
mergeMap(result => {
43-
return of({csar: result[0], buildPlan: result[1], terminationPlan: result[2]});
44-
}),
45-
catchError(reason => {
46-
return this.logger.handleError('[application-detail-resolver.service][resolve]', reason);
47-
}));
35+
.pipe(
36+
mergeMap(result => {
37+
const interfaces = <Interface[]>result[1];
38+
39+
const buildPlanExists = interfaces.find(value =>
40+
!!value.operations.find(operation => operation._embedded.plan.plan_type === PlanTypes.BuildPlan)
41+
);
42+
const terminationPlanExists = interfaces.find(value =>
43+
!!value.operations.find(operation => operation._embedded.plan.plan_type === PlanTypes.TerminationPlan)
44+
);
45+
46+
return of({
47+
csar: result[0], buildPlanAvailable: !!buildPlanExists,
48+
terminationPlanAvailable: !!terminationPlanExists, interfaces: interfaces
49+
});
50+
}),
51+
catchError(reason => {
52+
return this.logger.handleError('[application-detail-resolver.service][resolve]', reason);
53+
})
54+
);
4855
}
4956
}

src/app/application-management/application-detail/application-detail.component.html

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -34,17 +34,17 @@ <h3>{{ csar.display_name }}</h3>
3434
<div class="ui-toolbar-group-left">
3535
<button pButton type="button" icon="fas fa-plus"
3636
pTooltip="Provision new instance..." showDelay="300" tooltipPosition="right"
37-
[disabled]="(buildPlan | async) === null"
38-
(click)="dialogVisible = true"></button>
37+
[disabled]="!buildPlanExists"
38+
(click)="selectBuildPlan()"></button>
3939
&nbsp;
4040
<button pButton type="button" icon="fas fa-sync-alt"
4141
pTooltip="Reload instances" showDelay="300" tooltipPosition="top"
4242
(click)="triggerReloadAppInstances()"></button>
4343
</div>
4444
</p-toolbar>
4545
<opentosca-application-instance-list
46-
[terminationPlanAvailable]="(terminationPlan | async) !== null"
47-
(terminateInstance)="emitTerminationPlan($event)">
46+
[terminationPlanAvailable]="terminationPlanExists"
47+
(terminateInstance)="selectTerminationPlan($event)">
4848
</opentosca-application-instance-list>
4949
</p-fieldset>
5050
</div>
@@ -74,6 +74,7 @@ <h3>{{ csar.display_name }}</h3>
7474
<ng-template #loading>
7575
<p>Loading app info...</p>
7676
</ng-template>
77-
<opentosca-management-plan-execution-dialog [(visible)]="dialogVisible" [plan]="buildPlan | async"
77+
<opentosca-management-plan-execution-dialog [(visible)]="dialogVisible" [plan_type]="selectedPlanType"
78+
[instanceId]="instanceId"
7879
[inputValidation]="true">
7980
</opentosca-management-plan-execution-dialog>

src/app/application-management/application-detail/application-detail.component.ts

Lines changed: 25 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -15,16 +15,15 @@ import { Component, OnDestroy, OnInit } from '@angular/core';
1515
import { NgRedux, select } from '@angular-redux/store';
1616
import { ActivatedRoute, Router } from '@angular/router';
1717
import { ApplicationManagementService } from '../../core/service/application-management.service';
18-
import { LoggerService } from '../../core/service/logger.service';
1918
import { AppState } from '../../store/app-state.model';
2019
import { BreadcrumbActions } from '../../core/component/breadcrumb/breadcrumb-actions';
2120
import { ApplicationManagementActions } from '../application-management-actions';
2221
import { Csar } from '../../core/model/csar.model';
23-
import { Plan } from '../../core/model/plan.model';
2422
import { Observable } from 'rxjs';
2523
import { GrowlActions } from '../../core/growl/growl-actions';
26-
import * as _ from 'lodash';
2724
import { ApplicationInstanceManagementService } from '../../core/service/application-instance-management.service';
25+
import { Interface } from '../../core/model/interface.model';
26+
import { PlanTypes } from '../../core/model/plan-types.model';
2827

2928
@Component({
3029
selector: 'opentosca-application-detail',
@@ -33,30 +32,33 @@ import { ApplicationInstanceManagementService } from '../../core/service/applica
3332
export class ApplicationDetailComponent implements OnInit, OnDestroy {
3433

3534
@select(['container', 'application', 'csar']) csar: Observable<Csar>;
36-
@select(['container', 'application', 'buildPlan']) buildPlan: Observable<Plan>;
37-
@select(['container', 'application', 'terminationPlan']) terminationPlan: Observable<Plan>;
3835

3936
public dialogVisible = false;
37+
public selectedPlanType: PlanTypes;
38+
public buildPlanExists = false;
39+
public terminationPlanExists = false;
40+
public instanceId: string;
4041

4142
constructor(private route: ActivatedRoute,
4243
private router: Router,
4344
private ngRedux: NgRedux<AppState>,
4445
private appService: ApplicationManagementService,
45-
private instancesService: ApplicationInstanceManagementService,
46-
private logger: LoggerService) {
46+
private instancesService: ApplicationInstanceManagementService) {
4747
}
4848

4949
ngOnInit(): void {
50-
this.route.data.subscribe((data: { application: { csar: Csar, buildPlan: Plan, terminationPlan: Plan } }) => {
50+
this.route.data.subscribe((data: { application: { csar: Csar, buildPlanAvailable: boolean, terminationPlanAvailable: boolean, interfaces: Interface[] } }) => {
5151
// Prepare breadcrumb
5252
this.ngRedux.dispatch(BreadcrumbActions.updateBreadcrumb([
53-
{label: 'Applications', routerLink: 'applications'},
54-
{label: data.application.csar.id, routerLink: ['applications', data.application.csar.id]}
53+
{ label: 'Applications', routerLink: 'applications' },
54+
{ label: data.application.csar.id, routerLink: ['applications', data.application.csar.id] }
5555
]));
5656
this.ngRedux.dispatch(ApplicationManagementActions.updateApplicationCsar(data.application.csar));
57-
this.ngRedux.dispatch(ApplicationManagementActions.updateBuildPlan(data.application.buildPlan));
58-
this.ngRedux.dispatch(ApplicationManagementActions.updateTerminationPlan(data.application.terminationPlan));
59-
if (data.application.buildPlan === null) {
57+
this.ngRedux.dispatch(ApplicationManagementActions.updateInterfaces(data.application.interfaces));
58+
59+
this.buildPlanExists = data.application.buildPlanAvailable;
60+
this.terminationPlanExists = data.application.terminationPlanAvailable;
61+
if (!this.buildPlanExists) {
6062
this.ngRedux.dispatch(GrowlActions.addGrowl(
6163
{
6264
severity: 'info',
@@ -95,20 +97,15 @@ export class ApplicationDetailComponent implements OnInit, OnDestroy {
9597
});
9698
}
9799

98-
emitTerminationPlan(terminationEvent: string): void {
99-
const terminationPlan = Object.assign({}, this.ngRedux.getState().container.application.terminationPlan);
100-
terminationPlan._links['self'].href = _.replace(terminationPlan._links['self'].href, ':id', terminationEvent);
101-
console.log(terminationPlan);
102-
this.appService.triggerManagementPlan(terminationPlan)
103-
.subscribe(result => {
104-
this.logger.log('[application-detail.component][emitTerminationPlan]', result);
105-
this.ngRedux.dispatch(GrowlActions.addGrowl(
106-
{
107-
severity: 'info',
108-
summary: 'Termination started',
109-
detail: 'The termination plan has been started.'
110-
}
111-
));
112-
});
100+
selectBuildPlan() {
101+
this.selectedPlanType = PlanTypes.BuildPlan;
102+
this.instanceId = null;
103+
this.dialogVisible = true;
104+
}
105+
106+
selectTerminationPlan(instanceId: string) {
107+
this.selectedPlanType = PlanTypes.TerminationPlan;
108+
this.instanceId = instanceId;
109+
this.dialogVisible = true;
113110
}
114111
}

src/app/application-management/application-management-actions.ts

Lines changed: 10 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ import { Action } from '../store/store.action';
1717
import { Csar } from '../core/model/csar.model';
1818
import { Plan } from '../core/model/plan.model';
1919
import { ServiceTemplateInstance } from '../core/model/service-template-instance.model';
20+
import { Interface } from '../core/model/interface.model';
2021

2122
@Injectable()
2223
export class ApplicationManagementActions {
@@ -28,10 +29,8 @@ export class ApplicationManagementActions {
2829
static CLEAR_APPLICATION_CSAR = 'CLEAR_APPLICATION_CSAR';
2930
static UPDATE_APPLICATION_INSTANCES = 'UPDATE_APPLICATION_INSTANCES';
3031
static CLEAR_APPLICATION_INSTANCES = 'CLEAR_APPLICATION_INSTANCES';
31-
static UPDATE_APPLICATION_INSTANCE = 'UPDATE_APPLICATION_INSTANCE';
32-
static CLEAR_APPLICATION_INSTANCE = 'CLEAR_APPLICATION_INSTANCE';
33-
static UPDATE_APPLICATION_BUILDPLAN = 'UPDATE_APPLICATION_BUILDPLAN';
34-
static UPDATE_APPLICATION_TERMINATIONPLAN = 'UPDATE_APPLICATION_TERMINATIONPLAN';
32+
static UPDATE_APPLICATION_INTERFACES ='UPDATE_APPLICATION_INTERFACES';
33+
static CLEAR_APPLICATION_INTERFACES ='CLEAR_APPLICATION_INTERFACES';
3534

3635
static updateApplications(csars: Array<Csar>): Action {
3736
return {
@@ -69,17 +68,16 @@ export class ApplicationManagementActions {
6968
};
7069
}
7170

72-
static updateBuildPlan(plan: Plan): Action {
71+
static updateInterfaces(ifaces: Interface[]): Action {
7372
return {
74-
type: ApplicationManagementActions.UPDATE_APPLICATION_BUILDPLAN,
75-
payload: plan
76-
};
73+
type: ApplicationManagementActions.UPDATE_APPLICATION_INTERFACES,
74+
payload: ifaces
75+
}
7776
}
7877

79-
static updateTerminationPlan(plan: Plan): Action {
78+
static clearInterfaces(): Action {
8079
return {
81-
type: ApplicationManagementActions.UPDATE_APPLICATION_TERMINATIONPLAN,
82-
payload: plan
83-
};
80+
type: ApplicationManagementActions.CLEAR_APPLICATION_INTERFACES
81+
}
8482
}
8583
}

src/app/application-management/application-management.module.ts

Lines changed: 5 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -25,21 +25,9 @@ import { ApplicationDetailResolverService } from './application-detail/applicati
2525
import { ApplicationOverviewComponent } from './application-overview/application-overview.component';
2626
import { RouterModule } from '@angular/router';
2727
import {
28-
AccordionModule,
29-
ButtonModule,
30-
CardModule,
31-
ConfirmationService,
32-
ConfirmDialogModule,
33-
DataTableModule,
34-
DialogModule,
35-
FieldsetModule,
36-
FileUploadModule,
37-
ProgressBarModule,
38-
SharedModule,
39-
TabViewModule,
40-
ScrollPanelModule,
41-
ToolbarModule,
42-
TooltipModule, ProgressSpinnerModule, InputTextareaModule, PanelModule
28+
AccordionModule, ButtonModule, CardModule, ConfirmationService, ConfirmDialogModule, DataTableModule, DialogModule,
29+
DropdownModule, FieldsetModule, FileUploadModule, InputTextareaModule, PanelModule, ProgressBarModule,
30+
ProgressSpinnerModule, ScrollPanelModule, SharedModule, TabViewModule, ToolbarModule, TooltipModule
4331
} from 'primeng/primeng';
4432
import { FormsModule } from '@angular/forms';
4533
import { NgSpinKitModule } from 'ng-spin-kit';
@@ -80,7 +68,8 @@ import { ApplicationInstanceBoundaryDefinitionInterfacesListComponent } from './
8068
TabViewModule,
8169
CoreModule,
8270
ToolbarModule,
83-
ButtonModule
71+
ButtonModule,
72+
DropdownModule,
8473
],
8574
declarations: [
8675
ApplicationDetailComponent,

src/app/application-management/application-management.reducer.ts

Lines changed: 14 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -15,32 +15,25 @@
1515
import { Action } from '../store/store.action';
1616
import { ApplicationManagementActions } from './application-management-actions';
1717
import { Csar } from '../core/model/csar.model';
18-
import { Plan } from '../core/model/plan.model';
1918
import { ServiceTemplateInstance } from '../core/model/service-template-instance.model';
19+
import { Interface } from '../core/model/interface.model';
2020

2121
export interface ApplicationManagementState {
2222
applications?: Array<Csar>;
2323
application?: {
2424
csar?: Csar;
25-
buildPlan?: Plan;
26-
terminationPlan?: Plan;
2725
instances: Map<string, ServiceTemplateInstance>;
26+
interfaces: Interface[];
2827
};
2928
}
3029

3130
export const INITIAL_STATE: ApplicationManagementState = {
3231
applications: [],
3332
application: {
3433
csar: null,
35-
buildPlan: null,
36-
terminationPlan: null,
37-
instances: new Map<string, ServiceTemplateInstance>()
38-
},
39-
// currentApp: null,
40-
// currentAppInstances: [],
41-
// currentInstance: null,
42-
// buildPlan: null,
43-
// currentTerminationPlan: null
34+
instances: new Map<string, ServiceTemplateInstance>(),
35+
interfaces: null
36+
}
4437
};
4538

4639
export function applicationManagementReducer(state: ApplicationManagementState = INITIAL_STATE,
@@ -60,28 +53,29 @@ export function applicationManagementReducer(state: ApplicationManagementState =
6053
...state.application, csar: action.payload
6154
}
6255
});
63-
case ApplicationManagementActions.UPDATE_APPLICATION_BUILDPLAN:
56+
case ApplicationManagementActions.UPDATE_APPLICATION_INSTANCES:
6457
return Object.assign({}, state, {
6558
application: {
66-
...state.application, buildPlan: action.payload
59+
...state.application, instances: action.payload
6760
}
6861
});
69-
case ApplicationManagementActions.UPDATE_APPLICATION_TERMINATIONPLAN:
62+
case ApplicationManagementActions.CLEAR_APPLICATION_INSTANCES:
7063
return Object.assign({}, state, {
7164
application: {
72-
...state.application, terminationPlan: action.payload
65+
...state.application, instances: []
7366
}
7467
});
75-
case ApplicationManagementActions.UPDATE_APPLICATION_INSTANCES:
68+
case ApplicationManagementActions.UPDATE_APPLICATION_INTERFACES:
7669
return Object.assign({}, state, {
7770
application: {
78-
...state.application, instances: action.payload
71+
...state.application, interfaces: action.payload
7972
}
8073
});
81-
case ApplicationManagementActions.CLEAR_APPLICATION_INSTANCES:
74+
case ApplicationManagementActions.CLEAR_APPLICATION_INTERFACES:
8275
return Object.assign({}, state, {
8376
application: {
84-
...state.application, instances: []
77+
...state.application,
78+
interfaces: []
8579
}
8680
});
8781
default:

0 commit comments

Comments
 (0)