github.com/cilium/cilium@v1.16.2/operator/pkg/ingress/helpers.go (about)

     1  // SPDX-License-Identifier: Apache-2.0
     2  // Copyright Authors of Cilium
     3  
     4  package ingress
     5  
     6  import (
     7  	"context"
     8  	"fmt"
     9  	"strconv"
    10  
    11  	"github.com/sirupsen/logrus"
    12  	networkingv1 "k8s.io/api/networking/v1"
    13  	"k8s.io/apimachinery/pkg/api/errors"
    14  	"k8s.io/apimachinery/pkg/types"
    15  	"sigs.k8s.io/controller-runtime/pkg/client"
    16  )
    17  
    18  func isCiliumManagedIngress(ctx context.Context, c client.Client, logger logrus.FieldLogger, ing networkingv1.Ingress) bool {
    19  	ingressClassName := ingressClassName(ing)
    20  
    21  	if ingressClassName != nil && *ingressClassName == ciliumIngressClassName {
    22  		return true
    23  	}
    24  
    25  	// Check for default Ingress class
    26  	return (ingressClassName == nil || *ingressClassName == "") && isCiliumDefaultIngressController(ctx, c, logger)
    27  }
    28  
    29  func isCiliumDefaultIngressController(ctx context.Context, c client.Client, logger logrus.FieldLogger) bool {
    30  	ciliumIngressClass := &networkingv1.IngressClass{}
    31  	if err := c.Get(ctx, types.NamespacedName{Name: ciliumIngressClassName}, ciliumIngressClass); err != nil {
    32  		if !errors.IsNotFound(err) {
    33  			logger.WithError(err).Warn("Failed to load Cilium IngressClass")
    34  		}
    35  
    36  		return false
    37  	}
    38  
    39  	isDefault, err := isIngressClassMarkedAsDefault(*ciliumIngressClass)
    40  	if err != nil {
    41  		logger.WithError(err).Warn("Failed to detect default class on IngressClass cilium")
    42  		return false
    43  	}
    44  
    45  	return isDefault
    46  }
    47  
    48  func ingressClassName(ingress networkingv1.Ingress) *string {
    49  	annotations := ingress.GetAnnotations()
    50  	if className, ok := annotations["kubernetes.io/ingress.class"]; ok {
    51  		return &className
    52  	}
    53  
    54  	return ingress.Spec.IngressClassName
    55  }
    56  
    57  // isIngressClassMarkedDefault determines if the given IngressClass has an annotation marking it as the
    58  // default IngressClass for the cluster.
    59  // If the annotation's value fails to parse, then an error is returned to signal that processing the
    60  // IngressClass should be retried at a later point in time.
    61  // There are four possible cases:
    62  // 1. Annotation is set to "true": we are the default IngressClass.
    63  // 2. Annotation is set to "false", a non-bool value, or is missing: we are not the default IngressClass.
    64  func isIngressClassMarkedAsDefault(obj networkingv1.IngressClass) (bool, error) {
    65  	if val, ok := obj.GetAnnotations()[networkingv1.AnnotationIsDefaultIngressClass]; ok {
    66  		isDefault, err := strconv.ParseBool(val)
    67  		if err != nil {
    68  			return false, fmt.Errorf("failed to parse annotation value for %q: %w", networkingv1.AnnotationIsDefaultIngressClass, err)
    69  		}
    70  
    71  		return isDefault, nil
    72  	}
    73  
    74  	// If the annotation is not set, or set to an improper value,
    75  	// we should not be the default ingress class.
    76  	return false, nil
    77  }