Configuring Kubernetes ingress with a wildcard DNS certificate, single TLS secret and applications in multiple namespaces


An organisation wanted to deploy each application into a separate Kubernetes namespace. Each application will be available at a subdomain of, via a wildcard DNS entry of * pointing to the ingress controller’s service IP address. A single wildcard TLS certificate ( * ) will be used to protect all applications using the ingress controller. It was desired that only a single TLS secret should exist on the cluster to facilitate certificate renewal.


  1. Kubernetes secrets are only accessible from the namespace in which they are created.

    We discussed having a single namespace with all ingress resources and the secret, however still keep each application’s services and deployments in separate namespaces.

  2. nginx Ingress resources can only route to backend services within their own namespace.

    Looked at which can route to other namespaces, however this creates a new IP address for each application, which is not compatible with using a wildcard DNS name.

Another potential solution was was to use an service of type ExternalName to route traffic to the other namespace. Here’s how this worked:


Install ingress controller into an ingress namespace

helm install --namespace ingress --name ingress stable/nginx-ingress --set rbac.create=false --set rbac.createRole=false --set rbac.createClusterRole=false

Create TLS secret in ingress Namespace

As this was not a live deployment we created a self signed wildcard certificate. In production a certificate would be acquired from a trusted certification authority:

openssl req -new -x509 -keyout -out -days 365 -nodes -key

Then create a secret using that certificate:

kubectl create secret tls wildcard-example-com --key --cert  -n ingress

Create Helm Chart

Run the following command to create a new Helm chart in a directory named sample-app:

helm create sample-app

Add External Service

Added a service-ingress.yaml file to the Helm chart templates directory to create a service of type ExternalName that deploys into the ingress namespace:

{{- $fullName := include "sampleapp.fullname" . -}}
apiVersion: v1
kind: Service
  name: {{ $fullName }}
  namespace: ingress
  - name: http
    port: 80
  type: ExternalName
  externalName: {{ $fullName }}.{{ .Release.Namespace }}

Configure Ingress resource to deploy into the Ingress namespace

Specified a namespace to deploy the Ingress resource to by modifying the ingress.yaml file

  name: {{ $fullName }}
  namespace:  ingress

Update the helm chart values.yaml

Specify image:

  repository: marrobi/linuxwebsite
  tag: latest
  pullPolicy: Always

Specify TLS settings:

    - secretName:  wildcard-example-com

Deploy sample application

Deploy application into a new namespace called sample:

helm upgrade --install sample ./sample-app/ --namespace sample

Create DNS name

Retrieve the ingress controller’s IP address:

kubectl get service -n ingress

Record the EXTERNAL-IP of the ingress controller:

NAME                                    CLUSTER-IP     EXTERNAL-IP               PORT(S)                      AGE
ingress-nginx-ingress-controller            80:32164/TCP,443:32638/TCP   11m
ingress-nginx-ingress-default-backend   <none>                    80/TCP                       11m
sample-sampleapp                                       sample-sampleapp.sample   80/TCP                       32s

For testing purposes I added a entry to the hosts file on my local machine, in the real world this would be an A record with your public DNS provider:

Test the solution

Navigate to in a browser:

This solution works, however there may be other, "better" solutions. Do let me know if you a have an alternative solution.

1 Comment

  1. Mikael Morvan


    I'm wondering If you could give access to all the files involved in your sample. Sometimes, it's not clear between the "service.yml" or the "app.yml".

    Thank you


Leave a Comment

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.