I believe that I must create multiple Ingress
resources to achieve the desired effect, but must ask, is it possible to have multiple rewrite annotations with nginx (community) controller for the same host?
I have the following, but it won't work, as I understand it, because there is no way to link the rewrite rule to the path explicitly. In this case, I suppose it could use the fact that there are different numbers of capture groups, but that wouldn't always be the case.
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: api-ingress
annotations:
kubernetes.io/ingress.class: nginx
nginx.ingress.kubernetes.io/rewrite-target: https://staging.example.com/keyword-lnk/badnewsbears/$1/$2
nginx.ingress.kubernetes.io/rewrite-target: https://staging.example.com/lnk/$2
certmanager.k8s.io/cluster-issuer: staging-letsencrypt-prod
spec:
rules:
- host: staging.example.com
http:
paths:
- path: /
backend:
serviceName: api-service
servicePort: http
- host: badnewsbears.example.com
http:
paths:
- backend:
serviceName: api-service
servicePort: http
path: ^(/a/)(.*)$
- backend:
serviceName: api-service
servicePort: http
path: ^/([tbc])/(.*)
tls:
- hosts:
- staging.example.com
- badnewsbears.example.com
secretName: letsencrypt-prod-issuer-account-key
# ^ must be set to the key matching the annotation
# certmanager.k8s.io/cluster-issuer above
The goal is to have requests to staging.example.com
not have rewrites, but requests to badnewsbears.example.com/t/soup
rewrite to https://staging.example.com/keyword-lnk/badnewsbears/t/soup
, while badnewsbears.example.com/a/soup
yields https://staging.example.com/lnk/$2
Is there a way to specify a mapping of rewrite target->path in the Ingress
(or elsewhere), or will I have to separate out the different rewrite rules for the same host into different
TL;DR; you're not really meant to be able to configure multiple rewrites for the kubernetes/ingress-nginx controller type. Although it is possible to hack this together in a limited fashion using regex based rewrites with capture groups, as explained in this answer I posted to How to proxy_pass with nginx-ingress? .
Hope this helps.
You can create multiple ingresses with the same host and different path applying the annotation. So that would be the solution you suspected in the first place.
You could consider trying Nginx Plus based Ingress.
To configure URI rewriting you need to add the
nginx.org/rewrites
annotation to your Ingress resource definition. The annotation syntax is as follows:
nginx.org/rewrites: "serviceName=service1 rewrite=rewrite1[;serviceName=service2 rewrite=rewrite2;...]"
Here is the official example.
Please let me know if that helped.