Skip to content
This repository has been archived by the owner on Dec 16, 2024. It is now read-only.

GH-496 GW target own cluster #638

Merged
merged 4 commits into from
Nov 17, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion pkg/controllers/dnspolicy/dns_helper.go
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,6 @@ func (dh *dnsHelper) buildDNSRecordForListener(gateway *gatewayapiv1.Gateway, dn
}

// getDNSRecordForListener returns a v1alpha1.DNSRecord, if one exists, for the given listener in the given v1alpha1.ManagedZone.
// It needs a reference string to enforce DNS record serving a single traffic.Interface owner
func (dh *dnsHelper) getDNSRecordForListener(ctx context.Context, listener gatewayapiv1.Listener, owner metav1.Object) (*v1alpha1.DNSRecord, error) {
recordName := dnsRecordName(owner.GetName(), string(listener.Name))
dnsRecord := &v1alpha1.DNSRecord{}
Expand Down
101 changes: 21 additions & 80 deletions pkg/controllers/dnspolicy/dnspolicy_dnsrecords.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ package dnspolicy
import (
"context"
"fmt"
"strings"

clusterv1 "open-cluster-management.io/api/cluster/v1"

Expand All @@ -16,12 +15,8 @@ import (
"github.com/kuadrant/kuadrant-operator/pkg/reconcilers"

"github.com/Kuadrant/multicluster-gateway-controller/pkg/apis/v1alpha1"
"github.com/Kuadrant/multicluster-gateway-controller/pkg/controllers/gateway"
"github.com/Kuadrant/multicluster-gateway-controller/pkg/dns"
)

const (
singleCluster = "kudarant.io/single"
"github.com/Kuadrant/multicluster-gateway-controller/pkg/utils"
)

func (r *DNSPolicyReconciler) reconcileDNSRecords(ctx context.Context, dnsPolicy *v1alpha1.DNSPolicy, gwDiffObj *reconcilers.GatewayDiff) error {
Expand All @@ -45,42 +40,47 @@ func (r *DNSPolicyReconciler) reconcileDNSRecords(ctx context.Context, dnsPolicy
return nil
}

func (r *DNSPolicyReconciler) reconcileGatewayDNSRecords(ctx context.Context, gateway *gatewayapiv1.Gateway, dnsPolicy *v1alpha1.DNSPolicy) error {
func (r *DNSPolicyReconciler) reconcileGatewayDNSRecords(ctx context.Context, gw *gatewayapiv1.Gateway, dnsPolicy *v1alpha1.DNSPolicy) error {
log := crlog.FromContext(ctx)

if err := r.dnsHelper.removeDNSForDeletedListeners(ctx, gateway); err != nil {
gatewayWrapper := utils.NewGatewayWrapper(gw)
if err := gatewayWrapper.Validate(); err != nil {
return err
}
mikenairn marked this conversation as resolved.
Show resolved Hide resolved

if err := r.dnsHelper.removeDNSForDeletedListeners(ctx, gatewayWrapper.Gateway); err != nil {
log.V(3).Info("error removing DNS for deleted listeners")
return err
}

clusterGatewayAddresses := getClusterGatewayAddresses(gateway)
clusterGatewayAddresses := gatewayWrapper.GetClusterGatewayAddresses()

log.V(3).Info("checking gateway for attached routes ", "gateway", gateway.Name, "clusters", clusterGatewayAddresses)
log.V(3).Info("checking gateway for attached routes ", "gateway", gatewayWrapper.Name, "clusters", clusterGatewayAddresses)

for _, listener := range gateway.Spec.Listeners {
for _, listener := range gatewayWrapper.Spec.Listeners {
var clusterGateways []dns.ClusterGateway
var mz, err = r.dnsHelper.getManagedZoneForListener(ctx, gateway.Namespace, listener)
var mz, err = r.dnsHelper.getManagedZoneForListener(ctx, gatewayWrapper.Namespace, listener)
if err != nil {
return err
}
listenerHost := *listener.Hostname
if listenerHost == "" {
log.Info("skipping listener no hostname assigned", listener.Name, "in ns ", gateway.Namespace)
log.Info("skipping listener no hostname assigned", listener.Name, "in ns ", gatewayWrapper.Namespace)
continue
}
for clusterName, gatewayAddresses := range clusterGatewayAddresses {
// Only consider host for dns if there's at least 1 attached route to the listener for this host in *any* gateway

log.V(3).Info("checking downstream", "listener ", listener.Name)
attached := listenerTotalAttachedRoutes(gateway, clusterName, listener, gatewayAddresses)
attached := gatewayWrapper.ListenerTotalAttachedRoutes(clusterName, listener)

if attached == 0 {
log.V(1).Info("no attached routes for ", "listener", listener, "cluster ", clusterName)
continue
}
log.V(3).Info("hostHasAttachedRoutes", "host", listener.Name, "hostHasAttachedRoutes", attached)

cg, err := r.buildClusterGateway(ctx, clusterName, gatewayAddresses, gateway)
cg, err := r.buildClusterGateway(ctx, clusterName, gatewayAddresses, gatewayWrapper.Gateway)
if err != nil {
return fmt.Errorf("get cluster gateway failed: %s", err)
}
Expand All @@ -91,23 +91,23 @@ func (r *DNSPolicyReconciler) reconcileGatewayDNSRecords(ctx context.Context, ga
if len(clusterGateways) == 0 {
// delete record
log.V(3).Info("no cluster gateways, deleting DNS record", " for listener ", listener.Name)
if err := r.dnsHelper.deleteDNSRecordForListener(ctx, gateway, listener); client.IgnoreNotFound(err) != nil {
if err := r.dnsHelper.deleteDNSRecordForListener(ctx, gatewayWrapper, listener); client.IgnoreNotFound(err) != nil {
return fmt.Errorf("failed to delete dns record for listener %s : %s", listener.Name, err)
}
return nil
}
dnsRecord, err := r.dnsHelper.createDNSRecordForListener(ctx, gateway, dnsPolicy, mz, listener)
dnsRecord, err := r.dnsHelper.createDNSRecordForListener(ctx, gatewayWrapper.Gateway, dnsPolicy, mz, listener)
if err := client.IgnoreAlreadyExists(err); err != nil {
return fmt.Errorf("failed to create dns record for listener host %s : %s ", *listener.Hostname, err)
}
if k8serrors.IsAlreadyExists(err) {
dnsRecord, err = r.dnsHelper.getDNSRecordForListener(ctx, listener, gateway)
dnsRecord, err = r.dnsHelper.getDNSRecordForListener(ctx, listener, gatewayWrapper)
if err != nil {
return fmt.Errorf("failed to get dns record for host %s : %s ", listener.Name, err)
}
}

mcgTarget, err := dns.NewMultiClusterGatewayTarget(gateway, clusterGateways, dnsPolicy.Spec.LoadBalancing)
mcgTarget, err := dns.NewMultiClusterGatewayTarget(gatewayWrapper.Gateway, clusterGateways, dnsPolicy.Spec.LoadBalancing)
if err != nil {
return fmt.Errorf("failed to create multi cluster gateway target for listener %s : %s ", listener.Name, err)
}
Expand Down Expand Up @@ -156,7 +156,7 @@ func (r *DNSPolicyReconciler) buildClusterGateway(ctx context.Context, clusterNa
singleClusterAddresses := make([]gatewayapiv1.GatewayAddress, len(gatewayAddresses))

var metaObj client.Object
if clusterName != singleCluster {
if clusterName != utils.SingleClusterNameValue {
mc := &clusterv1.ManagedCluster{}
if err := r.Client().Get(ctx, client.ObjectKey{Name: clusterName}, mc, &client.GetOptions{}); err != nil {
return target, err
Expand All @@ -167,13 +167,7 @@ func (r *DNSPolicyReconciler) buildClusterGateway(ctx context.Context, clusterNa
}

for i, addr := range gatewayAddresses {
addrType := *addr.Type
if addrType == gateway.MultiClusterHostnameAddressType {
addrType = gatewayapiv1.HostnameAddressType
}
if addrType == gateway.MultiClusterIPAddressType {
addrType = gatewayapiv1.IPAddressType
}
addrType, _ := utils.AddressTypeToSingleCluster(addr)

singleClusterAddresses[i] = gatewayapiv1.GatewayAddress{
Type: &addrType,
Expand All @@ -184,56 +178,3 @@ func (r *DNSPolicyReconciler) buildClusterGateway(ctx context.Context, clusterNa

return target, nil
}

func getClusterGatewayAddresses(gw *gatewayapiv1.Gateway) map[string][]gatewayapiv1.GatewayAddress {
clusterAddrs := make(map[string][]gatewayapiv1.GatewayAddress, len(gw.Status.Addresses))

for _, address := range gw.Status.Addresses {
//Default to Single Cluster (Normal Gateway Status)
cluster := singleCluster
addressValue := address.Value

//Check for Multi Cluster (MGC Gateway Status)
if *address.Type == gateway.MultiClusterIPAddressType || *address.Type == gateway.MultiClusterHostnameAddressType {
tmpCluster, tmpAddress, found := strings.Cut(address.Value, "/")
//If this fails something is wrong and the value hasn't been set correctly
if found {
cluster = tmpCluster
addressValue = tmpAddress
}
}

if _, ok := clusterAddrs[cluster]; !ok {
clusterAddrs[cluster] = []gatewayapiv1.GatewayAddress{}
}

clusterAddrs[cluster] = append(clusterAddrs[cluster], gatewayapiv1.GatewayAddress{
Type: address.Type,
Value: addressValue,
})
}

return clusterAddrs
}

func listenerTotalAttachedRoutes(upstreamGateway *gatewayapiv1.Gateway, downstreamCluster string, specListener gatewayapiv1.Listener, addresses []gatewayapiv1.GatewayAddress) int {
for _, statusListener := range upstreamGateway.Status.Listeners {
// assuming all adresses of the same type on the gateway
// for Multi Cluster (MGC Gateway Status)
if *addresses[0].Type == gateway.MultiClusterIPAddressType || *addresses[0].Type == gateway.MultiClusterHostnameAddressType {
clusterName, listenerName, found := strings.Cut(string(statusListener.Name), ".")
if !found {
return 0
}
if clusterName == downstreamCluster && listenerName == string(specListener.Name) {
return int(statusListener.AttachedRoutes)
}
}
// Single Cluster (Normal Gateway Status)
if string(statusListener.Name) == string(specListener.Name) {
return int(statusListener.AttachedRoutes)
}
}

return 0
}
19 changes: 7 additions & 12 deletions pkg/controllers/gateway/gateway_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -51,15 +51,14 @@ import (
"github.com/Kuadrant/multicluster-gateway-controller/pkg/_internal/slice"
"github.com/Kuadrant/multicluster-gateway-controller/pkg/dns"
"github.com/Kuadrant/multicluster-gateway-controller/pkg/policysync"
"github.com/Kuadrant/multicluster-gateway-controller/pkg/utils"
)

const (
GatewayClusterLabelSelectorAnnotation = "kuadrant.io/gateway-cluster-label-selector"
GatewayClustersAnnotation = "kuadrant.io/gateway-clusters"
GatewayFinalizer = "kuadrant.io/gateway"
ManagedLabel = "kuadrant.io/managed"
MultiClusterIPAddressType gatewayapiv1.AddressType = "kuadrant.io/MultiClusterIPAddress"
MultiClusterHostnameAddressType gatewayapiv1.AddressType = "kuadrant.io/MultiClusterHostnameAddress"
GatewayClusterLabelSelectorAnnotation = "kuadrant.io/gateway-cluster-label-selector"
GatewayClustersAnnotation = "kuadrant.io/gateway-clusters"
GatewayFinalizer = "kuadrant.io/gateway"
ManagedLabel = "kuadrant.io/managed"
)

type GatewayPlacer interface {
Expand Down Expand Up @@ -214,12 +213,8 @@ func (r *GatewayReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ct
}
for _, address := range addresses {
log.V(3).Info("checking address type for mapping", "address.Type", address.Type)
var addressType gatewayapiv1.AddressType
if *address.Type == gatewayapiv1.IPAddressType {
addressType = MultiClusterIPAddressType
} else if *address.Type == gatewayapiv1.HostnameAddressType {
addressType = MultiClusterHostnameAddressType
} else {
addressType, supported := utils.AddressTypeToMultiCluster(address)
if !supported {
continue // ignore address type gatewayapiv1.NamedAddressType. Unsupported for multi cluster gateway
}
allAddresses = append(allAddresses, gatewayapiv1.GatewayStatusAddress{
Expand Down
19 changes: 0 additions & 19 deletions pkg/dns/fake/service.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import (

"github.com/Kuadrant/multicluster-gateway-controller/pkg/apis/v1alpha1"
. "github.com/Kuadrant/multicluster-gateway-controller/pkg/dns"
"github.com/Kuadrant/multicluster-gateway-controller/pkg/traffic"
. "github.com/Kuadrant/multicluster-gateway-controller/test/util"
)

Expand All @@ -27,14 +26,6 @@ func (h *FakeHostService) SetEndpoints(_ context.Context, _ *MultiClusterGateway
return nil
}

func (h *FakeHostService) GetDNSRecordsFor(_ context.Context, _ traffic.Interface) ([]*v1alpha1.DNSRecord, error) {
return nil, nil
}

func (h *FakeHostService) CleanupDNSRecords(_ context.Context, _ traffic.Interface) error {
return nil
}

func (h *FakeHostService) CreateDNSRecord(_ context.Context, subDomain string, _ *v1alpha1.ManagedZone, _ metav1.Object) (*v1alpha1.DNSRecord, error) {
if subDomain == Cluster {
return nil, fmt.Errorf(FailCreateDNSSubdomain)
Expand All @@ -59,13 +50,3 @@ func (h *FakeHostService) GetDNSRecord(ctx context.Context, subDomain string, ma
}
return record, nil
}

func (h *FakeHostService) AddEndpoints(_ context.Context, gateway traffic.Interface, _ *v1alpha1.DNSRecord) error {
hosts := gateway.GetHosts()
for _, host := range hosts {
if host == FailEndpointsHostname {
return fmt.Errorf(FailEndpointsHostname)
}
}
return nil
}
124 changes: 0 additions & 124 deletions pkg/traffic/gateway.go

This file was deleted.

Loading
Loading