mirror of
https://github.com/k3s-io/kubernetes.git
synced 2025-07-22 19:31:44 +00:00
Merge pull request #103181 from 249043822/bugfix-volumemanager
Add sync reconstructed volume from desired state of world for volumemanager
This commit is contained in:
commit
6aa160f3ba
@ -171,6 +171,10 @@ type ActualStateOfWorld interface {
|
||||
// to the node. This list can be used to determine volumes that are either in-use
|
||||
// or have a mount/unmount operation pending.
|
||||
GetAttachedVolumes() []AttachedVolume
|
||||
|
||||
// SyncReconstructedVolume check the volume.outerVolumeSpecName in asw and
|
||||
// the one populated from dsw , if they do not match, update this field from the value from dsw.
|
||||
SyncReconstructedVolume(volumeName v1.UniqueVolumeName, podName volumetypes.UniquePodName, outerVolumeSpecName string)
|
||||
}
|
||||
|
||||
// MountedVolume represents a volume that has successfully been mounted to a pod.
|
||||
@ -885,6 +889,19 @@ func (asw *actualStateOfWorld) GetUnmountedVolumes() []AttachedVolume {
|
||||
return unmountedVolumes
|
||||
}
|
||||
|
||||
func (asw *actualStateOfWorld) SyncReconstructedVolume(volumeName v1.UniqueVolumeName, podName volumetypes.UniquePodName, outerVolumeSpecName string) {
|
||||
asw.Lock()
|
||||
defer asw.Unlock()
|
||||
if volumeObj, volumeExists := asw.attachedVolumes[volumeName]; volumeExists {
|
||||
if podObj, podExists := volumeObj.mountedPods[podName]; podExists {
|
||||
if podObj.outerVolumeSpecName != outerVolumeSpecName {
|
||||
podObj.outerVolumeSpecName = outerVolumeSpecName
|
||||
asw.attachedVolumes[volumeName].mountedPods[podName] = podObj
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (asw *actualStateOfWorld) newAttachedVolume(
|
||||
attachedVolume *attachedVolume) AttachedVolume {
|
||||
return AttachedVolume{
|
||||
|
@ -306,7 +306,7 @@ func (dswp *desiredStateOfWorldPopulator) processPodVolumes(
|
||||
}
|
||||
|
||||
// Add volume to desired state of world
|
||||
_, err = dswp.desiredStateOfWorld.AddPodToVolume(
|
||||
uniqueVolumeName, err := dswp.desiredStateOfWorld.AddPodToVolume(
|
||||
uniquePodName, pod, volumeSpec, podVolume.Name, volumeGidValue)
|
||||
if err != nil {
|
||||
klog.ErrorS(err, "Failed to add volume to desiredStateOfWorld", "pod", klog.KObj(pod), "volumeName", podVolume.Name, "volumeSpecName", volumeSpec.Name())
|
||||
@ -315,6 +315,8 @@ func (dswp *desiredStateOfWorldPopulator) processPodVolumes(
|
||||
} else {
|
||||
klog.V(4).InfoS("Added volume to desired state", "pod", klog.KObj(pod), "volumeName", podVolume.Name, "volumeSpecName", volumeSpec.Name())
|
||||
}
|
||||
// sync reconstructed volume
|
||||
dswp.actualStateOfWorld.SyncReconstructedVolume(uniqueVolumeName, uniquePodName, podVolume.Name)
|
||||
|
||||
if expandInUsePV {
|
||||
dswp.checkVolumeFSResize(pod, podVolume, pvc, volumeSpec,
|
||||
|
@ -83,6 +83,72 @@ func prepareDswpWithVolume(t *testing.T) (*desiredStateOfWorldPopulator, kubepod
|
||||
return dswp, fakePodManager
|
||||
}
|
||||
|
||||
func TestFindAndAddNewPods_WithRescontructedVolume(t *testing.T) {
|
||||
// create dswp
|
||||
dswp, fakePodManager := prepareDswpWithVolume(t)
|
||||
|
||||
// create pod
|
||||
fakeOuterVolumeName := "dswp-test-volume-name"
|
||||
containers := []v1.Container{
|
||||
{
|
||||
VolumeMounts: []v1.VolumeMount{
|
||||
{
|
||||
Name: fakeOuterVolumeName,
|
||||
MountPath: "/mnt",
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
pod := createPodWithVolume("dswp-test-pod", fakeOuterVolumeName, "file-bound", containers)
|
||||
|
||||
fakePodManager.AddPod(pod)
|
||||
|
||||
podName := util.GetUniquePodName(pod)
|
||||
|
||||
mode := v1.PersistentVolumeFilesystem
|
||||
pv := &v1.PersistentVolume{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: fakeOuterVolumeName,
|
||||
},
|
||||
Spec: v1.PersistentVolumeSpec{
|
||||
ClaimRef: &v1.ObjectReference{Namespace: "ns", Name: "file-bound"},
|
||||
VolumeMode: &mode,
|
||||
},
|
||||
}
|
||||
generatedVolumeName := "fake-plugin/" + pod.Spec.Volumes[0].Name
|
||||
uniqueVolumeName := v1.UniqueVolumeName(generatedVolumeName)
|
||||
expectedOuterVolumeName := "dswp-test-volume-name"
|
||||
|
||||
opts := operationexecutor.MarkVolumeOpts{
|
||||
PodName: podName,
|
||||
PodUID: pod.UID,
|
||||
VolumeName: uniqueVolumeName,
|
||||
OuterVolumeSpecName: generatedVolumeName, // fake reconstructed volume
|
||||
VolumeGidVolume: "",
|
||||
VolumeSpec: volume.NewSpecFromPersistentVolume(pv, false),
|
||||
VolumeMountState: operationexecutor.VolumeMounted,
|
||||
}
|
||||
dswp.actualStateOfWorld.MarkVolumeAsAttached(opts.VolumeName, opts.VolumeSpec, "fake-node", "")
|
||||
dswp.actualStateOfWorld.MarkVolumeAsMounted(opts)
|
||||
|
||||
dswp.findAndAddNewPods()
|
||||
|
||||
mountedVolumes := dswp.actualStateOfWorld.GetMountedVolumesForPod(podName)
|
||||
found := false
|
||||
for _, volume := range mountedVolumes {
|
||||
if volume.OuterVolumeSpecName == expectedOuterVolumeName {
|
||||
found = true
|
||||
break
|
||||
}
|
||||
}
|
||||
if !found {
|
||||
t.Fatalf(
|
||||
"Could not found pod volume %v in the list of actual state of world volumes to mount.",
|
||||
expectedOuterVolumeName)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
func TestFindAndAddNewPods_WithReprocessPodAndVolumeRetrievalError(t *testing.T) {
|
||||
// create dswp
|
||||
dswp, fakePodManager := prepareDswpWithVolume(t)
|
||||
|
@ -579,7 +579,8 @@ func (rc *reconciler) reconstructVolume(volume podVolume) (*reconstructedVolume,
|
||||
volumeSpec: volumeSpec,
|
||||
// volume.volumeSpecName is actually InnerVolumeSpecName. It will not be used
|
||||
// for volume cleanup.
|
||||
// TODO: in case pod is added back before reconciler starts to unmount, we can update this field from desired state information
|
||||
// in case pod is added back to desired state, outerVolumeSpecName will be updated from dsw information.
|
||||
// See issue #103143 and its fix for details.
|
||||
outerVolumeSpecName: volume.volumeSpecName,
|
||||
pod: pod,
|
||||
deviceMounter: deviceMounter,
|
||||
|
Loading…
Reference in New Issue
Block a user