Skip to content

Commit 203343e

Browse files
committed
Improve VAC field on PVC details page
1 parent 335ed77 commit 203343e

File tree

2 files changed

+112
-9
lines changed

2 files changed

+112
-9
lines changed

frontend/public/components/persistent-volume-claim.tsx

Lines changed: 105 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@ import i18next, { TFunction } from 'i18next';
44
import { useTranslation } from 'react-i18next';
55
import { useDispatch, useSelector } from 'react-redux';
66
import {
7+
Alert,
8+
AlertActionCloseButton,
79
DescriptionList,
810
DescriptionListDescription,
911
DescriptionListGroup,
@@ -55,6 +57,7 @@ import { SectionHeading } from './utils/headings';
5557
import { ResourceLink } from './utils/resource-link';
5658
import { ResourceSummary } from './utils/details-page';
5759
import { Selector } from './utils/selector';
60+
import { truncateMiddle } from './utils/truncate-middle';
5861
import { humanizeBinaryBytes, convertToBaseValue } from './utils/units';
5962
import { ResourceEventStream } from './events';
6063
import { PVCMetrics, setPVCMetrics } from '@console/internal/actions/ui';
@@ -76,6 +79,30 @@ const tableColumnInfo = [
7679
{ id: '' },
7780
];
7881

82+
/**
83+
* Determines the VAC (VolumeAttributesClass) modification state for a PVC
84+
* @param pvc - The PersistentVolumeClaim resource
85+
* @returns Object containing error condition and pending state
86+
*/
87+
const getVACAlertState = (pvc: PersistentVolumeClaimKind) => {
88+
const volumeAttributesClassName = pvc?.spec?.volumeAttributesClassName;
89+
const currentVolumeAttributesClassName = pvc?.status?.currentVolumeAttributesClassName;
90+
const conditions = pvc?.status?.conditions;
91+
92+
// Check for explicit ModifyVolumeError condition
93+
const vacErrorCondition = conditions?.find(
94+
(condition) => condition.type === 'ModifyVolumeError' && condition.status === 'True',
95+
);
96+
97+
// Determine if modification is pending (only when applying or modifying VAC, not removing)
98+
const isVacPending =
99+
!vacErrorCondition &&
100+
volumeAttributesClassName &&
101+
volumeAttributesClassName !== currentVolumeAttributesClassName;
102+
103+
return { vacErrorCondition, isVacPending };
104+
};
105+
79106
export const PVCStatusComponent: React.FCC<PVCStatusProps> = ({ pvc }) => {
80107
const { t } = useTranslation();
81108
const [pvcStatusExtensions, resolved] = useResolvedExtensions<PVCStatus>(isPVCStatus);
@@ -249,6 +276,17 @@ const PVCDetails: React.FCC<PVCDetailsProps> = ({ obj: pvc }) => {
249276
const volumeMode = pvc?.spec?.volumeMode;
250277
const conditions = pvc?.status?.conditions;
251278

279+
// State to track dismissed alerts
280+
const [isErrorAlertDismissed, setIsErrorAlertDismissed] = React.useState(false);
281+
const [isInfoAlertDismissed, setIsInfoAlertDismissed] = React.useState(false);
282+
283+
// Reset alert dismiss states when PVC changes
284+
const pvcUid = pvc?.metadata?.uid;
285+
React.useEffect(() => {
286+
setIsErrorAlertDismissed(false);
287+
setIsInfoAlertDismissed(false);
288+
}, [pvcUid]);
289+
252290
const query =
253291
name && namespace
254292
? `kubelet_volume_stats_used_bytes{persistentvolumeclaim='${name}',namespace='${namespace}'}`
@@ -288,10 +326,53 @@ const PVCDetails: React.FCC<PVCDetailsProps> = ({ obj: pvc }) => {
288326
({ properties: { alert: AlertComponent }, uid }) => <AlertComponent key={uid} pvc={pvc} />,
289327
);
290328

329+
// Get VAC modification state using helper function
330+
const { vacErrorCondition, isVacPending } = getVACAlertState(pvc);
331+
291332
return (
292333
<>
293334
<PaneBody>
294335
{alertComponents}
336+
{isVACSupported && vacErrorCondition && !isErrorAlertDismissed && (
337+
<Alert
338+
isInline
339+
variant="danger"
340+
title={t('public~VolumeAttributesClass modification failed')}
341+
className="co-alert co-alert--margin-bottom-sm"
342+
actionClose={<AlertActionCloseButton onClose={() => setIsErrorAlertDismissed(true)} />}
343+
>
344+
{truncateMiddle(
345+
vacErrorCondition.message ||
346+
t('public~Failed to modify VolumeAttributesClass for this PersistentVolumeClaim.'),
347+
{ length: 200, truncateEnd: true },
348+
)}
349+
</Alert>
350+
)}
351+
{isVACSupported && isVacPending && !isInfoAlertDismissed && (
352+
<Alert
353+
isInline
354+
variant="info"
355+
title={
356+
volumeAttributesClassName && !currentVolumeAttributesClassName
357+
? t('public~VolumeAttributesClass application pending')
358+
: t('public~VolumeAttributesClass modification in progress')
359+
}
360+
className="co-alert co-alert--margin-bottom-sm"
361+
actionClose={<AlertActionCloseButton onClose={() => setIsInfoAlertDismissed(true)} />}
362+
>
363+
{!currentVolumeAttributesClassName
364+
? t('public~VolumeAttributesClass "{{target}}" is pending application.', {
365+
target: volumeAttributesClassName,
366+
})
367+
: t(
368+
'public~VolumeAttributesClass is being modified from "{{current}}" to "{{target}}".',
369+
{
370+
current: currentVolumeAttributesClassName,
371+
target: volumeAttributesClassName,
372+
},
373+
)}
374+
</Alert>
375+
)}
295376
<SectionHeading text={t('public~PersistentVolumeClaim details')} />
296377
{totalCapacityMetric && !loading && (
297378
<div className="co-pvc-donut">
@@ -383,19 +464,34 @@ const PVCDetails: React.FCC<PVCDetailsProps> = ({ obj: pvc }) => {
383464
)}
384465
</DescriptionListDescription>
385466
</DescriptionListGroup>
386-
{isVACSupported &&
387-
!!volumeAttributesClassName &&
388-
volumeAttributesClassName === currentVolumeAttributesClassName && (
389-
<DescriptionListGroup>
390-
<DescriptionListTerm>{t('public~VolumeAttributesClass')}</DescriptionListTerm>
391-
<DescriptionListDescription>
467+
{isVACSupported && (
468+
<DescriptionListGroup>
469+
<DescriptionListTerm>
470+
{t('public~Requested VolumeAttributesClass')}
471+
</DescriptionListTerm>
472+
<DescriptionListDescription data-test-id="pvc-requested-vac">
473+
{volumeAttributesClassName ? (
392474
<ResourceLink
393475
kind={referenceFor(VolumeAttributesClassModel)}
394476
name={volumeAttributesClassName}
395477
/>
396-
</DescriptionListDescription>
397-
</DescriptionListGroup>
398-
)}
478+
) : (
479+
DASH
480+
)}
481+
</DescriptionListDescription>
482+
</DescriptionListGroup>
483+
)}
484+
{isVACSupported && !!currentVolumeAttributesClassName && (
485+
<DescriptionListGroup>
486+
<DescriptionListTerm>{t('public~VolumeAttributesClass')}</DescriptionListTerm>
487+
<DescriptionListDescription data-test-id="pvc-current-vac">
488+
<ResourceLink
489+
kind={referenceFor(VolumeAttributesClassModel)}
490+
name={currentVolumeAttributesClassName}
491+
/>
492+
</DescriptionListDescription>
493+
</DescriptionListGroup>
494+
)}
399495
{volumeName && canListPV && (
400496
<DescriptionListGroup>
401497
<DescriptionListTerm>{t('public~PersistentVolumes')}</DescriptionListTerm>

frontend/public/locales/en/public.json

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1128,6 +1128,12 @@
11281128
"Used": "Used",
11291129
"StorageClass": "StorageClass",
11301130
"Total": "Total",
1131+
"VolumeAttributesClass modification failed": "VolumeAttributesClass modification failed",
1132+
"Failed to modify VolumeAttributesClass for this PersistentVolumeClaim.": "Failed to modify VolumeAttributesClass for this PersistentVolumeClaim.",
1133+
"VolumeAttributesClass application pending": "VolumeAttributesClass application pending",
1134+
"VolumeAttributesClass modification in progress": "VolumeAttributesClass modification in progress",
1135+
"VolumeAttributesClass \"{{target}}\" is pending application.": "VolumeAttributesClass \"{{target}}\" is pending application.",
1136+
"VolumeAttributesClass is being modified from \"{{current}}\" to \"{{target}}\".": "VolumeAttributesClass is being modified from \"{{current}}\" to \"{{target}}\".",
11311137
"PersistentVolumeClaim details": "PersistentVolumeClaim details",
11321138
"Available versus used capacity": "Available versus used capacity",
11331139
"Total capacity": "Total capacity",
@@ -1136,6 +1142,7 @@
11361142
"Access modes": "Access modes",
11371143
"Volume mode": "Volume mode",
11381144
"StorageClasses": "StorageClasses",
1145+
"Requested VolumeAttributesClass": "Requested VolumeAttributesClass",
11391146
"VolumeAttributesClass": "VolumeAttributesClass",
11401147
"PersistentVolumes": "PersistentVolumes",
11411148
"Bound": "Bound",

0 commit comments

Comments
 (0)