# Nginx 配置迁移到 K3s + Traefik 指南 --- tags: kubernetes, k3s, traefik, nginx-migration, ingress, services description: 将 Nginx 反向代理配置迁移到 K3s Kubernetes 集群,使用 Traefik 作为 Ingress Controller title: Nginx 到 K3s Traefik 迁移指南 createdAt: 2025-11-26 --- ## 概述 本指南说明如何将原有的 Nginx 反向代理配置迁移到 K3s Kubernetes 集群,使用 Traefik 作为 Ingress Controller。 ## 架构说明 ### 原架构(Nginx) - Nginx 直接反向代理到各个应用服务 - 使用 Let's Encrypt 证书 - 手动配置每个域名的 SSL ### 新架构(K3s + Traefik) - Traefik 作为统一的 Ingress Controller - 自动申请和续期 Let's Encrypt 证书 - 使用 Kubernetes Service 和 Endpoints 映射外部服务 - 使用 IngressRoute CRD 配置路由规则 ## 配置文件说明 ### 1. 外部服务配置 (`services/external-services.yaml`) 为每个外部运行的应用创建 Kubernetes Service 和 Endpoints: ```yaml # Service 定义服务接口 apiVersion: v1 kind: Service metadata: name: blinko-external namespace: default spec: type: ClusterIP ports: - port: 3111 targetPort: 3111 protocol: TCP name: http # Endpoints 指向实际的 IP 地址 apiVersion: v1 kind: Endpoints metadata: name: blinko-external namespace: default subsets: - addresses: - ip: 10.0.32.6 # 实际服务运行的 IP ports: - port: 3111 name: http ``` ### 2. Traefik IngressRoute 配置 (`ingress/apps-ingressroute.yaml`) 为每个服务配置域名路由和 HTTPS: ```yaml apiVersion: traefik.io/v1alpha1 kind: IngressRoute metadata: name: blinko-https namespace: default spec: entryPoints: - websecure # HTTPS 入口 routes: - match: Host(`blinko.xiongxiao.me`) kind: Rule services: - name: blinko-external port: 3111 tls: certResolver: letsencrypt # 自动申请 SSL 证书 ``` ## 服务列表 已迁移的服务包括: | 域名 | 服务名称 | 端口 | IP 地址 | 说明 | |------|---------|------|---------|------| | blinko.xiongxiao.me | blinko-external | 3111 | 10.0.32.6 | Blinko 笔记 | | chat.xiongxiao.me | chat-external | 3000 | 127.0.0.1 | 聊天服务 | | kevisual.xiongxiao.me | kevisual-external | 3005 | 127.0.0.1 | Kevisual | | www.xiongxiao.me | www-external | 3005 | 127.0.0.1 | 主网站 | | immich.xiongxiao.me | immich-external | 2283 | 127.0.0.1 | 图片管理 | | cloud.xiongxiao.me | cloud-external | 5212 | 127.0.0.1 | 云盘 | | docmost.xiongxiao.me | docmost-external | 3011 | 127.0.0.1 | 文档协作 | | drawio.xiongxiao.me | drawio-external | 13000 | 127.0.0.1 | 绘图工具 | | minio.xiongxiao.me | minio-external | 9000 | 127.0.0.1 | 对象存储 | | npm.xiongxiao.me | npm-external | 30001 | 10.0.32.6 | NPM 私有仓库 | | gist.xiongxiao.me | gist-external | 6157 | 127.0.0.1 | 代码片段 | | webdav.xiongxiao.me | webdav-external | 6060 | 127.0.0.1 | WebDAV | | esm.xiongxiao.me | esm-external | 12000 | 127.0.0.1 | ESM CDN | | umami.xiongxiao.me | umami-external | 4004 | 127.0.0.1 | 网站分析 | | pwd.xiongxiao.me | pwd-external | 8180 | 127.0.0.1 | 密码管理 | | meilisearch.xiongxiao.me | meilisearch-external | 7700 | 127.0.0.1 | 搜索引擎 | | memos.xiongxiao.me | memos-external | 8181 | 10.0.32.6 | Memos | | git.xiongxiao.me | gitea-external | 3000 | 10.0.32.6 | Gitea | ## 部署步骤 ### 1. 确保 Traefik 已部署 ```bash # 检查 Traefik 是否运行 kubectl get pods -n traefik # 如果未部署,先部署 Traefik kubectl apply -f k8s/xiongxiao.me/traefik/traefik-complete.yaml ``` ### 2. 部署外部服务配置 ```bash # 应用外部服务配置 kubectl apply -f k8s/xiongxiao.me/services/external-services.yaml # 验证服务创建成功 kubectl get svc -n default | grep external kubectl get endpoints -n default | grep external ``` ### 3. 部署 IngressRoute ```bash # 应用 IngressRoute 配置 kubectl apply -f k8s/xiongxiao.me/ingress/apps-ingressroute.yaml # 验证 IngressRoute 创建成功 kubectl get ingressroute -n default ``` ### 4. 验证路由配置 ```bash # 检查 Traefik Dashboard kubectl port-forward svc/traefik 8080:8080 -n traefik # 访问 http://localhost:8080/dashboard/ # 测试域名解析 curl -k https://blinko.xiongxiao.me ``` ## 注意事项 ### IP 地址说明 - `127.0.0.1` - 指向 Kubernetes 主节点本地运行的服务 - `10.0.32.6` - 指向局域网中其他机器运行的服务 **重要**: 如果服务是在 Pod 外部运行的: - 本地服务需要确保端口可以从 Pod 内访问 - 远程服务需要确保网络互通 ### WebSocket 支持 Traefik 默认支持 WebSocket,以下服务需要 WebSocket: - chat.xiongxiao.me - kevisual.xiongxiao.me - www.xiongxiao.me - immich.xiongxiao.me - docmost.xiongxiao.me - drawio.xiongxiao.me - minio.xiongxiao.me - gist.xiongxiao.me - webdav.xiongxiao.me - esm.xiongxiao.me - umami.xiongxiao.me ### SSL 证书 - Traefik 自动使用 Let's Encrypt 申请证书 - 证书存储在 `/data/traefik-acme/acme.json` - 自动续期,无需手动操作 ### 大文件上传 部分服务配置了大文件上传支持(原 Nginx 的 `client_max_body_size`): - blinko: 1024m - chat: 200m - kevisual: 200m - immich: 1024m - cloud: 1024m - docmost: 1024m - drawio: 1024m - minio: 200m - npm: 24m - gist: 1024m - webdav: 2024m - esm: 2048m - umami: 1024m - git: 2048m 如需在 Traefik 中配置,可添加 Middleware: ```yaml apiVersion: traefik.io/v1alpha1 kind: Middleware metadata: name: large-upload namespace: default spec: buffering: maxRequestBodyBytes: 2147483648 # 2GB ``` ## 特殊配置 ### look-good.xiongxiao.me (静态网站) 这是一个静态网站服务,需要单独处理: **方案 1**: 将静态文件打包到 Pod 中运行 Nginx ```bash # 创建 ConfigMap 或使用 PV 挂载静态文件 # 运行 Nginx Pod ``` **方案 2**: 继续使用原 Nginx 服务器,通过 Service 映射 ### home.mz.xiongxiao.me 这个服务指向外部域名 `xionmi.mz.zxj.im:8123`,需要特殊处理。 ## 故障排查 ### 服务无法访问 1. 检查 Service 和 Endpoints ```bash kubectl get svc,endpoints -n default | grep ``` 2. 检查 IngressRoute ```bash kubectl describe ingressroute -n default ``` 3. 检查 Traefik 日志 ```bash kubectl logs -n traefik -l app=traefik ``` ### SSL 证书问题 1. 检查证书文件 ```bash kubectl exec -n traefik -- cat /acme/acme.json ``` 2. 确认 Let's Encrypt 配置 ```bash kubectl describe deployment traefik -n traefik | grep acme ``` ## 回滚到 Nginx 如果需要回滚: 1. 在 DNS 中将域名指回原 Nginx 服务器 2. 删除 K3s 配置: ```bash kubectl delete -f k8s/xiongxiao.me/ingress/apps-ingressroute.yaml kubectl delete -f k8s/xiongxiao.me/services/external-services.yaml ``` ## 后续优化 1. **容器化服务**: 逐步将外部服务容器化并部署到 K3s 2. **服务网格**: 考虑使用 Istio 或 Linkerd 3. **监控告警**: 集成 Prometheus + Grafana 4. **自动扩展**: 配置 HPA (Horizontal Pod Autoscaler) 5. **日志聚合**: 使用 ELK 或 Loki 收集日志 ## 参考资料 - [Traefik 官方文档](https://doc.traefik.io/traefik/) - [K3s 官方文档](https://docs.k3s.io/) - [Kubernetes Services 文档](https://kubernetes.io/docs/concepts/services-networking/service/)