如何通过反向代理统一暴露多个可视化容器

解读

在国内生产环境中,一个公网 IP 只能绑定 80/443 端口,而微服务架构下 Grafana、Prometheus、Jaeger、Nacos、MinIO 等可视化组件各自监听独立端口。直接映射会暴露内部端口、增大攻击面,且不符合等保 2.0 要求。反向代理的核心价值是**“统一入口 + 七层路由”**:通过域名或路径区分服务,TLS 终结、身份认证、限流、白名单全部在代理层完成,容器侧只需监听容器网络内部端口,实现“零端口映射”暴露。

知识点

  1. 容器网络模型:所有可视化容器挂到同一自定义 bridge 网络(或 overlay),通过容器名 DNS 解析实现东西向互通,避免 host 模式端口抢占。
  2. 反向代理选型
    • Traefik:云原生首选,自动发现 Docker label,无需 reload 即可热更新,支持 TCP/UDP 与 HTTPS,Let’s Encrypt 自动证书续期完全合规国内云厂商。
    • Nginx:最稳,阿里系、腾讯系镜像源同步快,openresty + lua 可实现 WAF 与灰度,但需外挂 conf 文件或 etcd 做热更新。
  3. 路由规则
    • 域名路由:grafana.xxx.comjaeger.xxx.com——需提前在国内云厂商 DNS 备案
    • 路径路由:/grafana//prometheus/——需加 X-Forwarded-Prefix 重写,防止静态资源 404。
  4. 安全加固
    • 非 root 用户启动容器(USER 指令),只读文件系统--read-only),drop 掉所有 capability
    • BasicAuth 或 OIDC 对接企业微信、钉钉 SSO,满足最小权限与审计留痕
    • Header 安全:强制 HSTS、X-Content-Type-Options、X-Frame-Options DENY,通过代理层统一注入。
  5. 高可用
    • 代理容器双实例 + Swarm VIP 或 K8s Service 做负载均衡,健康检查路径 /ping 必须返回 200。
    • 配置版本化:Nginx 使用 configmap + GitOps,Traefik 使用 CRD,变更走钉钉审批 + GitLab CI,回滚秒级。

答案

  1. 创建统一网络
    docker network create --driver bridge visual
    
  2. 启动可视化容器,不映射任何宿主机端口,只暴露内部端口并加 label 供 Traefik 识别
    docker run -d --name grafana \
      --network visual \
      -e GF_SERVER_ROOT_URL="https://grafana.xxx.com" \
      -l "traefik.enable=true" \
      -l "traefik.http.routers.grafana.rule=Host(\`grafana.xxx.com\`)" \
      -l "traefik.http.routers.grafana.tls=true" \
      -l "traefik.http.routers.grafana.tls.certresolver=ali" \
      grafana/grafana:latest
    
  3. 启动 Traefik 反向代理,绑定 80/443,挂载阿里云 DNS 凭证用于自动 DNS-01 挑战签发证书
    docker run -d --name traefik \
      --network visual \
      -p 80:80 -p 443:443 \
      -v /var/run/docker.sock:/var/run/docker.sock:ro \
      -v $PWD/acme.json:/acme.json \
    traefik:v3.0 --api.dashboard=true \
      --providers.docker=true \
      --certificatesresolvers.ali.acme.email=your@xxx.com \
      --certificatesresolvers.ali.acme.storage=/acme.json \
      --certificatesresolvers.ali.acme.dnschallenge.provider=alidns
    
  4. 备案与解析:在阿里云 DNS 新增 A 记录 grafana.xxx.com 指向公网 IP,ICP 备案完成即可访问。
  5. 安全验证:
    • curl -I https://grafana.xxx.com 返回 HSTSX-Frame-Options 头。
    • 宿主机 netstat -tnlp 仅能看到 80/443,无 3000 端口暴露,通过等保扫描。

拓展思考

  1. 蓝绿发布:利用 Traefik weighted 服务标签,把新版本容器权重从 0 逐步调到 100,零中断完成可视化组件升级。
  2. 边缘场景:在边缘 K3s 集群中,用 Traefik CRD IngressRoute 替代传统 Ingress,HostPort 直接监听 80/443,节省一层 SLB 费用,适合零售门店、加油站等弱网环境。
  3. 多租户隔离:通过 Traefik Middleware 加 Header 鉴权(X-Tenant-ID),同一套 Grafana 多副本实例根据 Header 路由到不同数据库,实现** SaaS 化可观测平台**,满足金融客户硬多租需求。