Exposing TCP and UDP services from NGINX Ingress Controller - The Easy Way

This is something that I encounter on exposing one of our services (Redis) to the public from a Kubernetes that has an NGINX ingress controller. By default ingress doesn't support TCP or UDP services. Thus we should tweak something in order for our ingress controller will expose and redirect incoming tcp connection to the appropriate service.

First thing first:

We have a Service Object for Redis like so:

kind: Service
apiVersion: v1
metadata:
  name: redis
  namespace: my-namespace
  labels:
    app: redis
spec:
  ports:
    - port: 6379
  selector:
    app: redis

Now, as for NGINX Ingress Controller, it uses a config map to store the key mapping of exposed services for both TCP and UDP services. namely tcp-services and udp-services respectively. They both live in the namespace ingress-nginx.

Both config maps are empty initially, thus editing it on the fly works fine.

$ KUBE_EDITOR="nano" kubectl edit cm -n ingress-nginx tcp-services

add a data below the key value "data"

...
apiVersion: v1
data:
  "6379": my-namespace/redis:6379
...
# Remaining config left out for simplicity. 

So we basically are saying if the exposed controller got an incoming connection from port 6379, it'll automatically forward it to a service called redis found on a namespace called my-namespace of port 6379.

Finally, we gotta update the service (ingress-nginx) responsible to expose port 6379 to the public.

$ KUBE_EDITOR="nano" kubectl edit svc -n ingress-nginx ingress-nginx

And add a config under the key-value called ports:

- name: redis
  port: 6379
  targetPort: 6379
  protocol: TCP

And that's all. We're done. Remember that this is also applicable to UDP services. you may now see your svc has an exposed port number of 6379 using:

$ kubectl get svc -n ingress-nginx

And you'll be getting something like this (check the port included there).

NAME            TYPE           CLUSTER-IP     EXTERNAL-IP     PORT(S)                                     AGE
ingress-nginx   LoadBalancer   10.245.34.35   x.x.x.x   80:32342/TCP,443:30319/TCP,6379:30506/TCP   702d

It's super easy right?