kubernetes安装traefik ingress,替换原来的nginx-ingress

一.实施背景

现有环境的k8s集群的ingress控制器,原来使用的是nginx-ingress,现在想替换为traefik ingress,以下是实施步骤

二.实施步骤

1.首先梳理现有 Nginx-Ingress 的关键信息,避免冲突

复制代码
# 查看 Nginx-Ingress 的命名空间、Ingress Class、端口
kubectl get ingressclasses # 查看集群内的 IngressClass(K8s 1.18+ 支持,1.15 需看注解)
kubectl get pods -A -l app=nginx-ingress # 查看 Nginx Pod 所在命名空间
kubectl get svc -A -l app=nginx-ingress # 查看 Nginx 暴露的端口(如 NodePort: 30080/30443 或 HostPort 80/443)

2.部署traefik

  • 创建命名空间

    kubectl create namespace traefik

  • traefik依赖的RBAC 权限配置

Traefik 需要访问 K8s API 来监听 Ingress、Service 等资源,创建 traefik-rbac.yaml

复制代码
# traefik-rbac.yaml
apiVersion: v1
kind: ServiceAccount
metadata:
  name: traefik-ingress-controller
  namespace: traefik
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: traefik-ingress-controller
rules:
  - apiGroups:
      - ""
    resources:
      - services
      - endpoints
      - secrets
    verbs:
      - get
      - list
      - watch
  - apiGroups:
      - networking.k8s.io
    resources:
      - ingresses
      - ingressclasses # K8s 1.20 新增
    verbs:
      - get
      - list
      - watch
  - apiGroups:
      - ""
    resources:
      - pods
    verbs:
      - list
  - apiGroups:
      - ""
    resources:
      - nodes
    verbs:
      - get
      - list
      - watch
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: traefik-ingress-controller
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: traefik-ingress-controller
subjects:
  - kind: ServiceAccount
    name: traefik-ingress-controller
    namespace: traefik
  • 创建traefik的ds

DaemonSet 模式可让 Traefik 运行在每个节点,通过 HostPort 暴露 80/443 端口(如果nginx-ingress已经使用这些端口,修改进行替换其他端口),适合生产环境。创建 traefik-daemonset.yaml

复制代码
# traefik-daemonset.yaml
apiVersion: apps/v1
kind: DaemonSet
metadata:
  name: traefik
  namespace: traefik
  labels:
    app: traefik
spec:
  selector:
    matchLabels:
      app: traefik
  template:
    metadata:
      labels:
        app: traefik
    spec:
      serviceAccountName: traefik-ingress-controller
      terminationGracePeriodSeconds: 60
      hostNetwork: true # 主机网络,便于后续端口切换
      containers:
      - name: traefik
        image: traefik:v2.9.10 # 适配 K8s 1.20 的稳定版本
        args:
          - --api.insecure=true # 测试阶段开启仪表盘(生产关闭)
          - --accesslog=true
          - --entrypoints.web.address=:8080 # 非冲突 HTTP 端口
          - --entrypoints.websecure.address=:8443 # 非冲突 HTTPS 端口
          - --kubernetesIngress=true
          - --kubernetesIngress.ingressClass=traefik # 绑定 IngressClass
          - --providers.kubernetesCRD=false # 暂不启用 CRD,仅用 Ingress
          - --providers.kubernetesIngress=true
        ports:
        - name: web
          containerPort: 8080
          hostPort: 8080 # 主机端口(非冲突)
        - name: websecure
          containerPort: 8443
          hostPort: 8443 # 主机端口(非冲突)
        - name: dashboard
          containerPort: 8081
          hostPort: 8081 # 仪表盘端口
        securityContext:
          capabilities:
            drop: [ALL]
            add: [NET_BIND_SERVICE]
        resources:
          limits:
            cpu: 1000m
            memory: 512Mi
          requests:
            cpu: 100m
            memory: 64Mi
        livenessProbe:
          httpGet:
            path: /ping
            port: 8081
          initialDelaySeconds: 10
          periodSeconds: 10
        readinessProbe:
          httpGet:
            path: /ping
            port: 8081
          initialDelaySeconds: 5
          periodSeconds: 5
      tolerations:
        - key: node-role.kubernetes.io/control-plane
          operator: Exists
          effect: NoSchedule
        - key: node-role.kubernetes.io/master
          operator: Exists
          effect: NoSchedule
---
# Traefik 仪表盘 Service(测试用)
apiVersion: v1
kind: Service
metadata:
  name: traefik-dashboard
  namespace: traefik
spec:
  selector:
    app: traefik
  ports:
  - name: dashboard
    port: 8081
    targetPort: 8081
    nodePort: 30801
  type: NodePort

