This is an automated email from the ASF dual-hosted git repository.

alinsran pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/apisix-ingress-controller.git


The following commit(s) were added to refs/heads/master by this push:
     new 18882b92 fix(ingress): port.name matching failure for ExternalName 
Services (#2604)
18882b92 is described below

commit 18882b928a4679a85ba18e242f90e6c48151961c
Author: AlinsRan <[email protected]>
AuthorDate: Thu Oct 16 18:12:36 2025 +0800

    fix(ingress): port.name matching failure for ExternalName Services (#2604)
---
 internal/adc/translator/ingress.go | 45 ++++++++++++----------------------
 test/e2e/ingress/ingress.go        | 50 ++++++++++++++++++++++++++++++++++++++
 test/e2e/scaffold/httpbin.go       |  4 +++
 3 files changed, 69 insertions(+), 30 deletions(-)

diff --git a/internal/adc/translator/ingress.go 
b/internal/adc/translator/ingress.go
index 50bd5bc4..1d2a4186 100644
--- a/internal/adc/translator/ingress.go
+++ b/internal/adc/translator/ingress.go
@@ -25,6 +25,7 @@ import (
        discoveryv1 "k8s.io/api/discovery/v1"
        networkingv1 "k8s.io/api/networking/v1"
        "k8s.io/apimachinery/pkg/types"
+       "k8s.io/apimachinery/pkg/util/intstr"
        "k8s.io/utils/ptr"
 
        adctypes "github.com/apache/apisix-ingress-controller/api/adc"
@@ -172,12 +173,11 @@ func (t *Translator) resolveIngressUpstream(
        t.AttachBackendTrafficPolicyToUpstream(backendRef, 
tctx.BackendTrafficPolicies, upstream)
        // determine service port/port name
        var protocol string
-       var servicePort int32 = 0
-       var servicePortName string
+       var port intstr.IntOrString
        if backendService.Port.Number != 0 {
-               servicePort = backendService.Port.Number
+               port = intstr.FromInt32(backendService.Port.Number)
        } else if backendService.Port.Name != "" {
-               servicePortName = backendService.Port.Name
+               port = intstr.FromString(backendService.Port.Name)
        }
 
        getService := tctx.Services[types.NamespacedName{
@@ -187,43 +187,28 @@ func (t *Translator) resolveIngressUpstream(
        if getService == nil {
                return protocol
        }
-
+       getServicePort, _ := findMatchingServicePort(getService, port)
+       if getServicePort != nil && getServicePort.AppProtocol != nil {
+               protocol = *getServicePort.AppProtocol
+               if upstream.Scheme == "" {
+                       upstream.Scheme = 
appProtocolToUpstreamScheme(*getServicePort.AppProtocol)
+               }
+       }
        if getService.Spec.Type == corev1.ServiceTypeExternalName {
-               defaultServicePort := 80
-               if servicePort > 0 {
-                       defaultServicePort = int(servicePort)
+               servicePort := 80
+               if getServicePort != nil {
+                       servicePort = int(getServicePort.Port)
                }
                upstream.Nodes = adctypes.UpstreamNodes{
                        {
                                Host:   getService.Spec.ExternalName,
-                               Port:   defaultServicePort,
+                               Port:   servicePort,
                                Weight: 1,
                        },
                }
                return protocol
        }
 
-       // find matching service port object
-       var getServicePort *corev1.ServicePort
-       for _, port := range getService.Spec.Ports {
-               p := port
-               if servicePort > 0 && p.Port == servicePort {
-                       getServicePort = &p
-                       break
-               }
-               if servicePortName != "" && p.Name == servicePortName {
-                       getServicePort = &p
-                       break
-               }
-       }
-
-       if getServicePort != nil && getServicePort.AppProtocol != nil {
-               protocol = *getServicePort.AppProtocol
-               if upstream.Scheme == "" {
-                       upstream.Scheme = 
appProtocolToUpstreamScheme(*getServicePort.AppProtocol)
-               }
-       }
-
        endpointSlices := tctx.EndpointSlices[types.NamespacedName{
                Namespace: obj.Namespace,
                Name:      backendService.Name,
diff --git a/test/e2e/ingress/ingress.go b/test/e2e/ingress/ingress.go
index 1e3e3a50..f8faccb0 100644
--- a/test/e2e/ingress/ingress.go
+++ b/test/e2e/ingress/ingress.go
@@ -227,6 +227,36 @@ spec:
             name: httpbin-external-domain
             port:
               number: 80
+`
+               var ingressWithExternalNamePortName = `
+apiVersion: v1
+kind: Service
+metadata:
+  name: httpbin-external-domain
+spec:
+  type: ExternalName
+  externalName: httpbin-service-e2e-test
+  ports:
+  - name: http
+    port: 8080
+    protocol: TCP
+---
+apiVersion: networking.k8s.io/v1
+kind: Ingress
+metadata:
+  name: ingress-external-name-port-name
+spec:
+  rules:
+  - host: httpbin.external
+    http:
+      paths:
+      - path: /
+        pathType: Prefix
+        backend:
+          service:
+            name: httpbin-external-domain
+            port:
+              name: http
 `
                BeforeEach(func() {
                        By("create GatewayProxy")
@@ -294,6 +324,26 @@ spec:
                        })
                })
 
+               It("Mathch Service Port by Name", func() {
+                       By("create Ingress")
+                       err := 
s.CreateResourceFromString(ingressWithExternalNamePortName)
+                       Expect(err).NotTo(HaveOccurred(), "creating Ingress 
without IngressClass")
+
+                       By("checking the external service response")
+                       s.RequestAssert(&scaffold.RequestAssert{
+                               Method: "GET",
+                               Path:   "/get",
+                               Host:   "httpbin.external",
+                               Check:  
scaffold.WithExpectedStatus(http.StatusOK),
+                       })
+
+                       upstreams, err := 
s.DefaultDataplaneResource().Upstream().List(context.Background())
+                       Expect(err).NotTo(HaveOccurred(), "listing Upstream")
+                       Expect(upstreams).To(HaveLen(1), "the number of 
Upstream")
+                       Expect(upstreams[0].Nodes).To(HaveLen(1), "the number 
of Upstream nodes")
+                       Expect(upstreams[0].Nodes[0].Port).To(Equal(8080), "the 
port of Upstream node")
+               })
+
                It("Delete Ingress during restart", func() {
                        By("create Ingress with ExternalName")
                        ingressName := s.Namespace() + "-external"
diff --git a/test/e2e/scaffold/httpbin.go b/test/e2e/scaffold/httpbin.go
index 03a81007..e19528a4 100644
--- a/test/e2e/scaffold/httpbin.go
+++ b/test/e2e/scaffold/httpbin.go
@@ -89,6 +89,10 @@ spec:
       port: 80
       protocol: TCP
       targetPort: 80
+    - name: http-v2
+      port: 8080
+      protocol: TCP
+      targetPort: 80
   type: ClusterIP
 `
 )

Reply via email to