Repository: kubernetes/kubernetes
File: test/e2e/storage/framework/volume_group_snapshot_resource.go (Go)

Code before:
					}
				}
			}
		}
	}
	return contentNamesSet, nil
}

// cleanupRetainedVolumeSnapshotContents forcibly deletes VolumeSnapshotContents with Retain policy
func (r *VolumeGroupSnapshotResource) cleanupRetainedVolumeSnapshotContents(ctx context.Context, dc dynamic.Interface, contentNames sets.Set[string], timeouts *framework.TimeoutContext) {
	// Update deletion policy and delete each VolumeSnapshotContent
	for _, contentName := range contentNames.UnsortedList() {
		vsc, err := dc.Resource(utils.SnapshotContentGVR).Get(ctx, contentName, metav1.GetOptions{})
		if err != nil {
			if !apierrors.IsNotFound(err) {
				framework.Logf("Warning: failed to get VolumeSnapshotContent %q: %v", contentName, err)
			}
			continue
		}

		// Update deletion policy to Delete
		vscSpec := vsc.Object["spec"].(map[string]interface{})
		vscSpec["deletionPolicy"] = "Delete"
		_, err = dc.Resource(utils.SnapshotContentGVR).Update(ctx, vsc, metav1.UpdateOptions{})
		if err != nil && !apierrors.IsNotFound(err) {
			framework.Logf("Warning: failed to update VolumeSnapshotContent %q deletion policy: %v", contentName, err)
		}

		// Delete VolumeSnapshotContent
		err = dc.Resource(utils.SnapshotContentGVR).Delete(ctx, contentName, metav1.DeleteOptions{})
		if err != nil && !apierrors.IsNotFound(err) {
			framework.Logf("Warning: failed to delete VolumeSnapshotContent %q: %v", contentName, err)
		}
	}

	// Wait for all VolumeSnapshotContents to be deleted
	framework.Logf("Waiting for VolumeSnapshotContents to be deleted")
	for _, contentName := range contentNames.UnsortedList() {
		if err := utils.WaitForGVRDeletion(ctx, dc, utils.SnapshotContentGVR, contentName, framework.Poll, timeouts.SnapshotDelete); err != nil {
			framework.Logf("Warning: VolumeSnapshotContent %q may not be fully deleted: %v", contentName, err)
		}
	}
}

// cleanupRetainedVGSContent forcibly deletes VolumeGroupSnapshotContent with Retain policy
func (r *VolumeGroupSnapshotResource) cleanupRetainedVGSContent(ctx context.Context, dc dynamic.Interface, vgscName string, timeouts *framework.TimeoutContext) {
	framework.Logf("Deleting VGSContent %q", vgscName)

	// Refetch the latest version to avoid resource conflict
	boundVGSContent, err := dc.Resource(utils.VolumeGroupSnapshotContentGVR).Get(ctx, vgscName, metav1.GetOptions{})
	if err != nil && !apierrors.IsNotFound(err) {

Review comment (bug):
Same here, the update should succeed and it's a bug if it does not.
A `Patch()` would be slightly better though to prevent conflicts.

Code after:
					}
				}
			}
		}
	}
	return contentNamesSet, nil
}

// cleanupRetainedVolumeSnapshotContents forcibly deletes VolumeSnapshotContents with Retain policy
func (r *VolumeGroupSnapshotResource) cleanupRetainedVolumeSnapshotContents(ctx context.Context, dc dynamic.Interface, contentNames sets.Set[string], timeouts *framework.TimeoutContext) {
	// Update deletion policy and delete each VolumeSnapshotContent
	for _, contentName := range contentNames.UnsortedList() {
		// Patch deletion policy to Delete
		patchData := []byte(`{"spec":{"deletionPolicy":"Delete"}}`)
		_, err := dc.Resource(utils.SnapshotContentGVR).Patch(ctx, contentName, types.MergePatchType, patchData, metav1.PatchOptions{})
		if err != nil {
			framework.Failf("Failed to patch VolumeSnapshotContent %q deletion policy: %v", contentName, err)
			return
		}

		// Delete VolumeSnapshotContent
		err = dc.Resource(utils.SnapshotContentGVR).Delete(ctx, contentName, metav1.DeleteOptions{})
		if err != nil {
			framework.Failf("Failed to delete VolumeSnapshotContent %q: %v", contentName, err)
			return
		}
	}

	// Wait for all VolumeSnapshotContents to be deleted
	framework.Logf("Waiting for VolumeSnapshotContents to be deleted")
	for _, contentName := range contentNames.UnsortedList() {
		if err := utils.WaitForGVRDeletion(ctx, dc, utils.SnapshotContentGVR, contentName, framework.Poll, timeouts.SnapshotDelete); err != nil {
			framework.Failf("VolumeSnapshotContent %q was not fully deleted: %v", contentName, err)
			return
		}
	}
}

// cleanupRetainedVGSContent forcibly deletes VolumeGroupSnapshotContent with Retain policy
func (r *VolumeGroupSnapshotResource) cleanupRetainedVGSContent(ctx context.Context, dc dynamic.Interface, vgscName string, timeouts *framework.TimeoutContext) {
	framework.Logf("Deleting VGSContent %q", vgscName)

	// Patch deletion policy to Delete
	patchData := []byte(`{"spec":{"deletionPolicy":"Delete"}}`)
	_, err := dc.Resource(utils.VolumeGroupSnapshotContentGVR).Patch(ctx, vgscName, types.MergePatchType, patchData, metav1.PatchOptions{})
	if err != nil {
		framework.Failf("Failed to patch VGSContent %q deletion policy: %v", vgscName, err)
		return
	}

	// Delete VGSContent