Nginx Ingress Rewrite Rule

kubernetesnginxnginx-ingressrewrite

I have a spring microservice running on k8s having 2 API URL's.

  1. First is /api/actuator for health check – running on port 9010
  2. Second is /api for all other api calls – running on port 9000

I have created ClusterIP service to expose them on respective Ports.

apiVersion: v1
kind: Service
metadata:
  name: myapp-svc
spec:
  ports:
  - name: main-port
    port: 80
    protocol: TCP
    targetPort: 9000
  - name: health-port
    port: 9010
    protocol: TCP
    targetPort: 9010
  selector:
    app: myapp

Now I want to create an Ingress on top of this Service which follows path based routing.

Any request like /myapp/api/actuator/anything should be rewritten as /api/actuator/anything (same what comes from original request).

For instance /myapp/api/actuator/health should be rewritten as /api/actuator/health`.

Any request like /myapp/api/anything should be rewritten as /api/anything (same what comes from original request).

For instance /myapp/api/v1/getID/{id} should be rewritten as /api/v1/getID/{id}.

I am facing difficulty in writing the rewrite rule for the same.
So far I could only come up with following rule as of now:

apiVersion: networking.k8s.io/v1beta1
kind: Ingress
metadata:
  name: gitops-lkart-api
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /api/$1
spec:
 rules:
  - http:
      paths:
      - path: /myapp/api/actuator/(.*)
        backend:
          serviceName: myapp-svc
          servicePort: 9010
  - http:
      paths:
      - path: /myapp/api/(.*)
        backend:
          serviceName: myapp-svc
          servicePort: 80

But this would only work for /api paths and not for actuator.

Please recommend what rule should be written to achieve this?

Best Answer

This should work:

apiVersion: networking.k8s.io/v1beta1
kind: Ingress
metadata:
  name: gitops-lkart-api-1
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /api/actuator/$1
spec:
 rules:
  - http:
      paths:
      - path: /myapp/api/actuator/(.*)
        backend:
          serviceName: myapp-svc
          servicePort: 9010

apiVersion: networking.k8s.io/v1beta1
kind: Ingress
metadata:
  name: gitops-lkart-api-2
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /api/$1
spec:
  - http:
      paths:
      - path: /myapp/api/(.*)
        backend:
          serviceName: myapp-svc
          servicePort: 80

You can create 2 independent ingresses.

If traffic hits on /myapp/api/actuator/anything it will be rewritten to /api/actuator/anything.

In other situation if traffic hits on /myapp/api/anything it will be rewritten to /api/anything.