-
Notifications
You must be signed in to change notification settings - Fork 40k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[WIP] Set default storage class on PVC sync if default StorageClass is present #100031
[WIP] Set default storage class on PVC sync if default StorageClass is present #100031
Conversation
In case where there's no default StorageClass at the time of creation of a PVC, the PVC will stay without storage class. This logic was thus far only executed in AdmissionWebhook which would add a storageClassName to PVC with no defined storageClass. Therefore, PVC will stay without storageClassName, if the PVC manifest is not reapplied to the cluster.
Thanks for your pull request. Before we can look at your pull request, you'll need to sign a Contributor License Agreement (CLA). 📝 Please follow instructions at https://git.k8s.io/community/CLA.md#the-contributor-license-agreement to sign the CLA. It may take a couple minutes for the CLA signature to be fully registered; after that, please reply here with a new comment and we'll verify. Thanks.
Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. I understand the commands that are listed here. |
@LittleChimera: This issue is currently awaiting triage. If a SIG or subproject determines this is a relevant issue, they will accept it by applying the The Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. |
Welcome @LittleChimera! |
Hi @LittleChimera. Thanks for your PR. I'm waiting for a kubernetes member to verify that this patch is reasonable to test. If it is, they should reply with Once the patch is verified, the new status will be reflected by the I understand the commands that are listed here. Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. |
[APPROVALNOTIFIER] This PR is NOT APPROVED This pull-request has been approved by: LittleChimera The full list of commands accepted by this bot can be found here.
Needs approval from an approver in each of these files:
Approvers can indicate their approval by writing |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please add some unit tests too!
if storageClasses, err := ctrl.kubeClient.StorageV1().StorageClasses().List(context.TODO(), metav1.ListOptions{}); err != nil { | ||
for _, sc := range storageClasses.Items { | ||
if sutil.IsDefaultAnnotation(sc.ObjectMeta) { | ||
claim.Spec.StorageClassName = &sc.Name | ||
ctrl.updateClaim(claim) | ||
return nil | ||
} | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please extract all this getting default SC and modifying PV into a separate function and just call it. I like the giant if-then-else
in syncUnboundClaim
as clean as possible.
@@ -359,8 +360,19 @@ func (ctrl *PersistentVolumeController) syncUnboundClaim(claim *v1.PersistentVol | |||
return err | |||
} | |||
return nil | |||
case storagehelpers.GetPersistentVolumeClaimClass(claim) == "": | |||
if storageClasses, err := ctrl.kubeClient.StorageV1().StorageClasses().List(context.TODO(), metav1.ListOptions{}); err != nil { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Setting the default storage class should be done at line 337, "// User did not care which PV they get" - if the PVC has no storage class, file it there and return. Updated PVC will be enqueued shortly and it will have a SC.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hold on, maybe leave the code here - if there is a PV without a storage class, we try to bind to it once. If there is no such PV, we file the default SC into the PVC and try again, hoping for dynamic provisioning. This will keep at least a bit of the existing behavior there.
@msau42 what do you think? It's a bit confusing.
Is this really something we want to do? If I recall correctly, having no
class is semantically meaningful, isn't it?
…On Fri, May 21, 2021 at 8:27 AM Jan Šafránek ***@***.***> wrote:
***@***.**** commented on this pull request.
------------------------------
In pkg/controller/volume/persistentvolume/pv_controller.go
<#100031 (comment)>
:
> @@ -359,8 +360,19 @@ func (ctrl *PersistentVolumeController) syncUnboundClaim(claim *v1.PersistentVol
return err
}
return nil
+ case storagehelpers.GetPersistentVolumeClaimClass(claim) == "":
+ if storageClasses, err := ctrl.kubeClient.StorageV1().StorageClasses().List(context.TODO(), metav1.ListOptions{}); err != nil {
Hold on, maybe leave the code here - if there is a PV without a storage
class, we try to bind to it once. If there is no such PV, we file the
default SC into the PVC and try again, hoping for dynamic provisioning.
This will keep at least a bit of the existing behavior there.
@msau42 <https://github.com/msau42> what do you think? It's a bit
confusing.
—
You are receiving this because your review was requested.
Reply to this email directly, view it on GitHub
<#100031 (comment)>,
or unsubscribe
<https://github.com/notifications/unsubscribe-auth/ABKWAVFYPLGCLB3TGPRQKXDTOZ3VPANCNFSM4Y4M6WHQ>
.
|
Thank you for the feedback! ❤️
I was actually trying to modify these test cases which specify that nothing should be done when storageClass is set to an empty value (with this PR, I would expect that in these two cases, the default storageClass is overridden on this PVC instead, and then a PV provisioned and bound): Originally, there were written as part of dynamic provisioning. I cannot make out a reason as to why this behaviour was chosen. Default storage classes were added later, and I cannot find again the reason for this behavior: I would expect that storageClass is not overwritten by dynamic provisioner only if the associated PV was created manually. |
I think we definitely don't want to set the default storageclass for PVCs that have already been bound. For unbound PVCs, I see two scenarios:
IMO the scenario of depending on this behavior before installing a default StorageClass in the system seems a bit contrived and requires careful deployment ordering by the user. It could be mitigated by creating the PVC with "" storageclass. That being said, I do agree that this makes explaining the API semantics more complicated. There are other issues too, such as validation not allowing updates to storageclassname, and maybe some concerns (that I haven't thought about yet) with pvc templates (statefulset, generic ephemeral volumes). In summary, this is not as simple to change, we need to think more deeply on the api compatibility and impact to other features. |
I think that ordering probably isn't the best way to solve this. In case of CRDs and Namespaces, which fall into this category, API server doesn't accept applying the dependencies. In other words, either you get expected results, or you get an error. Doing this with StorageClasses would make two different results possible based on which order you apply your resources. I.e., this solution would not be eventually consistent, because you would be able to get different results based on order of operations.
It's a good point. But, I think we can break this down further in two scenarios:
I think it should be enough to change the logic so that storageClass can change only for PVCs with nil value. I.e. users that don't specify storage class on their PVC, expect that a default one will be set eventually. Users who want to provision PVs manually fall into one of the two scenarios above which both seem safe to me. Additionally, this might require changes to defaulter I think, so that might cause additional issues. Do you think that makes sense and is worth a try?
I didn't know about generic ephemeral volumes before, but from what I've read I don't see any clear issues for them or STS provisoned PVCs. |
I think that issues described my @msau42 are real, we have the same ordering problem too. Similarly, it's not possible to reliably change the default storage class - most fields are read-only and currently we must delete the storage class and re-create it later, hoping that no PVC is created in the meantime.
There is a difference between If I remember correctly, with fall back from I also remember that we used annotation + admission plugin for the default storage class to have possibility to have different defaulting rules / admission plugins in the future, e.g. a different default class for different namespaces. If this was real, then we cannot implement the defaulting in PV controller, because it does not know what the defaulting rules are. But I haven't seen these different defaulting rules used in the wild, IMO everyone uses our admission plugin. |
The Kubernetes project currently lacks enough contributors to adequately respond to all issues and PRs. This bot triages issues and PRs according to the following rules:
You can:
Please send feedback to sig-contributor-experience at kubernetes/community. /lifecycle stale |
/remove-lifecycle stale |
The Kubernetes project currently lacks enough contributors to adequately respond to all issues and PRs. This bot triages issues and PRs according to the following rules:
You can:
Please send feedback to sig-contributor-experience at kubernetes/community. /lifecycle stale |
/remove-lifecycle stale |
/close |
@dims: Closed this PR. In response to this:
Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. |
please reopen if you still need this WIP PR. Trying to declutter the open PR(s) |
@@ -359,8 +360,19 @@ func (ctrl *PersistentVolumeController) syncUnboundClaim(claim *v1.PersistentVol | |||
return err | |||
} | |||
return nil | |||
case storagehelpers.GetPersistentVolumeClaimClass(claim) == "": |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@jsafrane I think that we can change it to case claim.Spec.StorageClassName == nil:
to keep the behavior compatible for the case that users intentionally specify "" to Spec.StorageClassName
(Default StorageClass should be set to StorageClasssName
only when StorageClassName == nil
).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've added some codes on top of this PR in order to:
- Work (fix wrong error check, loosen validation)
- Avoid trying to add default StorageClass when "" is intentionally set by users (although, it is actually blocked by validation)
- Only allow one default StorageClass
master...mkimuram:storage-class-default-pv-controller-v3
It would be better tighten validation a bit more, but there won't be a big user facing change.
In case where there's no default StorageClass at the time of creation of a PVC, the PVC will stay without storage class.
This logic was thus far only executed in AdmissionWebhook which would add a storageClassName to PVC with no defined storageClass.
Therefore, PVC will stay without storageClassName, if the PVC manifest is not reapplied to the cluster.
What type of PR is this?
What this PR does / why we need it:
Which issue(s) this PR fixes:
Fixes #99629
Special notes for your reviewer:
Does this PR introduce a user-facing change?
Additional documentation e.g., KEPs (Kubernetes Enhancement Proposals), usage docs, etc.: