问题描述
我目前正在使用以下 docker-compose 文件运行一个使用 Traefik 作为负载均衡器的 docker 容器:
<LandingPage language={...}/>
它运行得相当好。作为我第一次使用 Nomad 的尝试的一部分,我只是希望能够使用 Nomad 作业 services:
loris:
image: bdlss/loris-grok-docker
labels:
- traefik.http.routers.loris.rule=Host(`loris.my_domain`)
- traefik.http.routers.loris.tls=true
- traefik.http.routers.loris.tls.certresolver=lets-encrypt
- traefik.port=80
networks:
- web
而不是使用 docker-compose 文件来启动这个容器。
Docker 容器“标签”和“网络”标识对于 Traefik 进行动态路由非常重要。
我的问题是:我可以将这个“标签”信息和“网络”信息放在 loris.nomad
文件中的什么位置,以便它以与 {{ 1}} 文件当前可以。
我已尝试将此信息放入 loris.nomad
节,但这不起作用,而且我在遵循文档时遇到问题。我见过添加了额外“服务”节的示例,但我仍然不确定。
docker-compose
非常感谢任何建议。
解决方法
好吧,在 nomad 中运行 traefik 并在容器之间进行负载平衡的最合适选项是使用 consul catalog(服务发现所必需的)。
要运行此程序,您必须在启动 nomad 时配置 consule connection。如果您想在本地进行测试,只需运行 sudo nomad agent -dev-connect
即可。 Consul 可以用 consul agent -dev -client="0.0.0.0"
启动。
现在您可以简单地使用 标签 提供您的 traefik 配置,如 here 所示。
如果您确实需要(这肯定会导致集群设置出现问题)在游牧中使用 docker provider 运行 traefik,您可以执行以下操作:
首先您需要在 docker 插件中启用主机路径挂载。请参阅 this 和 this。您可以将您的配置放在一个额外的文件中,例如 extra.hcl,如下所示:
plugin "docker" {
config {
volumes {
enabled = true
}
}
}
现在您可以使用此额外设置 sudo nomad agent -dev-connect -config=extra.hcl
启动游牧。现在您可以在 config/labels 块中提供您的 traefik 设置,例如(完整):
job "traefik" {
region = "global"
datacenters = ["dc1"]
type = "service"
group "traefik" {
count = 1
task "traefik" {
driver = "docker"
config {
image = "traefik:v2.3"
//network_mode = "host"
volumes = [
"local/traefik.yaml:/etc/traefik/traefik.yaml","/var/run/docker.sock:/var/run/docker.sock"
]
labels {
traefik.enable = true
traefik.http.routers.from-docker.rule = "Host(`docker.loris.mydomain`)"
traefik.http.routers.from-docker.entrypoints = "web"
traefik.http.routers.from-docker.service = "api@internal"
}
}
template {
data = <<EOF
log:
level: DEBUG
entryPoints:
traefik:
address: ":8080"
web:
address: ":80"
api:
dashboard: true
insecure: true
accessLog: {}
providers:
docker:
exposedByDefault: false
consulCatalog:
prefix: "traefik"
exposedByDefault: false
endpoint:
address: "10.0.0.20:8500"
scheme: "http"
datacenter: "dc1"
EOF
destination = "local/traefik.yaml"
}
resources {
cpu = 100
memory = 128
network {
mbits = 10
port "http" {
static = 80
}
port "traefik" {
static = 8080
}
}
}
service {
name = "traefik"
tags = [
"traefik.enable=true","traefik.http.routers.from-consul.rule=Host(`consul.loris.mydomain`)","traefik.http.routers.from-consul.entrypoints=web","traefik.http.routers.from-consul.service=api@internal"
]
check {
name = "alive"
type = "tcp"
port = "http"
interval = "10s"
timeout = "2s"
}
}
}
}
}
(可能有一个设置绑定到 0.0.0.0
我在我的 /etc/hosts
中定义了这些域以指向我的主接口 IP)。
您可以使用此修改后的 webapp 规范对其进行测试(我不知道如何正确映射端口,例如 container:80 -> host:<random>
,但我认为这足以说明它变得多么复杂:)):>
job "demo-webapp" {
datacenters = ["dc1"]
group "demo" {
count = 3
task "server" {
env {
// "${NOMAD_PORT_http}"
PORT = "80"
NODE_IP = "${NOMAD_IP_http}"
}
driver = "docker"
config {
image = "hashicorp/demo-webapp-lb-guide"
labels {
traefik.enable = true
traefik.http.routers.webapp-docker.rule = "Host(`docker.loris.mydomain`) && Path(`/myapp`)"
traefik.http.services.webapp-docker.loadbalancer.server.port = 80
}
}
resources {
network {
// Used for docker provider
mode ="bridge"
mbits = 10
port "http"{
// Used for docker provider
to = 80
}
}
}
service {
name = "demo-webapp"
port = "http"
tags = [
"traefik.enable=true","traefik.http.routers.webapp-consul.rule=Host(`consul.loris.mydomain`) && Path(`/myapp`)",]
check {
type = "http"
path = "/"
interval = "2s"
timeout = "2s"
}
}
}
}
}
我希望这能以某种方式回答您的问题。