news 2026/10/12 22:02:55

k8s集群搭建(四)-------- Ingress-Nginx 路由规则与 TLS 配置实战

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
k8s集群搭建(四)-------- Ingress-Nginx 路由规则与 TLS 配置实战

1. 从 Service 到外部访问:Ingress-Nginx 到底解决了什么问题

集群里 Pod 跑起来了,Service 也能在集群内部互相访问,但一到「让外面的人打开浏览器访问」这一步,很多人就卡住了。NodePort 要记端口号,LoadBalancer 在自建环境里又没有云厂商给你分配公网 IP,Service 数量一多,端口和 IP 就彻底乱套。Ingress-Nginx 就是来解决这最后一公里的:它本质是一个跑在集群里的 Nginx,通过监听 Ingress 资源的变化,动态生成 Nginx 配置并热加载,把外部请求按域名和路径转发到不同的 Service 上。

一句话概括它的能力:七层路由转发 + 负载均衡 + TLS 终止 + 静态资源托管 + 限流。适合谁?适合已经用 kubeadm 或二进制方式搭好集群、正在做自建环境对外暴露服务的同学。它和 Service 的分工是:Service 负责集群内部的四层寻址,Ingress 负责集群边缘的七层入口。你不需要给每个服务都开一个 LoadBalancer,只需要一个 Ingress-Nginx 的入口 IP,剩下的靠 Host 和 Path 规则分流。

这一篇是 k8s 集群搭建系列的第四篇,前三篇我们把控制面、工作节点、网络插件、Dashboard 都搞定了。现在集群是就绪状态,接下来要做的就是把 Dashboard 以及后续的业务服务,通过 Ingress-Nginx 暴露成一个带域名的 HTTPS 地址。整个过程分四步:装 MetalLB 拿到入口 IP、装 Ingress-Nginx 控制器、写 Ingress 资源定义路由、配 TLS 证书并用 curl 和 kubectl describe 验证。每一步我都会给出可直接复制的 YAML 和命令,你跟着敲就行。

先说清楚一个容易混淆的点:Ingress 是 k8s 的一种资源类型(规则声明),Ingress-Nginx 是具体实现这个规则的控制器(干活的人)。你写的是 Ingress YAML,真正让它生效的是 Ingress-Nginx Controller。市面上还有 Traefik、HAProxy Ingress 等实现,本文只讲 Ingress-Nginx,因为它是目前社区最主流、文档最全、踩坑资料最多的一个。

2. 前置准备:MetalLB 分配入口 IP 与 Ingress-Nginx 控制器部署

在自建内网环境里,Ingress-Nginx 的 Service 类型是 LoadBalancer,但裸机集群没有云厂商的 LB 实现,这个 Service 会一直卡在<pending>状态拿不到 external-ip。MetalLB 就是填补这个空缺的:它用 L2 或 BGP 模式,从一个你规划的 IP 地址池里给 LoadBalancer 类型的 Service 分配地址。如果你的服务器本身已经绑定了固定公网 IP,这一步可以跳过;但实验环境是内网,所以必须装。

装 MetalLB 之前有个前置动作:把 kube-proxy 的 IPVS 模式设为 strict ARP。执行kubectl edit configmap -n kube-system kube-proxy,找到mode和ipvs部分,改成下面这样:

apiVersion: kubeproxy.config.k8s.io/v1alpha1 kind: KubeProxyConfiguration mode: "ipvs" ipvs: strictARP: true

改完保存退出,然后重启 kube-proxy 让配置生效:kubectl rollout restart daemonset kube-proxy -n kube-system。这一步不做的话,MetalLB 的 L2 模式可能无法正常响应 ARP 请求,表现为 IP 分配了但 ping 不通。

接着部署 MetalLB 本体。官方安装清单比较大,我把它精简成关键部分,你直接 apply 即可。核心是命名空间、CRD、controller Deployment、speaker DaemonSet 和 webhook。注意镜像地址要换成你自己的私有仓库 tag:

kubectl apply -f metallb-native.yaml kubectl get pods -n metallb-system

看到 controller 和每个节点上的 speaker 都是 Running,就说明装好了。然后配置地址池,写一个metallb-layer2-config.yaml:

apiVersion: metallb.io/v1beta1 kind: IPAddressPool metadata: name: default-pool namespace: metallb-system spec: addresses: - 10.150.1.90-10.150.1.91 --- apiVersion: metallb.io/v1beta1 kind: L2Advertisement metadata: name: default-l2-advertisement namespace: metallb-system spec: ipAddressPools: - default-pool

