我已经设置了启用 ACL 的 Nomad 集群。我想运行一个使用 Nomad 内置服务发现的 traefik 作业。我的 traefik 工作如下所示(为简洁起见,编辑了一些部分):
job "traefik" {
group "traefik" {
service {
name = "traefik"
provider = "nomad"
}
task "traefik" {
driver = "docker"
config {
image = "traefik:v2.10.7"
network_mode = "host"
args = [
"--api.dashboard=true",
"--api.insecure=true",
"--entrypoints.web.address=:${NOMAD_PORT_http}",
"--entrypoints.traefik.address=:${NOMAD_PORT_admin}",
"--providers.nomad=true",
"--providers.nomad.exposedByDefault=false",
"--providers.nomad.endpoint.address=http://10.0.0.3:4646/",
"--providers.nomad.endpoint.token=<token>"
]
}
}
}
}
我遇到问题的部分是传递给 traefik 容器的
--providers.nomad.endpoint.token
参数。由于我的集群启用了 ACL,因此我需要在此处提供 Nomad 令牌,否则我会收到此错误:
提供商连接错误无法加载初始游牧服务:意外响应代码:403(权限被拒绝)
我在集群中创建了一个令牌供 Traefik 使用(当我在作业规范中对其进行硬编码时,它可以工作),并且我已将该令牌添加到 Nomad 变量中,路径为
nomad/jobs/traefik
,名称为NOMAD_TOKEN
。
我不明白的是如何更改我的工作规范以将此变量注入到
--providers.nomad.endpoint.token
中。本质上我想要这样的东西:
--providers.nomad.endpoint.token=:${NOMAD_TOKEN}
我想我必须使用模板块,但我不知道如何使用 docker args 来做到这一点?
或者有没有更好的方式为 traefik 提供 Nomad 代币?
我如何改变我的工作规格
我已将该令牌添加到 Nomad 变量中,路径为 nomad/jobs/traefik,
config.args 中的字符串未使用 Go Nomad 模板进行模板化。在 config.args 中无法做到这一点。
我们需要一些可以 Nomad 模板化的包装器脚本并运行该包装器脚本。这需要检查
traefik
docker image 内部入口点是什么,以便您可以从脚本运行相同的内容。一些事情:
task "traefik" {
driver = "docker"
config {
image = "traefik:v2.10.7"
network_mode = "host"
command = "sh"
args = ["-xc", "/local/script.sh"]
}
template {
destination = "/local/script.sh"
data = <<EOF
#!/bin/sh
traefik \
--api.dashboard=true \
--api.insecure=true \
--entrypoints.web.address=:{{env "NOMAD_PORT_http"}} \
--entrypoints.traefik.address=:{{env "NOMAD_PORT_admin"}} \
--providers.nomad=true \
--providers.nomad.exposedByDefault=false \
--providers.nomad.endpoint.address=http://10.0.0.3:4646/ \
--providers.nomad.endpoint.token={{with nomadVar "nomad/jobs/traefik"}}{{.THE_TOKEN}}{{end}}
EOF
}
}
总的来说,我不喜欢内联的长配置文件的想法。我宁愿只创建 traefik 配置文件。它看起来像下面这样,也未经测试,请参阅文档:
# traefik.yaml
---
api:
dashboard: true
insecure: true
entrypoints:
web:
address: :{{env "NOMAD_PORT_http"}}
traefik:
address: :{{env "NOMAD_PORT_admin"}}
providers:
nomad:
exposedByDefault: false
endpoint:
address: http://10.0.0.3:4646/
token: {{with nomadVar "nomad/jobs/traefik"}}{{.THE_TOKEN}}{{end}}
游牧工作只会使用配置文件来对其进行模板化。
file("./traefik.yaml")
路径是相对于您从 .运行
nomad run
的目录
task "traefik" {
driver = "docker"
config {
image = "traefik:v2.10.7"
network_mode = "host"
args = ["--configFile=/local/traefik.yaml"]
}
template {
destination = "/local/traefik.yaml"
data = file("./traefik.yaml")
}
}
在 Nomad 团队的一些人的帮助下,我能够通过
identity
块非常简单地做到这一点。我的 traefik 工作规范现在如下所示:
job "traefik" {
group "traefik" {
service {
name = "traefik"
provider = "nomad"
}
task "traefik" {
driver = "docker"
identity {
env = true
change_mode = "restart"
}
config {
image = "traefik:v2.10.7"
network_mode = "host"
args = [
"--api.dashboard=true",
"--api.insecure=true",
"--entrypoints.web.address=:${NOMAD_PORT_http}",
"--entrypoints.traefik.address=:${NOMAD_PORT_admin}",
"--providers.nomad=true",
"--providers.nomad.exposedByDefault=false",
"--providers.nomad.endpoint.address=http://10.0.0.3:4646/",
]
}
}
}
}