Refactoring. More chart clean up. Improving sorting by pod resources.

This commit is contained in:
Eric Herbrandson
2019-04-23 22:42:20 -05:00
parent 6d8392312c
commit 28de53c37c
8 changed files with 84 additions and 58 deletions
+28 -10
View File
@@ -34,22 +34,40 @@ export default class NodesPanel extends Base {
<Sorter field={getReadyStatus} sort={sort}>Ready</Sorter>
</th>
<th>
<Sorter field={this.sortByCpuUsage} sort={sort}>Cpu</Sorter>
<Sorter field={this.sortByCpuUsage} sort={sort}>
Cpu
<div className='smallText'>Actual</div>
</Sorter>
</th>
<th className='optional_xsmall'>
<Sorter field={this.sortByCpuRequest} sort={sort}>Requests</Sorter>
<Sorter field={this.sortByCpuRequest} sort={sort}>
Cpu
<div className='smallText'>Requests</div>
</Sorter>
</th>
<th className='optional_xsmall'>
<Sorter field={this.sortByCpuLimit} sort={sort}>Limits</Sorter>
<Sorter field={this.sortByCpuLimit} sort={sort}>
Cpu
<div className='smallText'>Limits</div>
</Sorter>
</th>
<th>
<Sorter field={this.sortByRamUsage} sort={sort}>Ram</Sorter>
<Sorter field={this.sortByRamUsage} sort={sort}>
Ram
<div className='smallText'>Actual</div>
</Sorter>
</th>
<th className='optional_xsmall'>
<Sorter field={this.sortByRamRequest} sort={sort}>Requests</Sorter>
<Sorter field={this.sortByRamRequest} sort={sort}>
Ram
<div className='smallText'>Requests</div>
</Sorter>
</th>
<th className='optional_xsmall'>
<Sorter field={this.sortByRamLimit} sort={sort}>Limits</Sorter>
<Sorter field={this.sortByRamLimit} sort={sort}>
Ram
<div className='smallText'>Limits</div>
</Sorter>
</th>
</tr>
</thead>
@@ -57,7 +75,7 @@ export default class NodesPanel extends Base {
<TableBody items={items} filter={filter} sort={sort} colSpan='11' row={x => (
<tr key={x.metadata.uid}>
<MetadataColumns item={x} href={`#!node/${x.metadata.name}`} />
<td className='podsPanel_label optional_medium'>{objectMap(x.metadata.labels)}</td>
<td className='smallText optional_medium'>{objectMap(x.metadata.labels)}</td>
<td className='optional_small'>{getReadyStatus(x)}</td>
<td>{getPercentDisplay(x, metrics, 'cpu')}</td>
<td className='optional_xsmall'>{getResourcePercentDisplay(x, pods, 'cpu', 'requests')}</td>
@@ -92,7 +110,7 @@ function getResourcePercentDisplay(node, pods, resource, type) {
function percent(node, used, resource) {
if (used == null) return <LoadingEllipsis />;
if (!used) return <span className='podsPanel_label'>-</span>;
if (!used) return <span className='smallText'>-</span>;
const unparser = resource === 'cpu' ? unparseCpu : unparseRam;
const result = unparser(used);
@@ -103,8 +121,8 @@ function percent(node, used, resource) {
return (
<div className={className}>
{displayPercent}<span className='podsPanel_label'>%</span>
<div className='podsPanel_label'>{result.value}{result.unit}</div>
{displayPercent}<span className='smallText'>%</span>
<div className='smallText'>{result.value}{result.unit}</div>
</div>
);
}
+40 -25
View File
@@ -1,4 +1,3 @@
import './podsPanel.scss';
import _ from 'lodash';
import React from 'react';
import Base from './base';
@@ -13,17 +12,17 @@ export default class PodsPanel extends Base {
super(props);
this.sortByCpuUsage = x => getPodUsage(x, this.props.metrics, 'cpu');
this.sortByCpuRequest = x => getPodResourcePercent(x, this.props.metrics, 'cpu', 'requests');
this.sortByCpuLimit = x => getPodResourcePercent(x, this.props.metrics, 'cpu', 'limits');
this.sortByCpuRequest = x => sortBy(x, this.props.metrics, 'cpu', 'requests');
this.sortByCpuLimit = x => sortBy(x, this.props.metrics, 'cpu', 'limits');
this.sortByRamUsage = x => getPodUsage(x, this.props.metrics, 'memory');
this.sortByRamRequest = x => getPodResourcePercent(x, this.props.metrics, 'memory', 'requests');
this.sortByRamLimit = x => getPodResourcePercent(x, this.props.metrics, 'memory', 'limits');
this.sortByRamRequest = x => sortBy(x, this.props.metrics, 'memory', 'requests');
this.sortByRamLimit = x => sortBy(x, this.props.metrics, 'memory', 'limits');
}
render() {
const {items, metrics, sort, filter, skipNamespace, skipNodeName} = this.props;
const col = 8 + !skipNamespace + !skipNodeName; // TODO: fix me
const {items, metrics, sort, filter, skipNamespace} = this.props;
const col = 10 + !skipNamespace;
return (
<div className='contentPanel'>
@@ -31,30 +30,42 @@ export default class PodsPanel extends Base {
<thead>
<tr>
<MetadataHeaders sort={sort} includeNamespace={!skipNamespace} />
{/*
TODO: remove this (and all callers too)
{!skipNodeName && (
<th className='optional_small'><Sorter field='spec.nodeName' sort={sort}>Node</Sorter></th>
)}
*/}
<th className='optional_medium'><Sorter field={getRestartCount} sort={sort}>Restarts</Sorter></th>
<th>
<Sorter field={this.sortByCpuUsage} sort={sort}>Cpu</Sorter>
<Sorter field={this.sortByCpuUsage} sort={sort}>
Cpu
<div className='smallText'>Actual</div>
</Sorter>
</th>
<th className='optional_xsmall'>
<Sorter field={this.sortByCpuRequest} sort={sort}>Request</Sorter>
<Sorter field={this.sortByCpuRequest} sort={sort}>
Cpu
<div className='smallText'>Request</div>
</Sorter>
</th>
<th className='optional_xsmall'>
<Sorter field={this.sortByCpuLimit} sort={sort}>Limit</Sorter>
<Sorter field={this.sortByCpuLimit} sort={sort}>
Cpu
<div className='smallText'>Limit</div>
</Sorter>
</th>
<th>
<Sorter field={this.sortByRamUsage} sort={sort}>Ram</Sorter>
<Sorter field={this.sortByRamUsage} sort={sort}>
Ram
<div className='smallText'>Actual</div>
</Sorter>
</th>
<th className='optional_xsmall'>
<Sorter field={this.sortByRamRequest} sort={sort}>Request</Sorter>
<Sorter field={this.sortByRamRequest} sort={sort}>
Ram
<div className='smallText'>Request</div>
</Sorter>
</th>
<th className='optional_xsmall'>
<Sorter field={this.sortByRamLimit} sort={sort}>Limit</Sorter>
<Sorter field={this.sortByRamLimit} sort={sort}>
Ram
<div className='smallText'>Limit</div>
</Sorter>
</th>
</tr>
</thead>
@@ -67,7 +78,6 @@ export default class PodsPanel extends Base {
includeNamespace={!skipNamespace}
href={`#!pod/${x.metadata.namespace}/${x.metadata.name}`}
/>
{/* {!skipNodeName && <td className='optional_small'>{x.spec.nodeName}</td>} */}
<td className='optional_medium'>{getRestartCount(x)}</td>
{getChart(x, metrics, 'cpu')}
{getChart(x, metrics, 'memory')}
@@ -79,6 +89,11 @@ export default class PodsPanel extends Base {
}
}
function sortBy(item, metrics, resource, type) {
const result = getPodResourcePercent(item, metrics, resource, type);
return Number.isFinite(result) ? result : -1;
}
function getRestartCount({status}) {
return _.sumBy(status.containerStatuses, 'restartCount');
}
@@ -104,16 +119,16 @@ function getRawDisplay(item, metrics, actual, resource) {
return (
<td>
{actualResult.value}
<span className='podsPanel_label'>{actualResult.unit}</span>
<span className='smallText'>{actualResult.unit}</span>
</td>
);
}
function getPercentDisplay(item, metrics, actual, resource, type) {
if (!item || !metrics) return <td><LoadingEllipsis /></td>;
if (!item || !metrics) return <td className='optional_xsmall'><LoadingEllipsis /></td>;
const request = getPodResourceValue(item, resource, type);
if (!request) return <td className='podsPanel_label'>-</td>;
if (!request) return <td className='smallText optional_xsmall'>-</td>;
const unparser = resource === 'cpu' ? unparseCpu : unparseRam;
const result = unparser(request);
@@ -122,8 +137,8 @@ function getPercentDisplay(item, metrics, actual, resource, type) {
return (
<td className={className}>
{percent}<span className='podsPanel_label'>%</span>
<div className='podsPanel_label'>{result.value}{result.unit}</div>
{percent}<span className='smallText'>%</span>
<div className='smallText'>{result.value}{result.unit}</div>
</td>
);
}
-7
View File
@@ -1,7 +0,0 @@
@import '../scss/settings.scss';
.podsPanel_label {
margin-left: 2px;
color: $color-light;
font-size: $font-size-small;
}
+5
View File
@@ -75,6 +75,11 @@ button.titleBar_hamburger {
fill: $color-white;
}
.smallText {
color: $color-light;
font-size: $font-size-small;
}
@media only screen and (max-width: $media-medium) {
.optional_medium {
display: none;
+1 -1
View File
@@ -21,4 +21,4 @@ $font-size-xlarge: 100px;
$media-xsmall: 700px;
$media-small: 812px;
$media-medium: 1024px;
$media-medium: 1200px;
+10 -13
View File
@@ -33,19 +33,14 @@ export function getNodeUsagePercent(node, metrics, resource) {
}
export function getNodeResourcesAvailable(node, resource) {
if (!node) return null;
return resource === 'cpu' ? parseCpu(node.status.capacity.cpu) : parseRam(node.status.capacity.memory);
return node ? parse(resource, node.status.capacity) : null;
}
export function getNodeUsage(node, metrics, resource) {
if (!node || !metrics) return null;
const result = metrics[node.metadata.name] || {};
if (!result) return null;
const value = resource === 'cpu' ? result.usage.cpu : result.usage.memory;
const parser = resource === 'cpu' ? parseCpu : parseRam;
return parser(value);
const result = metrics[node.metadata.name];
return result ? parse(resource, result.usage) : null;
}
@@ -60,14 +55,16 @@ export function getPodUsage(pod, metrics, resource) {
if (!pod || !metrics) return null;
const metric = metrics[pod.metadata.name] || {};
const parser = resource === 'cpu' ? parseCpu : parseRam;
return _.sumBy(metric.containers, x => parser(x.usage[resource]));
return _.sumBy(metric.containers, x => parse(resource, x.usage));
}
export function getPodResourceValue(pod, resource, type) {
const parser = resource === 'cpu' ? parseCpu : parseRam;
return _(pod.spec.containers)
.filter(x => x.resources && x.resources[type])
.sumBy(x => parser(x.resources[type][resource]));
.sumBy(x => parse(resource, x.resources[type]));
}
function parse(resource, target) {
const parser = resource === 'cpu' ? parseCpu : parseRam;
return parser(target[resource]);
}
-1
View File
@@ -70,7 +70,6 @@ export default class Namespace extends Base {
sort={podsSort}
metrics={filteredPodMetrics}
skipNamespace={true}
skipNodeName={false}
/>
<div className='contentPanel_header'>Events</div>
-1
View File
@@ -112,7 +112,6 @@ export default class Node extends Base {
items={filteredPods}
sort={podsSort}
metrics={filteredPodMetrics}
skipNodeName={true}
/>
</div>
);