O Traefik é um proxy reverso de código aberto para fácil manuseio de microsserviços e / ou apenas contêineres com seus aplicativos.
Um proxy reverso (proxy reverso, proxy reverso) serve para retransmitir solicitações da rede externa para quaisquer servidores / serviços na rede interna (por exemplo, um servidor Web, banco de dados ou armazenamento de arquivos) e permite:
- garantir a ocultação da estrutura da rede interna e detalhes dos serviços localizados nela;
- executar balanceamento de carga entre instâncias do mesmo serviço ou servidores com as mesmas tarefas;
- forneça uma conexão criptografada (HTTPS) entre o cliente e qualquer serviço, nesse caso, uma sessão SSL é criada entre o cliente e o proxy e uma conexão HTTP não criptografada é estabelecida entre o proxy e o serviço na rede interna; se o serviço suportar HTTPS, uma conexão criptografada também poderá ser estabelecida na rede interna;
- organize o controle de acesso aos serviços (autenticação de cliente) e instale um firewall (firewall).
O artigo descreverá o uso do Traefik no Docker como um proxy reverso para outros contêineres do Docker, bem como serviços não em contêiner.
Introdução
Traefik “Edge Router”, . , , : -, Traefik ; -, Traefik EE — , HA (Hight Availability, ), (), , . , Traefik.
Traefik (“ ”) , .
:
- Docker
- Kubernetes
- Consul Catalog
- Marathon
- Rancher
- File
.
, , — “File”, ( ), - , , -. .
Traefik, “File” TOML YAML, YAML , - , . Traefik Docker. docker-compose, .
* Linux.
Traefik
docker docker-compose, .
traefik
, ,
mkdir ~/traefik
cd ~/traefik
() Traefik docker-compose.yml
. :
version: '3'
services:
traefik:
image: traefik:v2.2
container_name: traefik
restart: unless-stopped
security_opt:
- no-new-privileges:true
ports:
- 80:80
- 443:443
volumes:
- /etc/localtime:/etc/localtime:ro
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./data/traefik.yml:/traefik.yml:ro
80 443 HTTP HTTPS . Docker . Traefik traefik.yml
data
.
networks Docker-, Traefik .
.
( , ):
entryPoints:
http:
address: ":80"
https:
address: ":443"
http
https
( , a
b
) .
— Docker, :
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
exposedByDefault: false
Traefik , . — Traefik ( ).
HTTP HTTPS ( ):
http:
routers:
http-catchall:
rule: HostRegexp(`{host:.+}`)
entrypoints:
- http
middlewares:
- redirect-to-https
middlewares:
redirect-to-https:
redirectScheme:
scheme: https
permanent: false
Traefik HTTP , TCP UDP, http
.
Traefik 2 routers () middlewares( ), .
:
http-catchall
— , ,http
Traefik;rule:
— , ,HostRegexp
,Host
.+
( ), Traefik — (host
),{name:reg_exp}
;entrypoints
— , ,http
;middlewares
— , ( ).
redirect-to-https
— , ,http
Traefik;redirectScheme
— , ;scheme: https
— HTTPS ;permanent: false
— .
entryPoints:
http:
address: ":80"
https:
address: ":443"
http:
routers:
http-catchall:
rule: hostregexp(`{host:.+}`)
entrypoints:
- http
middlewares:
- redirect-to-https
middlewares:
redirect-to-https:
redirectScheme:
scheme: https
permanent: false
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
exposedByDefault: false
.
sudo docker-compose up -d
, (sudo docker-compose logs -f
) , .
Let's Encrypt
HTTPS - SSL , , Let's Encrypt.
(traefik.yml
) :
certificatesResolvers:
letsEncrypt:
acme:
email: postmaster@example.com
storage: acme.json
caServer: "https://acme-staging-v02.api.letsencrypt.org/directory"
httpChallenge:
entryPoint: http
:
letsEncrypt
— ;acme
— ( - );storage
— , ;httpChallenge
— acme-, — ;caServer: "https://acme-staging-v02.api.letsencrypt.org/directory"
— Let's Encrypt , API ( , ).
volumes
docker-compose.yml
, ( data/acme.json
):
volumes:
- /etc/localtime:/etc/localtime:ro
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./data/traefik.yml:/traefik.yml:ro
- ./data/acme.json:/acme.json
Docker
HTTPS , , Traefik, Traefik Docker, .
Docker Traefik (labels) . docker-compose.yml
:
labels:
- "traefik.enable=true"
- "traefik.http.routers.traefik.entrypoints=https"
- "traefik.http.routers.traefik.rule=Host(`traefik.example.com`)"
- "traefik.http.routers.traefik.tls=true"
- "traefik.http.routers.traefik.tls.certresolver=letsEncrypt"
- "traefik.http.routers.traefik.service=api@internal"
- "traefik.http.services.traefik-traefik.loadbalancer.server.port=888"
:
traefik.enable=true
— Traefik , ;
traefik.http.routers.traefik.entrypoints=https
— https
;
traefik.http.routers.traefik.rule=Host(
traefik.example.com)
— traefik.example.com;
traefik.http.routers.traefik.tls=true
— TLS;
traefik.http.routers.traefik.tls.certresolver=letsEncrypt
— ;
traefik.http.routers.traefik.service=api@internal
— , — api@internal
, , , ;
traefik.http.services.traefik-traefik.loadbalancer.server.port=888
— , , .
, traefik.yml
:
api:
dashboard: true
( docker-compose.yml
):
sudo docker-compose down && sudo docker-compose up -d
traefik.example.com
( , Traefik) .
, , , BasicAuth, Traefik middleware.
(admin/password)^
$ htpasswd -nb admin password
admin:$apr1$vDSqkf.v$GTJOtsd9CBiAFFnHTI2Ds1
docker-compose.yml
:
- "traefik.http.middlewares.traefik-auth.basicauth.users=admin:$$apr1$$vDSqkf.v$$GTJOtsd9CBiAFFnHTI2Ds1"
- "traefik.http.routers.traefik.middlewares=traefik-auth"
, $
$$
.
traefik.http.middlewares.traefik-auth.basicauth.users=...
— middleware basicauth
users
;
traefik.http.routers.traefik.middlewares=traefik-auth
— traefik
- middleware.
version: '3'
services:
traefik:
image: traefik:v2.2
container_name: traefik
restart: unless-stopped
security_opt:
- no-new-privileges:true
ports:
- 80:80
- 443:443
volumes:
- /etc/localtime:/etc/localtime:ro
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./data/traefik.yml:/traefik.yml:ro
- ./data/acme.json:/acme.json
labels:
- "traefik.enable=true"
- "traefik.http.routers.traefik.entrypoints=https"
- "traefik.http.routers.traefik.rule=Host(`traefik.example.com`)"
- "traefik.http.routers.traefik.tls=true"
- "traefik.http.routers.traefik.tls.certresolver=letsEncrypt"
- "traefik.http.routers.traefik.service=api@internal"
- "traefik.http.services.traefik-traefik.loadbalancer.server.port=888"
- "traefik.http.middlewares.traefik-auth.basicauth.users=admin:$$apr1$$vDSqkf.v$$GTJOtsd9CBiAFFnHTI2Ds1"
- "traefik.http.routers.traefik.middlewares=traefik-auth"
.
, docker-compose ( docker):
labels:
- "traefik.enable=true"
- "traefik.http.routers.test.entrypoints=https"
- "traefik.http.routers.test.rule=Host(`test.example.com`)"
- "traefik.http.routers.test.tls=true"
- "traefik.http.routers.test.tls.certresolver=letsEncrypt"
- "traefik.http.services.test-service.loadbalancer.server.port=80"
traefik.http.services.test-service.loadbalancer.server.port=80
— test-service
80, test
, Traefik , .
File
, - ( IP 192.168.1.222 8080) , HTTPS. .
docker-compose.yml
volume
:
volumes:
- /etc/localtime:/etc/localtime:ro
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./data/traefik.yml:/traefik.yml:ro
- ./data/custom/:/custom/:ro
- ./data/acme.json:/acme.json
data/custom/
( , ).
traefik.yml
file :
providers:
...
file:
directory: /custom
watch: true
docker-compose.yml
, watch: true
Traefik ( “ ”, , ).
Traefik (data/custom/host.yml
):
http:
routers:
host:
entryPoints:
- https
service: service-host
rule: Host(`host.example.com`)
tls:
certResolver: letsEncrypt
services:
service-host:
loadBalancer:
servers:
- url: http://192.168.1.222:8080/
passHostHeader: true
, service: service-host
— , TLS.
:
_:
loadBalancer:
servers:
-
- ...
passHostHeader: true
, .
:
version: '3'
services:
traefik:
image: traefik:v2.2
container_name: traefik
restart: unless-stopped
security_opt:
- no-new-privileges:true
ports:
- 80:80
- 443:443
volumes:
- /etc/localtime:/etc/localtime:ro
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./data/traefik.yml:/traefik.yml:ro
- ./data/custom/:/custom/:ro
- ./data/acme.json:/acme.json
labels:
- "traefik.enable=true"
- "traefik.http.routers.traefik.entrypoints=https"
- "traefik.http.routers.traefik.rule=Host(`traefik.example.com`)"
- "traefik.http.routers.traefik.tls=true"
- "traefik.http.routers.traefik.tls.certresolver=letsEncrypt"
- "traefik.http.routers.traefik.service=api@internal"
- "traefik.http.services.traefik-traefik.loadbalancer.server.port=888"
- "traefik.http.middlewares.traefik-auth.basicauth.users=admin:$$apr1$$vDSqkf.v$$GTJOtsd9CBiAFFnHTI2Ds1"
- "traefik.http.routers.traefik.middlewares=traefik-auth"
api:
dashboard: true
entryPoints:
http:
address: ":80"
https:
address: ":443"
http:
routers:
http-catchall:
rule: hostregexp(`{host:.+}`)
entrypoints:
- http
middlewares:
- redirect-to-https
middlewares:
redirect-to-https:
redirectScheme:
scheme: https
permanent: false
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
exposedByDefault: false
file:
directory: /custom
watch: true
certificatesResolvers:
letsEncrypt:
acme:
email: postmaster@example.com
storage: acme.json
#caServer: "https://acme-staging-v02.api.letsencrypt.org/directory"
httpChallenge:
entryPoint: http
http:
routers:
host:
entryPoints:
- https
service: service-host
rule: Host(`host.example.com`)
tls:
certResolver: letsEncrypt
services:
service-host:
loadBalancer:
servers:
- url: http://192.168.1.222:8080/
passHostHeader: true
Traefik HTTP Docker File. SSL Let's Encrypt, HTTPS, .
TCP UDP ( , — TCP), , Traefik .
.
O Traefik permite que você colete informações sobre seu trabalho em vários formatos, vamos ver como isso é feito usando o Prometheus.
Vamos adicionar um novo ponto de entrada
data/traefik.yml
:
entryPoints:
...
metrics:
address: ":8082"
docker-compose.yml
:
ports:
- 80:80
- 443:443
- 8082:8082
E adicione a capacidade de coletar métricas para o Prometheus a partir desta porta data/traefik.yml
:
metrics:
prometheus:
entryPoint: metrics
Resta apenas configurar o Prometheus para coletar métricas traefik_ip:8082
.
Aqui está o conteúdo dos arquivos com as configurações resultantes:
version: '3'
services:
traefik:
image: traefik:v2.2
container_name: traefik
restart: unless-stopped
security_opt:
- no-new-privileges:true
ports:
- 80:80
- 443:443
- 8082:8082
volumes:
- /etc/localtime:/etc/localtime:ro
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./data/traefik.yml:/traefik.yml:ro
- ./data/custom/:/custom/:ro
- ./data/acme.json:/acme.json
labels:
- "traefik.enable=true"
- "traefik.http.routers.traefik.entrypoints=https"
- "traefik.http.routers.traefik.rule=Host(`traefik.example.com`)"
- "traefik.http.routers.traefik.tls=true"
- "traefik.http.routers.traefik.tls.certresolver=letsEncrypt"
- "traefik.http.routers.traefik.service=api@internal"
- "traefik.http.services.traefik-traefik.loadbalancer.server.port=888"
- "traefik.http.middlewares.traefik-auth.basicauth.users=admin:$$apr1$$vDSqkf.v$$GTJOtsd9CBiAFFnHTI2Ds1"
- "traefik.http.routers.traefik.middlewares=traefik-auth"
api:
dashboard: true
entryPoints:
http:
address: ":80"
https:
address: ":443"
metrics:
address: ":8082"
metrics:
prometheus:
entryPoint: metrics
http:
routers:
http-catchall:
rule: hostregexp(`{host:.+}`)
entrypoints:
- http
middlewares:
- redirect-to-https
middlewares:
redirect-to-https:
redirectScheme:
scheme: https
permanent: false
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
exposedByDefault: false
file:
directory: /custom
watch: true
certificatesResolvers:
letsEncrypt:
acme:
email: postmaster@example.com
storage: acme.json
#caServer: "https://acme-staging-v02.api.letsencrypt.org/directory"
httpChallenge:
entryPoint: http