From 643f0051c21d167fee483814dc968f76c727220e Mon Sep 17 00:00:00 2001 From: Wim Henderickx Date: Wed, 20 Nov 2024 16:53:08 -0700 Subject: [PATCH] updated geenric backend --- apis/backend/as/asclaim_object.go | 62 +++++-------- apis/backend/as/asindex_object.go | 7 +- apis/backend/claim_types.go | 4 +- apis/backend/extcomm/extcommclaim_object.go | 62 +++++-------- apis/backend/extcomm/extcommindex_object.go | 7 +- apis/backend/genid/genidclaim_object.go | 63 +++++-------- apis/backend/genid/genidentry_object.go | 2 + apis/backend/genid/genidindex_object.go | 7 +- apis/backend/ipam/ipindex_object.go | 2 +- apis/backend/object.go | 3 +- apis/backend/vlan/vlanclaim_object.go | 62 +++++-------- apis/backend/vlan/vlanindex_object.go | 7 +- go.mod | 2 + go.sum | 2 - pkg/backend/generic/applicator.go | 16 ++-- pkg/backend/generic/applicator_dynamic_id.go | 67 +++++++++----- .../generic/applicator_static_range.go | 20 ++--- pkg/backend/generic/backend.go | 16 ++-- pkg/backend/generic/backend_store.go | 90 ++++--------------- 19 files changed, 210 insertions(+), 291 deletions(-) diff --git a/apis/backend/as/asclaim_object.go b/apis/backend/as/asclaim_object.go index 91da86d..2d3c169 100644 --- a/apis/backend/as/asclaim_object.go +++ b/apis/backend/as/asclaim_object.go @@ -164,8 +164,7 @@ func (r *ASClaim) GetIndex() string { return r.Spec.Index } func (r *ASClaim) GetSelector() *metav1.LabelSelector { return r.Spec.Selector } func (r *ASClaim) IsOwner(labels labels.Set) bool { - ownerLabels := r.getOnwerLabels() - for k, v := range ownerLabels { + for k, v := range r.getOwnerLabels() { if val, ok := labels[k]; !ok || val != v { return false } @@ -173,29 +172,16 @@ func (r *ASClaim) IsOwner(labels labels.Set) bool { return true } -func (r *ASClaim) getOnwerLabels() map[string]string { - claimName := r.Name - claimKind := r.Kind - claimUID := r.UID - for _, owner := range r.GetOwnerReferences() { - if owner.APIVersion == SchemeGroupVersion.Identifier() && - owner.Kind == ASIndexKind { - claimName = owner.Name - claimKind = owner.Kind - claimUID = owner.UID - } - } - +func (r *ASClaim) getOwnerLabels() map[string]string { return map[string]string{ - backend.KuidClaimNameKey: claimName, - backend.KuidClaimUIDKey: string(claimUID), - backend.KuidOwnerKindKey: claimKind, + backend.KuidClaimNameKey: r.Name, + backend.KuidClaimUIDKey: string(r.UID), } } // GetOwnerSelector selects the route based on the name of the claim func (r *ASClaim) GetOwnerSelector() (labels.Selector, error) { - l := r.getOnwerLabels() + l := r.getOwnerLabels() fullselector := labels.NewSelector() for k, v := range l { @@ -213,24 +199,11 @@ func (r *ASClaim) GetLabelSelector() (labels.Selector, error) { return r.Spec.Ge func (r *ASClaim) GetClaimLabels() labels.Set { labels := r.Spec.GetUserDefinedLabels() - // for claims originated from the index we need to use the ownerreferences, since these claims - // are never stored in the apiserver, the ip entries need to reference the index instead - claimName := r.Name - claimKind := ASClaimKind - claimUID := r.UID - for _, owner := range r.GetOwnerReferences() { - if owner.APIVersion == SchemeGroupVersion.Identifier() && - owner.Kind == ASIndexKind { - claimName = owner.Name - claimKind = owner.Kind - claimUID = owner.UID - } - } // system defined labels labels[backend.KuidClaimTypeKey] = string(r.GetClaimType()) - labels[backend.KuidClaimNameKey] = claimName - labels[backend.KuidClaimUIDKey] = string(claimUID) - labels[backend.KuidOwnerKindKey] = claimKind + labels[backend.KuidClaimNameKey] = r.Name + labels[backend.KuidClaimUIDKey] = string(r.UID) + labels[backend.KuidOwnerKindKey] = r.Kind return labels } @@ -287,6 +260,13 @@ func (r *ASClaim) GetClaimID(t string, id uint64) tree.ID { return id32.NewID(uint32(id), id32.IDBitSize) } +func (r *ASClaim) GetStatusClaimID() tree.ID { + if r.Status.ID == nil { + return nil + } + return id32.NewID(uint32(*r.Status.ID), id32.IDBitSize) +} + func (r *ASClaim) GetRange() *string { return r.Spec.Range } @@ -349,17 +329,19 @@ func (r *ASClaim) GetClaimResponse() string { return "" } -func (r *ASClaim) GetClaimSet(typ string) (sets.Set[tree.ID], error) { +func (r *ASClaim) GetClaimSet(typ string) (map[string]tree.ID, sets.Set[string], error) { arange, err := r.GetRangeID(typ) if err != nil { - return nil, fmt.Errorf("cannot get range from claim: %v", err) + return nil, nil, fmt.Errorf("cannot get range from claim: %v", err) } // claim set represents the new entries - newClaimSet := sets.New[tree.ID]() + newClaimSet := sets.New[string]() + newClaimMap := map[string]tree.ID{} for _, rangeID := range arange.IDs() { - newClaimSet.Insert(rangeID) + newClaimSet.Insert(rangeID.String()) + newClaimMap[rangeID.String()] = rangeID } - return newClaimSet, nil + return newClaimMap, newClaimSet, nil } func (r *ASClaim) GetChoreoAPIVersion() string { diff --git a/apis/backend/as/asindex_object.go b/apis/backend/as/asindex_object.go index 911074b..715ada2 100644 --- a/apis/backend/as/asindex_object.go +++ b/apis/backend/as/asindex_object.go @@ -26,6 +26,7 @@ import ( "github.com/kuidio/kuid/apis/backend" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" + "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/types" "k8s.io/utils/ptr" ) @@ -113,7 +114,7 @@ func (r *ASIndex) GetMinClaim() backend.ClaimObject { Name: r.GetMinClaimNSN().Name, OwnerReferences: []metav1.OwnerReference{ { - APIVersion: r.APIVersion, + APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), Kind: r.Kind, Name: r.Name, UID: r.UID, @@ -135,8 +136,8 @@ func (r *ASIndex) GetMaxClaim() backend.ClaimObject { Name: r.GetMaxClaimNSN().Name, OwnerReferences: []metav1.OwnerReference{ { - APIVersion: r.APIVersion, - Kind: r.Kind, + APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), + Kind: ASIndexKind, Name: r.Name, UID: r.UID, }, diff --git a/apis/backend/claim_types.go b/apis/backend/claim_types.go index d791572..bc1e94e 100644 --- a/apis/backend/claim_types.go +++ b/apis/backend/claim_types.go @@ -41,6 +41,6 @@ func GetClaimTypeFromString(s string) ClaimType { } const ( - IndexReservedMinName = "rangeReservedMin" - IndexReservedMaxName = "rangeReservedMax" + IndexReservedMinName = "rangereservedmin" + IndexReservedMaxName = "rangereservedmax" ) diff --git a/apis/backend/extcomm/extcommclaim_object.go b/apis/backend/extcomm/extcommclaim_object.go index 3faf1b9..b4687af 100644 --- a/apis/backend/extcomm/extcommclaim_object.go +++ b/apis/backend/extcomm/extcommclaim_object.go @@ -179,8 +179,7 @@ func (r *EXTCOMMClaim) GetIndex() string { return r.Spec.Index } func (r *EXTCOMMClaim) GetSelector() *metav1.LabelSelector { return r.Spec.Selector } func (r *EXTCOMMClaim) IsOwner(labels labels.Set) bool { - ownerLabels := r.getOnwerLabels() - for k, v := range ownerLabels { + for k, v := range r.getOwnerLabels() { if val, ok := labels[k]; !ok || val != v { return false } @@ -188,29 +187,16 @@ func (r *EXTCOMMClaim) IsOwner(labels labels.Set) bool { return true } -func (r *EXTCOMMClaim) getOnwerLabels() map[string]string { - claimName := r.Name - claimKind := r.Kind - claimUID := r.UID - for _, owner := range r.GetOwnerReferences() { - if owner.APIVersion == SchemeGroupVersion.Identifier() && - owner.Kind == EXTCOMMIndexKind { - claimName = owner.Name - claimKind = owner.Kind - claimUID = owner.UID - } - } - +func (r *EXTCOMMClaim) getOwnerLabels() map[string]string { return map[string]string{ - backend.KuidClaimNameKey: claimName, - backend.KuidClaimUIDKey: string(claimUID), - backend.KuidOwnerKindKey: claimKind, + backend.KuidClaimNameKey: r.Name, + backend.KuidClaimUIDKey: string(r.UID), } } // GetOwnerSelector selects the route bVLANed on the name of the claim func (r *EXTCOMMClaim) GetOwnerSelector() (labels.Selector, error) { - l := r.getOnwerLabels() + l := r.getOwnerLabels() fullselector := labels.NewSelector() for k, v := range l { @@ -228,24 +214,11 @@ func (r *EXTCOMMClaim) GetLabelSelector() (labels.Selector, error) { return r.Sp func (r *EXTCOMMClaim) GetClaimLabels() labels.Set { labels := r.Spec.GetUserDefinedLabels() - // for claims originated from the index we need to use the ownerreferences, since these claims - // are never stored in the apiserver, the ip entries need to reference the index instead - claimName := r.Name - claimKind := EXTCOMMClaimKind - claimUID := r.UID - for _, owner := range r.GetOwnerReferences() { - if owner.APIVersion == SchemeGroupVersion.Identifier() && - owner.Kind == EXTCOMMIndexKind { - claimName = owner.Name - claimKind = owner.Kind - claimUID = owner.UID - } - } // system defined labels labels[backend.KuidClaimTypeKey] = string(r.GetClaimType()) - labels[backend.KuidClaimNameKey] = claimName - labels[backend.KuidClaimUIDKey] = string(claimUID) - labels[backend.KuidOwnerKindKey] = claimKind + labels[backend.KuidClaimNameKey] = r.Name + labels[backend.KuidClaimUIDKey] = string(r.UID) + labels[backend.KuidOwnerKindKey] = r.Kind return labels } @@ -302,6 +275,13 @@ func (r *EXTCOMMClaim) GetClaimID(t string, id uint64) tree.ID { return id16.NewID(uint16(id), id16.IDBitSize) } +func (r *EXTCOMMClaim) GetStatusClaimID() tree.ID { + if r.Status.ID == nil { + return nil + } + return id16.NewID(uint16(*r.Status.ID), id16.IDBitSize) +} + func (r *EXTCOMMClaim) GetRange() *string { return r.Spec.Range } @@ -358,17 +338,19 @@ func (r *EXTCOMMClaim) GetClaimResponse() string { return "" } -func (r *EXTCOMMClaim) GetClaimSet(typ string) (sets.Set[tree.ID], error) { +func (r *EXTCOMMClaim) GetClaimSet(typ string) (map[string]tree.ID, sets.Set[string], error) { arange, err := r.GetRangeID(typ) if err != nil { - return nil, fmt.Errorf("cannot get range from claim: %v", err) + return nil, nil, fmt.Errorf("cannot get range from claim: %v", err) } // claim set represents the new entries - newClaimSet := sets.New[tree.ID]() + newClaimSet := sets.New[string]() + newClaimMap := map[string]tree.ID{} for _, rangeID := range arange.IDs() { - newClaimSet.Insert(rangeID) + newClaimSet.Insert(rangeID.String()) + newClaimMap[rangeID.String()] = rangeID } - return newClaimSet, nil + return newClaimMap, newClaimSet, nil } func (r *EXTCOMMClaim) GetChoreoAPIVersion() string { diff --git a/apis/backend/extcomm/extcommindex_object.go b/apis/backend/extcomm/extcommindex_object.go index 847bbea..1eeda88 100644 --- a/apis/backend/extcomm/extcommindex_object.go +++ b/apis/backend/extcomm/extcommindex_object.go @@ -28,6 +28,7 @@ import ( "github.com/kuidio/kuid/apis/backend" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" + "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/types" "k8s.io/utils/ptr" ) @@ -131,7 +132,7 @@ func (r *EXTCOMMIndex) GetMinClaim() backend.ClaimObject { Name: r.GetMinClaimNSN().Name, OwnerReferences: []metav1.OwnerReference{ { - APIVersion: r.APIVersion, + APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), Kind: r.Kind, Name: r.Name, UID: r.UID, @@ -153,8 +154,8 @@ func (r *EXTCOMMIndex) GetMaxClaim() backend.ClaimObject { Name: r.GetMaxClaimNSN().Name, OwnerReferences: []metav1.OwnerReference{ { - APIVersion: r.APIVersion, - Kind: r.Kind, + APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), + Kind: EXTCOMMIndexKind, Name: r.Name, UID: r.UID, }, diff --git a/apis/backend/genid/genidclaim_object.go b/apis/backend/genid/genidclaim_object.go index 0f03be1..0929d6f 100644 --- a/apis/backend/genid/genidclaim_object.go +++ b/apis/backend/genid/genidclaim_object.go @@ -165,8 +165,7 @@ func (r *GENIDClaim) GetIndex() string { return r.Spec.Index } func (r *GENIDClaim) GetSelector() *metav1.LabelSelector { return r.Spec.Selector } func (r *GENIDClaim) IsOwner(labels labels.Set) bool { - ownerLabels := r.getOnwerLabels() - for k, v := range ownerLabels { + for k, v := range r.getOwnerLabels() { if val, ok := labels[k]; !ok || val != v { return false } @@ -174,29 +173,16 @@ func (r *GENIDClaim) IsOwner(labels labels.Set) bool { return true } -func (r *GENIDClaim) getOnwerLabels() map[string]string { - claimName := r.Name - claimKind := r.Kind - claimUID := r.UID - for _, owner := range r.GetOwnerReferences() { - if owner.APIVersion == SchemeGroupVersion.Identifier() && - owner.Kind == GENIDIndexKind { - claimName = owner.Name - claimKind = owner.Kind - claimUID = owner.UID - } - } - +func (r *GENIDClaim) getOwnerLabels() map[string]string { return map[string]string{ - backend.KuidClaimNameKey: claimName, - backend.KuidClaimUIDKey: string(claimUID), - backend.KuidOwnerKindKey: claimKind, + backend.KuidClaimNameKey: r.Name, + backend.KuidClaimUIDKey: string(r.UID), } } // GetOwnerSelector selects the route bVLANed on the name of the claim func (r *GENIDClaim) GetOwnerSelector() (labels.Selector, error) { - l := r.getOnwerLabels() + l := r.getOwnerLabels() fullselector := labels.NewSelector() for k, v := range l { @@ -214,25 +200,13 @@ func (r *GENIDClaim) GetLabelSelector() (labels.Selector, error) { return r.Spec func (r *GENIDClaim) GetClaimLabels() labels.Set { labels := r.Spec.GetUserDefinedLabels() - // for claims originated from the index we need to use the ownerreferences, since these claims - // are never stored in the apiserver, the ip entries need to reference the index instead - claimName := r.Name - claimKind := GENIDClaimKind - claimUID := r.UID - for _, owner := range r.GetOwnerReferences() { - if owner.APIVersion == SchemeGroupVersion.Identifier() && - owner.Kind == GENIDIndexKind { - claimName = owner.Name - claimKind = owner.Kind - claimUID = owner.UID - } - } // system defined labels labels[backend.KuidClaimTypeKey] = string(r.GetClaimType()) - labels[backend.KuidClaimNameKey] = claimName - labels[backend.KuidClaimUIDKey] = string(claimUID) - labels[backend.KuidOwnerKindKey] = claimKind + labels[backend.KuidClaimNameKey] = r.Name + labels[backend.KuidClaimUIDKey] = string(r.UID) + labels[backend.KuidOwnerKindKey] = r.Kind return labels + } func (r *GENIDClaim) ValidateOwner(labels labels.Set) error { @@ -288,6 +262,13 @@ func (r *GENIDClaim) GetClaimID(t string, id uint64) tree.ID { return id16.NewID(uint16(id), id16.IDBitSize) } +func (r *GENIDClaim) GetStatusClaimID() tree.ID { + if r.Status.ID == nil { + return nil + } + return id16.NewID(uint16(*r.Status.ID), id16.IDBitSize) +} + func (r *GENIDClaim) GetRange() *string { return r.Spec.Range } @@ -344,17 +325,19 @@ func (r *GENIDClaim) GetClaimResponse() string { return "" } -func (r *GENIDClaim) GetClaimSet(typ string) (sets.Set[tree.ID], error) { +func (r *GENIDClaim) GetClaimSet(typ string) (map[string]tree.ID, sets.Set[string], error) { arange, err := r.GetRangeID(typ) if err != nil { - return nil, fmt.Errorf("cannot get range from claim: %v", err) + return nil, nil, fmt.Errorf("cannot get range from claim: %v", err) } // claim set represents the new entries - newClaimSet := sets.New[tree.ID]() + newClaimSet := sets.New[string]() + newClaimMap := map[string]tree.ID{} for _, rangeID := range arange.IDs() { - newClaimSet.Insert(rangeID) + newClaimSet.Insert(rangeID.String()) + newClaimMap[rangeID.String()] = rangeID } - return newClaimSet, nil + return newClaimMap, newClaimSet, nil } func (r *GENIDClaim) GetChoreoAPIVersion() string { diff --git a/apis/backend/genid/genidentry_object.go b/apis/backend/genid/genidentry_object.go index 699a92c..5cef09f 100644 --- a/apis/backend/genid/genidentry_object.go +++ b/apis/backend/genid/genidentry_object.go @@ -109,6 +109,8 @@ func GetGENIDEntry(k store.Key, vrange, id string, labels map[string]string) bac name = fmt.Sprintf("%s.%s", vrange, id) } + fmt.Println("GetGENIDEntry kind", labels[backend.KuidOwnerKindKey]) + return BuildGENIDEntry( metav1.ObjectMeta{ Name: name, diff --git a/apis/backend/genid/genidindex_object.go b/apis/backend/genid/genidindex_object.go index 9bdf60c..1b064a9 100644 --- a/apis/backend/genid/genidindex_object.go +++ b/apis/backend/genid/genidindex_object.go @@ -28,6 +28,7 @@ import ( "github.com/kuidio/kuid/apis/backend" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" + "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/types" "k8s.io/utils/ptr" ) @@ -138,8 +139,8 @@ func (r *GENIDIndex) GetMinClaim() backend.ClaimObject { Name: r.GetMinClaimNSN().Name, OwnerReferences: []metav1.OwnerReference{ { - APIVersion: r.APIVersion, - Kind: r.Kind, + APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), + Kind: GENIDIndexKind, Name: r.Name, UID: r.UID, }, @@ -160,7 +161,7 @@ func (r *GENIDIndex) GetMaxClaim() backend.ClaimObject { Name: r.GetMaxClaimNSN().Name, OwnerReferences: []metav1.OwnerReference{ { - APIVersion: r.APIVersion, + APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), Kind: r.Kind, Name: r.Name, UID: r.UID, diff --git a/apis/backend/ipam/ipindex_object.go b/apis/backend/ipam/ipindex_object.go index a64c6b4..1cb31f5 100644 --- a/apis/backend/ipam/ipindex_object.go +++ b/apis/backend/ipam/ipindex_object.go @@ -96,7 +96,7 @@ func (r *IPIndex) GetClaim(prefix Prefix) (*IPClaim, error) { OwnerReferences: []metav1.OwnerReference{ { APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), - Kind: IPIndexKind, + Kind: r.Kind, Name: r.Name, UID: r.UID, }, diff --git a/apis/backend/object.go b/apis/backend/object.go index 96a8d5c..234c07b 100644 --- a/apis/backend/object.go +++ b/apis/backend/object.go @@ -54,6 +54,7 @@ type ClaimObject interface { GetStaticID() *uint64 GetStaticTreeID(t string) tree.ID GetClaimID(t string, id uint64) tree.ID + GetStatusClaimID() tree.ID GetRange() *string GetRangeID(t string) (tree.Range, error) GetTable(t string, to, from uint64) table.Table @@ -62,7 +63,7 @@ type ClaimObject interface { GetStatusID() *uint64 GetClaimRequest() string GetClaimResponse() string - GetClaimSet(typ string) (sets.Set[tree.ID], error) + GetClaimSet(typ string) (map[string]tree.ID, sets.Set[string], error) IsOwner(labels labels.Set) bool GetChoreoAPIVersion() string // a trick to translate the apiversion as per crd } diff --git a/apis/backend/vlan/vlanclaim_object.go b/apis/backend/vlan/vlanclaim_object.go index adf4b46..8da8aa7 100644 --- a/apis/backend/vlan/vlanclaim_object.go +++ b/apis/backend/vlan/vlanclaim_object.go @@ -164,8 +164,7 @@ func (r *VLANClaim) GetIndex() string { return r.Spec.Index } func (r *VLANClaim) GetSelector() *metav1.LabelSelector { return r.Spec.Selector } func (r *VLANClaim) IsOwner(labels labels.Set) bool { - ownerLabels := r.getOnwerLabels() - for k, v := range ownerLabels { + for k, v := range r.getOwnerLabels() { if val, ok := labels[k]; !ok || val != v { return false } @@ -173,29 +172,16 @@ func (r *VLANClaim) IsOwner(labels labels.Set) bool { return true } -func (r *VLANClaim) getOnwerLabels() map[string]string { - claimName := r.Name - claimKind := r.Kind - claimUID := r.UID - for _, owner := range r.GetOwnerReferences() { - if owner.APIVersion == SchemeGroupVersion.Identifier() && - owner.Kind == VLANIndexKind { - claimName = owner.Name - claimKind = owner.Kind - claimUID = owner.UID - } - } - +func (r *VLANClaim) getOwnerLabels() map[string]string { return map[string]string{ - backend.KuidClaimNameKey: claimName, - backend.KuidClaimUIDKey: string(claimUID), - backend.KuidOwnerKindKey: claimKind, + backend.KuidClaimNameKey: r.Name, + backend.KuidClaimUIDKey: string(r.UID), } } // GetOwnerSelector selects the route bVLANed on the name of the claim func (r *VLANClaim) GetOwnerSelector() (labels.Selector, error) { - l := r.getOnwerLabels() + l := r.getOwnerLabels() fullselector := labels.NewSelector() for k, v := range l { @@ -213,24 +199,11 @@ func (r *VLANClaim) GetLabelSelector() (labels.Selector, error) { return r.Spec. func (r *VLANClaim) GetClaimLabels() labels.Set { labels := r.Spec.GetUserDefinedLabels() - // for claims originated from the index we need to use the ownerreferences, since these claims - // are never stored in the apiserver, the ip entries need to reference the index instead - claimName := r.Name - claimKind := VLANClaimKind - claimUID := r.UID - for _, owner := range r.GetOwnerReferences() { - if owner.APIVersion == SchemeGroupVersion.Identifier() && - owner.Kind == VLANIndexKind { - claimName = owner.Name - claimKind = owner.Kind - claimUID = owner.UID - } - } // system defined labels labels[backend.KuidClaimTypeKey] = string(r.GetClaimType()) - labels[backend.KuidClaimNameKey] = claimName - labels[backend.KuidClaimUIDKey] = string(claimUID) - labels[backend.KuidOwnerKindKey] = claimKind + labels[backend.KuidClaimNameKey] = r.Name + labels[backend.KuidClaimUIDKey] = string(r.UID) + labels[backend.KuidOwnerKindKey] = r.Kind return labels } @@ -287,6 +260,13 @@ func (r *VLANClaim) GetClaimID(t string, id uint64) tree.ID { return id32.NewID(uint32(id), id32.IDBitSize) } +func (r *VLANClaim) GetStatusClaimID() tree.ID { + if r.Status.ID == nil { + return nil + } + return id32.NewID(uint32(*r.Status.ID), id32.IDBitSize) +} + func (r *VLANClaim) GetRange() *string { return r.Spec.Range } @@ -347,17 +327,19 @@ func (r *VLANClaim) GetChoreoAPIVersion() string { return schema.GroupVersion{Group: GroupName, Version: "vlan"}.String() } -func (r *VLANClaim) GetClaimSet(typ string) (sets.Set[tree.ID], error) { +func (r *VLANClaim) GetClaimSet(typ string) (map[string]tree.ID, sets.Set[string], error) { arange, err := r.GetRangeID(typ) if err != nil { - return nil, fmt.Errorf("cannot get range from claim: %v", err) + return nil, nil, fmt.Errorf("cannot get range from claim: %v", err) } // claim set represents the new entries - newClaimSet := sets.New[tree.ID]() + newClaimSet := sets.New[string]() + newClaimMap := map[string]tree.ID{} for _, rangeID := range arange.IDs() { - newClaimSet.Insert(rangeID) + newClaimSet.Insert(rangeID.String()) + newClaimMap[rangeID.String()] = rangeID } - return newClaimSet, nil + return newClaimMap, newClaimSet, nil } func VLANClaimFromUnstructured(ru runtime.Unstructured) (backend.ClaimObject, error) { diff --git a/apis/backend/vlan/vlanindex_object.go b/apis/backend/vlan/vlanindex_object.go index cfbf68d..a7879b8 100644 --- a/apis/backend/vlan/vlanindex_object.go +++ b/apis/backend/vlan/vlanindex_object.go @@ -26,6 +26,7 @@ import ( "github.com/kuidio/kuid/apis/backend" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" + "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/types" "k8s.io/utils/ptr" ) @@ -113,8 +114,8 @@ func (r *VLANIndex) GetMinClaim() backend.ClaimObject { Name: r.GetMinClaimNSN().Name, OwnerReferences: []metav1.OwnerReference{ { - APIVersion: r.APIVersion, - Kind: r.Kind, + APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), + Kind: VLANIndexKind, Name: r.Name, UID: r.UID, }, @@ -135,7 +136,7 @@ func (r *VLANIndex) GetMaxClaim() backend.ClaimObject { Name: r.GetMaxClaimNSN().Name, OwnerReferences: []metav1.OwnerReference{ { - APIVersion: r.APIVersion, + APIVersion: schema.GroupVersion{Group: SchemeGroupVersion.Group, Version: "v1alpha1"}.Identifier(), Kind: r.Kind, Name: r.Name, UID: r.UID, diff --git a/go.mod b/go.mod index 20c54d5..071eab4 100644 --- a/go.mod +++ b/go.mod @@ -6,6 +6,8 @@ toolchain go1.23.2 replace k8s.io/gengo/v2 => k8s.io/gengo/v2 v2.0.0-20240228010128-51d4e06bde70 +replace github.com/henderiw/idxtable => /Users/henderiw/code/idxtable + require ( github.com/dgraph-io/badger/v4 v4.3.0 github.com/google/go-cmp v0.6.0 diff --git a/go.sum b/go.sum index 09feb1e..fb8bee1 100644 --- a/go.sum +++ b/go.sum @@ -149,8 +149,6 @@ github.com/henderiw/apiserver-builder v0.0.4-0.20241027084658-10d7f9d97252 h1:+I github.com/henderiw/apiserver-builder v0.0.4-0.20241027084658-10d7f9d97252/go.mod h1:LfJu1JURnxHwnFa8CVb2XPw50TwdU1xQvuUNxpaSOlE= github.com/henderiw/apiserver-store v0.0.3-0.20241106073231-cbded10a8cee h1:Xp1+2fZb7GhS+2HCLlNfWh8oFdFc61ogM5rlCeILiCY= github.com/henderiw/apiserver-store v0.0.3-0.20241106073231-cbded10a8cee/go.mod h1:VVkUptd3MTyREmpo+C/t6l+mJAwo3A1UWvHi0QSH0yE= -github.com/henderiw/idxtable v0.0.0-20241021085446-f8d804551342 h1:gkdOvjxM6rNTkcyoykZLjAfPjn06/MEY4o8cy+3uj2g= -github.com/henderiw/idxtable v0.0.0-20241021085446-f8d804551342/go.mod h1:EPdUFZyKA2IORzohdu67+xBbfDmkHEDUaMN0BBsk8eY= github.com/henderiw/iputil v0.0.0-20231218081610-37f78ad9c81c h1:nFnCNyRV1Ej/zqV/gn8UnFESkoPUXhwpUCZyhSYGSYA= github.com/henderiw/iputil v0.0.0-20231218081610-37f78ad9c81c/go.mod h1:PrPJdVAwtl5tL323wykHZ5L/b7tfJJsjhegza/wq4fQ= github.com/henderiw/logger v0.0.0-20230911123436-8655829b1abe h1:+R53KH7fW+pmqlfSYVTCGPn8pj6gqBGcQ0nq7L1h8+g= diff --git a/pkg/backend/generic/applicator.go b/pkg/backend/generic/applicator.go index 6f2c197..9f1508f 100644 --- a/pkg/backend/generic/applicator.go +++ b/pkg/backend/generic/applicator.go @@ -102,7 +102,7 @@ func reclaimIDFromExisitingEntries(existingEntries map[string]tree.Entries, id u func claimIDFromExisitingEntries(existingEntries map[string]tree.Entries) (*uint64, string) { for treeName, existingEntries := range existingEntries { for _, existingEntry := range existingEntries { - return ptr.To[uint64](existingEntry.ID().ID()), treeName + return ptr.To(existingEntry.ID().ID()), treeName } } return nil, "" @@ -140,21 +140,23 @@ func isReserved(parentName, index string) bool { */ } -func (r *applicator) getExistingCLaimSet(ctx context.Context, claim backend.ClaimObject) (sets.Set[tree.ID], error) { - oldClaimIDSet := sets.New[tree.ID]() +func (r *applicator) getExistingCLaimSet(ctx context.Context, claim backend.ClaimObject) (map[string]tree.ID, sets.Set[string], error) { + oldClaimIDSet := sets.New[string]() + oldClaimMap := map[string]tree.ID{} existingEntries, err := r.getEntriesByOwner(ctx, claim) if err != nil { - return nil, err + return nil, nil, err } // delete the entries from the claimSet that overlap for treeName, existingEntries := range existingEntries { if treeName != "" { - return nil, fmt.Errorf("cannot have a range in non root tree: %s", treeName) + return nil, nil, fmt.Errorf("cannot have a range in non root tree: %s", treeName) } for _, existingEntry := range existingEntries { - oldClaimIDSet.Insert(existingEntry.ID()) + oldClaimIDSet.Insert(existingEntry.ID().String()) + oldClaimMap[existingEntry.ID().String()] = existingEntry.ID() } } - return oldClaimIDSet, nil + return oldClaimMap, oldClaimIDSet, nil } diff --git a/pkg/backend/generic/applicator_dynamic_id.go b/pkg/backend/generic/applicator_dynamic_id.go index 6bc1a23..1b2f99b 100644 --- a/pkg/backend/generic/applicator_dynamic_id.go +++ b/pkg/backend/generic/applicator_dynamic_id.go @@ -113,41 +113,68 @@ func (r *dynamicApplicator) Apply(ctx context.Context, claim backend.ClaimObject } if parentTreeName == "" { + // root tree apply if claimID != nil { if err := r.cacheInstanceCtx.tree.Update(claim.GetClaimID(r.cacheInstanceCtx.Type(), *claimID), claim.GetClaimLabels()); err != nil { return err } - } else { - e, err := r.cacheInstanceCtx.tree.ClaimFree(claim.GetClaimLabels()) - if err != nil { - return err + claim.SetStatusID(claimID) + claim.SetConditions(condition.Ready()) + return nil + } + if claim.GetStatusID() != nil { + // TODO check if free ? + if err := r.cacheInstanceCtx.tree.ClaimID(claim.GetStatusClaimID(), claim.GetClaimLabels()); err != nil { + return fmt.Errorf("reclaim status id claim failed, no claim ID found err: %s", err) } - claimID = ptr.To[uint64](e.ID().ID()) + claim.SetStatusID(claim.GetStatusID()) + claim.SetConditions(condition.Ready()) + return nil + } - } else { - k := store.ToKey(parentTreeName) - table, err := r.cacheInstanceCtx.ranges.Get(k) + e, err := r.cacheInstanceCtx.tree.ClaimFree(claim.GetClaimLabels()) if err != nil { - return fmt.Errorf("selectAddress range does not have corresponding range table: err: %s", err.Error()) + return fmt.Errorf("claimed failed, no claim ID found err: %s", err) } - if claimID != nil { - if err := table.Update(*claimID, claim.GetClaimLabels()); err != nil { - return err - } - } else { - e, err := table.ClaimFree(claim.GetClaimLabels()) - if err != nil { - return err + claimID = ptr.To[uint64](e.ID().ID()) + claim.SetStatusID(claimID) + claim.SetConditions(condition.Ready()) + return nil + } + // table - range entry apply + k := store.ToKey(parentTreeName) + table, err := r.cacheInstanceCtx.ranges.Get(k) + if err != nil { + return fmt.Errorf("selectAddress range does not have corresponding range table: err: %s", err.Error()) + } + if claimID != nil { + if err := table.Update(*claimID, claim.GetClaimLabels()); err != nil { + return err + } + claim.SetStatusID(claimID) + claim.SetConditions(condition.Ready()) + return nil + } + // try reclaim existing id + if claim.GetStatusID() != nil { + if table.IsFree(*claim.GetStatusID()) { + if err := table.Claim(*claim.GetStatusID(), claim.GetClaimLabels()); err != nil { + return fmt.Errorf("claimed failed, no claim ID found err: %s", err) } - claimID = ptr.To[uint64](e.ID().ID()) + claim.SetStatusID(claim.GetStatusID()) + claim.SetConditions(condition.Ready()) + return nil } } - if claimID == nil { - return fmt.Errorf("claimed failed, no claim ID found") + e, err := table.ClaimFree(claim.GetClaimLabels()) + if err != nil { + return fmt.Errorf("claimed failed, no claim ID found err: %s", err) } + claimID = ptr.To[uint64](e.ID().ID()) claim.SetStatusID(claimID) claim.SetConditions(condition.Ready()) return nil + } func (r *dynamicApplicator) Delete(ctx context.Context, claim backend.ClaimObject) error { diff --git a/pkg/backend/generic/applicator_static_range.go b/pkg/backend/generic/applicator_static_range.go index 8696c57..c7cc4c7 100644 --- a/pkg/backend/generic/applicator_static_range.go +++ b/pkg/backend/generic/applicator_static_range.go @@ -57,12 +57,12 @@ func (r *rangeApplicator) Validate(ctx context.Context, claim backend.ClaimObjec // validateChange checks if the range changed; change is only reported when the range existed func (r *rangeApplicator) validateChange(ctx context.Context, claim backend.ClaimObject) (bool, error) { - newClaimSet, err := claim.GetClaimSet(r.cacheInstanceCtx.Type()) + _, newClaimSet, err := claim.GetClaimSet(r.cacheInstanceCtx.Type()) if err != nil { return false, err } - oldClaimSet, err := r.getExistingCLaimSet(ctx, claim) + _, oldClaimSet, err := r.getExistingCLaimSet(ctx, claim) if err != nil { return false, err } @@ -106,12 +106,12 @@ func (r *rangeApplicator) Apply(ctx context.Context, claim backend.ClaimObject) if err != nil { return err } - newClaimSet, err := claim.GetClaimSet(r.cacheInstanceCtx.Type()) + newClaimMap, newClaimSet, err := claim.GetClaimSet(r.cacheInstanceCtx.Type()) if err != nil { return err } - oldClaimSet, err := r.getExistingCLaimSet(ctx, claim) + oldClaimMap, oldClaimSet, err := r.getExistingCLaimSet(ctx, claim) if err != nil { return err } @@ -120,18 +120,18 @@ func (r *rangeApplicator) Apply(ctx context.Context, claim backend.ClaimObject) existingEntries := newClaimSet.Intersection(oldClaimSet) deletedEntries := oldClaimSet.Difference(newClaimSet) - for id := range deletedEntries { - if err := r.cacheInstanceCtx.tree.ReleaseID(id); err != nil { + for idstr := range deletedEntries { + if err := r.cacheInstanceCtx.tree.ReleaseID(oldClaimMap[idstr]); err != nil { return err } } - for id := range newEntries { - if err := r.cacheInstanceCtx.tree.ClaimID(id, claim.GetClaimLabels()); err != nil { + for idstr := range newEntries { + if err := r.cacheInstanceCtx.tree.ClaimID(newClaimMap[idstr], claim.GetClaimLabels()); err != nil { return err } } - for id := range existingEntries { - if err := r.cacheInstanceCtx.tree.Update(id, claim.GetClaimLabels()); err != nil { + for idstr := range existingEntries { + if err := r.cacheInstanceCtx.tree.Update(newClaimMap[idstr], claim.GetClaimLabels()); err != nil { return err } } diff --git a/pkg/backend/generic/backend.go b/pkg/backend/generic/backend.go index d7d4dfa..1cfea57 100644 --- a/pkg/backend/generic/backend.go +++ b/pkg/backend/generic/backend.go @@ -100,7 +100,9 @@ func (r *be) CreateIndex(ctx context.Context, obj runtime.Object) error { index.SetConditions(condition.Ready()) obj = index - return r.cache.SetInitialized(ctx, key) + if err := r.cache.SetInitialized(ctx, key); err != nil { + return err + } } log.Debug("update IPIndex claims", "object", obj) return r.updateIndexClaims(ctx, index) @@ -132,8 +134,10 @@ func (r *be) DeleteIndex(ctx context.Context, obj runtime.Object) error { } func (r *be) Claim(ctx context.Context, obj runtime.Object, recursion bool) error { - r.m.Lock() - defer r.m.Unlock() + if !recursion { + r.m.Lock() + defer r.m.Unlock() + } claim, err := r.claimObjectFn(obj) if err != nil { return err @@ -170,8 +174,10 @@ func (r *be) Claim(ctx context.Context, obj runtime.Object, recursion bool) erro } func (r *be) Release(ctx context.Context, obj runtime.Object, recursion bool) error { - r.m.Lock() - defer r.m.Unlock() + if !recursion { + r.m.Lock() + defer r.m.Unlock() + } claim, err := r.claimObjectFn(obj) if err != nil { return err diff --git a/pkg/backend/generic/backend_store.go b/pkg/backend/generic/backend_store.go index 6246351..324b359 100644 --- a/pkg/backend/generic/backend_store.go +++ b/pkg/backend/generic/backend_store.go @@ -10,7 +10,6 @@ import ( "github.com/henderiw/logger/log" "github.com/henderiw/store" "github.com/kuidio/kuid/apis/backend" - "github.com/kuidio/kuid/apis/backend/ipam" bebackend "github.com/kuidio/kuid/pkg/backend" "k8s.io/apimachinery/pkg/runtime" "k8s.io/apimachinery/pkg/types" @@ -63,49 +62,46 @@ func (r *be) saveAll(ctx context.Context, k store.Key) error { log := log.FromContext(ctx) log.Debug("SaveAll") - newEntries, err := r.getEntriesFromCache(ctx, k) + cacheEntries, err := r.getEntriesFromCache(ctx, k) if err != nil { return err } - curEntries, err := r.listEntries(ctx, k) + + apiEntries, err := r.listEntries(ctx, k) if err != nil { return err } - for _, newEntry := range newEntries { - newEntry := newEntry + for _, cacheEntry := range cacheEntries { found := false var oldEntry backend.EntryObject - for idx, curEntry := range curEntries { - idx := idx - curEntry := curEntry - if curEntry.GetNamespacedName() == newEntry.GetNamespacedName() { + for idx, apiEntry := range apiEntries { + if apiEntry.GetNamespacedName() == cacheEntry.GetNamespacedName() { // delete the current entry - curEntries = append(curEntries[:idx], curEntries[idx+1:]...) + apiEntries = append(apiEntries[:idx], apiEntries[idx+1:]...) found = true - oldEntry = curEntry + oldEntry = apiEntry break } } if !found { - if err := r.bestorage.CreateEntry(ctx, newEntry); err != nil { - log.Error("saveAll create failed", "name", newEntry.GetName(), "error", err.Error()) + if err := r.bestorage.CreateEntry(ctx, cacheEntry); err != nil { + log.Error("saveAll create failed", "name", cacheEntry.GetName(), "error", err.Error()) return err } continue } - if err := r.bestorage.UpdateEntry(ctx, newEntry, oldEntry); err != nil { - log.Error("saveAll update failed", "name", newEntry.GetName(), "error", err.Error()) + if err := r.bestorage.UpdateEntry(ctx, cacheEntry, oldEntry); err != nil { + log.Error("saveAll update failed", "name", cacheEntry.GetName(), "error", err.Error()) return err } } - for _, curEntry := range curEntries { - fmt.Println("backend generic delete entry", curEntry) - if err := r.bestorage.DeleteEntry(ctx, curEntry); err != nil { - log.Error("saveAll delete failed", "name", curEntry.GetName(), "error", err.Error()) + for _, apiEntry := range apiEntries { + if err := r.bestorage.DeleteEntry(ctx, apiEntry); err != nil { + log.Error("saveAll delete failed", "name", apiEntry.GetName(), "error", err.Error()) return err } } @@ -129,13 +125,11 @@ func (r *be) getEntriesFromCache(ctx context.Context, k store.Key) ([]backend.En entries := make([]backend.EntryObject, 0, cacheInstanceCtx.Size()) // add the main rib entry for _, entry := range cacheInstanceCtx.tree.GetAll() { - entry := entry entries = append(entries, r.entryFromCacheFn(k, "", entry.ID().String(), entry.Labels())) } // add all the range entries cacheInstanceCtx.ranges.List(func(key store.Key, t table.Table) { for _, entry := range t.GetAll() { - entry := entry entries = append(entries, r.entryFromCacheFn(k, key.Name, entry.ID().String(), entry.Labels())) } }) @@ -172,59 +166,12 @@ func (r *be) listClaims(ctx context.Context, k store.Key) (map[string]backend.Cl return r.bestorage.ListClaims(ctx, k) } -/* -func (r *be) restoreMinMaxRanges(ctx context.Context, cacheInstanceCtx *CacheInstanceContext, entries []backend.EntryObject, index backend.IndexObject) error { - fmt.Println("restoreMinMaxRanges index", index) - storedEntries := sets.New[string]() - for i := len(entries) - 1; i >= 0; i-- { - entry := entries[i] - for _, ownerref := range entry.GetOwnerReferences() { - if ownerref.APIVersion == index.GetObjectKind().GroupVersionKind().GroupVersion().Identifier() && - ownerref.Kind == index.GetObjectKind().GroupVersionKind().Kind && - ownerref.Name == index.GetName() && - ownerref.UID == index.GetUID() { - entries = append(entries[:i], entries[i+1:]...) - storedEntries.Insert(entry.GetSpecID()) - } - } - } - - if index.GetMinID() != nil && *index.GetMinID() != 0 { - claim := index.GetMinClaim() - fmt.Println("restoreMinMaxRanges minclaim", claim) - if err := r.restoreClaim(ctx, cacheInstanceCtx, claim); err != nil { - return err - } - } - if index.GetMaxID() != nil && *index.GetMaxID() != index.GetMax() { - claim := index.GetMaxClaim() - fmt.Println("restoreMinMaxRanges maxclaim", claim) - if err := r.restoreClaim(ctx, cacheInstanceCtx, claim); err != nil { - return err - } - } - // At init when there is no entries initialized this allows to store the entries in the database - if storedEntries.Len() == 0 { - entries, err := r.getEntriesFromCache(ctx, index.GetKey()) - if err != nil { - return err - } - for _, entry := range entries { - if err := r.bestorage.CreateEntry(ctx, entry); err != nil { - return err - } - } - } - return nil -} -*/ - func (r *be) restoreClaims(ctx context.Context, cacheInstanceCtx *CacheInstanceContext, entries []backend.EntryObject, kind string, claimType backend.ClaimType, claimmap map[string]backend.ClaimObject) error { log := log.FromContext(ctx) for i := len(entries) - 1; i >= 0; i-- { entry := entries[i] - if (kind == ipam.IPIndexKind && entry.IsIndexEntry() && claimType == entry.GetClaimType()) || - (kind != ipam.IPIndexKind && !entry.IsIndexEntry() && claimType == entry.GetClaimType()) { + if (kind == r.indexKind && entry.IsIndexEntry() && claimType == entry.GetClaimType()) || + (kind != r.indexKind && !entry.IsIndexEntry() && claimType == entry.GetClaimType()) { claimName := "" if len(entry.GetOwnerReferences()) > 0 { claimName = entry.GetOwnerReferences()[0].Name @@ -268,6 +215,7 @@ func (r *be) restoreClaim(ctx context.Context, cacheInstanceCtx *CacheInstanceCo if err != nil { return err } + // validate is needed, mainly for addresses since the parent route determines // e.g. the fact the address belongs to a range or not errList := claim.ValidateSyntax(cacheInstanceCtx.Type()) @@ -365,6 +313,6 @@ func ClaimTransformer(_ context.Context, newObj runtime.Object, oldObj runtime.O func (r *be) listIndexClaims(ctx context.Context, k store.Key) (map[string]backend.ClaimObject, error) { return r.bestorage.ListClaims(ctx, k, &ListOptions{ - OwnerKind: ipam.IPIndexKind, + OwnerKind: r.indexKind, }) }