From 9522b4f0968962a612ead5a526d046af26f5b760 Mon Sep 17 00:00:00 2001 From: ajanikow <12255597+ajanikow@users.noreply.github.com> Date: Mon, 27 Dec 2021 23:57:26 +0000 Subject: [PATCH] [Feature] Member endpoint --- CHANGELOG.md | 1 + .../v1/arango_member_pod_template.go | 2 + pkg/apis/deployment/v1/server_group.go | 12 ++++++ .../deployment/v1/zz_generated.deepcopy.go | 25 ++++++++++++ .../v2alpha1/arango_member_pod_template.go | 2 + pkg/apis/deployment/v2alpha1/server_group.go | 12 ++++++ .../v2alpha1/zz_generated.deepcopy.go | 25 ++++++++++++ pkg/deployment/client/client_cache.go | 39 +++++++++++++------ pkg/deployment/deployment.go | 6 +-- pkg/deployment/deployment_suite_test.go | 2 +- .../action_arango_member_update_pod_spec.go | 10 +++-- 11 files changed, 115 insertions(+), 21 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 8298b28f9..cb78d0f3c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ - Fix Core InitContainers check - Remove unused `status.members..sidecars-specs` variable - Keep only recent terminations +- Add endpoint into member status ## [1.2.6](https://github.com/arangodb/kube-arangodb/tree/1.2.6) (2021-12-15) - Add ArangoBackup backoff functionality diff --git a/pkg/apis/deployment/v1/arango_member_pod_template.go b/pkg/apis/deployment/v1/arango_member_pod_template.go index 217c3b658..365fa4831 100644 --- a/pkg/apis/deployment/v1/arango_member_pod_template.go +++ b/pkg/apis/deployment/v1/arango_member_pod_template.go @@ -53,6 +53,8 @@ type ArangoMemberPodTemplate struct { PodSpec *core.PodTemplateSpec `json:"podSpec,omitempty"` PodSpecChecksum string `json:"podSpecChecksum,omitempty"` Checksum string `json:"checksum,omitempty"` + + Endpoint *string `json:"endpoint,omitempty"` } func (a *ArangoMemberPodTemplate) GetChecksum() string { diff --git a/pkg/apis/deployment/v1/server_group.go b/pkg/apis/deployment/v1/server_group.go index ddaa9ed8a..cef33187d 100644 --- a/pkg/apis/deployment/v1/server_group.go +++ b/pkg/apis/deployment/v1/server_group.go @@ -27,6 +27,18 @@ import ( "time" ) +type ServerGroups []ServerGroup + +func (s ServerGroups) Contains(group ServerGroup) bool { + for _, a := range s { + if a == group { + return true + } + } + + return false +} + type ServerGroup int func (g *ServerGroup) UnmarshalJSON(bytes []byte) error { diff --git a/pkg/apis/deployment/v1/zz_generated.deepcopy.go b/pkg/apis/deployment/v1/zz_generated.deepcopy.go index ea0582a5a..6d7ce2645 100644 --- a/pkg/apis/deployment/v1/zz_generated.deepcopy.go +++ b/pkg/apis/deployment/v1/zz_generated.deepcopy.go @@ -315,6 +315,11 @@ func (in *ArangoMemberPodTemplate) DeepCopyInto(out *ArangoMemberPodTemplate) { *out = new(corev1.PodTemplateSpec) (*in).DeepCopyInto(*out) } + if in.Endpoint != nil { + in, out := &in.Endpoint, &out.Endpoint + *out = new(string) + **out = **in + } return } @@ -2202,6 +2207,26 @@ func (in ServerGroupSpecVolumes) DeepCopy() ServerGroupSpecVolumes { return *out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in ServerGroups) DeepCopyInto(out *ServerGroups) { + { + in := &in + *out = make(ServerGroups, len(*in)) + copy(*out, *in) + return + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ServerGroups. +func (in ServerGroups) DeepCopy() ServerGroups { + if in == nil { + return nil + } + out := new(ServerGroups) + in.DeepCopyInto(out) + return *out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ServerIDGroupSpec) DeepCopyInto(out *ServerIDGroupSpec) { *out = *in diff --git a/pkg/apis/deployment/v2alpha1/arango_member_pod_template.go b/pkg/apis/deployment/v2alpha1/arango_member_pod_template.go index 06a8a0ebe..e07129f85 100644 --- a/pkg/apis/deployment/v2alpha1/arango_member_pod_template.go +++ b/pkg/apis/deployment/v2alpha1/arango_member_pod_template.go @@ -53,6 +53,8 @@ type ArangoMemberPodTemplate struct { PodSpec *core.PodTemplateSpec `json:"podSpec,omitempty"` PodSpecChecksum string `json:"podSpecChecksum,omitempty"` Checksum string `json:"checksum,omitempty"` + + Endpoint *string `json:"endpoint,omitempty"` } func (a *ArangoMemberPodTemplate) GetChecksum() string { diff --git a/pkg/apis/deployment/v2alpha1/server_group.go b/pkg/apis/deployment/v2alpha1/server_group.go index 5aa77f1de..a60745039 100644 --- a/pkg/apis/deployment/v2alpha1/server_group.go +++ b/pkg/apis/deployment/v2alpha1/server_group.go @@ -27,6 +27,18 @@ import ( "time" ) +type ServerGroups []ServerGroup + +func (s ServerGroups) Contains(group ServerGroup) bool { + for _, a := range s { + if a == group { + return true + } + } + + return false +} + type ServerGroup int func (g *ServerGroup) UnmarshalJSON(bytes []byte) error { diff --git a/pkg/apis/deployment/v2alpha1/zz_generated.deepcopy.go b/pkg/apis/deployment/v2alpha1/zz_generated.deepcopy.go index 6783075e6..6967c2418 100644 --- a/pkg/apis/deployment/v2alpha1/zz_generated.deepcopy.go +++ b/pkg/apis/deployment/v2alpha1/zz_generated.deepcopy.go @@ -315,6 +315,11 @@ func (in *ArangoMemberPodTemplate) DeepCopyInto(out *ArangoMemberPodTemplate) { *out = new(v1.PodTemplateSpec) (*in).DeepCopyInto(*out) } + if in.Endpoint != nil { + in, out := &in.Endpoint, &out.Endpoint + *out = new(string) + **out = **in + } return } @@ -2202,6 +2207,26 @@ func (in ServerGroupSpecVolumes) DeepCopy() ServerGroupSpecVolumes { return *out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in ServerGroups) DeepCopyInto(out *ServerGroups) { + { + in := &in + *out = make(ServerGroups, len(*in)) + copy(*out, *in) + return + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ServerGroups. +func (in ServerGroups) DeepCopy() ServerGroups { + if in == nil { + return nil + } + out := new(ServerGroups) + in.DeepCopyInto(out) + return *out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ServerIDGroupSpec) DeepCopyInto(out *ServerIDGroupSpec) { *out = *in diff --git a/pkg/deployment/client/client_cache.go b/pkg/deployment/client/client_cache.go index ee8467e88..de36f0807 100644 --- a/pkg/deployment/client/client_cache.go +++ b/pkg/deployment/client/client_cache.go @@ -28,6 +28,8 @@ import ( "strconv" "sync" + "github.com/arangodb/kube-arangodb/pkg/deployment/resources" + "github.com/arangodb/kube-arangodb/pkg/util/errors" "github.com/arangodb/go-driver/agency" @@ -48,16 +50,21 @@ type Cache interface { GetAgency(ctx context.Context) (agency.Agency, error) } -func NewClientCache(apiObjectGetter func() *api.ArangoDeployment, factory conn.Factory) Cache { +type CacheGen interface { + resources.DeploymentEndpoints + resources.DeploymentInfoGetter +} + +func NewClientCache(in CacheGen, factory conn.Factory) Cache { return &cache{ - apiObjectGetter: apiObjectGetter, - factory: factory, + in: in, + factory: factory, } } type cache struct { - mutex sync.Mutex - apiObjectGetter func() *api.ArangoDeployment + mutex sync.Mutex + in CacheGen factory conn.Factory } @@ -68,7 +75,7 @@ func (cc *cache) Connection(ctx context.Context, host string) (driver.Connection func (cc *cache) extendHost(host string) string { scheme := "http" - if cc.apiObjectGetter().Spec.TLS.IsSecure() { + if cc.in.GetSpec().TLS.IsSecure() { scheme = "https" } @@ -76,9 +83,14 @@ func (cc *cache) extendHost(host string) string { } func (cc *cache) getClient(group api.ServerGroup, id string) (driver.Client, error) { - m, _, _ := cc.apiObjectGetter().Status.Members.ElementByID(id) + m, _, _ := cc.in.GetStatusSnapshot().Members.ElementByID(id) - c, err := cc.factory.Client(cc.extendHost(m.GetEndpoint(k8sutil.CreatePodDNSName(cc.apiObjectGetter(), group.AsRole(), id)))) + endpoint, err := cc.in.GenerateMemberEndpoint(group, m) + if err != nil { + return nil, err + } + + c, err := cc.factory.Client(cc.extendHost(m.GetEndpoint(endpoint))) if err != nil { return nil, errors.WithStack(err) } @@ -114,7 +126,7 @@ func (cc *cache) GetAuth() conn.Auth { } func (cc *cache) getDatabaseClient() (driver.Client, error) { - c, err := cc.factory.Client(cc.extendHost(k8sutil.CreateDatabaseClientServiceDNSName(cc.apiObjectGetter()))) + c, err := cc.factory.Client(cc.extendHost(k8sutil.CreateDatabaseClientServiceDNSName(cc.in.GetAPIObject()))) if err != nil { return nil, errors.WithStack(err) } @@ -148,8 +160,13 @@ func (cc *cache) GetDatabase(ctx context.Context) (driver.Client, error) { func (cc *cache) getAgencyClient() (agency.Agency, error) { // Not found, create a new client var dnsNames []string - for _, m := range cc.apiObjectGetter().Status.Members.Agents { - dnsNames = append(dnsNames, cc.extendHost(m.GetEndpoint(k8sutil.CreatePodDNSName(cc.apiObjectGetter(), api.ServerGroupAgents.AsRole(), m.ID)))) + for _, m := range cc.in.GetStatusSnapshot().Members.Agents { + endpoint, err := cc.in.GenerateMemberEndpoint(api.ServerGroupAgents, m) + if err != nil { + return nil, err + } + + dnsNames = append(dnsNames, cc.extendHost(m.GetEndpoint(endpoint))) } if len(dnsNames) == 0 { diff --git a/pkg/deployment/deployment.go b/pkg/deployment/deployment.go index b87a4d0c6..a4b08b0dc 100644 --- a/pkg/deployment/deployment.go +++ b/pkg/deployment/deployment.go @@ -222,7 +222,7 @@ func New(config Config, deps Dependencies, apiObject *api.ArangoDeployment) (*De agencyCache: agency.NewCache(apiObject.Spec.Mode), } - d.clientCache = deploymentClient.NewClientCache(d.getArangoDeployment, conn.NewFactory(d.getAuth, d.getConnConfig)) + d.clientCache = deploymentClient.NewClientCache(d, conn.NewFactory(d.getAuth, d.getConnConfig)) d.status.last = *(apiObject.Status.DeepCopy()) d.reconciler = reconcile.NewReconciler(deps.Log, d) @@ -628,10 +628,6 @@ func (d *Deployment) SetNumberOfServers(ctx context.Context, noCoordinators, noD return nil } -func (d *Deployment) getArangoDeployment() *api.ArangoDeployment { - return d.apiObject -} - func (d *Deployment) ApplyPatch(ctx context.Context, p ...patch.Item) error { parser := patch.Patch(p) diff --git a/pkg/deployment/deployment_suite_test.go b/pkg/deployment/deployment_suite_test.go index 6984ced96..0ee385534 100644 --- a/pkg/deployment/deployment_suite_test.go +++ b/pkg/deployment/deployment_suite_test.go @@ -492,7 +492,7 @@ func createTestDeployment(t *testing.T, config Config, arangoDeployment *api.Ara eventCh: make(chan *deploymentEvent, deploymentEventQueueSize), stopCh: make(chan struct{}), } - d.clientCache = client.NewClientCache(d.getArangoDeployment, conn.NewFactory(d.getAuth, d.getConnConfig)) + d.clientCache = client.NewClientCache(d, conn.NewFactory(d.getAuth, d.getConnConfig)) cachedStatus, err := inspector.NewInspector(context.Background(), d.getKubeCli(), d.getMonitoringV1Cli(), d.getArangoCli(), d.GetNamespace()) require.NoError(t, err) diff --git a/pkg/deployment/reconcile/action_arango_member_update_pod_spec.go b/pkg/deployment/reconcile/action_arango_member_update_pod_spec.go index 017ab3f33..2a2807dd9 100644 --- a/pkg/deployment/reconcile/action_arango_member_update_pod_spec.go +++ b/pkg/deployment/reconcile/action_arango_member_update_pod_spec.go @@ -25,8 +25,6 @@ package reconcile import ( "context" - "github.com/arangodb/kube-arangodb/pkg/deployment/pod" - "github.com/arangodb/kube-arangodb/pkg/deployment/resources" "github.com/arangodb/kube-arangodb/pkg/util/errors" "github.com/rs/zerolog/log" @@ -82,7 +80,7 @@ func (a *actionArangoMemberUpdatePodSpec) Start(ctx context.Context) (bool, erro return false, err } - endpoint, err := pod.GenerateMemberEndpoint(a.actionCtx.GetCachedStatus(), a.actionCtx.GetAPIObject(), spec, a.action.Group, m) + endpoint, err := a.actionCtx.GenerateMemberEndpoint(a.action.Group, m) if err != nil { log.Error().Err(err).Msg("Unable to render endpoint") return false, err @@ -90,7 +88,6 @@ func (a *actionArangoMemberUpdatePodSpec) Start(ctx context.Context) (bool, erro if m.Endpoint == nil || *m.Endpoint != endpoint { // Update endpoint - m.Endpoint = &endpoint if err := status.Members.Update(m, a.action.Group); err != nil { log.Error().Err(err).Msg("Unable to update endpoint") return false, err @@ -127,6 +124,11 @@ func (a *actionArangoMemberUpdatePodSpec) Start(ctx context.Context) (bool, erro return false, err } + if z := m.Endpoint; z != nil { + q := *z + template.Endpoint = &q + } + if err := a.actionCtx.WithArangoMemberUpdate(context.Background(), member.GetNamespace(), member.GetName(), func(member *api.ArangoMember) bool { if !member.Spec.Template.Equals(template) { member.Spec.Template = template.DeepCopy()