Skip to content

Commit 3be3f1b

Browse files
authored
Merge pull request #3516 from k8s-infra-cherrypick-robot/cherry-pick-3515-to-release-0.24
[release-0.24] 🐛 Fix regression in Apply typed error handling
2 parents d3eaef3 + 0f7b33d commit 3be3f1b

2 files changed

Lines changed: 42 additions & 6 deletions

File tree

pkg/client/client_test.go

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ import (
3838
policyv1 "k8s.io/api/policy/v1"
3939
apierrors "k8s.io/apimachinery/pkg/api/errors"
4040
"k8s.io/apimachinery/pkg/api/meta"
41+
"k8s.io/apimachinery/pkg/api/validation"
4142
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
4243
"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
4344
"k8s.io/apimachinery/pkg/runtime"
@@ -1101,6 +1102,26 @@ U5wwSivyi7vmegHKmblOzNVKA5qPO8zWzqBC
11011102
Expect(secret.Data).To(BeComparableTo(data))
11021103
Expect(secret.Data).To(BeComparableTo(secretApplyConfiguration.Data))
11031104
})
1105+
1106+
It("should propagate a typed error", func(ctx SpecContext) {
1107+
cl, err := client.New(cfg, client.Options{})
1108+
Expect(err).NotTo(HaveOccurred())
1109+
Expect(cl).NotTo(BeNil())
1110+
1111+
obj := corev1applyconfigurations.
1112+
Secret("typed-secret", "default").
1113+
WithType(corev1.SecretTypeDockercfg).
1114+
WithStringData(map[string]string{".dockercfg": "{}"})
1115+
1116+
err = cl.Apply(ctx, obj, &client.ApplyOptions{FieldManager: "test-manager"})
1117+
Expect(err).ToNot(HaveOccurred())
1118+
1119+
obj = corev1applyconfigurations.
1120+
Secret(*obj.Name, *obj.Namespace).
1121+
WithType(corev1.SecretTypeOpaque)
1122+
err = cl.Apply(ctx, obj, &client.ApplyOptions{FieldManager: "test-manager"})
1123+
Expect(isImmutableError(err)).To(BeTrue())
1124+
})
11041125
})
11051126
})
11061127

@@ -4433,3 +4454,8 @@ func toUnstructured(o client.Object) (*unstructured.Unstructured, error) {
44334454
u := &unstructured.Unstructured{}
44344455
return u, json.Unmarshal(serialized, u)
44354456
}
4457+
4458+
func isImmutableError(err error) bool {
4459+
return apierrors.IsInvalid(err) &&
4460+
strings.Contains(err.Error(), validation.FieldImmutableErrorMsg)
4461+
}

pkg/client/typed_client.go

Lines changed: 16 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -147,13 +147,18 @@ func (c *typedClient) Apply(ctx context.Context, obj runtime.ApplyConfiguration,
147147
applyOpts := &ApplyOptions{}
148148
applyOpts.ApplyOptions(opts)
149149

150-
var contentType string
151-
body, err := req.
150+
resp := req.
152151
NamespaceIfScoped(o.namespace, o.isNamespaced()).
153152
Resource(o.resource()).
154153
Name(o.name).
155154
VersionedParams(applyOpts.AsPatchOptions(), c.paramCodec).
156-
Do(ctx).
155+
Do(ctx)
156+
if err := resp.Error(); err != nil {
157+
return err
158+
}
159+
160+
var contentType string
161+
body, err := resp.
157162
ContentType(&contentType).
158163
Raw()
159164
if err != nil {
@@ -332,14 +337,19 @@ func (c *typedClient) ApplySubResource(ctx context.Context, obj runtime.ApplyCon
332337
return fmt.Errorf("failed to create apply request: %w", err)
333338
}
334339

335-
var contentType string
336-
respBody, err := req.
340+
resp := req.
337341
NamespaceIfScoped(o.namespace, o.isNamespaced()).
338342
Resource(o.resource()).
339343
Name(o.name).
340344
SubResource(subResource).
341345
VersionedParams(applyOpts.AsPatchOptions(), c.paramCodec).
342-
Do(ctx).
346+
Do(ctx)
347+
if err := resp.Error(); err != nil {
348+
return err
349+
}
350+
351+
var contentType string
352+
respBody, err := resp.
343353
ContentType(&contentType).
344354
Raw()
345355
if err != nil {

0 commit comments

Comments
 (0)