Skip to content

Commit

Permalink
Merge pull request #2309 from upalatucci/fix-persistent-hotplug
Browse files Browse the repository at this point in the history
CNV-52060: fix persistent hotplug after restart
  • Loading branch information
openshift-merge-bot[bot] authored Dec 10, 2024
2 parents 848cf61 + 28f1d07 commit 8941b29
Show file tree
Hide file tree
Showing 2 changed files with 64 additions and 13 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,7 @@ import {
import ConfirmActionMessage from '@kubevirt-utils/components/ConfirmActionMessage/ConfirmActionMessage';
import TabModal from '@kubevirt-utils/components/TabModal/TabModal';
import { useKubevirtTranslation } from '@kubevirt-utils/hooks/useKubevirtTranslation';
import { getVolumes } from '@kubevirt-utils/resources/vm';
import { getVMIVolumes } from '@kubevirt-utils/resources/vmi';
import { isEmpty } from '@kubevirt-utils/utils/utils';
import { Stack, StackItem } from '@patternfly/react-core';

import { updateDisks } from '../../../details/utils/utils';
Expand All @@ -36,9 +34,6 @@ const MakePersistentModal: FC<MakePersistentModalProps> = ({

const makePersistent = () => {
const volumeToPersist = getVMIVolumes(vmi).find((vmiVolume) => vmiVolume.name === volume?.name);
const vmHasVolume = getVolumes(vm).find((vmVolume) => vmVolume.name === volume?.name);

if (vmHasVolume || isEmpty(volumeToPersist)) return Promise.resolve();

const vmPersistent = persistVolume(vm, vmi, volumeToPersist);

Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
import produce from 'immer';
import { WritableDraft } from 'immer/dist/internal';

import { DEFAULT_PREFERENCE_LABEL } from '@catalog/CreateFromInstanceTypes/utils/constants';
import {
V1Disk,
V1VirtualMachine,
V1VirtualMachineInstance,
V1Volume,
Expand All @@ -11,7 +13,13 @@ import {
emptyDataSource,
} from '@kubevirt-utils/components/AddBootableVolumeModal/utils/constants';
import { createPVCBootableVolume } from '@kubevirt-utils/components/AddBootableVolumeModal/utils/utils';
import { getDisks, getPreferenceMatcher } from '@kubevirt-utils/resources/vm';
import { getNamespace } from '@kubevirt-utils/resources/shared';
import {
getDataVolumeTemplates,
getDisks,
getPreferenceMatcher,
getVolumes,
} from '@kubevirt-utils/resources/vm';
import { DiskRowDataLayout } from '@kubevirt-utils/resources/vm/utils/disk/constants';
import { getVMIDevices } from '@kubevirt-utils/resources/vmi';
import { ClaimPropertySets } from '@kubevirt-utils/types/storage';
Expand Down Expand Up @@ -43,6 +51,44 @@ export const createBootableVolumeFromDisk = async (
);
};

const addDiskToVM = (draftVM: WritableDraft<V1VirtualMachine>, diskToPersist: V1Disk) => {
const disks = getDisks(draftVM) || [];

if (isEmpty(diskToPersist) || disks.find((disk) => disk.name === diskToPersist.name)) return;

disks.push({ ...diskToPersist, serial: null });

draftVM.spec.template.spec.domain.devices.disks = disks;
};

const addDataVolumeToVM = (draftVM: WritableDraft<V1VirtualMachine>, dataVolumeName: string) => {
const dataVolumeTemplates = getDataVolumeTemplates(draftVM);

if (dataVolumeTemplates.find((dataVolume) => dataVolume.metadata.name === dataVolumeName)) return;

dataVolumeTemplates.push({
metadata: {
name: dataVolumeName,
},
spec: {
source: {
pvc: {
name: dataVolumeName,
namespace: getNamespace(draftVM),
},
},
},
});
};

const removeHotplugFromVolume = (volume: V1Volume) =>
produce(volume, (draftVolume) => {
if (draftVolume?.dataVolume?.hotpluggable) delete draftVolume.dataVolume.hotpluggable;

if (draftVolume?.persistentVolumeClaim?.hotpluggable)
delete draftVolume.persistentVolumeClaim.hotpluggable;
});

export const persistVolume = (
vm: V1VirtualMachine,
vmi: V1VirtualMachineInstance,
Expand All @@ -51,19 +97,29 @@ export const persistVolume = (
produce(vm, (draftVM) => {
ensurePath(draftVM, 'spec.template.spec.domain.devices');

draftVM.spec.template.spec.volumes.push(volumeToPersist);
const vmVolumes = getVolumes(draftVM);

const vmVolumeToPersist = vmVolumes.find((vmVolume) => vmVolume.name === volumeToPersist?.name);

if (vmVolumeToPersist) {
draftVM.spec.template.spec.volumes = [
...vmVolumes.filter((volume) => volume.name !== vmVolumeToPersist.name),
removeHotplugFromVolume(vmVolumeToPersist),
];
}

if (!vmVolumeToPersist) {
vmVolumes.push(removeHotplugFromVolume(volumeToPersist));
}

const diskToPersist = getVMIDevices(vmi)?.disks?.find(
(disk) => disk.name === volumeToPersist.name,
);

if (isEmpty(diskToPersist)) return;

const disks = getDisks(draftVM) || [];

disks.push({ ...diskToPersist, serial: null });
addDiskToVM(draftVM, diskToPersist);

draftVM.spec.template.spec.domain.devices.disks = disks;
if (!isEmpty(volumeToPersist?.dataVolume?.name))
addDataVolumeToVM(draftVM, volumeToPersist?.dataVolume?.name);

return draftVM;
});

0 comments on commit 8941b29

Please sign in to comment.