kubectl apply -f traefik.yaml
  • 验证部署

    kubectl get pods -n traefik

    输出示例(每个节点一个 Pod):

    traefik-ingress-controller-7f557 1/1 Running 0 5m

    在任意节点执行

    netstat -tulpn | grep 80

    应看到 traefik 进程监听 80/443/8080 端口

  • 创建 Traefik IngressClass(K8s 1.20 原生)

    traefik-ingressclass.yaml

    apiVersion: networking.k8s.io/v1
    kind: IngressClass
    metadata:
    name: traefik
    annotations:
    ingressclass.kubernetes.io/is-default-class: "false" # 非默认,避免抢占流量
    spec:
    controller: traefik.containo.us/ingress-controller # Traefik 2.x 标识

  • 全量迁移 Ingress

单Ingress 修改(少量),前期测试

复制代码
kubectl edit ingress <ingress-name> -n <namespace>
# 修改 spec.ingressClassName 为 traefik(替换原 nginx)

批量修改(大量 Ingress)

复制代码
# 批量更新 default 命名空间所有 Ingress 的 ingressClassName
kubectl get ingress -n default -o name | xargs -I {} kubectl patch {} -n default --type='json' -p='[{"op": "replace", "path": "/spec/ingressClassName", "value":"traefik"}]'

# 跨命名空间批量更新(需 jq)
for ns in $(kubectl get ns -o json | jq -r '.items[].metadata.name'); do
  kubectl get ingress -n $ns -o name 2>/dev/null | xargs -I {} kubectl patch {} -n $ns --type='json' -p='[{"op": "replace", "path": "/spec/ingressClassName", "value":"traefik"}]' 2>/dev/null
done
  • 待全量迁移完成后,将 Traefik 设为默认控制器,新创建的 Ingress 会自动使用 Traefik

    编辑 Traefik IngressClass,添加默认注解

    kubectl edit ingressclass traefik
    metadata:
    annotations:
    ingressclass.kubernetes.io/is-default-class: "true" # 设为默认

    同时将 Nginx IngressClass 的该注解改为 "false"

    kubectl edit ingressclass nginx
    metadata:
    annotations:
    ingressclass.kubernetes.io/is-default-class: "false"

  • 下线 Nginx-Ingress(可选)

待 Traefik 稳定运行 24-72 小时后,逐步下线 Nginx-Ingress

复制代码
# 缩容 Nginx DaemonSet/Deployment 为 0
kubectl scale daemonset nginx-ingress-controller -n ingress-nginx --replicas=0
# 或 Deployment 模式:
kubectl scale deployment nginx-ingress-controller -n ingress-nginx --replicas=0

#完全删除
# 删除 Nginx-Ingress 相关资源
kubectl delete ns ingress-nginx
kubectl delete ingressclass nginx
kubectl delete clusterrole nginx-ingress-clusterrole
kubectl delete clusterrolebinding nginx-ingress-clusterrolebinding
  • 回退(紧急情况)

    1. 批量恢复 IngressClassName 为 nginx

    for ns in (kubectl get ns -o json | jq -r '.items[].metadata.name'); do kubectl get ingress -n ns -o name 2>/dev/null | xargs -I {} kubectl patch {} -n $ns --type='json' -p='[{"op": "replace", "path": "/spec/ingressClassName", "value":"nginx"}]' 2>/dev/null
    done

    2. 恢复 Nginx 副本数

    kubectl scale daemonset nginx-ingress-controller -n ingress-nginx --replicas=3

    3. 临时切回 Nginx 端口(按节点恢复 HostPort/LoadBalancer)

相关推荐
L-影27 分钟前
单体与微服务区别
微服务·云原生·架构
极客先躯1 小时前
高级java每日一道面试题-2026年04月18日-实战篇[Docker]-如何处理金融行业的时序数据容器化?
java·运维·docker·容器·金融·时序数据·高级面试
运维大师2 小时前
【K8S 运维实战】01-K8s架构深度剖析
运维·架构·kubernetes
杨了个杨89822 小时前
docker的网络模式
网络·docker·容器
spider_xcxc4 小时前
docker-compose.yaml 是“开发/测试环境”的利器,而 Kubernetes 配置是“生产环境”的标准。
docker·容器·kubernetes
chen_ke_hao5 小时前
K8s 高可用集群部署
java·docker·kubernetes
Geek-Chow6 小时前
Kubernetes HPA Behavior When Deployment Is Scaled to 0
云原生·容器·kubernetes
张忠琳16 小时前
【kubernetes】Node Feature Discovery 0.20.0-devel 源码深度解析 — 第四卷:CLI入口、工具链与全局架构总结
云原生·容器·架构·kubernetes·nvidia
Navicat中国17 小时前
开发者入门:无服务器数据库
数据库·云原生·serverless·navicat
nuo53420220 小时前
基础 6 —— Docker 容器数据卷
docker·容器