addresses换成你内网里一段没人用的空闲 IP,我这里是 10.150.1.90 到 91 两个地址。执行kubectl apply -f metallb-layer2-config.yaml应用。L2 模式不需要路由器支持 BGP,配置最简单,适合实验环境。

接下来装 Ingress-Nginx。可以用 helm,也可以直接 apply 官方 yaml。我用后者,方便控制镜像来源。官方清单里包含 Namespace、ServiceAccount、RBAC、ConfigMap、两个 Service(controller 和 admission)、Deployment、两个 Job(生成和 patch webhook 证书)、IngressClass 和 ValidatingWebhookConfiguration。关键点在于 controller 的 Service 类型是 LoadBalancer,MetalLB 会从这里分配 external-ip:

kubectl apply -f ingress-nginx.yaml kubectl get svc -n ingress-nginx

等一会儿,你会看到ingress-nginx-controller的 EXTERNAL-IP 变成了 10.150.1.90,这就是集群的统一入口。同时确认 IngressClass 存在:kubectl get ingressclass,应该有一个名为 nginx 的类,controller 字段是k8s.io/ingress-nginx。这个类名后面写 Ingress 资源时要用到。

3. 可复制的 Ingress 资源与 TLS 证书配置

现在入口有了,开始写路由规则。我拿第三篇里部署的 Kubernetes Dashboard 做例子,把它通过k8s.test.com/dashboard暴露出来。Dashboard 后端本身是 HTTPS 的,所以 Ingress 这里要加一个backend-protocol: HTTPS的注解,否则会 502。

先创建 TLS 证书。自签一张就行,生产环境换成正式证书:

openssl req -x509 -nodes -days 365 -newkey rsa:2048 \ -keyout dashboard.key -out dashboard.crt \ -subj "/CN=k8s.test.com/O=dashboard" kubectl create secret tls dashboard-tls-secret \ --key dashboard.key --cert dashboard.crt \ -n kubernetes-dashboard

这里 Secret 必须建在 Dashboard 所在的kubernetes-dashboard命名空间,因为 Ingress 资源也在那个命名空间,TLS 引用是同命名空间的。创建完用kubectl get secret -n kubernetes-dashboard dashboard-tls-secret确认类型是kubernetes.io/tls。

然后写 Ingress 资源ingress-dashboard-config.yaml:

apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: kubernetes-dashboard-ingress namespace: kubernetes-dashboard annotations: nginx.ingress.kubernetes.io/backend-protocol: "HTTPS" nginx.ingress.kubernetes.io/rewrite-target: /$2 spec: ingressClassName: nginx tls: - hosts: - k8s.test.com secretName: dashboard-tls-secret rules: - host: k8s.test.com http: paths: - path: /dashboard(/|$)(.*) pathType: ImplementationSpecific backend: service: name: kubernetes-dashboard-kong-proxy port: number: 443

几个关键字段解释一下。ingressClassName: nginx指定用哪个控制器,必须和 IngressClass 名字一致。rewrite-target: /$2配合正则路径/dashboard(/|$)(.*),把/dashboard/xxx重写成/xxx再转发给后端,因为 Dashboard 后端不认识/dashboard这个前缀。backend-protocol: HTTPS告诉 Nginx 用 HTTPS 去连后端。pathType: ImplementationSpecific是因为用了正则,必须用这个类型。

如果你要配多个域名或多个路径,就在rules下面继续加。比如再加一个api.test.com指向另一个 Service:

- host: api.test.com http: paths: - path: / pathType: Prefix backend: service: name: my-api-service port: number: 8080

Prefix类型做前缀匹配,适合普通 HTTP 服务。多个 Ingress 资源可以共存,控制器会把它们合并成一份 Nginx 配置。写完执行kubectl apply -f ingress-dashboard-config.yaml。

4. 验证路由生效:curl 与 kubectl describe 实操

配置提交后,先看 Ingress 资源本身的状态:

kubectl describe ingress kubernetes-dashboard-ingress -n kubernetes-dashboard

输出里重点看三块:Rules段确认 Host 和 Path 解析正确,TLS段确认 secretName 是 dashboard-tls-secret,Events段如果没有报错就说明控制器接受了这份配置。如果 Events 里有invalid ingress class或admission webhook denied,说明类名写错或 webhook 校验没过。

