[YUNIKORN-1136] Show absolute used capacity in web UI (#87)

Closes: #87
diff --git a/src/app/components/queue-rack/queue-rack.component.ts b/src/app/components/queue-rack/queue-rack.component.ts
index 326fe6f..3165b77 100644
--- a/src/app/components/queue-rack/queue-rack.component.ts
+++ b/src/app/components/queue-rack/queue-rack.component.ts
@@ -20,6 +20,7 @@
 
 import { QueueInfo, ToggleQueueChildrenEvent } from '@app/models/queue-info.model';
 import { NOT_AVAILABLE } from '@app/utils/constants';
+import { queueScheduler } from 'rxjs';
 
 @Component({
   selector: 'app-queue-rack',
@@ -63,30 +64,19 @@
     this.queueSelected.emit(queue);
   }
 
-  // FIXME: Implement using absolute usage value in new /{partition}/queues REST API.
-  // Currently absolute usage value is not available in /{partition}/queues REST API.
   getQueueCapacityColor(queue: QueueInfo) {
+    const value = queue.absoluteUsedPercent;
+    if (value > 60 && value <= 75) {
+      return '#60cea5';
+    } else if (value > 75 && value < 90) {
+      return '#ffbc0b';
+    } else if (value >= 90) {
+      return '#ef6162';
+    }
     return '#fff';
   }
 
-  // FIXME: Implement using absolute usage value in new /{partition}/queues REST API.
-  // Currently absolute usage value is not available in /{partition}/queues REST API.
   getProgressBarValue(queue: QueueInfo) {
-    return 0;
-  }
-
-  getMaxAbsValue(absCapacities: string): number {
-    let max = 0;
-    if (absCapacities !== null) {
-      const splitted = absCapacities
-        .replace(NOT_AVAILABLE, '0')
-        .replace(/[^:0-9]/g, '')
-        .split(':');
-      if (splitted.length !== 0) {
-        const capacities: number[] = splitted.map((x) => +x);
-        max = Math.max(...capacities);
-      }
-    }
-    return max;
+    return queue.absoluteUsedPercent;
   }
 }
diff --git a/src/app/components/queues-view/queues-view.component.html b/src/app/components/queues-view/queues-view.component.html
index 55c5561..2f769f0 100644
--- a/src/app/components/queues-view/queues-view.component.html
+++ b/src/app/components/queues-view/queues-view.component.html
@@ -84,6 +84,13 @@
                 [innerHTML]="resourceValueFormatter(selectedQueue.guaranteedResource)"
               ></div>
             </div>
+            <div class="flex-grid item-wrapper">
+              <div class="left-item">Absolute Used Capacity:</div>
+              <div
+                class="right-item"
+                [innerHTML]="resourceValueFormatter(selectedQueue.absoluteUsedCapacity)"
+              ></div>
+            </div>
             <div class="flex-grid item-wrapper" *ngFor="let prop of selectedQueue.properties">
               <div class="left-item">{{ prop.name }}:</div>
               <div class="right-item">{{ prop.value }}</div>
diff --git a/src/app/models/queue-info.model.ts b/src/app/models/queue-info.model.ts
index 9014f6b..827e975 100644
--- a/src/app/models/queue-info.model.ts
+++ b/src/app/models/queue-info.model.ts
@@ -23,6 +23,8 @@
   maxResource: string = '';
   guaranteedResource: string = '';
   allocatedResource: string = '';
+  absoluteUsedCapacity: string = '';
+  absoluteUsedPercent: number = 0;
   parentQueue: null | QueueInfo = null;
   children: null | QueueInfo[] = null;
   properties: QueuePropertyItem[] = [];
diff --git a/src/app/services/scheduler/scheduler.service.ts b/src/app/services/scheduler/scheduler.service.ts
index 4bf1c99..1e77669 100644
--- a/src/app/services/scheduler/scheduler.service.ts
+++ b/src/app/services/scheduler/scheduler.service.ts
@@ -18,7 +18,7 @@
 
 import { Injectable } from '@angular/core';
 import { HttpClient } from '@angular/common/http';
-import { Observable } from 'rxjs';
+import { Observable, queueScheduler } from 'rxjs';
 import { map } from 'rxjs/operators';
 
 import { QueueInfo, QueuePropertyItem } from '@app/models/queue-info.model';
@@ -278,9 +278,12 @@
     const maxResource = data['maxResource'] as SchedulerResourceInfo;
     const guaranteedResource = data['guaranteedResource'] as SchedulerResourceInfo;
     const allocatedResource = data['allocatedResource'] as SchedulerResourceInfo;
+    const absUsedCapacity = data['absUsedCapacity'] as SchedulerResourceInfo;
     queue.maxResource = this.formatResource(maxResource);
     queue.guaranteedResource = this.formatResource(guaranteedResource);
     queue.allocatedResource = this.formatResource(allocatedResource);
+    queue.absoluteUsedCapacity = this.formatPercent(absUsedCapacity);
+    queue.absoluteUsedPercent = this.absUsagePercent(absUsedCapacity);
   }
 
   private fillQueuePropertiesAndTemplate(data: any, queue: QueueInfo) {
@@ -339,4 +342,18 @@
 
     return formatted.join(', ');
   }
+
+  private absUsagePercent(resource: SchedulerResourceInfo): number {
+    let result = 0;
+
+    if (resource && resource.memory !== undefined) {
+      result = Math.max(result, resource.memory);
+    }
+
+    if (resource && resource.vcore !== undefined) {
+      result = Math.max(result, resource.vcore);
+    }
+
+    return Math.max(0, Math.min(result, 100));
+  }
 }