diff --git a/stable/traefik/Chart.yaml b/stable/traefik/Chart.yaml index 371f9fb7b7..2c29b95d93 100755 --- a/stable/traefik/Chart.yaml +++ b/stable/traefik/Chart.yaml @@ -1,7 +1,7 @@ apiVersion: v1 name: traefik -version: 1.18.2 -appVersion: 1.4.6 +version: 1.19.0 +appVersion: 1.5.1 description: A Traefik based Kubernetes ingress controller with Let's Encrypt support keywords: - traefik diff --git a/stable/traefik/README.md b/stable/traefik/README.md index da55c780a8..da8f668e7a 100644 --- a/stable/traefik/README.md +++ b/stable/traefik/README.md @@ -106,6 +106,9 @@ The following tables lists the configurable parameters of the Traefik chart and | `ssl.defaultCert` | Base64 encoded default certificate | A self-signed certificate | | `ssl.defaultKey` | Base64 encoded private key for the certificate above | The private key for the certificate above | | `acme.enabled` | Whether to use Let's Encrypt to obtain certificates | `false` | +| `acme.challengeType` | Type of ACME challenge to perform domain validation. `tls-sni-01` or `dns-01` | `tls-sni-01` | +| `acme.dnsProvider.name` | Which DNS provider to use. See [here](https://github.com/xenolf/lego/tree/master/providers/dns) for the list of possible values. | `nil` | +| `acme.dnsProvider.$name` | The configuration environment variables (encoded as a secret) needed for the DNS provider to do DNS challenge. See [here](#example-aws-route-53). | `{}` | | `acme.email` | Email address to be used in certificates obtained from Let's Encrypt | `admin@example.com` | | `acme.staging` | Whether to get certs from Let's Encrypt's staging environment | `true` | | `acme.logging` | display debug log messages from the acme client library | `false` | @@ -188,6 +191,44 @@ dashboard: test: $apr1$H6uskkkW$IgXLP6ewTrSuBkTrqE8wj/ ``` +### Let's Encrypt domain verification using DNS challenge + +When obtaining an ACME (Let's Encrypt) certificate, sometimes it's more desirable to do DNS challenge, for example, if the +server you want to obtain a certificate for does not have a public IP address. + +First, check if your DNS provider is supported by [lego](https://github.com/xenolf/lego/tree/master/providers/dns)(the ACME library that Traefik is using). +Next, you will need to configure the Traefik chart to use DNS challenge. In the ACME section: + +```yaml +acme: + enabled: true + challengeType: "dns-01" + dnsProvider: + name: # name of the dns provider to use + $name: # the configuration of the dns provider. See the following section for an example + # variables that the specific dns provider requires +``` + +#### Example: AWS Route 53 + +Route 53 requires the [following configuration variables to be set](values.yaml#L98-L101): +- `AWS_ACCESS_KEY_ID` +- `AWS_SECRET_ACCESS_KEY` +- `AWS_REGION` + +The configuration for the DNS provider would look like this: + +```yaml +acme: + enabled: true + dnsProvider: + name: route53 + route53: + AWS_ACCESS_KEY_ID: ... + AWS_SECRET_ACCESS_KEY: ... + AWS_REGION: us-east-1 +``` + ### Proxy Protocol In situations where Traefik lives behind an Internet-facing loadbalancer (like an AWS ELB) and you still want it to see the actual source IP of the visitor instead of the internal IP of the loadbalancer, you can enable the loadbalancer to use the Proxy protocol to talk to Traefik. This effectively makes the loadbalancer transparant, as Traefik will still get the actual visitor IP address for each request. This only works if Traefik knows it's receiving traffic via the Proxy Protocol and the loadbalancer IP addresses need to be whitelisted as well. @@ -196,4 +237,4 @@ How to set this up on AWS is described in the Kubernetes documentation [here](ht **Caution** -If only one of the components (either the loadbalancer or traefik) is set to use the Proxy protocol and the other is not, this will break badly as they will not be able to communicate with each other. +If only one of the components (either the loadbalancer or traefik) is set to use the Proxy protocol and the other is not, this will break badly as they will not be able to communicate with each other. \ No newline at end of file diff --git a/stable/traefik/templates/configmap.yaml b/stable/traefik/templates/configmap.yaml index ec5e3be4b4..488dd35554 100644 --- a/stable/traefik/templates/configmap.yaml +++ b/stable/traefik/templates/configmap.yaml @@ -82,6 +82,10 @@ data: {{- if .Values.acme.logging }} acmeLogging = true {{- end }} + {{- if eq .Values.acme.challengeType "dns-01" }} + [acme.dnsChallenge] + provider = "{{ .Values.acme.dnsProvider.name }}" + {{- end }} {{- end }} {{- if or .Values.dashboard.enabled .Values.metrics.prometheus.enabled .Values.metrics.statsd.enabled .Values.metrics.datadog.enabled }} [web] diff --git a/stable/traefik/templates/deployment.yaml b/stable/traefik/templates/deployment.yaml index 9d77d17546..64af1a6e6d 100644 --- a/stable/traefik/templates/deployment.yaml +++ b/stable/traefik/templates/deployment.yaml @@ -64,6 +64,16 @@ spec: periodSeconds: 10 successThreshold: 1 timeoutSeconds: 2 + {{- if and .Values.acme.enabled (eq .Values.acme.challengeType "dns-01") .Values.acme.dnsProvider.name }} + env: + {{- range $k, $_ := (index .Values.acme.dnsProvider .Values.acme.dnsProvider.name) }} + - name: {{ $k }} + valueFrom: + secretKeyRef: + name: {{ template "fullname" $ }}-dnsprovider-config + key: {{ $k }} + {{- end }} + {{- end }} volumeMounts: - mountPath: /config name: config diff --git a/stable/traefik/templates/dns-provider-secret.yaml b/stable/traefik/templates/dns-provider-secret.yaml new file mode 100644 index 0000000000..d1bdfff3fb --- /dev/null +++ b/stable/traefik/templates/dns-provider-secret.yaml @@ -0,0 +1,16 @@ +{{- if and .Values.acme.enabled (eq .Values.acme.challengeType "dns-01") .Values.acme.dnsProvider.name }} +apiVersion: v1 +kind: Secret +metadata: + name: {{ template "fullname" . }}-dnsprovider-config + labels: + app: {{ template "fullname" . }} + chart: "{{ .Chart.Name }}-{{ .Chart.Version }}" + release: "{{ .Release.Name }}" + heritage: "{{ .Release.Service }}" +type: Opaque +data: +{{- range $k, $v := (index .Values.acme.dnsProvider .Values.acme.dnsProvider.name) }} + {{ $k }}: {{ $v | b64enc | quote }} +{{- end }} +{{- end }} diff --git a/stable/traefik/values.yaml b/stable/traefik/values.yaml index 996f42a808..c62d3af024 100644 --- a/stable/traefik/values.yaml +++ b/stable/traefik/values.yaml @@ -1,6 +1,6 @@ ## Default values for Traefik image: traefik -imageTag: 1.4.6 +imageTag: 1.5.1 ## can switch the service type to NodePort if required serviceType: LoadBalancer loadBalancerIP: @@ -39,6 +39,87 @@ acme: email: admin@example.com staging: true logging: false + ## ACME challenge type: "tls-sni-01" or "dns-01" + ## Note the chart's default of tls-sni-01 has been DEPRECATED and (except in + ## certain circumstances) DISABLED by Let's Encrypt. It remains as a default + ## value in this chart to preserve legacy behavior and avoid a breaking + ## change. Users of this chart should strongly consider making the switch to + ## the dns-01 challenge. + challengeType: tls-sni-01 + ## Configure dnsProvider to perform domain verification using dns challenge + ## Applicable only if using the dns-01 challenge type + dnsProvider: + name: nil + auroradns: + AURORA_USER_ID: "" + AURORA_KEY: "" + AURORA_ENDPOINT: "" + azure: + AZURE_CLIENT_ID: "" + AZURE_CLIENT_SECRET: "" + AZURE_SUBSCRIPTION_ID: "" + AZURE_TENANT_ID: "" + AZURE_RESOURCE_GROUP: "" + cloudflare: + CLOUDFLARE_EMAIL: "" + CLOUDFLARE_API_KEY: "" + digitalocean: + DO_AUTH_TOKEN: "" + dnsimple: + DNSIMPLE_OAUTH_TOKEN: "" + DNSIMPLE_BASE_URL: "" + dnsmadeeasy: + DNSMADEEASY_API_KEY: "" + DNSMADEEASY_API_SECRET: "" + DNSMADEEASY_SANDBOX: "" + dnspod: + DNSPOD_API_KEY: "" + dyn: + DYN_CUSTOMER_NAME: "" + DYN_USER_NAME: "" + DYN_PASSWORD: "" + exoscale: + EXOSCALE_API_KEY: "" + EXOSCALE_API_SECRET: "" + EXOSCALE_ENDPOINT: "" + gandi: + GANDI_API_KEY: "" + godaddy: + GODADDY_API_KEY: "" + GODADDY_API_SECRET: "" + gcloud: + GCE_PROJECT: "" + GCE_SERVICE_ACCOUNT_FILE: "" + linode: + LINODE_API_KEY: "" + namecheap: + NAMECHEAP_API_USER: "" + NAMECHEAP_API_KEY: "" + ns1: + NS1_API_KEY: "" + otc: + OTC_DOMAIN_NAME: "" + OTC_USER_NAME: "" + OTC_PASSWORD: "" + OTC_PROJECT_NAME: "" + OTC_IDENTITY_ENDPOINT: "" + pdns: + PDNS_API_URL: "" + rackspace: + RACKSPACE_USER: "" + RACKSPACE_API_KEY: "" + rfc2136: + RFC2136_NAMESERVER: "" + RFC2136_TSIG_ALGORITHM: "" + RFC2136_TSIG_KEY: "" + RFC2136_TSIG_SECRET: "" + RFC2136_TIMEOUT: "" + route53: + AWS_REGION: "" + AWS_ACCESS_KEY_ID: "" + AWS_SECRET_ACCESS_KEY: "" + vultr: + VULTR_API_KEY: "" ## Save ACME certs to a persistent volume. WARNING: If you do not do this, you will re-request ## certs every time a pod (re-)starts and you WILL be rate limited! persistence: