如何解决Traefik 反向代理 + 边缘路由器:防止直接容器访问
总的来说,我对 Docker、Traefik 和反向代理的世界完全陌生。我正在创建一个示例应用程序,它应该代理对特定服务的请求,并防止直接访问这些服务。应该允许的唯一请求应该是通过公开的反向代理端口。不幸的是,当容器端口暴露时,我只能成功地将请求代理到我的服务。这是可以/应该由反向代理处理的东西吗?这是 Traefik 可以/应该作为边缘路由器处理的事情吗?
如果我在 docker-compose.yml
文件中启用我的服务并公开端口,那么我可以代理处理能够直接调用容器的附加问题。下面写的内容产生 404 Not Found
我认为这是有道理的,因为我试图不暴露与容器的直接接触。
请记住,这旨在通过 HTTP 在 localhost
上提供服务。 HTTPS 将在稍后合并,这是一个未来的问题。
这是我的文件结构:
./app/
|- traefik/
| |_ traefik.toml
| |_ traefik_dynamic.toml
| |_ Dockerfile
|
|_ build.sh
|_ docker-compose.yml
|_ Dockerfile
|_ index.js
这是每个文件的内容:
traefik/Dockerfile:
FROM traefik:latest
# Traefik Static Configuration
ADD traefik.toml /etc/traefik/traefik.toml
# Traefik Dynamic Configuration
ADD traefik_dynamic.toml /etc/traefik/traefik_dynamic.toml
traefik.toml
##
#
# Traefik Static Configuration
#
##
[entryPoints]
[entryPoints.http]
address = ":80"
[providers]
[providers.docker]
watch = true
endpoint = "unix:///var/run/docker.sock"
exposedByDefault = false
network = "helloworld_network"
[providers.file]
watch = true
filename = "/etc/traefik/traefik_dynamic.toml"
[api]
insecure = true
dashboard = true
debug = true
[log]
level = "DEBUG"
[accessLog]
traefik_dynamic.toml:
[http]
[http.services]
# Hello,World #1
[http.services.helloworld1_service.loadBalancer]
[[http.services.helloworld1_service.loadBalancer.servers]]
url = "http://helloworld1:8181"
# Hello,World #2
[http.services.helloworld2_service.loadBalancer]
[[http.services.helloworld2_service.loadBalancer.servers]]
url = "http://helloworld2:8282"
[http.routers]
# Hello,World Router Numero Uno
[http.routers.helloworld1_router]
entrypoints = ["http"]
service = "helloworld1_service"
# Navigate here in the browser
rule = "Host(`hello1.localhost`)"
# Hello,World Router Numero Dos
[http.routers.helloworld2_router]
entrypoints = ["http"]
service = "helloworld2_service"
# Navigate here in the browser
rule = "Host(`hello2.localhost`)"
# Traefik router
[http.routers.traefik_router]
entrypoints = ["http"]
service = "api@internal"
rule = "Host(`traefik.localhost`)"
Dockerfile:
FROM alpine:3.7
RUN apk update \
&& apk upgrade \
&& apk add bash \
&& apk add nodejs=8.9.3-r1 \
&& mkdir -p /usr/app \
&& adduser -D -u 1000 app \
&& chmod 700 -R /usr/app \
&& chown -R app /usr/app
COPY ./index.js /usr/app/
USER app
CMD ["/bin/bash","-c","cd /usr/app && node index"]
docker-compose.yml :
version: "3"
services:
traefik:
image: traefik:v2.4
container_name: "traefik"
# Enables the web UI and tells Traefik to listen to docker
command:
- "--log.level=DEBUG"
- "--api.insecure=true"
- "--providers.docker"
# Enabling Docker providers to gather information
- "--providers.docker=true"
# Don't expose containers unless explicitly told so
- "--providers.docker.exposedbydefault=false"
- "--entrypoints.web.address=:80"
ports:
# The HTTP port
- "80:80"
# The Web UI (enabled by --api.insecure=true)
- "8080:8080"
volumes:
# So that Traefik can listen to the Docker events
- "/var/run/docker.sock:/var/run/docker.sock:ro"
networks:
- helloworld_network
helloworld1:
container_name: "helloworld1"
image: "one/helloworld"
restart: unless-stopped
environment:
PORT : 8181
# `ports` can be disabled with the label `traefik.enable=false`
# ports:
# - "8181:8181"
networks:
- helloworld_network
labels:
# Honestly I don't know if this is needed.
# - traefik.port=80
# Tell Traefik explicitly to expose this container
- "traefik.enable=false"
# The domain to which the service will respond
- "traefik.http.routers.helloworld1.rule=Host(`hello1.localhost`)"
# Allow requests only from the predefined entry point "http"
- "traefik.http.routers.helloworld1_router.entrypoints=http"
helloworld2:
container_name: "helloworld2"
image: "two/helloworld"
restart: unless-stopped
environment:
PORT : 8282
# ports:
networks:
- helloworld_network
labels:
- traefik.port=8282
# Tell Traefik explicitly to expose this container
- "traefik.enable=false"
# The domain to which the service will respond
- "traefik.http.routers.helloworld2_router.rule=Host(`hello2.localhost`)"
# Allow requests only from the predefined entry point "http"
- "traefik.http.routers.helloworld2_router.entrypoints=http"
networks:
helloworld_network:
name: helloworld_network
attachable: true
driver: overlay
default:
driver: bridge
index.js :
const http = require('http')
process = require('process'),port = process.env.PORT ? parseInt(process.env.PORT.trim()) : 8080,server = http.createServer(function (req,res) {
res.writeHead(200,{'Content-Type': 'text/plain'});
res.end(`Hello World from: ${process.env.PORT} \n`);
});
server.listen(port);
console.log(`Server listening on port ${port}`);
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。