接着验证控制器有没有真正生成 Nginx 配置。看 controller 的日志:

kubectl logs -n ingress-nginx deploy/ingress-nginx-controller --tail=50

正常会看到类似Adding ingress kubernetes-dashboard/kubernetes-dashboard-ingress和Reloading nginx configuration的日志。如果日志里出现error obtaining ingress class或unexpected error,就要回头检查 IngressClass。

然后从集群外部(你的办公电脑)验证。先在 hosts 文件里加一行,把域名指到入口 IP:

# Linux/macOS: /etc/hosts # Windows: C:\Windows\System32\drivers\etc\hosts 10.150.1.90 k8s.test.com

用 curl 带-k跳过自签证书校验,验证 HTTPS 路由:

curl -k -I https://k8s.test.com/dashboard

期望看到HTTP/2 200或者HTTP/1.1 302(Dashboard 可能重定向到登录页)。如果返回 404,说明 rewrite 规则没匹配上;返回 502,说明后端协议或端口不对;返回 503,说明后端 Service 没有可用 Endpoint。

再验证一下 HTTP 到 HTTPS 的跳转(如果你配了强制跳转注解的话),以及不带路径的根访问:

curl -k -I https://k8s.test.com/

还可以直接绕过域名,用入口 IP 加 Host 头测试,排除 DNS 干扰:

curl -k -I https://10.150.1.90/dashboard -H "Host: k8s.test.com"

这个命令能直接验证 Ingress 的 Host 匹配逻辑,如果它通了但域名访问不通,问题就在 DNS 或 hosts 配置上。最后浏览器打开https://k8s.test.com/dashboard,能看到 Dashboard 登录页就大功告成了。

5. 常见报错排查:从 401 到 local proxy failed 的对照表

Ingress-Nginx 的报错大多集中在几个固定位置,我把踩过的坑整理成对照表,你按现象查。

现象可能原因排查动作
Service 一直 pending,无 external-ipMetalLB 未装或地址池未配kubectl get pods -n metallb-system,检查 IPAddressPool
访问返回 404Path 或 rewrite 规则不匹配kubectl describe ingress看 Rules,核对正则
访问返回 502后端协议/端口错误检查backend-protocol注解和 Service port
访问返回 503后端无可用 Endpointkubectl get endpoints -n <ns> <svc>
报错local proxy failed后端 Pod 未就绪或探针失败看后端 Pod 的 readinessProbe
报错reading choices证书 Secret 格式错误确认 Secret 类型是kubernetes.io/tls
报错401 UnauthorizedDashboard token 过期或 RBAC 不足重新生成 token,检查 ServiceAccount
报错OAuth相关后端要求 OAuth 认证检查后端服务自身的认证配置
webhook 拒绝创建 Ingress类名错误或 webhook 证书失效kubectl get ingressclass,重启 admission Job

重点说几个高频的。local proxy failed通常不是 Ingress 本身的问题,而是后端 Pod 没通过就绪探针,Endpoints 列表是空的,Nginx 转发过去没人接。用kubectl get endpoints -n kubernetes-dashboard kubernetes-dashboard-kong-proxy一看便知,如果 ENDPOINTS 是<none>,就去查后端 Pod 的 readinessProbe。

reading choices这个报错一般出现在 TLS 配置上,多半是 Secret 里的 crt 或 key 内容不对,或者 Secret 类型不是kubernetes.io/tls。用kubectl get secret dashboard-tls-secret -n kubernetes-dashboard -o yaml看 data 里有没有 tls.crt 和 tls.key 两个键。

401 Unauthorized在 Dashboard 场景很常见,那是 Dashboard 自己的登录认证,不是 Ingress 的问题。你需要用kubectl create token生成一个 token 去登录。如果确认是 Ingress 层面的 401,检查有没有配auth-type或auth-secret注解。

还有一个隐蔽的坑:如果你用了rewrite-target但路径正则写错,请求会被重写成空路径,后端收到/返回 404。调试时把rewrite-target临时去掉,看原始路径能不能通,能通就说明是 rewrite 的问题。

6. 把 AI 编码助手接进你的集群工作流

集群搭好、Ingress 通了之后,日常写 YAML、调 Ingress 注解、排查报错这些活儿,其实可以交给 AI 编码助手来加速。我现在的习惯是:遇到不熟悉的注解组合,先让助手生成一版草稿,再自己核对官方文档。这里推荐用 TaoToken 作为统一的模型接入层,它把多家模型的 API 收敛成一个 OpenAI 兼容的入口,配置一次就能在 Claude Code、Cline、Codex 这些工具里切换模型。

