Traefik 最近终于发布了大版本升级后的第一个修正版本,或许是时候正式迁移程序到新版本了。
写在前面
最近 Traefik 发布了 3.1 版本。作为从 Traefik 1.x 开始使用的用户,Traefik 每个大版本升级都会出现一些配置不兼容的情况,这次 3.x 的正式升级也不例外。
虽然早在 Traefik 3.0 beta 的时候,我就写过尽可能兼容 3.x 版本的上手内容《Traefik v3.0 Docker 全面使用指南:基础篇》,上个季度正式发布 3.0 后,我们还是需要调整一些配置。
为了简化配置和上手的过程,我将我使用的基础配置开源在了 soulteary/traefik-v3-example,有需要可以自取。
下面,让我们来了解 Traefik 3 正式版的使用。
准备工作
为了上手简单,我们使用上面的开源项目代码为基础进行配置。
默认情况下,服务将运行在 80
和 443
端口,所以,需要确保这两个端口没有其他程序占用。
获取基础配置代码
使用 git
将包含基础配置的项目下载到本地:
git clone https://github.com/soulteary/traefik-v3-example.git
然后进入代码目录:
cd traefik-v3-example
Docker 环境
关于 Docker 环境的准备,非常简单。
如果你使用的是图形化界面,尤其是 Windows 或者 macOS,可以访问 “Docker 官方网站”,从网页下载安装程序,“一路下一步”,完成环境准备。
当然,你也可以参考之前的一些文章:
- 如果你是 Windows 环境,可以参考《基于 Docker 的深度学习环境:Windows 篇》中的“准备 Docker 虚拟化运行环境”来完成环境准备。
- 如果你是 Linux 操作系统,可以参考《在笔记本上搭建高性价比的 Linux 学习环境:基础篇》中的“更简单的 Docker 安装”来完成环境准备。
准备 Traefik Docker 专用网络
在完成 Docker 的安装后,我们执行代码目录的脚本文件,就能够自动创建 Traefik 运行所需要的虚拟网络了:
bash scripts/prepare-network.sh
命令执行后,如果一切正常,我们能够看到类似下面的日志内容:
# bash scripts/prepare-network.sh
create docker network for traefik ok
让 Traefik 支持使用 HTTPS 证书
Traefik 支持两种方式来使用 HTTPS 证书:一种是使用我们准备好的证书文件,另一种是为我们拥有的域名自动申请“Let’s Encrypt”免费证书。去年这家非盈利证书机构已经为 3.63 亿网站提供了 TLS 证书。
关于第一种方式,我们可以在各种云服务商处购买或者申请免费的 HTTPS 证书,将 HTTPS 证书下载到本地,放在项目目录的 ssl
目录中即可。
当然,我们也可以贯彻免费到底,根据自己需求,自己生成一套证书来使用。
这里,推荐一个几年前写的开源证书生成小工具:soulteary/certs-maker。如果你对自签名证书的基础知识、如何快速部署到系统感兴趣,可以阅读之前的文章:《如何制作和使用自签名证书》。
如果你已经完成了 Docker 的安装,那么只需要使用下面的命令,就能够快速的完成自签名证书的生成了:
docker run --rm -it -v `pwd`/ssl:/ssl soulteary/certs-maker:v3.5.0 "--CERT_DNS=lab.com,*.lab.com,*.data.lab.com"
当命令执行后,就能够得到证书文件了。
[soulteary/certs-maker] v3.5.0
Flags:
- CERT_COUNTRY= CN
- CERT_STATE= BJ
- CERT_LOCALITY= HD
- CERT_ORGANIZATION= Lab
- CERT_ORGANIZATIONAL_UNIT= Dev
- CERT_COMMON_NAME= Hello World
- CERT_DOMAINS= [lab.com *.lab.com *.data.lab.com]
- APP_FOR_K8S= false
- APP_FOR_FIREFOX= false
- APP_OUTPUT_DIR= ./ssl
上面的命令中,我们指定了本地系统目录的 ssl
目录和容器内的 /ssl
目录打通,所以只需要查看本地的 ssl
目录,就能够验收证书了:
ls ssl
lab.com.conf lab.com.crt lab.com.key
不论是购买的证书还是自己生成的证书,我们只要放在 ssl
目录中就可以了,一会再用。
更新 Traefik 配置文件
根据你想 Traefik 使用 HTTPS 证书方式的不同,我们需要对示例代码的配置进行一些调整。
如果你选择自签名证书(参考上面的方法生成),或者云服务商处购买的域名,我们需要修改项目中的 .env
配置文件和 config/tls.toml
配置。
在 .env
配置文件中,我们需要将 Traefik 管理界面的域名地址修改为适配证书的域名:
# 服务域名
SERVICE_DOMAIN=traefik.example.com
并在 config/certs.toml
配置中,更新相关的域名:
[tls.stores.default.defaultCertificate]
certFile = "/data/ssl/example.com.crt"
keyFile = "/data/ssl/example.com.key"
[[tls.certificates]]
certFile = "/data/ssl/example.com.crt"
keyFile = "/data/ssl/example.com.key"
# others...
# [[tls.certificates]]
# certFile = "/data/ssl/lab.com.crt"
# keyFile = "/data/ssl/lab.com.key"
如果你拥有域名,希望使用免费申请的 HTTPS 证书,我们可以删除掉 config/certs.toml
配置文件,然后更新 .env
中的相关配置:
# 服务域名
SERVICE_DOMAIN=traefik.example.com
# 示例,使用 CloudFlare 来申请证书
ACME_PROVIDER=cloudflare
ACME_EMAIL=your-email@company.ltd
# CF DNS API Token
CF_DNS_API_TOKEN=your-cf-dns-api-token
# DNS Domain (main)
DNS_MAIN=example.com
# DNS Domain (list)
DNS_LIST=example.com,*.example.com
除了要和上面一样更新域名之外,我们还需要配置一些申请免费证书必须的配置,包括下面的内容(使用 CloudFlare DNS 申请证书为例):
ACME_PROVIDER
:使用什么方式来申请免费证书。ACME_EMAIL
:申请证书要使用的邮箱。CF_DNS_API_TOKEN
:我使用 Cloudflare,这里需要配置 API Token 来操作 DNS 记录,完成域名所有权验证,进行证书申请。DNS_MAIN
和DNS_LIST
我们想要申请的域名证书列表,需要拥有域名所有权,比如,你不能够申请www.google.com
或者www.apple.com
这种不属于你的域名。
至于 Cloudflare 的 API Key,我们可以在登录后的“API 令牌”页面获得,配置方式参考下面的图片:
快速上手
下面来分别介绍两种启动并使用 Traefik ,支持使用 HTTPS 证书的方法。
快速启动一个 Traefik 3 正式版程序
我们先来介绍配合购买或使用自签名的证书文件的使用方式。
想要使用这种方式,我们需要将目录中的 docker-compose.local-certs.yml
重命名为 docker-compose.yml
,或者复制一份,将配置文件进行改名:
cp docker-compose.local-certs.yml docker-compose.yml
上面的准备工作结束后,在代码目录中,我们执行下面的命令,就能够自动启动 Traefik 来提供服务了。
docker compose down && docker compose up -d
命令执行后,我们将看到类似下面的日志内容:
# docker compose down && docker compose up -d
[+] Building 0.0s (0/0) docker:desktop-linux
[+] Running 1/1
✔ Container traefik Started
如果我们执行 docker compose ps
,将能够看到 Traefik 健康运行:
NAME IMAGE COMMAND SERVICE CREATED STATUS PORTS
traefik traefik:v3.1.1 "/entrypoint.sh --global.sendanonymoususage=false --global.checknewversion=false --entrypoints.http.address=:80 --entrypoints.https.address=:443 --entryPoints.https.asDefault=true --entryPoints.https.http3 --entryPoints.https.http3.advertisedport=443 --serverstransport.insecureskipverify=true --entryPoints.http.forwardedHeaders.trustedIPs=127.0.0.1/32,172.18.0.1/24 --entryPoints.https.forwardedHeaders.trustedIPs=127.0.0.1/32,172.18.0.1/24 --api=true --api.dashboard=true --ping=true --log.level=INFO --log.maxsize=100 --log.format=common --accesslog=false --providers.docker=true --providers.docker.watch=true --providers.docker.exposedbydefault=false --providers.docker.endpoint=unix:///var/run/docker.sock --providers.docker.useBindPortIP=false --providers.docker.network=traefik --providers.file=true --providers.file.watch=true --providers.file.directory=/etc/traefik/config --providers.file.debugloggeneratedtemplate=true" traefik 3 minutes ago Up 3 minutes (healthy) 0.0.0.0:80->80/tcp, 0.0.0.0:443->443/tcp, 0.0.0.0:443->443/udp
当服务出现问题的时候,Docker 将会自动恢复程序的运行。
在这个示例代码中,默认的自签名证书支持 example.com
和 *.exmaple.com
相关的域名,而 Traefik 默认的管理界面域名是 traefik.example.com
。
我们可以通过修改系统的 /etc/hosts
或者局域网 DNS 指向,将 traefik.example.com
指向启动 traefik 容器的 IP 地址。比如,我启动的容器在本地:
127.0.0.1 traefik.example.com
使用浏览器访问 https://traefik.example.com
,我们就能够看到 Traefik 的管理界面了:
如果你使用的是购买的证书,那么图中的小红锁默认应该就是绿色的。
如果你使用的是自签名证书,我们可以通过信任自签名证书,来解决浏览器中展示的“小红锁”,在不泄漏自签名证书的前提下,同样能够保证安全的访问,以及 HTTP2/3 请求特性。
启动 Traefik 并自动申请 HTTPS 证书
如果我们拥有某个域名,并且希望 Traefik 能够自动从网上申请免费的 HTTPS 证书,可以使用下面的方式。
我们需要将目录中的 docker-compose.acme.yml
重命名为 docker-compose.yml
,或者复制一份,将配置文件进行改名:
cp docker-compose.acme.yml docker-compose.yml
本文中,我使用的是 CloudFlare 的方式来申请证书,所以我们需要确保配置文件 .env
中的变量 CF_DNS_API_TOKEN
配置在 docker-compose.yml
中:
environment:
- CF_DNS_API_TOKEN=${CF_DNS_API_TOKEN}
和上文中一样,我们使用下面的命令,就能够创建干净的容器,来运行 Traefik 并自动申请证书了:
docker compose down && docker compose up -d
使用这种方式注册的证书,Traefik 会进行自动维护,在证书到期之前进行自动替换。不过,第一次注册的时候会比较漫长,如果我们打开 Traefik 可能看到它的申请或者证书续期的过程:
# docker compose logs -f
traefik | 2024-08-04T19:23:17+08:00 INF Traefik version 3.1.1 built on 2024-07-30T13:55:22Z version=3.1.1
traefik | 2024-08-04T19:23:17+08:00 INF
traefik | Stats collection is disabled.
traefik | Help us improve Traefik by turning this feature on :)
traefik | More details on: https://doc.traefik.io/traefik/contributing/data-collection/
traefik |
traefik | 2024-08-04T19:23:17+08:00 INF Starting provider aggregator aggregator.ProviderAggregator
traefik | 2024-08-04T19:23:17+08:00 INF Starting provider *file.Provider
traefik | 2024-08-04T19:23:17+08:00 INF Starting provider *traefik.Provider
traefik | 2024-08-04T19:23:17+08:00 INF Starting provider *docker.Provider
traefik | 2024-08-04T19:23:17+08:00 INF Starting provider *acme.ChallengeTLSALPN
traefik | 2024-08-04T19:23:17+08:00 INF Starting provider *acme.Provider
traefik | 2024-08-04T19:23:17+08:00 INF Testing certificate renew... acmeCA=https://acme-v02.api.letsencrypt.org/directory providerName=le.acme
...
一般情况下,3~5 分钟证书就注册好了。
快速启动一个服务,注册到 Traefik 上
接下来,使用一个简单的例子,来说明如何将一个运行在某个具体端口上的程序,注册到 Traefik 网关中,并支持 HTTPS 访问。
还是以之前写过的一个简单的开源程序 flare
为例,下面的命令将下载 flare
并运行它,最终允许我们使用 5005
端口来访问它:
docker pull soulteary/flare:0.5.1
docker run --rm -it -p 5005:5005 soulteary/flare:0.5.1
如果我们访问 http://localhost:5005
,就能够看到上面的界面啦。
我们将上面的命令简化,去掉调试和自动清理容器的参数:
docker run -p 5005:5005 soulteary/flare:0.5.1
然后,我们将命令粘贴到在线转换 Docker 命令到 Compose 的工具里,可以得到最简单的 Docker Compose 配置文件:
name: flare
services:
flare:
ports:
- 5005:5005
image: soulteary/flare:0.5.1
我们可以对上面的配置进行一些修改,将上面的通过 5005
端口访问的程序,能够通过 flare.example.com
进行访问,并且支持自动将 HTTP 请求转换为 HTTPS 请求,并对访问内容自动进行 GZIP 压缩,提升访问加速:
name: flare
services:
flare:
image: soulteary/flare:0.5.1
networks:
- traefik
labels:
# 用于 Traefik 服务发现
- "traefik.enable=true"
- "traefik.docker.network=traefik"
# HTTP 相关
# 使用 HTTP 协议访问 Flare,将使用 `http`(80端口) 提供服务
- "traefik.http.routers.flare-http.entrypoints=http"
# 并自动跳转至 HTTPS 协议(443端口)
- "traefik.http.routers.flare-http.middlewares=redir-https"
# 默认服务域名为 flare.example.com
- "traefik.http.routers.flare-http.rule=Host(`flare.example.com`)"
# 服务名称为 noop@internal,表示不提供任何服务 (因为自动跳转,没必要请求服务)
- "traefik.http.routers.flare-http.service=noop@internal"
# HTTPS 相关
# 使用 HTTPS 协议访问 Flare,将使用 `https`(443端口) 提供服务
- "traefik.http.routers.flare-https.entrypoints=https"
# 在这个端口上使用 TLS 协议
- "traefik.http.routers.flare-https.tls=true"
# 对响应内容启用 GZIP 压缩
- "traefik.http.routers.flare-https.middlewares=gzip"
# 默认服务域名为 flare.example.com
- "traefik.http.routers.flare-https.rule=Host(`flare.example.com`)"
# (可选)HTTPS 服务名称为 flare-backend,使用 5005 端口提供服务
- "traefik.http.routers.flare-https.service=flare-backend"
# 服务相关
# 声明服务名称为 flare-backend,使用 5005 端口提供服务
- "traefik.http.services.flare-backend.loadbalancer.server.scheme=http"
- "traefik.http.services.flare-backend.loadbalancer.server.port=5005"
networks:
traefik:
external: true
我们将上面的内容保存为 docker-compose.flare.yml
后,使用 docker compose -f docker-compose.flare.yml up -d
启动容器后。使用浏览器访问 flare.example.com
就能够通过 HTTPS 的方式来访问到我们的程序啦。
其他的程序也是如此,尤其是基于 Docker 运行的程序,都可以使用这个方式来处理,是不是非常简单?
最后
通过上面的介绍,相信你应该已经能够快速的将 Traefik 运行起来,完成一个支持 HTTPS 的网关服务的部署了。
并且,也应该能够快速的将原本只支持使用 HTTP 或者具体端口访问的程序,通过 Traefik 来统一管理和提供服务,告别需要为每一个程序都配置和管理证书的日子了。
–EOF
我们有一个小小的折腾群,里面聚集了一些喜欢折腾、彼此坦诚相待的小伙伴。
我们在里面会一起聊聊软硬件、HomeLab、编程上、生活里以及职场中的一些问题,偶尔也在群里不定期的分享一些技术资料。
关于交友的标准,请参考下面的文章:
致新朋友:为生活投票,不断寻找更好的朋友
当然,通过下面这篇文章添加好友时,请备注实名和公司或学校、注明来源和目的,珍惜彼此的时间 😄
关于折腾群入群的那些事
本文使用「署名 4.0 国际 (CC BY 4.0)」许可协议,欢迎转载、或重新修改使用,但需要注明来源。 署名 4.0 国际 (CC BY 4.0)
本文作者: 苏洋
创建时间: 2024年08月04日
统计字数: 10293字
阅读时间: 21分钟阅读
本文链接: https://soulteary.com/2024/08/04/best-practices-for-traefik-3-in-docker-getting-started-quickly.html