Skip to content

Commit

Permalink
Merge pull request #20 from StatCan/18-destroy-old-notebooks
Browse files Browse the repository at this point in the history
Support notebook volume (PVC) management
  • Loading branch information
brendangadd authored Oct 6, 2020
2 parents 1a50add + 4fabd14 commit 2e9daf6
Show file tree
Hide file tree
Showing 20 changed files with 446 additions and 178 deletions.
4 changes: 3 additions & 1 deletion frontend/src/app/app.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ import { NamespaceSelectComponent } from "./main-table/namespace-select/namespac
import { ResourceTableComponent } from "./main-table/resource-table/resource-table.component";
import { SnackBarComponent } from "./services/snack-bar/snack-bar.component";
import { ResourceFormComponent } from "./resource-form/resource-form.component";
import { ConfirmDialogComponent } from "./main-table/resource-table/confirm-dialog/confirm-dialog.component";
import { ConfirmDialogComponent } from "./main-table/confirm-dialog/confirm-dialog.component";
import { VolumeComponent } from "./resource-form/volume/volume.component";
import { FormNameComponent } from "./resource-form/form-name/form-name.component";
import { FormImageComponent } from "./resource-form/form-image/form-image.component";
Expand All @@ -48,6 +48,7 @@ import { RokFormDataVolumesComponent } from "./uis/rok/rok-resource-form/rok-for
import { RokErrorMsgComponent } from "./uis/rok/rok-error-msg/rok-error-msg.component";
import { FormConfigurationsComponent } from "./resource-form/form-configurations/form-configurations.component";
import { FormGpusComponent } from "./resource-form/form-gpus/form-gpus.component";
import { VolumeTableComponent } from "./main-table/volumes-table/volume-table.component";