接入方式很简单,以 Claude Code 为例,核心是三件套:Base URL、API Key、Model ID。Base URL 填https://taotoken.net/api,API Key 在控制台的 API Keys 页面生成,Model ID 按你需要的模型填。如果你用的是 Cline 或 Codex,配置逻辑一样,只是配置文件位置不同——Codex 改auth.json,Cline 在 MCP 设置里填 Base URL 和 Key。

具体操作路径:先去 API Keys 页面 生成一个 Key,然后参考接入文档 把 Base URL 和 Key 填进你的工具。想先试试模型效果,可以直接在模型对话 里问几个 Ingress 注解的问题,验证通了再配到本地工具。如果你长期做编码和 Agent 任务,Coding Plan 会更划算。

配好之后,你可以直接让助手帮你生成 Ingress YAML、解释kubectl describe的输出、或者根据报错日志给出排查方向。比如把local proxy failed的日志贴进去,它能快速定位到是 Endpoint 为空还是探针失败。但记住一点:助手给的是草稿,最终 apply 到集群前,注解和路径正则一定要自己核对一遍,尤其是rewrite-target这种容易写错的地方。集群操作不可逆,多一层人工确认不亏。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/10/12 22:02:33

基于Python机器学习的年龄和性别预测:源码、数据集与实战避坑指南

简介&#xff1a;这份资源面向计算机相关专业的在校学生、教师及企业员工&#xff0c;提供一套基于Python机器学习的年龄与性别预测完整项目&#xff0c;适合作为课程设计、大作业、毕业设计或入门进阶的学习案例。压缩包共36个文件&#xff0c;约34KB&#xff0c;以20个Python…

作者头像 李华
网站建设 2026/10/12 22:00:38

基于YOLOv5的直肠息肉检测实战:从数据标注到推理部署全流程

简介&#xff1a;这份资源面向医学影像分析人员、机器学习开发者及疾病筛查研发工程师&#xff0c;提供一套基于YOLOv5的直肠息肉检测系统完整实现方案&#xff0c;用于辅助医疗专家进行息肉自动检测与早期筛查。内容覆盖环境搭建、数据集创建与配置文件编写、模型训练、ONNX格…

作者头像 李华
网站建设 2026/10/12 21:57:09

Spring与微服务高频考点全梳理:从Bean生命周期到分布式锁

1. 面试官到底想从Spring和微服务里问出什么做Java面试辅导这些年&#xff0c;我越来越确定一件事&#xff1a;Spring和微服务这两个词&#xff0c;已经成了Java面试里绕不开的“基本盘”。不管你是面初级、中级还是高级&#xff0c;面试官总能在这些领域里找到切入点。有些候选…

作者头像 李华
网站建设 2026/10/12 21:56:27

从Session到JWT:无状态SSO在微服务中的落地实践

公司内部两套业务系统各自为政&#xff0c;每个系统都维护一套账号密码&#xff0c;用户烦、运维也烦——这个场景在三年前我负责的那条业务线上真实上演过。当时团队里现状很分裂&#xff1a;老系统还在用 Session 挂会话&#xff0c;新系统已经拆成了前后端分离的微服务结构。…

作者头像 李华
网站建设 2026/10/12 21:55:28

AI编码技能框架实战:从提示词到可复用技能模块,提升代码首次可用率

1. 从趋势榜第七说起&#xff1a;这个技能框架到底在解决什么问题前几天刷开源社区热榜的时候&#xff0c;一个叫“AI编码技能框架”的项目突然冲到了第七位&#xff0c;单日新增476颗星。这个增速在近半年的工具类项目里算是相当扎眼的。我第一时间把它clone下来跑了一遍&…

作者头像 李华
网站建设 2026/10/12 21:55:20

AI辅助城市情歌创作全链路:从意象到成品的实操指南

1. 一首AI情歌背后的完整创作链路拆解1.1 为什么选“城市情歌”这个切口做文创的人都有一个共识&#xff1a;城市题材是最难写、也最容易写砸的题材。难在哪&#xff1f;难在几乎所有能被想到的意象都被用过了——宽窄巷子、锦里、火锅、熊猫、玉林路的小酒馆。你随便打开一个短…

作者头像 李华