Change:
Is this a BUG REPORT or FEATURE REQUEST?: /kind bug What happened: Pod stuck in terminating state. What you expected to happen: Pod successfully cleaned up. How to reproduce it (as minimally and precisely as possible): up a LimitRange. (Say "limits: defaultRequest: cpu: 100m type: Container") a mutating webhook on pod which creates an additional container on the pod (Eg. ) without the limit range. a Pod with foreground deletion finalizer. that you have a Pod with 2 containers. The 1 you created which now has a limit and the istio container which does not. to delete the Pod. garbage collector tries to update the pod to remove the finalizer, however this triggers the limit range admission control to add the limit to the istio container. This then causes the API server to get the error "invalid: spec: Forbidden: pod updates may not change fields other than , , or " the pod is now stuck in terminating. Anything else we need to know?: Environment: Kubernetes version (use ): 1.9.6 /sig api-machinery
Issues go stale after 90d of inactivity. Mark the issue as fresh with . Stale issues rot after an additional 30d of inactivity and eventually close. If this issue is safe to close now please do so with . Send feedback to sig-testing, kubernetes/test-infra and/or . /lifecycle stale
/remove-lifecycle stale PR open

Discussion:
return false } <ins> // Since containers and initContainers cannot currently be added, removed, or updated, it is unnecessary // to mutate and validate limitrange on pod updates. Trying to mutate containers or initContainers on a pod // update request will always fail pod validation because those fields are immutable once the object is created. if a.GetKind().GroupKind() == api.Kind("Pod") && a.GetOperation() == admission.Update { return false } </ins> return a.GetKind().GroupKind() == api.Kind("Pod") || a.GetKind().GroupKind() == api.Kind("PersistentVolumeClaim") }

informerFactory.Start(wait.NeverStop) testPod := validPod("testPod", 1, api.ResourceRequirements{}) <del> err = handler.Admit(admission.NewAttributesRecord(&testPod, nil, api.Kind("Pod").WithVersion("version"), limitRange.Namespace, "testPod", api.Resource("pods").WithVersion("version"), "", admission.Update, false, nil)) </del> <ins> err = handler.Admit(admission.NewAttributesRecord(&testPod, nil, api.Kind("Pod").WithVersion("version"), limitRange.Namespace, "testPod", api.Resource("pods").WithVersion("version"), "", admission.Create, false, nil)) </ins> if err != nil { t.Fatal(err) } <del> err = handler.Validate(admission.NewAttributesRecord(&testPod, nil, api.Kind("Pod").WithVersion("version"), limitRange.Namespace, "testPod", api.Resource("pods").WithVersion("version"), "", admission.Update, false, nil)) </del> <ins> err = handler.Validate(admission.NewAttributesRecord(&testPod, nil, api.Kind("Pod").WithVersion("version"), limitRange.Namespace, "testPod", api.Resource("pods").WithVersion("version"), "", admission.Create, false, nil)) </ins> if err == nil { <del> t.Errorf("Expected an error since the pod did not specify resource limits in its update call") </del> <ins> t.Errorf("Expected an error since the pod did not specify resource limits in its create call") } err = handler.Validate(admission.NewAttributesRecord(&testPod, nil, api.Kind("Pod").WithVersion("version"), limitRange.Namespace, "testPod", api.Resource("pods").WithVersion("version"), "", admission.Update, false, nil)) if err != nil { t.Errorf("Expected not to call limitranger actions on pod updates") </ins> } err = handler.Validate(admission.NewAttributesRecord(&testPod, nil, api.Kind("Pod").WithVersion("version"), limitRange.Namespace, "testPod", api.Resource("pods").WithVersion("version"), "status", admission.Update, false, nil))