跳到正文
Træfɪk

在 Kubernetes 上使用 Traefik 暴露服务:基础篇

本指南帮助你开始在 Kubernetes 上通过 Traefik Proxy 暴露服务。你将学习 HTTP 流量路由的基础知识、基于路径的路由配置,以及使用 TLS 保护服务的方法。

对于路由,本指南提供两种选择:

你可以根据自己的需求选择最适合的一种。

前提条件

暴露你的第一个 HTTP 服务

我们将使用 whoami 应用暴露一个简单的 HTTP 服务,以演示到后端服务的基本路由。

首先,创建 Deployment 和 Service:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: whoami
  namespace: default
spec:
  replicas: 2
  selector:
    matchLabels:
      app: whoami
  template:
    metadata:
      labels:
        app: whoami
    spec:
      containers:
      - name: whoami
        image: traefik/whoami
        ports:
        - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  name: whoami
  namespace: default
spec:
  selector:
    app: whoami
  ports:
  - port: 80

将其保存为 whoami.yaml,然后应用:

kubectl apply -f whoami.yaml

现在使用 Gateway API 或 IngressRoute 创建路由。

使用 Gateway API

apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  name: whoami
  namespace: default
spec:
  parentRefs:
  - name: traefik-gateway  # This Gateway is automatically created by Traefik
  hostnames:
  - "whoami.docker.localhost"
  rules:
  - matches:
    - path:
        type: PathPrefix
        value: /
    backendRefs:
    - name: whoami
      port: 80

将其保存为 whoami-route.yaml,然后应用:

kubectl apply -f whoami-route.yaml

使用 IngressRoute

apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
  name: whoami
  namespace: default
spec:
  entryPoints:
    - web
  routes:
  - match: Host(`whoami.docker.localhost`)
    kind: Rule
    services:
    - name: whoami
      port: 80

将其保存为 whoami-ingressroute.yaml,然后应用:

kubectl apply -f whoami-ingressroute.yaml

验证服务

现在可以通过 http://whoami.docker.localhost/ 访问服务。测试服务是否正常工作:

curl -H "Host: whoami.docker.localhost" http://localhost/

提示

如果你按照 Kubernetes 部署指南安装了 Traefik,请务必移除 ports.web.http.redirections 配置块(位于 values.yaml 文件中),否则请求将重定向到 HTTPS 入口点:

redirections:
  entryPoint:
    to: websecure

你应该看到类似以下内容的输出:

Hostname: whoami-6d5d964cb-8pv4k
IP: 127.0.0.1
IP: ::1
IP: 10.42.0.18
IP: fe80::d4c0:3bff:fe20:b0a3
RemoteAddr: 10.42.0.17:39872
GET / HTTP/1.1
Host: whoami.docker.localhost
User-Agent: curl/7.68.0
Accept: */*
Accept-Encoding: gzip
X-Forwarded-For: 10.42.0.1
X-Forwarded-Host: whoami.docker.localhost
X-Forwarded-Port: 80
X-Forwarded-Proto: http
X-Forwarded-Server: traefik-76cbd5b89c-rx5xn
X-Real-Ip: 10.42.0.1

这说明 Traefik 已成功将请求路由到 whoami 应用。

添加路由规则

接下来,我们将根据 URL 路径将流量分发到不同服务,增强路由配置。这适用于 API 版本管理、前后端分离或微服务组织。

首先,部署第二个服务来模拟 API:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: whoami-api
  namespace: default
spec:
  replicas: 1
  selector:
    matchLabels:
      app: whoami-api
  template:
    metadata:
      labels:
        app: whoami-api
    spec:
      containers:
      - name: whoami
        image: traefik/whoami
        env:
        - name: WHOAMI_NAME
          value: "API Service"
        ports:
        - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  name: whoami-api
  namespace: default
spec:
  selector:
    app: whoami-api
  ports:
  - port: 80

将其保存为 whoami-api.yaml,然后应用:

kubectl apply -f whoami-api.yaml

现在设置基于路径的路由:

为 Gateway API 添加路径规则

更新现有的 HTTPRoute,加入基于路径的路由:

apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  name: whoami
  namespace: default
spec:
  parentRefs:
  - name: traefik-gateway
  hostnames:
  - "whoami.docker.localhost"
  rules:
  - matches:
    - path:
        type: PathPrefix
        value: /api
    backendRefs:
    - name: whoami-api
      port: 80
  - matches:
    - path:
        type: PathPrefix
        value: /
    backendRefs:
    - name: whoami
      port: 80

更新 whoami-route.yaml 文件,然后应用:

kubectl apply -f whoami-route.yaml

为 IngressRoute 添加路径规则

更新现有的 IngressRoute,加入基于路径的路由:

apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
  name: whoami
  namespace: default
spec:
  entryPoints:
    - web
  routes:
  - match: Host(`whoami.docker.localhost`) && Path(`/api`)
    kind: Rule
    services:
    - name: whoami-api
      port: 80
  - match: Host(`whoami.docker.localhost`)
    kind: Rule
    services:
    - name: whoami
      port: 80

将其保存为 whoami-ingressroute.yaml,然后应用:

kubectl apply -f whoami-ingressroute.yaml

测试基于路径的路由

验证不同路径是否会路由到不同服务:

# Root path should go to the main whoami service
curl -H "Host: whoami.docker.localhost" http://localhost/

# /api path should go to the whoami-api service
curl -H "Host: whoami.docker.localhost" http://localhost/api

对于 /api 请求,你应该在响应的环境变量部分看到“API Service”,这说明基于路径的路由工作正常:

{"hostname":"whoami-api-67d97b4868-dvvll","ip":["127.0.0.1","::1","10.42.0.9","fe80::10aa:37ff:fe74:31f2"],"headers":{"Accept":["*/*"],"Accept-Encoding":["gzip"],"User-Agent":["curl/8.7.1"],"X-Forwarded-For":["10.42.0.1"],"X-Forwarded-Host":["whoami.docker.localhost"],"X-Forwarded-Port":["80"],"X-Forwarded-Proto":["http"],"X-Forwarded-Server":["traefik-669c479df8-vkj22"],"X-Real-Ip":["10.42.0.1"]},"url":"/api","host":"whoami.docker.localhost","method":"GET","name":"API Service","remoteAddr":"10.42.0.13:36592"}

