Home

Awesome

ExternalDNS - Hetzner Webhook

⚠️ This software is experimental and NOT FIT FOR PRODUCTION USE!

🛈 NOTE: This Webhook was forked and modified from the IONOS Webhook to work with Hetzner. It also contains huge parts from DrBu7cher's Hetzner provider.

ExternalDNS is a Kubernetes add-on for automatically managing Domain Name System (DNS) records for Kubernetes services by using different DNS providers. By default, Kubernetes manages DNS records internally, but ExternalDNS takes this functionality a step further by delegating the management of DNS records to an external DNS provider such as this one. Therefore, the Hetzner webhook allows to manage your Hetzner domains inside your kubernetes cluster with ExternalDNS.

To use ExternalDNS with Hetzner, you need your Hetzner API token of the account managing your domains. For detailed technical instructions on how the Hetzner webhook is deployed using the Bitnami Helm charts for ExternalDNS, seedeployment instructions.

Kubernetes Deployment

The Hetzner webhook is provided as a regular Open Container Initiative (OCI) image released in the GitHub container registry. The deployment can be performed in every way Kubernetes supports. The following example shows the deployment as a sidecar container in the ExternalDNS pod using the Bitnami Helm charts for ExternalDNS.

⚠️ This webhook requires at least ExternalDNS v0.14.0.

The webhook can be installed using either the Bitnami chart or the ExternalDNS one.

First, create the Hetzner secret:

kubectl create secret generic hetzner-credentials --from-literal=api-key='<EXAMPLE_PLEASE_REPLACE>' -n external-dns

Using the Bitnami chart

Skip this if you already have the Bitnami repository added:

helm repo add bitnami https://charts.bitnami.com/bitnami

You can then create the helm values file, for example external-dns-hetzner-values.yaml:

image:
  registry: registry.k8s.io
  repository: external-dns/external-dns
  tag: v0.14.0

provider: webhook

extraArgs:
  webhook-provider-url: http://localhost:8888
  txt-prefix: "reg-%{record_type}-"

sidecars:
  - name: hetzner-webhook
    image: ghcr.io/mconfalonieri/external-dns-hetzner-webhook:v0.6.0
    ports:
      - containerPort: 8888
        name: webhook
      - containerPort: 8080
        name: http
    livenessProbe:
      httpGet:
        path: /health
        port: http
      initialDelaySeconds: 10
      timeoutSeconds: 5
    readinessProbe:
      httpGet:
        path: /ready
        port: http
      initialDelaySeconds: 10
      timeoutSeconds: 5
    env:
      - name: HETZNER_API_KEY
        valueFrom:
          secretKeyRef:
            name: hetzner-credentials
            key: api-key

And then:

# install external-dns with helm
helm install external-dns-hetzner bitnami/external-dns -f external-dns-hetzner-values.yaml -n external-dns

Using the ExternalDNS chart

Skip this if you already have the ExternalDNS repository added:

helm repo add external-dns https://kubernetes-sigs.github.io/external-dns/

You can then create the helm values file, for example external-dns-hetzner-values.yaml:

namespace: external-dns
policy: sync
provider:
  name: webhook
  webhook:
    image:
      repository: ghcr.io/mconfalonieri/external-dns-hetzner-webhook
      tag: v0.6.0
    env:
      - name: HETZNER_API_KEY
        valueFrom:
          secretKeyRef:
            name: hetzner-credentials
            key: api-key
    livenessProbe:
      httpGet:
        path: /health
        port: http-wh-metrics
      initialDelaySeconds: 10
      timeoutSeconds: 5
    readinessProbe:
      httpGet:
        path: /ready
        port: http-wh-metrics
      initialDelaySeconds: 10
      timeoutSeconds: 5

extraArgs:
  - "--txt-prefix=reg-%{record_type}-"

And then:

# install external-dns with helm
helm install external-dns-hetzner external-dns/external-dns -f external-dns-hetzner-values.yaml --version 1.14.3 -n external-dns

Environment variables

The following environment variables are available:

VariableDescriptionNotes
HETZNER_API_KEYHetzner API tokenMandatory
DRY_RUNIf set, changes won't be appliedDefault: false
HETZNER_DEBUGEnables debugging messagesDefault: false
BATCH_SIZENumber of zones per callDefault: 100, max: 100
DEFAULT_TTLDefault TTL if not specifiedDefault: 7200
WEBHOOK_HOSTWebhook hostname or IP addressDefault: localhost
WEBHOOK_PORTWebhook portDefault: 8888
HEALTH_HOSTLiveness and readiness hostnameDefault: 0.0.0.0
HEALTH_PORTLiveness and readiness portDefault: 8080
READ_TIMEOUTServers' read timeout in msDefault: 60000
WRITE_TIMEOUTServers' write timeout in msDefault: 60000

Additional environment variables for domain filtering:

Environment variableDescription
DOMAIN_FILTERFiltered domains
EXCLUDE_DOMAIN_FILTERExcluded domains
REGEXP_DOMAIN_FILTERRegex for filtered domains
REGEXP_DOMAIN_FILTER_EXCLUSIONRegex for excluded domains

If the REGEXP_DOMAIN_FILTER is set, the following variables will be used to build the filter:

otherwise, the filter will be built using:

Tweaking the configuration

While tweaking the configuration, there are some points to take into consideration:

Development

The basic development tasks are provided by make. Run make help to see the available targets.