@NgModule({
Expand Down Expand Up @@ -77,6 +78,7 @@ import { FormGpusComponent } from "./resource-form/form-gpus/form-gpus.component
RokErrorMsgComponent,
FormConfigurationsComponent,
FormGpusComponent,
VolumeTableComponent,
],
imports: [
BrowserModule,
Expand Down
17 changes: 16 additions & 1 deletion frontend/src/app/main-table/main-table.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,21 @@
<!-- The Table showing our Resource -->
<div class="parent" [class.spacing]="ns.dashboardConnected()">
<div class="spacer"></div>
<app-resource-table></app-resource-table>
<app-resource-table
[notebooks]="resources"
(deleteNotebookEvent)="deleteResource($event)"
></app-resource-table>
<div class="spacer"></div>
</div>

<!-- The Table showing the persistent volume claims -->
<div class="parent spacing">
<div class="spacer"></div>
<app-volume-table
[pvcProperties]="pvcProperties"
(deletePvcEvent)="deletePvc($event)"
>
</app-volume-table>
<div class="spacer"></div>
</div>

95 changes: 95 additions & 0 deletions frontend/src/app/main-table/main-table.component.scss
Original file line number Diff line number Diff line change
Expand Up @@ -9,3 +9,98 @@
.spacing {
padding-top: 1.5rem;
}

.card {
width: 900px;
padding: 0px;
border-radius: 5px;
background: white;
}

table {
width: 100%;
}

.header {
display: flex;
align-items: center;
padding: 0px 16px 0px 16px;
height: 64px;
}

.header mat-icon {
margin: 3px 10px 0 0;
}

.header p {
font-weight: 400;
font-size: 20px;
}

.cdk-column-actions {
text-align: center;
}

.mat-icon {
line-height: 0.85;
}

td.mat-cell:last-of-type,
td.mat-footer-cell:last-of-type,
th.mat-header-cell:last-of-type {
padding-right: 0px;
}

.inline {
display: inline-block;
}

// Status Icons
.running {
color: green;
}

.warning {
color: orange;
}

.error {
color: red;
}

.status {
display: inline-flex;
vertical-align: middle;
}

.delete {
color: red;
}

// Flex
.parent {
display: flex;
}

.spacer {
flex-grow: 1;
}

th,
td {
overflow: hidden;
text-overflow: ellipsis;
}

td.mat-column-image,
td.mat-column-name {
max-width: 200px;
}

td.mat-column-cpu {
width: 40px;
}

td.mat-column-actions{
text-align: center;
}
81 changes: 76 additions & 5 deletions frontend/src/app/main-table/main-table.component.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,87 @@
import { Component, OnInit } from "@angular/core";
import { NamespaceService } from "../services/namespace.service";
import {Component, OnInit} from "@angular/core";
import {NamespaceService} from "../services/namespace.service";
import {KubernetesService} from "src/app/services/kubernetes.service";

import {Subscription} from "rxjs";
import {isEqual} from "lodash";
import {first} from "rxjs/operators";

import {ExponentialBackoff} from "src/app/utils/polling";
import {Volume, Resource} from "../utils/types";
import {PvcWithStatus} from "./volumes-table/volume-table.component"

@Component({
selector: "app-main-table",
templateUrl: "./main-table.component.html",
styleUrls: ["./main-table.component.scss"]
})
export class MainTableComponent implements OnInit {
currNamespace = "";
namespaces = [];
currNamespace: string;
resources = [];

pvcs: Volume[] = [];
pvcProperties: PvcWithStatus[] = [];

subscriptions = new Subscription();
poller: ExponentialBackoff;

constructor(
public ns: NamespaceService,
private k8s: KubernetesService,
) {}

ngOnInit() {
this.poller = new ExponentialBackoff({interval: 2000, retries: 3});
const resourcesSub = this.poller.start().subscribe(() => {
if (!this.currNamespace) {
return;
}

Promise.all([
this.k8s.getResource(this.currNamespace).toPromise(),
this.k8s.getVolumes(this.currNamespace).toPromise()
]).then(([notebooks, volumes]) => {
if (!isEqual(notebooks, this.resources) || !isEqual(volumes, this.pvcs)) {
this.poller.reset();
}
this.resources = notebooks;
this.pvcs = volumes;
let mounts = Object.fromEntries(
notebooks.flatMap(nb => nb.volumes.map(v => [v, nb]))
);
this.pvcProperties = volumes.map(v => ({
pvc: v,
mountedBy: mounts[v.name]?.name
}));
});
});

// Keep track of the selected namespace
const namespaceSub = this.ns.getSelectedNamespace().subscribe(namespace => {
this.currNamespace = namespace;
this.poller.reset();
});

this.subscriptions.add(resourcesSub);
this.subscriptions.add(namespaceSub);
}

constructor(public ns: NamespaceService) {}
deleteResource(rsrc: Resource): void {
this.k8s
.deleteResource(rsrc.namespace, rsrc.name)
.pipe(first())
.subscribe(r => {
this.poller.reset();
});
}

ngOnInit() {}
deletePvc(p: PvcWithStatus): void {
this.k8s
.deletePersistentVolumeClaim(p.pvc.namespace, p.pvc.name)
.pipe(first())
.subscribe(_ => {
this.poller.reset();
});
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
<div class="card mat-elevation-z2">
<div class="header">
<mat-icon>computer</mat-icon>
<p>Notebook Servers</p>

<div class="spacer"></div>
Expand All @@ -13,7 +14,7 @@

<mat-divider></mat-divider>

<table mat-table [dataSource]="dataSource" [trackBy]="trackByFn" matSort>
<table mat-table [dataSource]="notebooks" matSort>
<!-- Status Column -->
<ng-container matColumnDef="status">
<th mat-header-cell *matHeaderCellDef>Status</th>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,86 +0,0 @@
.card {
width: 900px;
padding: 0px;
border-radius: 5px;
background: white;
}

table {
width: 100%;
}

.header {
display: flex;
align-items: center;
padding: 0px 16px 0px 16px;
height: 64px;
}

.header p {
font-weight: 400;
font-size: 20px;
}

.cdk-column-actions {
text-align: center;
}

.mat-icon {
line-height: 0.85;
}

td.mat-cell:last-of-type,
td.mat-footer-cell:last-of-type,
th.mat-header-cell:last-of-type {
padding-right: 0px;
}

.inline {
display: inline-block;
}

// Status Icons
.running {
color: green;
}

.warning {
color: orange;
}

.error {
color: red;
}

.status {
display: inline-flex;
vertical-align: middle;
}

.delete {
color: red;
}

// Flex
.parent {
display: flex;
}

.spacer {
flex-grow: 1;
}

th,
td {
overflow: hidden;
text-overflow: ellipsis;
}

td.mat-column-image,
td.mat-column-name {
max-width: 200px;
}

td.mat-column-cpu {
width: 40px;
}
Loading

0 comments on commit 2e9daf6

Please sign in to comment.