1

I'm using ingress-nginx and getting infinite redirects when issuing a 302 redirect in my backend service.

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: main-ing
  namespace: default
  annotations:
    nginx.ingress.kubernetes.io/ssl-passthrough: "true"
spec:
  ingressClassName: nginx
  rules:
  - host: service.example.com
    http:
      paths:
      - pathType: Prefix
        path: /
        backend:
          service:
            name: prometheus-service
            port:
              number: 443
  - host: login.example.com
    http:
      paths:
      - pathType: Prefix
        path: /
        backend:
          service:
            name: authentication-grant-service
            port:
              number: 443

I hit https://service.example.com and if auth fails, I redirect to https://login.example.com, which somehow results in an infinite loop.

Additionally, I notice that the request actually just goes straight back into service.example.com and fails continuously in a loop.

func unauthorizedPage(logger *zap.Logger, w http.ResponseWriter, req *http.Request) {
    logger.Error("The user is not authorized to make this request - referring",
        zap.String("refer", req.Host+req.URL.Path))

    for name, values := range req.Header {
        for _, value := range values {
            fmt.Println(name, value)
        }
    }

    http.Redirect(w,
        req,
        "https://login.example.com",
        http.StatusFound)
}

Logs:

{"level":"error","ts":1658531352.658133,"caller":"proxy/proxy.go:30","msg":"The user is not authorized to make this request - referring","refer":"service.example.com/","....


{"level":"error","ts":1658531352.658133,"caller":"proxy/proxy.go:30","msg":"The user is not authorized to make this request - referring","refer":"login.example.com/","....

How is this even possible? If you notice in the logs above, first it shows the expected refer value, then it shows the refer for the login page, which shouldn't be possible since the login page has no relation to this service. This tells me it's some nginx issue.

Is this because it (internally) reaches out to my login service, fetches a response and it returns back through the service route again, validates, fails and that process just continues over and over again?

Attempted Fix

// unauthorizedPage is the default redirect page
func unauthorizedPage(logger *zap.Logger, w http.ResponseWriter, req *http.Request) {

    refer := req.Host + req.URL.Path
    if refer != "service.example.com/" {
        logger.Info("Not failing request since redundant", zap.String("refer", refer))
        return
    }

    logger.Error("The user is not authorized to make this request - referring",
        zap.String("refer", req.Host+req.URL.Path))

    for name, values := range req.Header {
        for _, value := range values {
            fmt.Println(name, value)
        }
    }

    http.Redirect(w,
        req,
        "https://login.example.com",
        http.StatusFound)
}

In this case, it doesn't fail and redirect on auth if the request is the login page, I just let it proxy through. However, in this case, I get a white page in my response.

Ryan
  • 1,102
  • 1
  • 15
  • 30
  • Does your 302 redirect have a TTL set by any chance? – Norbert Jul 22 '22 at 23:15
  • Not to my knowledge. Does the last paragraph of my question make any sense or is that not true? – Ryan Jul 22 '22 at 23:20
  • Yes, you certainly have to not refer when you are already on the root page of the application (the login page). White page: I think it is the return in the `if refer!=`. Why not write "if refer==loginpage" then render login page instead of the current if refer!="servicepage"? – Norbert Jul 22 '22 at 23:27
  • I can't write the inverse because rendering the login page requires an HTTP redirect (separate microservice). This issue I'm having is these redirects are causing infinite loops, which is what is really confusing to me. As for the white page, might be software bug on my part, testing change. – Ryan Jul 22 '22 at 23:30
  • Do you have a relevant part of the login microservice code? – Norbert Jul 22 '22 at 23:31
  • I can post, but I want to clarify one thing just in case it helps. I have 2 services. Login service and Example service. Example service has a container in front of it who is solely responsible for validating the auth token, if it fails, it performs the redirect above, which redirects to the auth service. It's the redirection that is causing this infinite loop. Am I not allowed to redirect like this behind a reverse proxy? – Ryan Jul 22 '22 at 23:39
  • Let us [continue this discussion in chat](https://chat.stackoverflow.com/rooms/246686/discussion-between-ryan-and-norbert-van-nobelen). – Ryan Jul 22 '22 at 23:41

0 Answers0