Force HTTPS with Traefik

12/27/2018

I am using traefik as ingress controller in a K8s cluster. I'd like to enforce all traffic via HTTPS.

It is a bit confusing the documentation because apparently there are different ways to do the same thing? Namely, I'd like to know what is the difference between these 2:

If I use K8s is enough to use general annotations or I still have to edit the TOML file?

I have tried to use traefik.ingress.kubernetes.io/redirect-entry-point: https but doesn't find the service so I guess something is missing in my config.

If I remove the above line then everything works but HTTP -> HTTPS is, of course, not working. When I place the line back it returns a 404.

FWIW, the ingress definition is as follows (with traefik redirecting to 404):

  - apiVersion: extensions/v1beta1
    kind: Ingress
    metadata:
      generation: 1
      name: rekover-ingress
      namespace: prod
      annotations:
        kubernetes.io/ingress.class: traefik
        traefik.ingress.kubernetes.io/frontend-entry-points: http, https
        traefik.ingress.kubernetes.io/redirect-entry-point: https
    spec:
      rules:
        - host: www.xxx.com
          http:
            paths:
              - backend:
                  serviceName: xxx-frontend
                  servicePort: 80

I have tried the very same configuration with nginx and changing to respective metadata and worked!. Below metadata used for nginx and Ingress:

nginx.ingress.kubernetes.io/force-ssl-redirect: "true"
kubernetes.io/ingress.class: nginx

For completeness, I copy-paste the service definition for both nginx and traefik. First one works as expected:

kind: Service
apiVersion: v1
metadata:
  name: ingress-nginx
  namespace: ingress-nginx
  labels:
    app.kubernetes.io/name: ingress-nginx
    app.kubernetes.io/part-of: ingress-nginx
  annotations:
    service.beta.kubernetes.io/aws-load-balancer-backend-protocol: http
    service.beta.kubernetes.io/aws-load-balancer-ssl-cert: arn:aws:acm:xxxx
    service.beta.kubernetes.io/aws-load-balancer-ssl-ports: https
spec:
  selector:
    app.kubernetes.io/name: ingress-nginx
    app.kubernetes.io/part-of: ingress-nginx
  ports:
    - name: http
      port: 80
      targetPort: http
    - name: https
      port: 443
      targetPort: http
  type: LoadBalancer
</code>
<code>
kind: Service
apiVersion: v1
metadata:
  name: traefik-ingress-service
  namespace: ingress-prod
  annotations:
    service.beta.kubernetes.io/aws-load-balancer-backend-protocol: http
    service.beta.kubernetes.io/aws-load-balancer-ssl-cert: arn:aws:acm:xxxx
    service.beta.kubernetes.io/aws-load-balancer-ssl-ports: https
spec:
  selector:
    k8s-app: traefik-ingress-lb
  ports:
    - name: http
      port: 80
      targetPort: http
      protocol: TCP
    - name: https
      port: 443
      targetPort: http
      protocol: TCP
  type: LoadBalancer
-- Oscar Perez
devops
kubernetes
traefik

2 Answers

12/28/2018

I give you the solution as valid because you provided a correct answer to the original question though the original question was badly formulated, my bad. I found a related question which answers my question and worked like a charm:

Unable to redirect from http to https behind AWS load balancer

What frustates me is that, for instance, with nginx is just enough to use metadata annotations to force redirect to ssl whereas with traefik you have to edit the TOML file (or at least I didnt find the equivalent annotation for the problem).

-- Oscar Perez
Source: StackOverflow

12/27/2018

The first one is the toml Traefik configuration file, that can be modified in Kubernetes through a ConfigMap or in the Traefik container itself, or in the Traefik container command line (depending on how you deployed the Traefik Ingress Controller).

The second is what is mostly used to manage the configuration in the Traefik Ingress Controller through the Ingress Kubernetes resource.

You didn't post your Ingress definition but most likely it doesn't have a way to handle HTTPS and that's why when you add the annotation it sends traffic to port 443 and Traefik returns a 404.

To handle HTTPS/TLS you would need to enable it first (Create a K8s cert secret, configure TLS in the Ingress, etc). Or this is another example on how to enable it using a ConfigMap.

-- Rico
Source: StackOverflow