feat: Rework analysis view top to contain piechart

This commit is contained in:
Christoph Kluge 2023-08-10 18:06:19 +02:00
parent da8cefe153
commit e80ce7a474

View File

@ -6,7 +6,8 @@
import Filters from './filters/Filters.svelte' import Filters from './filters/Filters.svelte'
import PlotSelection from './PlotSelection.svelte' import PlotSelection from './PlotSelection.svelte'
import Histogramuplot from './plots/Histogramuplot.svelte' import Histogramuplot from './plots/Histogramuplot.svelte'
import Histogram, { binsFromFootprint } from './plots/Histogram.svelte' import Pie from './plots/Pie.svelte'
import { binsFromFootprint } from './plots/Histogram.svelte'
import ScatterPlot from './plots/Scatter.svelte' import ScatterPlot from './plots/Scatter.svelte'
import PlotTable from './PlotTable.svelte' import PlotTable from './PlotTable.svelte'
import Roofline from './plots/Roofline.svelte' import Roofline from './plots/Roofline.svelte'
@ -30,7 +31,7 @@
let filterComponent; // see why here: https://stackoverflow.com/questions/58287729/how-can-i-export-a-function-from-a-svelte-component-that-changes-a-value-in-the let filterComponent; // see why here: https://stackoverflow.com/questions/58287729/how-can-i-export-a-function-from-a-svelte-component-that-changes-a-value-in-the
let jobFilters = []; let jobFilters = [];
let rooflineMaxY; let rooflineMaxY;
let colWidth; let colWidth1, colWidth2, colWidth3, colWidth4;
let numBins = 50; let numBins = 50;
let maxY = -1; let maxY = -1;
const ccconfig = getContext('cc-config') const ccconfig = getContext('cc-config')
@ -135,82 +136,103 @@
</Col> </Col>
</Row> </Row>
{:else if $statsQuery.data} {:else if $statsQuery.data}
<Row> <Row cols={3} class="mb-4">
<div class="col-3" bind:clientWidth={colWidth}> <Col>
<div style="height: 40%"> <Table>
<Table> <tr>
<tr> <th scope="col">Total Jobs</th>
<th scope="col">Total Jobs</th> <td>{$statsQuery.data.stats[0].totalJobs}</td>
<td>{$statsQuery.data.stats[0].totalJobs}</td> </tr>
</tr> <tr>
<tr> <th scope="col">Short Jobs</th>
<th scope="col">Short Jobs</th> <td>{$statsQuery.data.stats[0].shortJobs}</td>
<td>{$statsQuery.data.stats[0].shortJobs}</td> </tr>
</tr> <tr>
<tr> <th scope="col">Total Walltime</th>
<th scope="col">Total Walltime</th> <td>{$statsQuery.data.stats[0].totalWalltime}</td>
<td>{$statsQuery.data.stats[0].totalWalltime}</td> </tr>
</tr> <tr>
<tr> <th scope="col">Total Core Hours</th>
<th scope="col">Total Core Hours</th> <td>{$statsQuery.data.stats[0].totalCoreHours}</td>
<td>{$statsQuery.data.stats[0].totalCoreHours}</td> </tr>
</tr> </Table>
</Table> </Col>
<Col>
<div bind:clientWidth={colWidth1}>
<h5>Top Users</h5>
{#key $statsQuery.data.topUsers}
<Pie
size={colWidth1}
sliceLabel='Hours'
quantities={$statsQuery.data.topUsers.sort((a, b) => b.count - a.count).map((tu) => tu.count)}
entities={$statsQuery.data.topUsers.sort((a, b) => b.count - a.count).map((tu) => tu.name)}
/>
{/key}
</div> </div>
<div style="height: 60%;"> </Col>
{#key $statsQuery.data.topUsers} <Col>
<h4>Top Users (by node hours)</h4> <Table>
<Histogram <tr class="mb-2"><th>User Name</th><th>Node Hours</th></tr>
width={colWidth - 25} height={300 * 0.5} small={true} {#each $statsQuery.data.topUsers.sort((a, b) => b.count - a.count) as { name, count }}
data={$statsQuery.data.topUsers.sort((a, b) => b.count - a.count).map(({ count }, idx) => ({ count, value: idx }))} <tr>
label={(x) => x < $statsQuery.data.topUsers.length ? $statsQuery.data.topUsers[Math.floor(x)].name : 'No Users'} <th scope="col"><a href="/monitoring/user/{name}?cluster={cluster.name}">{name}</a></th>
ylabel="Node Hours [h]"/> <td>{count}</td>
</tr>
{/each}
</Table>
</Col>
</Row>
<Row cols={3} class="mb-2">
<Col>
{#if $rooflineQuery.fetching}
<Spinner />
{:else if $rooflineQuery.error}
<Card body color="danger">{$rooflineQuery.error.message}</Card>
{:else if $rooflineQuery.data && cluster}
<div bind:clientWidth={colWidth2}>
{#key $rooflineQuery.data}
<Roofline
width={colWidth2} height={300}
tiles={$rooflineQuery.data.rooflineHeatmap}
cluster={cluster.subClusters.length == 1 ? cluster.subClusters[0] : null}
maxY={rooflineMaxY} />
{/key} {/key}
</div> </div>
</div> {/if}
<div class="col-3"> </Col>
<Col>
<div bind:clientWidth={colWidth3}>
{#key $statsQuery.data.stats[0].histDuration} {#key $statsQuery.data.stats[0].histDuration}
<Histogramuplot <Histogramuplot
width={colWidth3} height={300}
data={convert2uplot($statsQuery.data.stats[0].histDuration)} data={convert2uplot($statsQuery.data.stats[0].histDuration)}
width={colWidth - 25}
title="Duration Distribution" title="Duration Distribution"
xlabel="Current Runtimes" xlabel="Current Runtimes"
xunit="Hours" xunit="Hours"
ylabel="Number of Jobs" ylabel="Number of Jobs"
yunit="Jobs"/> yunit="Jobs"/>
{/key} {/key}
</div> </div>
<div class="col-3"> </Col>
<Col>
<div bind:clientWidth={colWidth4}>
{#key $statsQuery.data.stats[0].histNumNodes} {#key $statsQuery.data.stats[0].histNumNodes}
<Histogramuplot <Histogramuplot
width={colWidth4} height={300}
data={convert2uplot($statsQuery.data.stats[0].histNumNodes)} data={convert2uplot($statsQuery.data.stats[0].histNumNodes)}
width={colWidth - 25}
title="Number of Nodes Distribution" title="Number of Nodes Distribution"
xlabel="Allocated Nodes" xlabel="Allocated Nodes"
xunit="Nodes" xunit="Nodes"
ylabel="Number of Jobs" ylabel="Number of Jobs"
yunit="Jobs"/> yunit="Jobs"/>
{/key} {/key}
</div> </div>
<div class="col-3"> </Col>
{#if $rooflineQuery.fetching}
<Spinner />
{:else if $rooflineQuery.error}
<Card body color="danger">{$rooflineQuery.error.message}</Card>
{:else if $rooflineQuery.data && cluster}
{#key $rooflineQuery.data}
<Roofline
width={colWidth - 25}
tiles={$rooflineQuery.data.rooflineHeatmap}
cluster={cluster.subClusters.length == 1 ? cluster.subClusters[0] : null}
maxY={rooflineMaxY} />
{/key}
{/if}
</div>
</Row> </Row>
{/if} {/if}
<br/> <hr class="my-6"/>
{#if $footprintsQuery.error} {#if $footprintsQuery.error}
<Row> <Row>
<Col> <Col>
@ -284,7 +306,7 @@
{/if} {/if}
<style> <style>
h4 { h5 {
text-align: center; text-align: center;
} }
</style> </style>