-
Notifications
You must be signed in to change notification settings - Fork 14
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Resource client patch for apply status (#517)
* Add patch to resource client to cut api calls in half * Move to apply status since consul api doesn't have patch * Implement the other apply status functions * Get rid of debug info * Clean up extra code * Actually use the bytes from the provided status * Add changelog * Pod resource client to implement interface * Api client to implement interface * Namespace resource client to implement interface * Use more performant one with standard k8s clients * Namespace client needs too * Codegen * Fix reporter unit test * Fix reconciler unit tests * Codegen * Update interface to use status client * Codegen * Use namespaced status by default * Fix reporter unit test * Fix reconciler unit test * Prefer merge patch type * Ensure we render all fields * Codegen * Go mod tidy * Prefer json patch type * Ensure statuses is always defaulted * Prefer json encoding * Codegen * Improve comment readability * Get rid of gogo * Get rid of gogo * Get rid of gogo, with codegen * Move shared impl to shared package * Move shared impl for jsonpatch to shared package * Move other clients to shared impl for jsonpatch * Remove gogo * Only clone if we are going to write status * Be clear we are patching the status * Add note in changelog about rendering enums as strings Co-authored-by: soloio-bulldozer[bot] <48420018+soloio-bulldozer[bot]@users.noreply.github.com>
- Loading branch information
1 parent
2b31151
commit 618b1c9
Showing
24 changed files
with
490 additions
and
117 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
changelog: | ||
- type: FIX | ||
resolvesIssue: false | ||
description: >- | ||
Improve scalability of v2 status reporter by using k8s patch instead of read then write. | ||
Also updates the status written to render enums as strings rather than ints for readability. | ||
issueLink: https://github.com/solo-io/gloo/issues/7076 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,71 @@ | ||
package shared | ||
|
||
import ( | ||
"bytes" | ||
"fmt" | ||
|
||
"github.com/golang/protobuf/jsonpb" | ||
"github.com/solo-io/solo-kit/pkg/api/v1/clients" | ||
"github.com/solo-io/solo-kit/pkg/api/v1/resources" | ||
"github.com/solo-io/solo-kit/pkg/errors" | ||
) | ||
|
||
// ApplyStatus is used by clients that don't support patch updates to resource statuses (e.g. consul, files, in-memory) | ||
func ApplyStatus(rc clients.ResourceClient, statusClient resources.StatusClient, inputResource resources.InputResource, opts clients.ApplyStatusOpts) (resources.Resource, error) { | ||
name := inputResource.GetMetadata().GetName() | ||
namespace := inputResource.GetMetadata().GetNamespace() | ||
res, err := rc.Read(namespace, name, clients.ReadOpts{ | ||
Ctx: opts.Ctx, | ||
Cluster: opts.Cluster, | ||
}) | ||
|
||
if err != nil { | ||
return nil, errors.Wrapf(err, "error reading before applying status") | ||
} | ||
|
||
inputRes, ok := res.(resources.InputResource) | ||
if !ok { | ||
return nil, errors.Errorf("error converting resource of type %T to input resource to apply status", res) | ||
} | ||
|
||
statusClient.SetStatus(inputRes, statusClient.GetStatus(inputResource)) | ||
updatedRes, err := rc.Write(inputRes, clients.WriteOpts{ | ||
Ctx: opts.Ctx, | ||
OverwriteExisting: true, | ||
}) | ||
|
||
if err != nil { | ||
return nil, errors.Wrapf(err, "error writing to apply status") | ||
} | ||
return updatedRes, nil | ||
} | ||
|
||
// GetJsonPatchData returns the json patch data for the input resource. | ||
// Prefer using json patch for single api call status updates when supported (e.g. k8s) to avoid ratelimiting | ||
// to the k8s apiserver (e.g. https://github.com/solo-io/gloo/blob/a083522af0a4ce22f4d2adf3a02470f782d5a865/projects/gloo/api/v1/settings.proto#L337-L350) | ||
func GetJsonPatchData(inputResource resources.InputResource) ([]byte, error) { | ||
namespacedStatuses := inputResource.GetNamespacedStatuses().GetStatuses() | ||
if len(namespacedStatuses) != 1 { | ||
// we only expect our namespace to report here; we don't want to blow away statuses from other reporters | ||
return nil, errors.Errorf("unexpected number of namespaces in input resource: %v", len(inputResource.GetNamespacedStatuses().GetStatuses())) | ||
} | ||
ns := "" | ||
for loopNs := range inputResource.GetNamespacedStatuses().GetStatuses() { | ||
ns = loopNs | ||
} | ||
status := inputResource.GetNamespacedStatuses().GetStatuses()[ns] | ||
|
||
buf := &bytes.Buffer{} | ||
var marshaller jsonpb.Marshaler | ||
marshaller.EnumsAsInts = false // prefer jsonpb over encoding/json marshaller since it renders enum as string not int (i.e., state is human-readable) | ||
marshaller.EmitDefaults = false // keep status as small as possible | ||
err := marshaller.Marshal(buf, status) | ||
if err != nil { | ||
return nil, errors.Wrapf(err, "marshalling input resource") | ||
} | ||
|
||
bytes := buf.Bytes() | ||
patch := fmt.Sprintf(`[{"op": "replace", "path": "/status/statuses/%s", "value": %s}]`, ns, string(bytes)) // only replace our status so other reporters are not affected (e.g. blue-green of gloo) | ||
data := []byte(patch) | ||
return data, nil | ||
} |
Oops, something went wrong.