From 9aaee96293bf235023b711acccc0e51f7e4423be Mon Sep 17 00:00:00 2001 From: michaeljguarino Date: Tue, 2 Jan 2024 10:09:35 -0500 Subject: [PATCH] Extended Ping (#100) Adds the ability to detect cluster distribution and return that info in ping requests. Also refactor pinging into its own package as the logic might become more expansive as this evolves. --- go.mod | 2 +- go.sum | 2 ++ pkg/agent/agent.go | 15 ++++++------ pkg/client/cluster.go | 5 ++++ pkg/ping/build.go | 17 ++++++++++++++ pkg/ping/distro.go | 41 ++++++++++++++++++++++++++++++++ pkg/ping/pinger.go | 54 +++++++++++++++++++++++++++++++++++++++++++ 7 files changed, 127 insertions(+), 9 deletions(-) create mode 100644 pkg/ping/build.go create mode 100644 pkg/ping/distro.go create mode 100644 pkg/ping/pinger.go diff --git a/go.mod b/go.mod index 953362ce..54e5d3ff 100644 --- a/go.mod +++ b/go.mod @@ -12,7 +12,7 @@ require ( github.com/orcaman/concurrent-map/v2 v2.0.1 github.com/osteele/liquid v1.3.2 github.com/pkg/errors v0.9.1 - github.com/pluralsh/console-client-go v0.0.57 + github.com/pluralsh/console-client-go v0.0.64 github.com/pluralsh/gophoenix v0.1.3-0.20231201014135-dff1b4309e34 github.com/pluralsh/polly v0.1.4 github.com/samber/lo v1.38.1 diff --git a/go.sum b/go.sum index 50a15688..9c0ca6cf 100644 --- a/go.sum +++ b/go.sum @@ -563,6 +563,8 @@ github.com/pkg/sftp v1.10.1/go.mod h1:lYOWFsE0bwd1+KfKJaKeuokY15vzFx25BLbzYYoAxZ github.com/pkg/sftp v1.13.1/go.mod h1:3HaPG6Dq1ILlpPZRO0HVMrsydcdLt6HRDccSgb87qRg= github.com/pluralsh/console-client-go v0.0.57 h1:XVs2fSrHCU/gB79DKqmsHF9Fo/D9oy8R69oSewFgGfI= github.com/pluralsh/console-client-go v0.0.57/go.mod h1:u/RjzXE3wtl3L6wiWxwhQHSpxFX46+EYvpkss2mALN4= +github.com/pluralsh/console-client-go v0.0.64 h1:IZDbjDS+VMHVpIabcx2YYsBMzvtefbBv1LAVxsi1aNw= +github.com/pluralsh/console-client-go v0.0.64/go.mod h1:u/RjzXE3wtl3L6wiWxwhQHSpxFX46+EYvpkss2mALN4= github.com/pluralsh/gophoenix v0.1.3-0.20231201014135-dff1b4309e34 h1:ab2PN+6if/Aq3/sJM0AVdy1SYuMAnq4g20VaKhTm/Bw= github.com/pluralsh/gophoenix v0.1.3-0.20231201014135-dff1b4309e34/go.mod h1:IagWXKFYu6NTHzcJx2dJyrIlZ1Sv2PH3fhOtplA9qOs= github.com/pluralsh/polly v0.1.4 h1:Kz90peCgvsfF3ERt8cujr5TR9z4wUlqQE60Eg09ZItY= diff --git a/pkg/agent/agent.go b/pkg/agent/agent.go index ccc9187c..46ca2d9e 100644 --- a/pkg/agent/agent.go +++ b/pkg/agent/agent.go @@ -2,7 +2,6 @@ package agent import ( "fmt" - "strings" "time" "k8s.io/apimachinery/pkg/util/wait" @@ -18,6 +17,7 @@ import ( "github.com/pluralsh/deployment-operator/pkg/applier" "github.com/pluralsh/deployment-operator/pkg/client" "github.com/pluralsh/deployment-operator/pkg/manifests" + "github.com/pluralsh/deployment-operator/pkg/ping" deploysync "github.com/pluralsh/deployment-operator/pkg/sync" "github.com/pluralsh/deployment-operator/pkg/websocket" ) @@ -29,6 +29,7 @@ var ( type Agent struct { consoleClient *client.Client discoveryClient *discovery.DiscoveryClient + pinger *ping.Pinger config *rest.Config engine *deploysync.Engine deathChan chan interface{} @@ -80,8 +81,11 @@ func New(config *rest.Config, refresh, processingTimeout time.Duration, consoleU return nil, err } + pinger := ping.New(consoleClient, dc, f) + return &Agent{ discoveryClient: dc, + pinger: pinger, consoleClient: consoleClient, engine: engine, deathChan: deathChan, @@ -119,15 +123,10 @@ func (agent *Agent) Run() { agent.svcQueue.Add(svc.ID) } - info, err := agent.discoveryClient.ServerVersion() - if err != nil { - log.Error(err, "failed to fetch cluster version") - return false, nil - } - vs := strings.Split(info.GitVersion, "-") - if err := agent.consoleClient.Ping(strings.TrimPrefix(vs[0], "v")); err != nil { + if err := agent.pinger.Ping(); err != nil { log.Error(err, "failed to ping cluster after scheduling syncs") } + agent.engine.ScrapeKube() return false, nil }) diff --git a/pkg/client/cluster.go b/pkg/client/cluster.go index 392f578b..d09d257a 100644 --- a/pkg/client/cluster.go +++ b/pkg/client/cluster.go @@ -4,6 +4,11 @@ import ( console "github.com/pluralsh/console-client-go" ) +func (c *Client) PingCluster(attributes console.ClusterPing) error { + _, err := c.consoleClient.PingCluster(c.ctx, attributes) + return err +} + func (c *Client) Ping(vsn string) error { _, err := c.consoleClient.PingCluster(c.ctx, console.ClusterPing{CurrentVersion: vsn}) return err diff --git a/pkg/ping/build.go b/pkg/ping/build.go new file mode 100644 index 00000000..8991c7b7 --- /dev/null +++ b/pkg/ping/build.go @@ -0,0 +1,17 @@ +package ping + +import ( + "strings" + + console "github.com/pluralsh/console-client-go" + "github.com/samber/lo" + "k8s.io/apimachinery/pkg/version" +) + +func pingAttributes(info *version.Info, pods []string) console.ClusterPing { + vs := strings.Split(info.GitVersion, "-") + return console.ClusterPing{ + CurrentVersion: strings.TrimPrefix(vs[0], "v"), + Distro: lo.ToPtr(findDistro(append(pods, info.GitVersion))), + } +} diff --git a/pkg/ping/distro.go b/pkg/ping/distro.go new file mode 100644 index 00000000..8bf9beb1 --- /dev/null +++ b/pkg/ping/distro.go @@ -0,0 +1,41 @@ +package ping + +import ( + "strings" + + console "github.com/pluralsh/console-client-go" +) + +func findDistro(vals []string) console.ClusterDistro { + for _, v := range vals { + if dist, ok := distro(v); ok { + return dist + } + } + + return console.ClusterDistroGeneric +} + +func distro(val string) (console.ClusterDistro, bool) { + if strings.Contains(val, "eks") { + return console.ClusterDistroEks, true + } + + if strings.Contains(val, "aks") || strings.Contains(val, "azure") { + return console.ClusterDistroAks, true + } + + if strings.Contains(val, "gke") { + return console.ClusterDistroGke, true + } + + if strings.Contains(val, "k3s") { + return console.ClusterDistroK3s, true + } + + if strings.Contains(val, "rke") { + return console.ClusterDistroRke, true + } + + return console.ClusterDistroGeneric, false +} diff --git a/pkg/ping/pinger.go b/pkg/ping/pinger.go new file mode 100644 index 00000000..02ad91c7 --- /dev/null +++ b/pkg/ping/pinger.go @@ -0,0 +1,54 @@ +package ping + +import ( + "context" + + "github.com/pluralsh/deployment-operator/pkg/client" + "github.com/samber/lo" + corev1 "k8s.io/api/core/v1" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/client-go/discovery" + "k8s.io/kubectl/pkg/cmd/util" +) + +type Pinger struct { + consoleClient *client.Client + discoveryClient *discovery.DiscoveryClient + factory util.Factory +} + +func New(console *client.Client, discovery *discovery.DiscoveryClient, factory util.Factory) *Pinger { + return &Pinger{ + consoleClient: console, + discoveryClient: discovery, + factory: factory, + } +} + +func (p *Pinger) Ping() error { + info, err := p.discoveryClient.ServerVersion() + if err != nil { + return err + } + + cs, err := p.factory.KubernetesClientSet() + if err != nil { + return nil + } + + podNames := []string{} + // can find some distro information by checking what's running in kube-system + if pods, err := cs.CoreV1().Pods("kube-system").List(context.TODO(), metav1.ListOptions{}); err == nil { + podNames = lo.Map(pods.Items, func(pod corev1.Pod, ind int) string { + return pod.Name + }) + } + + attrs := pingAttributes(info, podNames) + if err := p.consoleClient.PingCluster(attrs); err != nil { + attrs.Distro = nil + return p.consoleClient.PingCluster(attrs) // fallback to no distro to support old console servers + } + + return nil +}