启用 TLS

下面添加 TLS,通过 HTTPS 保护服务。我们先使用适合本地开发的自签名证书。

创建自签名证书

生成自签名证书:

openssl req -x509 -nodes -days 365 -newkey rsa:2048 \
  -keyout tls.key -out tls.crt \
  -subj "/CN=whoami.docker.localhost"

在 Kubernetes 中创建 TLS Secret:

kubectl create secret tls whoami-tls --cert=tls.crt --key=tls.key

Gateway API 使用 TLS 的前提条件

在 Gateway API 中使用 TLS 之前,必须在 Traefik 安装配置中定义 websecure 监听器。通常在 Helm values 中完成这项配置。

values.yaml 中的配置示例:

ports:
  web:
    port: 80
  websecure:
    port: 443
gateway:
  listeners:
    web:
      port: 80
      protocol: HTTP
      namespacePolicy:
        from: All
    websecure:
      port: 443
      protocol: HTTPS
      namespacePolicy:
        from: All
      mode: Terminate
      certificateRefs:
        - kind: Secret
          name: whoami-tls
          group: ""

完整安装详情请参阅 Traefik Kubernetes 部署指南。

为 Gateway API 启用 TLS

更新现有的 HTTPRoute,使其使用启用了安全连接的网关监听器:

apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  name: whoami
  namespace: default
spec:
  parentRefs:
  - name: traefik-gateway
    sectionName: websecure  # The HTTPS listener
  hostnames:
  - "whoami.docker.localhost"
  rules:
  - matches:
    - path:
        type: PathPrefix
        value: /api
    backendRefs:
    - name: whoami-api
      port: 80
  - matches:
    - path:
        type: PathPrefix
        value: /
    backendRefs:
    - name: whoami
      port: 80

更新 whoami-route.yaml 文件,然后应用:

kubectl apply -f whoami-route.yaml

为 IngressRoute 启用 TLS

更新现有的 IngressRoute,启用 TLS:

apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
  name: whoami
  namespace: default
spec:
  entryPoints:
    - websecure  # Changed from 'web' to 'websecure'
  routes:
  - match: Host(`whoami.docker.localhost`) && Path(`/api`)
    kind: Rule
    services:
    - name: whoami-api
      port: 80
  - match: Host(`whoami.docker.localhost`)
    kind: Rule
    services:
    - name: whoami
      port: 80
  tls:
    secretName: whoami-tls  # Added TLS configuration

更新 whoami-ingressroute.yaml 文件,然后应用:

kubectl apply -f whoami-ingressroute.yaml

验证 HTTPS 访问

现在你可以安全地访问服务。由于使用的是自签名证书,需要跳过证书验证:

curl -k -H "Host: whoami.docker.localhost" https://localhost/

你也可以在浏览器中访问 https://whoami.docker.localhost/(需要接受自签名证书的安全警告)。

后续步骤

现在你已掌握在 Kubernetes 上使用 Traefik 暴露服务的基础知识,可以继续探索中间件、Let's Encrypt 证书、粘性会话和多层路由等高级功能。

继续阅读高级指南,了解:

  • 添加用于安全防护和访问控制的中间件
  • 使用 Let's Encrypt(IngressRoute)或 cert-manager(Gateway API)生成证书
  • 为有状态应用配置粘性会话
  • 使用 IngressRoute 设置多层路由,实现基于身份认证的路由

版权所有 © 头文件软件工作室

文档由 HeadFile Studio 翻译。

Traefik v3.7 中文快照 · 原文版权归 Traefik Labs 及贡献者所有 · MIT 许可证