在 Docker 中单机部署 Traefik 代理
Docker
本指南提供了使用官方 Traefik Docker 镜像和 Docker Compose 在 Docker 容器中安装和配置 Traefik 代理的详尽步骤。在本指南中,我们将涵盖以下内容:
- 启用 Docker Provider
- 暴露 web(HTTP :80)和 websecure(HTTPS :443)入口点
- 将所有 HTTP 流量重定向到 HTTPS
- 使用 Basic 认证保护 Traefik 仪表盘
- 为
*.docker.localhost终止自签名证书的 TLS - 部署 whoami 演示服务
- 启用访问日志和 Prometheus 指标
前置条件
- Docker Desktop / Engine
- Docker Compose
opensslapache2-utils中的htpasswd
创建自签名证书
在 Traefik 可以在本地提供 HTTPS 之前,它需要一张证书。在生产环境中,你应该使用来自可信 CA 的证书,但对于单机栈来说,一张快速的自签名证书就足够了。我们可以使用 openssl 创建一张:
mkdir -p certs
openssl req -x509 -nodes -days 365 -newkey rsa:2048 \
-keyout certs/local.key -out certs/local.crt \
-subj "/CN=*.docker.localhost"certs 目录现在包含 local.crt 和 local.key,它们将以只读方式挂载到 Traefik 中。
创建 Traefik 仪表盘凭证
在生产环境中,建议为 Traefik 仪表盘启用某种形式的认证/安全。Traefik 可以使用 Basic 认证中间件 来保护。为此,生成一个哈希后的用户名/密码对,Traefik 的中间件将对其进行校验:
htpasswd -nb admin "P@ssw0rd" | sed -e 's/\$/\$\$/g'复制完整输出(例如 admin:$$apr1$$…)——我们稍后会在中间件配置中使用它。
创建 docker-compose.yaml
现在在 Compose 文件中定义整个栈。该文件声明了 Traefik,挂载了证书,设置了专用网络,并稍后承载 whoami 演示服务。
注意
你也可以选择使用 Docker CLI 和配置文件来运行 Traefik,但在本教程中,我们将使用 Docker Compose。
首先,创建一个名为 dynamic 的目录,并创建名为 tls.yaml 的文件用于动态配置。将 TLS 证书配置粘贴到该文件中:
tls:
certificates:
- certFile: /certs/local.crt
keyFile: /certs/local.key在你的项目根目录(dynamic/tls.yaml 文件的父目录),创建一个 docker-compose.yaml 文件,并包含以下内容:
services:
traefik:
image: traefik:v3.7
container_name: traefik
restart: unless-stopped
security_opt:
- no-new-privileges:true
networks:
# 连接到 'traefik_proxy' 覆盖网络,用于跨节点的容器间通信
- proxy
ports:
- "80:80"
- "443:443"
volumes:
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./certs:/certs:ro
- ./dynamic:/dynamic:ro
command:
# 入口点
- "--entrypoints.web.address=:80"
- "--entrypoints.web.http.redirections.entrypoint.to=websecure"
- "--entrypoints.web.http.redirections.entrypoint.scheme=https"
- "--entrypoints.web.http.redirections.entrypoint.permanent=true"
- "--entrypoints.websecure.address=:443"
- "--entrypoints.websecure.http.tls=true"
# 附加包含 TLS 配置设置的静态配置文件 tls.yaml
- "--providers.file.filename=/dynamic/tls.yaml"
# Providers
- "--providers.docker=true"
- "--providers.docker.exposedbydefault=false"
- "--providers.docker.network=proxy"
# API & 仪表盘
- "--api.dashboard=true"
- "--api.insecure=false"
# 可观测性
- "--log.level=INFO"
- "--accesslog=true"
- "--metrics.prometheus=true"
# 通过 Docker 标签进行 Traefik 动态配置
labels:
# 启用自路由
- "traefik.enable=true"
# 仪表盘路由器
- "traefik.http.routers.dashboard.rule=Host(`dashboard.docker.localhost`)"
- "traefik.http.routers.dashboard.entrypoints=websecure"
- "traefik.http.routers.dashboard.service=api@internal"
- "traefik.http.routers.dashboard.tls=true"
# Basic 认证中间件
- "traefik.http.middlewares.dashboard-auth.basicauth.users=<PASTE_HASH_HERE>"
- "traefik.http.routers.dashboard.middlewares=dashboard-auth@docker"
# Whoami 应用
whoami:
image: traefik/whoami
container_name: whoami
restart: unless-stopped
networks:
- proxy
labels:
- "traefik.enable=true"
- "traefik.http.routers.whoami.rule=Host(`whoami.docker.localhost`)"
- "traefik.http.routers.whoami.entrypoints=websecure"
- "traefik.http.routers.whoami.tls=true"
networks:
proxy:
name: proxyℹ️ 提示
- 记得将
<PASTE_HASH_HERE>替换为之前生成的哈希值。--api.insecure=false标志用于保护 API 并防止仪表盘暴露在 8080 端口上。这样做是因为我们正在通过 HTTPS 路由器暴露仪表盘。
启动栈
Compose 文件和辅助资源就位后,启动容器,让 Docker 在幕后完成网络连接:
docker compose up -dTraefik 将启动,从 command 参数中读取其静态配置,连接到 Docker socket,检测其自身的标签进行动态配置(仪表盘路由和认证),并开始在 80 和 443 端口上监听。HTTP 请求将被重定向到 HTTPS。
访问仪表盘
现在 Traefik 已部署,你可以通过 https://dashboard.docker.localhost 访问仪表盘,它将提示你输入配置的 Basic 认证凭证:
测试 whoami 应用
你可以使用 curl 测试该应用:
curl -k https://whoami.docker.localhost/返回内容:
Hostname: whoami-76c9859cfc-k7jzs
IP: 127.0.0.1
IP: ::1
IP: 10.42.0.59
IP: fe80::50d7:a2ff:fed5:2530
RemoteAddr: 10.42.0.60:54148
GET / HTTP/1.1
Host: whoami.docker.localhost
User-Agent: curl/8.7.1
Accept: */*
Accept-Encoding: gzip
X-Forwarded-For: 10.42.0.1
X-Forwarded-Host: whoami.docker.localhost
X-Forwarded-Port: 443
X-Forwarded-Proto: https
X-Forwarded-Server: traefik-644b7c67d9-f2tn9
X-Real-Ip: 10.42.0.1向 HTTP 入口点发起相同的请求将返回:
curl -k http://whoami.docker.localhost
Moved Permanently以上确认了重定向已生效,意味着我们的设置工作正常。
你也可以在浏览器中打开 https://whoami.docker.localhost 来查看服务的 JSON 转储:
ℹ️ 提示
你也可以导航到 Traefik 仪表盘 https://dashboard.docker.localhost 查看已创建的路由。
其他关键配置领域
除了此初始设置,Traefik 还提供了广泛的配置可能性。以下是使用 Docker Compose command 参数或 labels 的简要介绍和最小示例。详细选项请查阅主文档。
TLS 证书管理(Let's Encrypt)
要使 websecure 入口点自动提供有效的 HTTPS 证书,请启用 Let's Encrypt(ACME)。
command 添加示例:
command:
# ... 其他 command 参数 ...
- "[email protected]"
- "--certificatesresolvers.le.acme.storage=/letsencrypt/acme.json" # 容器内挂载卷的路径
- "--certificatesresolvers.le.acme.httpchallenge.entrypoint=web"
# - "--certificatesresolvers.le.acme.dnschallenge.provider=your-dns-provider" # 需要 Provider 配置
# 可选:让 'le' 成为 TLS 启用路由器的默认解析器
- "--entrypoints.websecure.http.tls.certresolver=le"这定义了一个名为 le 的解析器,设置了必需的电子邮件和存储路径(在挂载的 /letsencrypt 卷内),并启用了 HTTP challenge。有关 challenge 和 DNS provider 配置的详细信息,请参阅 HTTPS/TLS 文档 和 Let's Encrypt 文档。
指标(Prometheus)
你可以暴露 Traefik 的内部指标供 Prometheus 监控。我们在设置中已启用 Prometheus,但可以进一步配置它。
command 添加示例:
command:
# 如果使用专用指标入口点,请定义它:
- "--entrypoints.metrics.address=:8082"
# ... 其他 command 参数 ...
- "--metrics.prometheus=true"
# 可选:更改暴露指标的入口点(默认为 'traefik')
- "--metrics.prometheus.entrypoint=metrics"
# 为指标添加路由器/服务的标签(可能增加基数)
- "--metrics.prometheus.addrouterslabels=true"
- "--metrics.prometheus.addserviceslabels=true"这会启用 /metrics 端点(通常通过内部 API 端口访问,如果未保护则默认为 8080,或者通过专用入口点)。有关选项,请参阅指标文档。
链路追踪(OTel)
你可以启用分布式追踪来跟踪通过 Traefik 的请求。
command 添加示例:
command:
# ... 其他 command 参数 ...
- "--tracing.otel=true"
- "--tracing.otel.grpcendpoint=otel-collector:4317" # 根据需要调整端点
- "--tracing.otel.httpendpoint=otel-collector.observability:4318" # 根据需要调整端点注意:此选项需要 Traefik 可访问的运行中的 OTEL 收集器。请参阅链路追踪文档。
访问日志
你可以将 Traefik 配置为记录传入请求以进行调试和分析。
command 添加示例:
command:
# ... 其他 command 参数 ...
- "--accesslog=true" # 启用到 stdout 的访问日志
# 可选:更改格式或输出文件(需要卷)
- "--accesslog.format=json"
- "--accesslog.filepath=/path/to/access.log"
# 可选:过滤日志
- "--accesslog.filters.statuscodes=400-599"这会启用对容器标准输出的访问日志(可通过 docker compose logs <traefik-container-id> 查看)。请参阅访问日志文档。
结论
现在你已在 Docker 中完成了基本的 Traefik 设置,包括安全的仪表盘访问和 HTTP 到 HTTPS 的重定向。
在生产环境使用 Traefik OSS?
如果你在工作中使用 Traefik,可以考虑为其添加企业级 API 网关能力或获取 Traefik OSS 的商业支持。