Skip to content

Commit

Permalink
Improve handling of maxed state and observables (#3370)
Browse files Browse the repository at this point in the history
* Store more maxed detail in store instead of deduced later on

* Make maxed style pagination entity observables opaque and accessible
- Enables other entities to easily use observables for determinng maxed world state
- Add additional obs to PaginationObservables
- Tidy up endpoint service app observables
- Removed unused card-cf-usage component
  • Loading branch information
richard-cox authored and KlapTrap committed Jan 30, 2019
1 parent 80dabaf commit 9db90ca
Show file tree
Hide file tree
Showing 32 changed files with 147 additions and 198 deletions.
2 changes: 1 addition & 1 deletion src/frontend/app/features/cloud-foundry/cf.helpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -304,7 +304,7 @@ export function fetchTotalResults(

export const cfOrgSpaceFilter = (entities: APIResource[], paginationState: PaginationEntityState) => {
// Filtering is done remotely when maxedResults are hit (see `setMultiFilter`)
if (!!paginationState.maxedResults) {
if (!!paginationState.maxedMode) {
return entities;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { Injectable } from '@angular/core';
import { Store } from '@ngrx/store';
import { Observable, of as observableOf } from 'rxjs';
import { filter, first, map, publishReplay, refCount, switchMap } from 'rxjs/operators';
import { Observable } from 'rxjs';
import { filter, first, map, publishReplay, refCount } from 'rxjs/operators';

import { IApp, ICfV2Info, IOrganization, ISpace } from '../../../core/cf-api.types';
import { EntityService } from '../../../core/entity-service';
Expand Down Expand Up @@ -30,7 +30,10 @@ import {
createEntityRelationKey,
createEntityRelationPaginationKey,
} from '../../../store/helpers/entity-relations/entity-relations.types';
import { getPaginationObservables } from '../../../store/reducers/pagination-reducer/pagination-reducer.helper';
import {
getPaginationObservables,
PaginationObservables,
} from '../../../store/reducers/pagination-reducer/pagination-reducer.helper';
import { APIResource, EntityInfo } from '../../../store/types/api.types';
import { CfApplicationState } from '../../../store/types/application.types';
import { EndpointModel, EndpointUser } from '../../../store/types/endpoint.types';
Expand Down Expand Up @@ -58,10 +61,7 @@ export class CloudFoundryEndpointService {
hasSSHAccess$: Observable<boolean>;
totalMem$: Observable<number>;
paginationSubscription: any;
allApps$: Observable<APIResource<IApp>[]>;
hasAllApps$: Observable<boolean>;
loadingApps$: Observable<boolean>;
totalApps$: Observable<number>;
appsPagObs: PaginationObservables<APIResource<IApp>>;
users$: Observable<APIResource<CfUser>[]>;
orgs$: Observable<APIResource<IOrganization>[]>;
info$: Observable<EntityInfo<APIResource<ICfV2Info>>>;
Expand Down Expand Up @@ -172,34 +172,12 @@ export class CloudFoundryEndpointService {
}

constructAppObservables() {

const pagObs = getPaginationObservables<APIResource<IApp>>({
const paginationMonitor = this.pmf.create(this.getAllAppsAction.paginationKey, entityFactory(this.getAllAppsAction.entityKey));
this.appsPagObs = getPaginationObservables<APIResource<IApp>>({
store: this.store,
action: this.getAllAppsAction,
paginationMonitor: this.pmf.create(this.getAllAppsAction.paginationKey, entityFactory(this.getAllAppsAction.entityKey))
paginationMonitor
});

this.allApps$ = pagObs.entities$.pipe(// Ensure we sub to entities to kick off fetch process
switchMap(() => pagObs.pagination$),
filter(pagination => !!pagination && !!pagination.pageRequests && !!pagination.pageRequests[1] && !pagination.pageRequests[1].busy),
switchMap(pagination => pagination.maxedResults ? observableOf(null) : pagObs.entities$),
publishReplay(1),
refCount()
);

this.loadingApps$ = pagObs.entities$.pipe(// Ensure we sub to entities to kick off fetch process
switchMap(() => pagObs.pagination$),
filter(pagination => !!pagination && !!pagination.pageRequests && !!pagination.pageRequests[pagination.currentPage]),
map(pagination => pagination.pageRequests[pagination.currentPage].busy)
);

this.hasAllApps$ = this.allApps$.pipe(
map((allApps: APIResource<IApp>[]) => !!allApps)
);

this.totalApps$ = pagObs.pagination$.pipe(
map(pag => pag.totalResults)
);
}

private constructSecondaryObservable() {
Expand All @@ -209,7 +187,7 @@ export class CloudFoundryEndpointService {
p.entity.entity.app_ssh_host_key_fingerprint &&
p.entity.entity.app_ssh_oauth_client))
);
this.totalMem$ = this.allApps$.pipe(map(apps => this.getMetricFromApps(apps, 'memory')));
this.totalMem$ = this.appsPagObs.entities$.pipe(map(apps => this.getMetricFromApps(apps, 'memory')));

this.connected$ = this.endpoint$.pipe(
map(p => p.entity.connectionStatus === 'connected')
Expand All @@ -219,7 +197,7 @@ export class CloudFoundryEndpointService {
}

public getAppsInOrgViaAllApps(org: APIResource<IOrganization>): Observable<APIResource<IApp>[]> {
return this.allApps$.pipe(
return this.appsPagObs.entities$.pipe(
filter(allApps => !!allApps),
map(allApps => {
const spaces = org.entity.spaces || [];
Expand All @@ -230,7 +208,7 @@ export class CloudFoundryEndpointService {
}

public getAppsInSpaceViaAllApps(space: APIResource<ISpace>): Observable<APIResource<IApp>[]> {
return this.allApps$.pipe(
return this.appsPagObs.entities$.pipe(
filter(allApps => !!allApps),
map(apps => {
return apps.filter(a => a.entity.space_guid === space.metadata.guid);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ export abstract class OrgSpaceQuotaHelper<T = IOrganization | ISpace> {
public createStateObs(): Observable<CardStatus> {
return combineLatest(
this.hasQuotas(),
this.cfEndpointService.hasAllApps$
this.cfEndpointService.appsPagObs.hasEntities$
).pipe(
switchMap(([validQuotas, hasApps]) =>
// It can be expensive to iterate over apps to determine usage, so cut out early if there's no quotas or we can't determine all apps
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import { filter, map, publishReplay, refCount, switchMap } from 'rxjs/operators'

import { IServiceInstance } from '../../../core/cf-api-svc.types';
import { IApp, IOrganization, IPrivateDomain, IQuotaDefinition, ISpace } from '../../../core/cf-api.types';
import { getStartedAppInstanceCount, getEntityFlattenedList } from '../../../core/cf.helpers';
import { getEntityFlattenedList, getStartedAppInstanceCount } from '../../../core/cf.helpers';
import { EntityServiceFactory } from '../../../core/entity-service-factory.service';
import { CfUserService } from '../../../shared/data-services/cf-user.service';
import { PaginationMonitorFactory } from '../../../shared/monitors/pagination-monitor.factory';
Expand Down Expand Up @@ -153,11 +153,11 @@ export class CloudFoundryOrganizationService {

this.totalMem$ = this.apps$.pipe(map(a => this.cfEndpointService.getMetricFromApps(a, 'memory')));

this.appCount$ = this.cfEndpointService.hasAllApps$.pipe(
this.appCount$ = this.cfEndpointService.appsPagObs.hasEntities$.pipe(
switchMap(hasAllApps => hasAllApps ? this.countExistingApps() : this.fetchAppCount()),
);

this.loadingApps$ = this.cfEndpointService.loadingApps$;
this.loadingApps$ = this.cfEndpointService.appsPagObs.fetchingEntities$;
}

private countExistingApps(): Observable<number> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -163,11 +163,11 @@ export class CloudFoundrySpaceService {
map(a => this.cfEndpointService.getMetricFromApps(a, 'memory'))
);

this.appCount$ = this.cfEndpointService.hasAllApps$.pipe(
this.appCount$ = this.cfEndpointService.appsPagObs.hasEntities$.pipe(
switchMap(hasAllApps => hasAllApps ? this.countExistingApps() : this.fetchAppCount()),
);

this.loadingApps$ = this.cfEndpointService.loadingApps$;
this.loadingApps$ = this.cfEndpointService.appsPagObs.fetchingEntities$;
}

private countExistingApps(): Observable<number> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
<app-tile>
<app-card-number-metric link="/cloud-foundry/{{cfSpaceService.cfGuid}}/organizations/{{cfSpaceService.orgGuid}}/spaces/{{cfSpaceService.spaceGuid}}/apps" icon="apps" label="Applications" labelSingular="Application" value="{{ cfSpaceService.appCount$ | async }}"></app-card-number-metric>
</app-tile>
<app-tile *ngIf="cfEndpointService.hasAllApps$ | async">
<app-tile *ngIf="cfEndpointService.appsPagObs.hasEntities$ | async">
<app-card-number-metric icon="content_copy" label="App Instances" value="{{ (cfSpaceService.appInstances$ | async) }}" limit="{{ (cfSpaceService.quotaDefinition$ | async)?.entity.app_instance_limit}}"></app-card-number-metric>
</app-tile>
<app-tile>
Expand All @@ -26,7 +26,7 @@
<app-tile>
<app-card-number-metric link="/cloud-foundry/{{cfSpaceService.cfGuid}}/organizations/{{cfSpaceService.orgGuid}}/spaces/{{cfSpaceService.spaceGuid}}/service-instances" iconFont="stratos-icons" icon="service" label="Service Instances" value="{{ (cfSpaceService.serviceInstances$ | async)?.length }}" limit="{{ (cfSpaceService.quotaDefinition$ | async)?.entity.total_services }}"></app-card-number-metric>
</app-tile>
<app-tile *ngIf="cfEndpointService.hasAllApps$ | async">
<app-tile *ngIf="cfEndpointService.appsPagObs.hasEntities$ | async">
<app-card-number-metric icon="memory" label="Memory Usage" units="mb" value="{{ (cfSpaceService.totalMem$ | async) }}" limit="{{ (cfSpaceService.quotaDefinition$ | async)?.entity.memory_limit }}"></app-card-number-metric>
</app-tile>
</app-tile-group>
Expand All @@ -38,4 +38,4 @@
</app-tile-group>
</app-loading-page>
</app-tile-grid>
</div>
</div>
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { Component } from '@angular/core';
import { combineLatest, Observable } from 'rxjs';
import { map, startWith } from 'rxjs/operators';
import { filter, map, startWith } from 'rxjs/operators';

import { CloudFoundryEndpointService } from '../../../../../services/cloud-foundry-endpoint.service';
import { CloudFoundrySpaceService } from '../../../../../services/cloud-foundry-space.service';
Expand All @@ -18,7 +18,9 @@ export class CloudFoundrySpaceSummaryComponent {
public cfSpaceService: CloudFoundrySpaceService
) {
this.detailsLoading$ = combineLatest([
cfEndpointService.hasAllApps$,
cfEndpointService.appsPagObs.fetchingEntities$.pipe(
filter(loading => !loading)
),
cfSpaceService.appCount$,
cfSpaceService.allSpaceUsers$
]).pipe(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
<app-tile>
<app-card-number-metric [link]="appLink" icon="apps" label="Applications" labelSingular="Application" value="{{ cfOrgService.appCount$ | async }}"></app-card-number-metric>
</app-tile>
<app-tile *ngIf="cfEndpointService.hasAllApps$ | async">
<app-tile *ngIf="cfEndpointService.appsPagObs.hasEntities$ | async">
<app-card-number-metric icon="content_copy" label="App Instances" value="{{ (cfOrgService.appInstances$ | async) }}" limit="{{ (cfOrgService.quotaDefinition$ | async)?.app_instance_limit}}"></app-card-number-metric>
</app-tile>
<app-tile>
Expand All @@ -31,7 +31,7 @@
<app-tile>
<app-card-number-metric iconFont="stratos-icons" icon="service" label="Service Instances" value="{{ (cfOrgService.serviceInstances$ | async)?.length }}" limit="{{ (cfOrgService.quotaDefinition$ | async)?.total_services }}"></app-card-number-metric>
</app-tile>
<app-tile *ngIf="cfEndpointService.hasAllApps$ | async">
<app-tile *ngIf="cfEndpointService.appsPagObs.hasEntities$ | async">
<app-card-number-metric icon="memory" label="Memory Usage" units="mb" value="{{ (cfOrgService.totalMem$ | async) }}" limit="{{ (cfOrgService.quotaDefinition$ | async)?.memory_limit }}"></app-card-number-metric>
</app-tile>
</app-tile-group>
Expand All @@ -42,4 +42,4 @@
</app-tile-group>
</app-loading-page>
</app-tile-grid>
</div>
</div>
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { Component } from '@angular/core';
import { Store } from '@ngrx/store';
import { combineLatest, Observable } from 'rxjs';
import { map, startWith } from 'rxjs/operators';
import { filter, map, startWith } from 'rxjs/operators';

import { AppState } from '../../../../../store/app-state';
import { goToAppWall } from '../../../cf.helpers';
Expand All @@ -27,7 +27,9 @@ export class CloudFoundryOrganizationSummaryComponent {
goToAppWall(store, cfOrgService.cfGuid, cfOrgService.orgGuid);
};
this.detailsLoading$ = combineLatest([
cfEndpointService.hasAllApps$,
cfEndpointService.appsPagObs.fetchingEntities$.pipe(
filter(loading => !loading)
),
cfOrgService.allOrgUsers$,
cfOrgService.appCount$
]).pipe(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,23 +8,23 @@
<app-loading-page [isLoading]="detailsLoading$" text="Retrieving details">
<app-tile-group>
<app-tile>
<app-card-number-metric [link]="appLink" icon="apps" label="Applications" labelSingular="Application" value="{{ (cfEndpointService.totalApps$ | async) }}"></app-card-number-metric>
<app-card-number-metric [link]="appLink" icon="apps" label="Applications" labelSingular="Application" value="{{ (cfEndpointService.appsPagObs.totalEntities$ | async) }}"></app-card-number-metric>
</app-tile>
<app-tile>
<app-card-number-metric link="/cloud-foundry/{{cfEndpointService.cfGuid}}/organizations" iconFont="stratos-icons" icon="organization" label="Orgs" labelSingular="Org" value="{{ (cfEndpointService.orgs$ | async)?.length }}"></app-card-number-metric>
</app-tile>
<app-tile *ngIf="(cfEndpointService.users$ | async)?.length">
<app-card-number-metric link="/cloud-foundry/{{cfEndpointService.cfGuid}}/users" icon="person" label="Users" labelSingular="User" value="{{ (cfEndpointService.users$ | async)?.length }}"></app-card-number-metric>
</app-tile>
<app-tile *ngIf="cfEndpointService.hasAllApps$ | async">
<app-tile *ngIf="cfEndpointService.appsPagObs.hasEntities$ | async">
<app-card-number-metric icon="memory" units="mb" label="Memory Usage" value="{{ (cfEndpointService.totalMem$ | async) }}"></app-card-number-metric>
</app-tile>
</app-tile-group>
<app-tile-group>
<app-tile>
<app-card-cf-recent-apps *ngIf="!(detailsLoading$ | async)" [allApps$]="cfEndpointService.allApps$" [loading$]="cfEndpointService.loadingApps$" (refresh)="cfEndpointService.fetchApps()"></app-card-cf-recent-apps>
<app-card-cf-recent-apps *ngIf="!(detailsLoading$ | async)" [allApps$]="cfEndpointService.appsPagObs.entities$" [loading$]="cfEndpointService.appsPagObs.fetchingEntities$" (refresh)="cfEndpointService.fetchApps()"></app-card-cf-recent-apps>
</app-tile>
</app-tile-group>
</app-loading-page>
</app-tile-grid>
</div>
</div>
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { Component } from '@angular/core';
import { Store } from '@ngrx/store';
import { combineLatest, Observable } from 'rxjs';
import { map, startWith } from 'rxjs/operators';
import { filter, map, startWith } from 'rxjs/operators';

import { AppState } from '../../../../store/app-state';
import { goToAppWall } from '../../cf.helpers';
Expand All @@ -21,7 +21,9 @@ export class CloudFoundrySummaryTabComponent {
goToAppWall(store, cfEndpointService.cfGuid);
};
this.detailsLoading$ = combineLatest([
cfEndpointService.hasAllApps$,
cfEndpointService.appsPagObs.fetchingEntities$.pipe(
filter(loading => !loading)
),
cfEndpointService.users$
]).pipe(
map(() => false),
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
<ng-container *ngIf="(cfEndpointService.hasAllApps$ | async) !== false">
<ng-container *ngIf="(cfEndpointService.appsPagObs.hasEntities$ | async) !== false">
<mat-card class="recent-apps-card">
<mat-card-header class="recent-apps-card__header">
<mat-card-title>Recently updated applications</mat-card-title>
Expand All @@ -15,4 +15,4 @@
</div>
</mat-card-content>
</mat-card>
</ng-container>
</ng-container>

This file was deleted.

Empty file.

This file was deleted.

This file was deleted.

Loading

0 comments on commit 9db90ca

Please sign in to comment.