Kubernetes Ingress und Gateway mit Traefik
7 Minuten Lesezeit
Diese Anleitung wurde mit Version 38.0.2 des Traefik‑Helm‑Charts geschrieben und getestet. Verwenden Sie bitte die aktuellste Version.
Außerdem sollten Sie TLS für Ihre Anwendungen einrichten und verwenden. Da TLS nicht Teil dieser Anleitung ist, sind die entsprechenden Konfigurationsbeispiele im Folgenden auskommentiert.
Installieren
Erstellen Sie eine leere Helm‑values.yaml‑Datei. Traefik funktioniert „Out‑of‑the‑Box“, sodass die Datei vorerst nicht nötig ist. In den folgenden Schritten fügen wir ihr aber benutzerdefinierte Konfigurationen hinzu.
touch values.yaml
Wählen Sie das Ziel‑Kubernetes‑Cluster aus, zum Beispiel indem Sie die Umgebungsvariable KUBECONFIG setzen:
export KUBECONFIG=/pfad/zur/kubeconfig/datei
Installieren Sie Traefik im traefik‑Namespace des Clusters:
helm install traefik oci://ghcr.io/traefik/helm/traefik \
--create-namespace \
--namespace=traefik \
--values=values.yaml \
--version=38.0.2 \
--wait
Weiterführende Links …
Aktualisieren
Verwenden Sie den folgenden Befehl, um das Release zu aktualisieren – zum Beispiel nachdem Sie Änderungen an der values.yaml vorgenommen haben:
helm upgrade traefik oci://ghcr.io/traefik/helm/traefik \
--namespace=traefik \
--values=values.yaml \
--version=38.0.2 \
--wait
Konfigurieren
Floating‑IP reservieren
Fügen Sie die Annotation loadbalancer.openstack.org/keep-floatingip hinzu, wenn Sie die IP-Adresse des Load Balancers reservieren möchten:
# values.yaml
service:
annotations:
loadbalancer.openstack.org/keep-floatingip: "true"
Wenn Sie eine bereits reservierte IP mit Traefik nutzen wollen, fügen Sie die folgende Konfiguration hinzu:
# values.yaml
service:
annotations:
loadbalancer.openstack.org/keep-floatingip: "true"
loadbalancer.openstack.org/load-balancer-address: "192.0.2.255" # Beispiel‑IP
spec:
loadBalancerIP: "192.0.2.255" # Beispiel‑IP
Weiterführende Links …
Proxy‑Protocol nutzen
Aktivieren Sie das Proxy‑Protocol im Load Balancer (über die Annotation) und in Traefik, falls Ihre Anwendung die IP-Adressen der Clients kennen muss. Andernfalls sieht die Anwendung nur die internen IP-Adressen der Load‑Balancer.
# values.yaml
ports:
web:
proxyProtocol:
trustedIPs:
- "10.250.0.0/16"
websecure:
proxyProtocol:
trustedIPs:
- "10.250.0.0/16"
service:
annotations:
loadbalancer.openstack.org/proxy-protocol: v2
Als trustedIPs tragen Sie bitte die interne IP-Adresse Ihres Load Balancers ein bzw. den möglichen IP-Adressraum. Zur Zeit ist dies der oben gezeigte Bereich, welcher auch mit dem „Nodes CIDR“ übereinstimmt, der Ihnen im PSKE Dashboard angezeigt wird.
Weiterführende Links …
Übermittlung von Nutzungsstatistiken deaktivieren
Die Erfassung von Nutzungsstatistiken ist standardmäßig deaktiviert, Traefik prüft jedoch regelmäßig, ob eine neue Version verfügbar ist und gibt dabei Informationen preis. Fügen Sie die folgende Einstellungen hinzu, um beides zu deaktivieren:
# values.yaml
global:
checkNewVersion: false # Standard: true
sendAnonymousUsage: false # Standard: false
Weiterführende Links …
Logging konfigurieren
Stellen Sie das Log-Format auf JSON ein, um die Log-Daten maschinell leichter verarbeiten und analysieren zu können. Durch das Anpassen des Log‑Levels entstehen weniger unnötige Ausgaben:
# values.yaml
logs:
general:
format: json # Standard: common
level: ERROR # Standard: INFO
Weiterführende Links …
Access‑Logs aktivieren
Traefik Access-Logs werden normalerweise nicht gebraucht, aber wenn Fehler auftreten können sie hilfreich sein. Falls aktiviert, kann die Ausgabe des Access-Logs gefiltert werden, zum Beispiel nach Dauer der Requests (in Sekunden) oder nach HTTP‑Statuscodes:
# values.yaml
logs:
access:
enabled: true # Standard: false
format: json # Standard: common
filters:
minduration: "5" # Standard: ""
statuscodes: "400" # Standard: ""
Weiterführende Links …
Pfad-Filterung und -Bereinigung deaktivieren
Traefik blockiert standardmäßig manche URL‑encoded Zeichen in der URL und führt Pfad-Bereinigung durch. Falls nötig, können Sie dieses Verhalten mit den folgenden Einstellungen deaktivieren:
# values.yaml
ports:
web:
http:
encodedCharacters:
allowEncodedSlash: true # Standard: false
allowEncodedBackSlash: true # Standard: false
allowEncodedNullCharacter: true # Standard: false
allowEncodedSemicolon: true # Standard: false
allowEncodedPercent: true # Standard: false
allowEncodedQuestionMark: true # Standard: false
allowEncodedHash: true # Standard: false
sanitizePath: false # Standard: true
websecure:
http:
encodedCharacters:
allowEncodedSlash: true # Standard: false
allowEncodedBackSlash: true # Standard: false
allowEncodedNullCharacter: true # Standard: false
allowEncodedSemicolon: true # Standard: false
allowEncodedPercent: true # Standard: false
allowEncodedQuestionMark: true # Standard: false
allowEncodedHash: true # Standard: false
sanitizePath: false # Standard: true
Weiterführende Links …
Verwenden
Test‑Deployment vorbereiten
Erstellen Sie eine Datei httpbin.yaml mit folgendem Inhalt:
# httpbin.yaml
apiVersion: v1
kind: Namespace
metadata:
name: httpbin
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: httpbin
namespace: httpbin
spec:
replicas: 1
selector:
matchLabels:
app: httpbin
template:
metadata:
labels:
app: httpbin
spec:
containers:
# Bitte eine aktuelle Version des Containers verwenden.
- image: ghcr.io/mccutchen/go-httpbin:2.20
imagePullPolicy: IfNotPresent
name: httpbin
ports:
- containerPort: 8080
securityContext:
allowPrivilegeEscalation: false
capabilities:
drop:
- ALL
readOnlyRootFilesystem: true
runAsNonRoot: true
resources:
limits:
memory: 50Mi
requests:
cpu: 50m
livenessProbe:
tcpSocket:
port: 8080
readinessProbe:
httpGet:
path: /status/200
port: 8080
scheme: HTTP
---
apiVersion: v1
kind: Service
metadata:
name: httpbin
namespace: httpbin
labels:
app: httpbin
service: httpbin
spec:
ports:
- name: http
port: 8080
targetPort: 8080
selector:
app: httpbin
Erstellen Sie die Deployment- und Service‑Ressourcen im Namespace httpbin:
kubectl apply --filename=httpbin.yaml
Kubernetes Ingress erstellen
Fügen Sie die folgende Ergänzung ans Ende der Datei httpbin.yaml ein:
# httpbin.yaml
---
kind: Ingress
apiVersion: networking.k8s.io/v1
metadata:
name: httpbin
namespace: httpbin
spec:
ingressClassName: traefik
rules:
- host: example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: httpbin
port:
number: 8080
# tls:
# - hosts:
# - example.com
# secretName: httpbin-tls
Erstellen Sie die Ingress‑Ressource:
kubectl apply --filename=httpbin.yaml
Testen Sie den Ingress mit curl:
EXTERNAL_IP=$(kubectl --namespace=traefik get svc/traefik \
--output=jsonpath='{.status.loadBalancer.ingress[0].ip}')
curl --header Host:example.com --verbose "http://${EXTERNAL_IP:?}/status/200"
Weiterführende Links …
Basic‑Auth zum Ingress hinzufügen
Erstellen Sie in httpbin.yaml ein Secret und einen Basic‑Auth‑Middleware:
# httpbin.yaml
---
kind: Secret
apiVersion: v1
metadata:
name: basic-auth
namespace: httpbin
type: Opaque
data:
# Username: admin
# Password: insecure
# Bitte ein sicheres Passwort benutzen!
auth: YWRtaW46JGFwcjEkWU5iT0trNVkkNlVaa2pKN1dneUpVYWcvYXlqdzE3Lgo=
---
apiVersion: traefik.io/v1alpha1
kind: Middleware
metadata:
name: basic-auth
namespace: httpbin
spec:
basicAuth:
secret: basic-auth
Fügen Sie die folgende Annotation zur Ingress‑Ressource hinzu. Der Annotationswert hat das Format <namespace>-<middleware>@kubernetescrd:
# httpbin.yaml
metadata:
annotations:
traefik.ingress.kubernetes.io/router.middlewares: httpbin-basic-auth@kubernetescrd
Weiterführende Links …
IP‑Allow‑List zum Ingress hinzufügen
Erstellen Sie einen IP‑Allow‑List‑Middleware:
# httpbin.yaml
---
apiVersion: traefik.io/v1alpha1
kind: Middleware
metadata:
name: ip-allow-list
namespace: httpbin
spec:
ipAllowList:
sourceRange:
- 192.0.2.255 # Beispiel
- 198.51.100.0/24 # Beispiel
Fügen Sie dann die Annotation zur Ingress‑Ressource hinzu:
# httpbin.yaml
metadata:
annotations:
traefik.ingress.kubernetes.io/router.middlewares: httpbin-ip-allow-list@kubernetescrd
Oder beide Middlewares gleichzeitig:
# httpbin.yaml
metadata:
annotations:
traefik.ingress.kubernetes.io/router.middlewares: |-
httpbin-basic-auth@kubernetescrd,httpbin-ip-allow-list@kubernetescrd
Weiterführende Links …
Kubernetes Gateway erstellen
Aktivieren Sie den Kubernetes‑Gateway‑Provider von Traefik in der Datei values.yaml und aktualisieren Sie Ihr Release:
# values.yaml
providers:
kubernetesGateway:
enabled: true # Standard: false
gateway:
enabled: false # Wird in dieser Anleitung nicht gebraucht. Standard: true
Fügen Sie einen Gateway‑ und einen HTTPRoute‑Eintrag in die Datei httpbin.yaml ein:
# httpbin.yaml
---
apiVersion: gateway.networking.k8s.io/v1
kind: Gateway
metadata:
name: httpbin
namespace: httpbin
spec:
gatewayClassName: traefik
listeners:
- allowedRoutes:
namespaces:
from: Same
name: web # Der Name des HTTP‑Endpoints von Traefik
port: 8000 # Der Standard‑Port des HTTP‑Endpoints von Traefik
protocol: HTTP
# - allowedRoutes:
# namespaces:
# from: Same
# name: websecure # Der Name des HTTPS‑Endpoints von Traefik
# port: 8443 # Der Standard‑Port des HTTPS‑Endpoints von Traefik
# protocol: HTTPS
# tls:
# certificateRefs:
# - kind: Secret
# name: httpbin-tls
---
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: httpbin
namespace: httpbin
spec:
parentRefs:
- name: httpbin
namespace: httpbin
hostnames:
- example.com
rules:
- backendRefs:
- name: httpbin # Der Name Ihres Kubernetes‑Services
namespace: httpbin
port: 8080 # Der Port Ihres Kubernetes‑Services
matches:
- path:
type: PathPrefix
value: /
Erstellen Sie die Ressourcen:
kubectl apply --filename=httpbin.yaml
Falls bereits ein Ingress vorhanden ist, löschen Sie ihn, um Verwirrung zu vermeiden:
kubectl --namespace=httpbin delete --ignore-not-found ingress/httpbin
Jetzt können Sie prüfen, ob Gateway und HTTPRoute wie erwartet funktionieren:
EXTERNAL_IP=$(kubectl --namespace=traefik get svc/traefik \
--output=jsonpath='{.status.loadBalancer.ingress[0].ip}')
curl --header Host:example.com --verbose "http://${EXTERNAL_IP:?}/status/200"
Fügen Sie die Middlewares (siehe oben, im Abschnitt Kubernetes Ingress erstellen) als Filter zur HTTPRoute hinzu:
# httpbin.yaml
filters:
- type: ExtensionRef
extensionRef:
group: traefik.io
kind: Middleware
name: ip-allow-list
- type: ExtensionRef
extensionRef:
group: traefik.io
kind: Middleware
name: basic-auth
Weiterführende Links …
Deinstallieren
Bevor Sie Traefik deinstallieren, müssen Sie entscheiden, ob Sie die Floating‑IP-Adresse reservieren möchten.
Floating‑IP-Adresse reservieren …
helm upgrade traefik oci://ghcr.io/traefik/helm/traefik \
--namespace=traefik \
--reuse-values \
--set-string=service.annotations.loadbalancer\\.openstack\\.org/keep-floatingip=true
Notieren Sie sich die IP-Adresse, damit Sie sie später wiederverwenden können:
kubectl --namespace=traefik get svc/traefik \
--output=jsonpath='{.status.loadBalancer.ingress[0].ip}'
Oder Floating‑IP-Adresse freigeben …
helm upgrade traefik oci://ghcr.io/traefik/helm/traefik \
--namespace=traefik \
--reuse-values \
--set-string=service.annotations.loadbalancer\\.openstack\\.org/keep-floatingip=false
Dann können Sie Traefik deinstallieren:
helm uninstall traefik --namespace=traefik
Prüfen Sie, ob noch irgendwo Traefik‑CustomResourceDefinitions (CRDs) verwendet werden:
kubectl api-resources --api-group=traefik.io --output=name |
tr '\n' ',' | sed -E 's/,$//' |
xargs --no-run-if-empty kubectl get --all-namespaces
kubectl api-resources --api-group=hub.traefik.io --output=name |
tr '\n' ',' | sed -E 's/,$//' |
xargs --no-run-if-empty kubectl get --all-namespaces
Dies könnten zum Beispiel die Middlewares sein, die im Abschnitt Kubernetes Ingress erstellen erstellt wurden. Falls nichts gefunden wird (zweimal „No resources found“) – oder wenn Sie sich sicher sind, dass Sie die gefundenen Ressourcen nicht mehr benötigen – können Sie die CRDs löschen:
kubectl api-resources --api-group=traefik.io --output=name |
xargs --no-run-if-empty kubectl delete crds
kubectl api-resources --api-group=hub.traefik.io --output=name |
xargs --no-run-if-empty kubectl delete crds
Anschließend löschen Sie den Namespace:
kubectl delete namespace traefik