Docker¶
标签和容器的故事
将标签添加到你的容器之上,让 Traefik 来完成其余的工作!
快速入门使用 Docker
如果你还没使用 Docker Provider 的话,可以通过这个 快速开始 的示例来了解 Docker Provider!
配置示例¶
配置 Docker 和部署/暴露服务
开启 docker provider
[providers.docker]
providers:
docker: {}
--providers.docker=true
添加 label 标签到容器上 (在 docker compose 文件中)
version: "3"
services:
my-container:
# ...
labels:
- traefik.http.routers.my-container.rule=Host(`mydomain.com`)
移除 Docker Swarm 文档
由于现阶段 Docker Swarm 的使用不是很多,所以移除 Swarm 的相关文档介绍,重点放在 Docker 和 Kubernetes 上面,有需要的可以千万官方文档查看 Swarm 相关配置。
路由配置¶
查看特定的 路由文档 部分了解更多信息。
Provider 配置¶
endpoint
¶
必填, 默认值:"unix:///var/run/docker.sock"
[providers.docker]
endpoint = "unix:///var/run/docker.sock"
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
--providers.docker.endpoint="unix:///var/run/docker.sock"
Traefik 需要访问 Docker 套接字来获取其动态配置。
安全须知
根据你的上下文,对 Docker API 进行无限制的访问可能是一个安全问题:如果 Traefik 受到攻击,则攻击者可能会访问到 Docker 后端程序。更多信息可以查看 Docker 官方文档 关于 Docker Daemon 的攻击信息:
[...] 只有 **被信任的** 用户才允许访问控制你的 Docker Daemon [...]
安全补偿
通过 TCP 来暴露 Docker socket,而不是使用默认的 Unix socket 文件。
根据你的安全评估,它允许 AAA (Authentication, Authorization, Accounting) 概念 的不同实现级别:
AAA 提供的安全服务具体是指
- 认证(Authentication):是对用户的身份进行验证,判断其是否为合法用户。
- 授权(Authorization):是对通过认证的用户,授权其可以使用哪些服务。
- 计费(Accounting):是记录用户使用网络服务的资源情况,这些信息将作为计费的依据。
- 使用客户端证书进行身份认证:"保护 Docker Daemon Socket"
- 使用 Docker 授权插件机制 进行授权
- 在网络级别进行计费,只在 Docker 私有网络中暴露套接字文件,仅对 Traefik 可用。
- 在容器级别进行计费,通过将套接字暴露在 Traefik 以外的另一个容器上。
- 在内核级别进行计费,通过使用 SELinux 之类的机制强制执行内核调用,从而仅允许为 Traefik 的进程指定一组确定的操作。
使用 docker.sock
docker-compose 文件和 Traefik 容器共享 docker sock 文件
version: '3'
services:
traefik:
image: traefik:v2.0 # The official v2.0 Traefik docker image
ports:
- "80:80"
volumes:
- /var/run/docker.sock:/var/run/docker.sock
在 Traefik 的配置文件中指定 docker.sock。
[providers.docker]
endpoint = "unix:///var/run/docker.sock"
# ...
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
# ...
--providers.docker.endpoint="unix:///var/run/docker.sock"
# ...
useBindPortIP
¶
可选, 默认值为 false
[providers.docker]
useBindPortIP = true
# ...
providers:
docker:
useBindPortIP: true
# ...
--providers.docker.useBindPortIP=true
# ...
Traefik 将请求路由到匹配容器的 IP/Port。当设置 useBindPortIP=true
时,Traefik 使用连接到容器的 binding 的 IP/Port,而不是其内部网络的 IP/Port。
当与 traefik.http.services.<name>.loadbalancer.server.port
标签结合使用(告诉 Traefik 将请求路由到特定端口)时,Traefik 尝试在端口 traefik.http.services.<name>.loadbalancer.server.port
上找到绑定。
如果这不到这样的绑定,Traefik 将退回到容器的内部网络 IP 上,但仍使用标签中设置的 traefik.http.services.<name>.loadbalancer.server.port
。
不同情形下的 usebindportip
示例
端口标签 | 容器的绑定 | 路由目标 |
---|---|---|
- | - | IntIP:IntPort |
- | ExtPort:IntPort | IntIP:IntPort |
- | ExtIp:ExtPort:IntPort | ExtIp:ExtPort |
LblPort | - | IntIp:LblPort |
LblPort | ExtIp:ExtPort:LblPort | ExtIp:ExtPort |
LblPort | ExtIp:ExtPort:OtherPort | IntIp:LblPort |
LblPort | ExtIp1:ExtPort1:IntPort1 & ExtIp2:LblPort:IntPort2 | ExtIp2:LblPort |
在上表中:
ExtIp
表示 "绑定中找到的外部 IP"IntIp
表示 "内部网络容器的 IP"ExtPort
表示 "绑定中找到的外部端口"IntPort
表示 "内部网络容器的端口"
exposedByDefault
¶
可选, 默认为 true
[providers.docker]
exposedByDefault = false
# ...
providers:
docker:
exposedByDefault: false
# ...
--providers.docker.exposedByDefault=false
# ...
默认情况下通过 Traefik 暴露容器。如果设置为 false,没有 traefik.enable=true
标签的容器则会被最终的路由配置所忽略。
也可以查看 限制服务发现范围 文档了解更多信息。
network
¶
可选, 默认为 empty
[providers.docker]
network = "test"
# ...
providers:
docker:
network: test
# ...
--providers.docker.network=test
# ...
定义用于连接所有容器的默认 docker 网络。也可以使用容器标签 traefik.docker.network
来覆盖该选项。
defaultRule
¶
可选, 默认值为 Host(`{{ normalize .Name }}`)
[providers.docker]
defaultRule = "Host(`{{ .Name }}.{{ index .Labels \"customLabel\"}}`)"
# ...
providers:
docker:
defaultRule: "Host(`{{ .Name }}.{{ index .Labels \"customLabel\"}}`)"
# ...
--providers.docker.defaultRule="Host(`{{ .Name }}.{{ index .Labels \"customLabel\"}}`)"
# ...
对于一个特定的容器,如果标签没有定义任何路由规则,则由 defaultRule
来代替。该值必须是一个有效的 Go 模板,另外还包括一些 sprig 模板函数。
容器服务名称可以作为 Name
标识来访问,并且模板可以访问该容器上定义的所有标签。
constraints
¶
可选, 默认为空 ""
[providers.docker]
constraints = "Label(`a.label.name`, `foo`)"
# ...
providers:
docker:
constraints: "Label(`a.label.name`, `foo`)"
# ...
--providers.docker.constraints="Label(`a.label.name`, `foo`)"
# ...
约束是 Traefik 和容器标签匹配的一个表达式,用来确定是否为该容器创建路由信息。也就是说,如果容器的标签不匹配表达式的话,就不会创建容器的路由。如果表达式为空,则包括所有检测到的容器(也就是不过滤)。
表达式语法基于 Label("key", "value")
和 LabelRegex("key", "value")
函数以及通常的布尔逻辑,如下所示:
约束表达式示例
# 包含 key 为 `a.label.name` value 为 `foo` 的标签的容器
constraints = "Label(`a.label.name`, `foo`)"
# 包含 key 为 `a.label.name` value 为 `foo` 的标签的容器
constraints = "!Label(`a.label.name`, `value`)"
# 逻辑 `与` 操作
constraints = "Label(`a.label.name`, `valueA`) && Label(`another.label.name`, `valueB`)"
# 逻辑 `或` 操作
constraints = "Label(`a.label.name`, `valueA`) || Label(`another.label.name`, `valueB`)"
# 使用逻辑 `与` 和 `或` 操作,通过括号设置优先级。
constraints = "Label(`a.label.name`, `valueA`) && (Label(`another.label.name`, `valueB`) || Label(`yet.another.label.name`, `valueC`))"
# 包括 key 为 `a.label.name` value 匹配 `a.+` 正则表达式的值的容器
constraints = "LabelRegex(`a.label.name`, `a.+`)"
同样也可以查看 限制服务发现范围 文档了解更多信息。
tls
¶
可选
tls.ca
¶
用于安全连接 Docker 的 CA 证书。
[providers.docker.tls]
ca = "path/to/ca.crt"
providers:
docker:
tls:
ca: path/to/ca.crt
--providers.docker.tls.ca=path/to/ca.crt
tls.caOptional
¶
遵循与 TLS 客户端身份验证到 Docker 的安全连接策略。需要定义 tls.ca
:
true
: VerifyClientCertIfGivenfalse
: RequireAndVerifyClientCert- 如果
tls.ca
未定义 NoClientCert
[providers.docker.tls]
caOptional = true
providers:
docker:
tls:
caOptional: true
--providers.docker.tls.caOptional=true
tls.cert
¶
用于安全连接到 Docker 的公钥证书。
[providers.docker.tls]
cert = "path/to/foo.cert"
key = "path/to/foo.key"
providers:
docker:
tls:
cert: path/to/foo.cert
key: path/to/foo.key
--providers.docker.tls.cert=path/to/foo.cert
--providers.docker.tls.key=path/to/foo.key
tls.key
¶
用于安全连接到 Docker 的私钥证书。
[providers.docker.tls]
cert = "path/to/foo.cert"
key = "path/to/foo.key"
providers:
docker:
tls:
cert: path/to/foo.cert
key: path/to/foo.key
--providers.docker.tls.cert=path/to/foo.cert
--providers.docker.tls.key=path/to/foo.key
tls.insecureSkipVerify
¶
如果 insecureSkipVerify
设置为 true
,则与 Docker 连接的 TLS 可以接收服务器提供的任何证书和证书中的任何主机名。
[providers.docker.tls]
insecureSkipVerify = true
providers:
docker:
tls:
insecureSkipVerify: true
--providers.docker.tls.insecureSkipVerify=true