Skip to content

Commit c43d4a0

Browse files
complete review of context initialization and access, streamlining
1 parent a8d385a commit c43d4a0

21 files changed

+365
-318
lines changed

web/frontend/src/Job.root.svelte

Lines changed: 100 additions & 93 deletions
Original file line numberDiff line numberDiff line change
@@ -68,12 +68,8 @@
6868
energyFootprint { hardware, metric, value }
6969
}
7070
`);
71-
const client = getContextClient();
72-
const ccconfig = getContext("cc-config");
73-
const showRoofline = !!ccconfig[`jobView_showRoofline`];
74-
const showStatsTable = !!ccconfig[`jobView_showStatTable`];
75-
7671
/* Note: Actual metric data queried in <Metric> Component, only require base infos here -> reduce backend load by requesting just stats */
72+
const client = getContextClient();
7773
const query = gql`
7874
query ($dbid: ID!, $selectedMetrics: [String!]!, $selectedScopes: [MetricScope!]!) {
7975
scopedJobStats(id: $dbid, metrics: $selectedMetrics, scopes: $selectedScopes) {
@@ -89,25 +85,68 @@
8985
/* State Init */
9086
let plots = $state({});
9187
let isMetricsSelectionOpen = $state(false);
92-
let selectedMetrics = $state([]);
93-
let selectedScopes = $state([]);
9488
let totalMetrics = $state(0);
9589
96-
/* Derived */
97-
const showSummary = $derived((!!ccconfig[`jobView_showFootprint`] || !!ccconfig[`jobView_showPolarPlot`]))
90+
/* Derived Init Return */
91+
const thisJob = $derived($initq?.data ? $initq.data.job : null);
92+
93+
/* Derived Settings */
94+
const globalMetrics = $derived(thisJob ? getContext("globalMetrics") : null);
95+
const clusterInfo = $derived(thisJob ? getContext("clusters") : null);
96+
const ccconfig = $derived(thisJob ? getContext("cc-config") : null);
97+
const showRoofline = $derived(ccconfig ? !!ccconfig[`jobView_showRoofline`] : false);
98+
const showStatsTable = $derived(ccconfig ? !!ccconfig[`jobView_showStatTable`] : false);
99+
const showSummary = $derived(ccconfig ? (!!ccconfig[`jobView_showFootprint`] || !!ccconfig[`jobView_showPolarPlot`]) : false)
100+
101+
/* Derived Var Preprocessing*/
102+
let selectedMetrics = $derived.by(() => {
103+
if(thisJob && ccconfig) {
104+
if (thisJob.cluster) {
105+
if (thisJob.subCluster) {
106+
return ccconfig[`metricConfig_jobViewPlotMetrics:${thisJob.cluster}:${thisJob.subCluster}`] ||
107+
ccconfig[`metricConfig_jobViewPlotMetrics:${thisJob.cluster}`] ||
108+
ccconfig.metricConfig_jobViewPlotMetrics
109+
}
110+
return ccconfig[`metricConfig_jobViewPlotMetrics:${thisJob.cluster}`] ||
111+
ccconfig.metricConfig_jobViewPlotMetrics
112+
}
113+
return ccconfig.metricConfig_jobViewPlotMetrics
114+
}
115+
return [];
116+
});
117+
118+
let selectedScopes = $derived.by(() => {
119+
const pendingScopes = ["node"]
120+
if (thisJob) {
121+
const accScopeDefault = [...selectedMetrics].some(function (m) {
122+
const thisCluster = clusterInfo.find((c) => c.name == thisJob.cluster);
123+
const subCluster = thisCluster.subClusters.find((sc) => sc.name == thisJob.subCluster);
124+
return subCluster.metricConfig.find((smc) => smc.name == m)?.scope === "accelerator";
125+
});
126+
127+
128+
if (accScopeDefault) pendingScopes.push("accelerator")
129+
if (thisJob.numNodes === 1) {
130+
pendingScopes.push("socket")
131+
pendingScopes.push("core")
132+
}
133+
}
134+
return[...new Set(pendingScopes)];
135+
});
136+
137+
/* Derived Query and Postprocessing*/
98138
const jobMetrics = $derived(queryStore({
99139
client: client,
100140
query: query,
101141
variables: { dbid, selectedMetrics, selectedScopes },
102142
})
103143
);
104-
144+
105145
const missingMetrics = $derived.by(() => {
106-
if ($initq?.data && $jobMetrics?.data) {
107-
let job = $initq.data.job;
146+
if (thisJob && $jobMetrics?.data) {
108147
let metrics = $jobMetrics.data.scopedJobStats;
109-
let metricNames = $initq.data.globalMetrics.reduce((names, gm) => {
110-
if (gm.availability.find((av) => av.cluster === job.cluster)) {
148+
let metricNames = globalMetrics.reduce((names, gm) => {
149+
if (gm.availability.find((av) => av.cluster === thisJob.cluster)) {
111150
names.push(gm.name);
112151
}
113152
return names;
@@ -118,9 +157,10 @@
118157
!metrics.some((jm) => jm.name == metric) &&
119158
selectedMetrics.includes(metric) &&
120159
!checkMetricDisabled(
160+
globalMetrics,
121161
metric,
122-
$initq.data.job.cluster,
123-
$initq.data.job.subCluster,
162+
thisJob.cluster,
163+
thisJob.subCluster,
124164
),
125165
);
126166
} else {
@@ -129,17 +169,16 @@
129169
});
130170
131171
const missingHosts = $derived.by(() => {
132-
if ($initq?.data && $jobMetrics?.data) {
133-
let job = $initq.data.job;
172+
if (thisJob && $jobMetrics?.data) {
134173
let metrics = $jobMetrics.data.scopedJobStats;
135-
let metricNames = $initq.data.globalMetrics.reduce((names, gm) => {
136-
if (gm.availability.find((av) => av.cluster === job.cluster)) {
174+
let metricNames = globalMetrics.reduce((names, gm) => {
175+
if (gm.availability.find((av) => av.cluster === thisJob.cluster)) {
137176
names.push(gm.name);
138177
}
139178
return names;
140179
}, []);
141180
142-
return job.resources
181+
return thisJob.resources
143182
.map(({ hostname }) => ({
144183
hostname: hostname,
145184
metrics: metricNames.filter(
@@ -165,51 +204,19 @@
165204
? "Loading..."
166205
: $initq?.error
167206
? "Error"
168-
: `Job ${$initq.data.job.jobId} - ClusterCockpit`;
169-
});
170-
171-
/* On Init */
172-
getContext("on-init")(() => {
173-
let job = $initq.data.job;
174-
if (!job) return;
175-
const pendingMetrics = (
176-
ccconfig[`metricConfig_jobViewPlotMetrics:${job.cluster}:${job.subCluster}`] ||
177-
ccconfig[`metricConfig_jobViewPlotMetrics:${job.cluster}`]
178-
) ||
179-
$initq.data.globalMetrics.reduce((names, gm) => {
180-
if (gm.availability.find((av) => av.cluster === job.cluster && av.subClusters.includes(job.subCluster))) {
181-
names.push(gm.name);
182-
}
183-
return names;
184-
}, [])
185-
186-
// Select default Scopes to load: Check before if any metric has accelerator scope by default
187-
const accScopeDefault = [...pendingMetrics].some(function (m) {
188-
const cluster = $initq.data.clusters.find((c) => c.name == job.cluster);
189-
const subCluster = cluster.subClusters.find((sc) => sc.name == job.subCluster);
190-
return subCluster.metricConfig.find((smc) => smc.name == m)?.scope === "accelerator";
191-
});
192-
193-
const pendingScopes = ["node"]
194-
if (accScopeDefault) pendingScopes.push("accelerator")
195-
if (job.numNodes === 1) {
196-
pendingScopes.push("socket")
197-
pendingScopes.push("core")
198-
}
199-
200-
selectedMetrics = [...new Set(pendingMetrics)];
201-
selectedScopes = [...new Set(pendingScopes)];
207+
: `Job ${thisJob.jobId} - ClusterCockpit`;
202208
});
203209
204210
/* Functions */
205-
const orderAndMap = (grouped, selectedMetrics) =>
206-
selectedMetrics.map((metric) => ({
211+
const orderAndMap = (grouped, inputMetrics) =>
212+
inputMetrics.map((metric) => ({
207213
metric: metric,
208214
data: grouped.find((group) => group[0].name == metric),
209215
disabled: checkMetricDisabled(
216+
globalMetrics,
210217
metric,
211-
$initq.data.job.cluster,
212-
$initq.data.job.subCluster,
218+
thisJob.cluster,
219+
thisJob.subCluster,
213220
),
214221
}));
215222
</script>
@@ -219,34 +226,34 @@
219226
<Col xs={12} md={6} xl={3} class="mb-3 mb-xxl-0">
220227
{#if $initq.error}
221228
<Card body color="danger">{$initq.error.message}</Card>
222-
{:else if $initq?.data}
229+
{:else if thisJob}
223230
<Card class="overflow-auto" style="height: auto;">
224231
<TabContent> <!-- on:tab={(e) => (status = e.detail)} -->
225-
{#if $initq.data?.job?.metaData?.message}
232+
{#if thisJob?.metaData?.message}
226233
<TabPane tabId="admin-msg" tab="Admin Note" active>
227234
<CardBody>
228235
<Card body class="mb-2" color="warning">
229-
<h5>Job {$initq.data?.job?.jobId} ({$initq.data?.job?.cluster})</h5>
236+
<h5>Job {thisJob?.jobId} ({thisJob?.cluster})</h5>
230237
The following note was added by administrators:
231238
</Card>
232239
<Card body>
233-
{@html $initq.data.job.metaData.message}
240+
{@html thisJob.metaData.message}
234241
</Card>
235242
</CardBody>
236243
</TabPane>
237244
{/if}
238-
<TabPane tabId="meta-info" tab="Job Info" active={$initq.data?.job?.metaData?.message?false:true}>
245+
<TabPane tabId="meta-info" tab="Job Info" active={thisJob?.metaData?.message?false:true}>
239246
<CardBody class="pb-2">
240-
<JobInfo job={$initq.data.job} {username} {authlevel} {roles} showTagEdit/>
247+
<JobInfo job={thisJob} {username} {authlevel} {roles} showTagEdit/>
241248
</CardBody>
242249
</TabPane>
243-
{#if $initq.data.job.concurrentJobs != null && $initq.data.job.concurrentJobs.items.length != 0}
250+
{#if thisJob.concurrentJobs != null && thisJob.concurrentJobs.items.length != 0}
244251
<TabPane tabId="shared-jobs">
245252
<span slot="tab">
246-
{$initq.data.job.concurrentJobs.items.length} Concurrent Jobs
253+
{thisJob.concurrentJobs.items.length} Concurrent Jobs
247254
</span>
248255
<CardBody>
249-
<ConcurrentJobs cJobs={$initq.data.job.concurrentJobs} showLinks={(authlevel > roles.manager)}/>
256+
<ConcurrentJobs cJobs={thisJob.concurrentJobs} showLinks={(authlevel > roles.manager)}/>
250257
</CardBody>
251258
</TabPane>
252259
{/if}
@@ -261,9 +268,9 @@
261268
<Col xs={12} md={6} xl={4} xxl={3} class="mb-3 mb-xxl-0">
262269
{#if $initq.error}
263270
<Card body color="danger">{$initq.error.message}</Card>
264-
{:else if $initq?.data}
271+
{:else if thisJob}
265272
{#if showSummary}
266-
<JobSummary job={$initq.data.job}/>
273+
<JobSummary job={thisJob}/>
267274
{/if}
268275
{:else}
269276
<Spinner secondary />
@@ -274,9 +281,9 @@
274281
<Col xs={12} md={12} xl={5} xxl={6}>
275282
{#if $initq.error}
276283
<Card body color="danger">{$initq.error.message}</Card>
277-
{:else if $initq?.data}
284+
{:else if thisJob}
278285
{#if showRoofline}
279-
<JobRoofline job={$initq.data.job} clusters={$initq.data.clusters}/>
286+
<JobRoofline job={thisJob} {clusterInfo}/>
280287
{/if}
281288
{:else}
282289
<Spinner secondary />
@@ -285,10 +292,10 @@
285292
</Row>
286293
287294
<!-- Row 2: Energy Information if available -->
288-
{#if $initq?.data && $initq.data.job.energyFootprint.length != 0}
295+
{#if thisJob && thisJob?.energyFootprint?.length != 0}
289296
<Row class="mb-3">
290297
<Col>
291-
<EnergySummary jobId={$initq.data.job.jobId} jobEnergy={$initq.data.job.energy} jobEnergyFootprint={$initq.data.job.energyFootprint}/>
298+
<EnergySummary jobId={thisJob.jobId} jobEnergy={thisJob.energy} jobEnergyFootprint={thisJob.energyFootprint}/>
292299
</Col>
293300
</Row>
294301
{/if}
@@ -297,7 +304,7 @@
297304
<Card class="mb-3">
298305
<CardBody>
299306
<Row class="mb-2">
300-
{#if $initq?.data}
307+
{#if thisJob}
301308
<Col xs="auto">
302309
<Button outline onclick={() => (isMetricsSelectionOpen = true)} color="primary">
303310
Select Metrics (Selected {selectedMetrics.length} of {totalMetrics} available)
@@ -310,7 +317,7 @@
310317
{#if $jobMetrics.error}
311318
<Row class="mt-2">
312319
<Col>
313-
{#if $initq?.data && ($initq.data.job?.monitoringStatus == 0 || $initq.data.job?.monitoringStatus == 2)}
320+
{#if thisJob && (thisJob?.monitoringStatus == 0 || thisJob?.monitoringStatus == 2)}
314321
<Card body color="warning">Not monitored or archiving failed</Card>
315322
<br />
316323
{/if}
@@ -323,26 +330,26 @@
323330
<Spinner secondary />
324331
</Col>
325332
</Row>
326-
{:else if $initq?.data && $jobMetrics?.data?.scopedJobStats}
333+
{:else if thisJob && $jobMetrics?.data?.scopedJobStats}
327334
<!-- Note: Ignore '#snippet' Error in IDE -->
328335
{#snippet gridContent(item)}
329336
{#if item.data}
330337
<Metric
331338
bind:this={plots[item.metric]}
332-
job={$initq.data.job}
339+
job={thisJob}
333340
metricName={item.metric}
334-
metricUnit={$initq.data.globalMetrics.find((gm) => gm.name == item.metric)?.unit}
335-
nativeScope={$initq.data.globalMetrics.find((gm) => gm.name == item.metric)?.scope}
341+
metricUnit={globalMetrics.find((gm) => gm.name == item.metric)?.unit}
342+
nativeScope={globalMetrics.find((gm) => gm.name == item.metric)?.scope}
336343
presetScopes={item.data.map((x) => x.scope)}
337-
isShared={$initq.data.job.shared != "none"}
344+
isShared={thisJob.shared != "none"}
338345
/>
339346
{:else if item.disabled == true}
340347
<Card color="info">
341348
<CardHeader class="mb-0">
342349
<b>Disabled Metric</b>
343350
</CardHeader>
344351
<CardBody>
345-
<p>Metric <b>{item.metric}</b> is disabled for cluster <b>{$initq.data.job.cluster}:{$initq.data.job.subCluster}</b>.</p>
352+
<p>Metric <b>{item.metric}</b> is disabled for cluster <b>{thisJob.cluster}:{thisJob.subCluster}</b>.</p>
346353
<p class="mb-1">To remove this card, open metric selection and press "Close and Apply".</p>
347354
</CardBody>
348355
</Card>
@@ -353,7 +360,7 @@
353360
</CardHeader>
354361
<CardBody>
355362
<p>No dataset(s) returned for <b>{item.metric}</b>.</p>
356-
<p class="mb-1">Metric was not found in metric store for cluster <b>{$initq.data.job.cluster}</b>.</p>
363+
<p class="mb-1">Metric was not found in metric store for cluster <b>{thisJob.cluster}</b>.</p>
357364
</CardBody>
358365
</Card>
359366
{/if}
@@ -374,7 +381,7 @@
374381
<!-- Metadata && Statistcics Table -->
375382
<Row class="mb-3">
376383
<Col>
377-
{#if $initq?.data}
384+
{#if thisJob}
378385
<Card>
379386
<TabContent>
380387
{#if somethingMissing}
@@ -409,21 +416,21 @@
409416
{/if}
410417
{#if showStatsTable}
411418
<!-- Includes <TabPane> Statistics Table with Independent GQL Query -->
412-
<StatsTab job={$initq.data.job} clusters={$initq.data.clusters} tabActive={!somethingMissing}/>
419+
<StatsTab job={thisJob} {clusterInfo} {globalMetrics} {ccconfig} tabActive={!somethingMissing}/>
413420
{/if}
414421
<TabPane tabId="job-script" tab="Job Script">
415422
<div class="pre-wrapper">
416-
{#if $initq.data.job.metaData?.jobScript}
417-
<pre><code>{$initq.data.job.metaData?.jobScript}</code></pre>
423+
{#if thisJob.metaData?.jobScript}
424+
<pre><code>{thisJob.metaData?.jobScript}</code></pre>
418425
{:else}
419426
<Card body color="warning">No job script available</Card>
420427
{/if}
421428
</div>
422429
</TabPane>
423430
<TabPane tabId="slurm-info" tab="Slurm Info">
424431
<div class="pre-wrapper">
425-
{#if $initq.data.job.metaData?.slurmInfo}
426-
<pre><code>{$initq.data.job.metaData?.slurmInfo}</code></pre>
432+
{#if thisJob.metaData?.slurmInfo}
433+
<pre><code>{thisJob.metaData?.slurmInfo}</code></pre>
427434
{:else}
428435
<Card body color="warning"
429436
>No additional slurm information available</Card
@@ -437,15 +444,15 @@
437444
</Col>
438445
</Row>
439446
440-
{#if $initq?.data}
447+
{#if thisJob}
441448
<MetricSelection
442449
bind:isOpen={isMetricsSelectionOpen}
443450
bind:totalMetrics
444451
presetMetrics={selectedMetrics}
445-
cluster={$initq.data.job.cluster}
446-
subCluster={$initq.data.job.subCluster}
452+
cluster={thisJob.cluster}
453+
subCluster={thisJob.subCluster}
447454
configName="metricConfig_jobViewPlotMetrics"
448-
preInitialized
455+
{globalMetrics}
449456
applyMetrics={(newMetrics) =>
450457
selectedMetrics = [...newMetrics]
451458
}

0 commit comments

Comments
 (0)