What is the proper way to Patch an object with controller-runtime?

8/29/2019

I am trying to update an object's Env field but I don't want to have to iterate through them to figure out which fields already exist and need to be updated instead of inserted if that isn't necessary. I'm using controller-runtime.

I tried patching using an ApplyPatchType, like so:
r.Patch(ctx, myDeployment, client.Apply)
where client.Apply is here, and myDeployment is an *appsv1.Deployment that I found with List(...) and then modified.

This failed with a 415 Unsupported Media Type. I assume it has something to do with it needing to be encoded in YAML (since the type's value is "application/apply-patch+yaml"

I got it working by doing this (r has an embedded controller-runtime Client):

newDeploy := dep.DeepCopy()
original := dep.DeepCopy()
// ... (changing newDeploy)
rawObj, _ := apijson.Marshal(newDeploy)
r.Patch(ctx, original, client.ConstantPatch(types.StrategicMergePatchType, rawObj))

This feels inefficient though, with possibly unnecessary DeepCopies, and I feel like I'm unnecessarily Marshalling my object. I figured I could somehow use the Patch command similar to how I use the Update command, where I could just pass in the object in its already modified state and get the StrategicMergePatchType (or ApplyPatchType) behavior.

It seems to me like if I want to just pass in the modified object and have the client "figure out" what to patch, I want to use the client.Apply (ApplyPatchType) behavior, since I think that StrategicMergePatchType is just for diffs to apply (though providing the whole object can still be a valid diff I suppose). Any guidance is appreciated!

-- Andrew D.
kubernetes
kubernetes-apiserver

1 Answer

9/9/2019

For now, I got the behavior I'm looking for without having to manually write the merging logic by using client.MergeFrom:

MergeFrom creates a Patch that patches using the merge-patch strategy with the given object as base.

Relevant code:

r.Patch(ctx, newDeploy, client.MergeFrom(original))

-- Andrew D.
Source: StackOverflow