Ingress Configuration
HTTPS Backend
Traffic Management
Network Security
Kubernetes

how to configure ingress to direct traffic to an https backend using https

Master System Design with Codemia

Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.

Introduction

Sending traffic from an Ingress controller to an HTTPS backend is usually a re-encryption configuration, not just a normal route rule. The exact YAML depends on the controller, but the core idea is always the same: terminate or accept TLS at the edge, then tell the controller to use HTTPS when proxying to the service.

Understand the Three Common TLS Patterns

Before writing YAML, decide which pattern you actually want:

  1. TLS termination at the ingress, then HTTP to the backend.
  2. TLS termination at the ingress, then HTTPS to the backend.
  3. TLS passthrough all the way to the backend.

This article is about the second case. The ingress still proxies the request, but it speaks HTTPS to the service behind it.

That is different from pure passthrough, where the ingress does not terminate TLS for normal HTTP routing logic.

NGINX Ingress Re-Encryption Example

With the NGINX ingress controller, the key annotation is usually:

yaml
nginx.ingress.kubernetes.io/backend-protocol: "HTTPS"

Example:

yaml
1apiVersion: networking.k8s.io/v1
2kind: Ingress
3metadata:
4  name: secure-app
5  annotations:
6    nginx.ingress.kubernetes.io/backend-protocol: "HTTPS"
7spec:
8  ingressClassName: nginx
9  tls:
10    - hosts:
11        - app.example.com
12      secretName: app-example-com-tls
13  rules:
14    - host: app.example.com
15      http:
16        paths:
17          - path: /
18            pathType: Prefix
19            backend:
20              service:
21                name: secure-app-svc
22                port:
23                  number: 443

And the service should target the pod port that actually serves HTTPS.

yaml
1apiVersion: v1
2kind: Service
3metadata:
4  name: secure-app-svc
5spec:
6  selector:
7    app: secure-app
8  ports:
9    - port: 443
10      targetPort: 8443

Without the backend-protocol annotation, the ingress controller may still try plain HTTP to the service and fail with TLS handshake or upstream protocol errors.

When You Need TLS Passthrough Instead

If the backend must receive the original TLS session and do its own certificate handling, you may need TLS passthrough rather than re-encryption.

For NGINX ingress, passthrough is a different mode and typically uses:

yaml
nginx.ingress.kubernetes.io/ssl-passthrough: "true"

But this comes with tradeoffs:

  • fewer HTTP-layer routing features
  • different controller requirements
  • less visibility into HTTP details at the ingress layer

Use passthrough only when you specifically need end-to-end TLS termination at the application.

Backend Certificates and Trust

If the backend serves HTTPS with a self-signed or internal certificate, the ingress controller may not trust it by default. In that case, routing fails even though the annotation is correct.

Controller-specific trust configuration may be required, such as:

  • mounting a CA bundle
  • configuring proxy SSL trust settings
  • using a controller-specific secret annotation

Do not assume "backend uses HTTPS" is enough. The ingress must also trust the backend certificate chain if certificate validation is enabled.

Common Failure Symptoms

Misconfiguration usually shows up as:

  • '502 Bad Gateway'
  • upstream TLS handshake failures
  • backend connection reset errors
  • requests hanging because the controller and backend disagree on protocol

The two fastest checks are:

  1. verify the service port actually serves HTTPS
  2. verify the ingress annotation matches the controller you use

A useful pod-level test:

bash
kubectl run curlbox --rm -it --image=curlimages/curl -- sh
curl -vk https://secure-app-svc.default.svc.cluster.local:443/

If that fails from inside the cluster, the backend is not ready for HTTPS traffic regardless of the ingress config.

Controller-Specific Behavior Matters

Do not copy annotations blindly between ingress controllers. NGINX, Traefik, HAProxy, AWS Load Balancer Controller, and others use different configuration models.

The generic Kubernetes Ingress resource does not define "HTTPS to backend" as a universal field. That behavior is usually implemented through controller-specific annotations or custom resources.

So the reliable approach is:

  • identify the ingress controller
  • use the controller's documented annotation or CRD
  • test inside the cluster and through the ingress endpoint

Common Pitfalls

  • Assuming TLS at the ingress automatically means TLS to the backend.
  • Using the wrong annotation for the installed ingress controller.
  • Pointing the ingress at a service port that actually serves plain HTTP.
  • Confusing re-encryption with TLS passthrough.
  • Forgetting backend certificate trust requirements for internal or self-signed certs.

Summary

  • HTTPS to the backend is usually configured as ingress re-encryption.
  • For NGINX ingress, the usual key is nginx.ingress.kubernetes.io/backend-protocol: "HTTPS".
  • Make sure the service port really serves HTTPS, not plain HTTP.
  • Use TLS passthrough only when you need the backend to terminate the original TLS session.
  • Always validate the setup from inside the cluster as well as through the external ingress hostname.

Course illustration
Course illustration

All Rights Reserved.