Skip to content

Commit 1071de1

Browse files
committed
add ingress class support
1 parent 03986db commit 1071de1

File tree

5 files changed

+429
-33
lines changed

5 files changed

+429
-33
lines changed

controllers/ingress/group_controller.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ func NewGroupReconciler(cloud aws.Cloud, k8sClient client.Client, eventRecorder
5252
stackDeployer := deploy.NewDefaultStackDeployer(cloud, k8sClient, networkingSGManager, networkingSGReconciler,
5353
config, ingressTagPrefix, logger)
5454
ingressConfig := config.IngressConfig
55-
groupLoader := ingress.NewDefaultGroupLoader(k8sClient, annotationParser, ingressConfig.IngressClass)
55+
groupLoader := ingress.NewDefaultGroupLoader(k8sClient, eventRecorder, annotationParser, ingressConfig.IngressClass)
5656
groupFinalizerManager := ingress.NewDefaultFinalizerManager(finalizerManager)
5757

5858
return &groupReconciler{

pkg/config/ingress_config.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ type IngressConfig struct {
1414
// Name of the Ingress class this controller satisfies
1515
// If empty, all Ingresses without ingress.class annotation, or ingress.class==alb get considered
1616
IngressClass string
17+
1718
// Max concurrent reconcile loops for Ingress objects
1819
MaxConcurrentReconciles int
1920
}

pkg/ingress/group_loader.go

Lines changed: 64 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,11 @@ package ingress
33
import (
44
"context"
55
"github.com/pkg/errors"
6+
corev1 "k8s.io/api/core/v1"
67
networking "k8s.io/api/networking/v1beta1"
8+
"k8s.io/apimachinery/pkg/types"
79
"k8s.io/apimachinery/pkg/util/sets"
10+
"k8s.io/client-go/tools/record"
811
"regexp"
912
"sigs.k8s.io/aws-load-balancer-controller/pkg/annotations"
1013
"sigs.k8s.io/aws-load-balancer-controller/pkg/k8s"
@@ -13,11 +16,13 @@ import (
1316
)
1417

1518
const (
16-
defaultGroupOrder int64 = 0
17-
minGroupOrder int64 = 1
18-
maxGroupOder int64 = 1000
19-
maxGroupNameLength int = 63
20-
defaultIngressClass = "alb"
19+
defaultGroupOrder int64 = 0
20+
minGroupOrder int64 = 1
21+
maxGroupOder int64 = 1000
22+
maxGroupNameLength int = 63
23+
ingressClassALB = "alb"
24+
// the controller name used in IngressClass for ALB.
25+
ingressClassControllerALB = "ingress.k8s.aws/alb"
2126
)
2227

2328
var (
@@ -36,9 +41,10 @@ type GroupLoader interface {
3641
}
3742

3843
// NewDefaultGroupLoader constructs new GroupLoader instance.
39-
func NewDefaultGroupLoader(client client.Client, annotationParser annotations.Parser, ingressClass string) *defaultGroupLoader {
44+
func NewDefaultGroupLoader(client client.Client, eventRecorder record.EventRecorder, annotationParser annotations.Parser, ingressClass string) *defaultGroupLoader {
4045
return &defaultGroupLoader{
4146
client: client,
47+
eventRecorder: eventRecorder,
4248
annotationParser: annotationParser,
4349
ingressClass: ingressClass,
4450
}
@@ -49,13 +55,18 @@ var _ GroupLoader = (*defaultGroupLoader)(nil)
4955
// default implementation for GroupLoader
5056
type defaultGroupLoader struct {
5157
client client.Client
58+
eventRecorder record.EventRecorder
5259
annotationParser annotations.Parser
5360

5461
ingressClass string
5562
}
5663

5764
func (m *defaultGroupLoader) FindGroupID(ctx context.Context, ing *networking.Ingress) (*GroupID, error) {
58-
if !m.matchesIngressClass(ing) {
65+
matchesIngressClass, err := m.matchesIngressClass(ctx, ing)
66+
if err != nil {
67+
return nil, err
68+
}
69+
if !matchesIngressClass {
5970
return nil, nil
6071
}
6172

@@ -85,7 +96,7 @@ func (m *defaultGroupLoader) Load(ctx context.Context, groupID GroupID) (Group,
8596
ing := &ingList.Items[index]
8697
isGroupMember, err := m.isGroupMember(ctx, groupID, ing)
8798
if err != nil {
88-
return Group{}, err
99+
return Group{}, errors.Wrapf(err, "ingress: %v", k8s.NamespacedName(ing))
89100
}
90101
if isGroupMember {
91102
members = append(members, ing)
@@ -104,13 +115,52 @@ func (m *defaultGroupLoader) Load(ctx context.Context, groupID GroupID) (Group,
104115
}, nil
105116
}
106117

107-
// matchesIngressClass tests whether Ingress matches ingress class of this group manager.
108-
func (m *defaultGroupLoader) matchesIngressClass(ing *networking.Ingress) bool {
109-
ingClass := ing.Annotations[annotations.IngressClass]
110-
if m.ingressClass == "" {
111-
return ingClass == "" || ingClass == defaultIngressClass
118+
// matchesIngressClass tests whether provided Ingress are matched by this group loader.
119+
func (m *defaultGroupLoader) matchesIngressClass(ctx context.Context, ing *networking.Ingress) (bool, error) {
120+
var matchesIngressClassResults []bool
121+
if ingClassAnnotation, exists := ing.Annotations[annotations.IngressClass]; exists {
122+
matchesIngressClass := m.matchesIngressClassAnnotation(ctx, ingClassAnnotation)
123+
matchesIngressClassResults = append(matchesIngressClassResults, matchesIngressClass)
124+
}
125+
126+
if ing.Spec.IngressClassName != nil {
127+
matchesIngressClass, err := m.matchesIngressClassName(ctx, *ing.Spec.IngressClassName)
128+
if err != nil {
129+
return false, err
130+
}
131+
matchesIngressClassResults = append(matchesIngressClassResults, matchesIngressClass)
132+
}
133+
134+
if len(matchesIngressClassResults) == 2 {
135+
if matchesIngressClassResults[0] != matchesIngressClassResults[1] {
136+
m.eventRecorder.Event(ing, corev1.EventTypeWarning, k8s.IngressEventReasonConflictIngressClass, "conflict IngressClass by `spec.IngressClass` and `kubernetes.io/ingress.class` annotation")
137+
}
138+
return matchesIngressClassResults[0], nil
139+
}
140+
if len(matchesIngressClassResults) == 1 {
141+
return matchesIngressClassResults[0], nil
142+
}
143+
144+
return m.ingressClass == "", nil
145+
}
146+
147+
// matchesIngressClassAnnotation tests whether provided ingClassAnnotation are matched by this group loader.
148+
func (m *defaultGroupLoader) matchesIngressClassAnnotation(_ context.Context, ingClassAnnotation string) bool {
149+
if m.ingressClass == "" && ingClassAnnotation == ingressClassALB {
150+
return true
151+
}
152+
return ingClassAnnotation == m.ingressClass
153+
}
154+
155+
// matchesIngressClassName tests whether provided ingClassName are matched by this group loader.
156+
func (m *defaultGroupLoader) matchesIngressClassName(ctx context.Context, ingClassName string) (bool, error) {
157+
ingClassKey := types.NamespacedName{Name: ingClassName}
158+
ingClass := &networking.IngressClass{}
159+
if err := m.client.Get(ctx, ingClassKey, ingClass); err != nil {
160+
return false, err
112161
}
113-
return ingClass == m.ingressClass
162+
matchesIngressClass := ingClass.Spec.Controller == ingressClassControllerALB
163+
return matchesIngressClass, nil
114164
}
115165

116166
// isGroupMember checks whether an ingress is member of a Ingress group

0 commit comments

Comments
 (0)