k8s ingress 规则对不上?把 YAML 贴给走 TaoToken 的 Codex 对照

发布时间:2026/9/18 18:47:53
k8s ingress 规则对不上?把 YAML 贴给走 TaoToken 的 Codex 对照 k8s 的 ingress 规则对不上是那种看着最没脾气、查起来最耗时间的故障。kubectl apply -f ingress.yaml返回 createdkubectl get ingress的 ADDRESS 也有值可域名一访问不是 404 就是 503。要查这种错最省事的做法是先在 https://taotoken.net/?utm_sourcetaotoken_aicg_blog_end 创建 TaoToken 的 API Key把 Codex 接到 https://taotoken.net/api 这条兼容通道上再把 ingress YAML、Service 定义和 ingress-controller 的日志贴给它逐项对照。这篇的重点不是教你背 ingress 字段含义而是把「人对 YAML 容易只盯着自己写的那一行」这个毛病绕过去。ingress 只能用 YAML 配规则再按域名和 URL 路径把请求交给对应的 Service真正干活的是以 Pod 形式跑在集群里的 ingress-controller。规则、Service、controller 日志分别属于三个文件或三个命令的输出凑齐它们才能交叉验证。下面按排障顺序走先看症状怎么分类再把 Codex 接到 TaoToken 通道然后整理三段对照材料接着逐项排 NodePort、443、tls.crt/tls.key 和 default backend 8181最后在本地执行 kubectl 与 curl 验证。1. Ingress 规则写了却不生效先把症状拆开1.1 域名、路径、Service 名对不上的三种现场第一种是 host 对不上。Ingress rule 里写的是api.example.com实际访问用了裸 IP 或者www.api.example.com请求进不到这条 rule。ingress-controller 在没有 server_name 命中时会落到默认 server返回默认后端的 404 页面页面上往往带一行 default backend 的提示。这种情况在浏览器里看就是「域名能解析、TCP 能连上、就是 404」很容易误判成后端服务挂了。第二种是 path 和 pathType 的组合没想清楚。path: /api/v1配pathType: Exact那你访问/api/v1/带斜杠就匹配不上改成Prefix才会做前缀匹配。ImplementationSpecific交给不同 controller 自己解释行为随版本变排查阶段别拿它当赌注。还有一类是写了/api却期望它能接住/apiV2前缀匹配是按路径段切的不是字符串包含。第三种是 backend 里的 service name 或 port 写错。Ingress 的backend.service.name默认只认同一 namespace 下的 Service跨 namespace 得另想办法。port 部分要注意填的是 Service 的spec.ports[].port数字或者该端口的name不是 Pod 的 containerPort也不是 targetPort。名字或端口对不上controller 在 Endpoints 里找不到可用地址日志里就会出现 upstream 连不上的记录。1.2 为什么不先改 YAML而是先攒一份对照材料盯着自己写的 YAML 改通常越改越乱因为判断依据只有「我觉得应该这样」。更可靠的办法是把四份材料并排放在一起ingress 全文、匹配到的 Service 全文、kubectl get endpoints的输出、以及 ingress-controller 最近几百行日志。这四份东西分属不同文件交叉看才能定位到底哪一层断了。这活适合交给 Codex 做但前提是它得能稳定读到长上下文。官方通道的额度和多 Key 切换问题会把排查节奏打断所以先把执行工具接到 TaoToken 的统一接入通道上让 Codex 能一口气读完这几份材料。你的工作是执行 kubectl、复制输出它的工作是找不一致改不改由你在本地决定。2. 给 Codex 接上 TaoTokenconfig.toml 里只动三行2.1 在模型广场确认模型 ID再创建 API Key打开 TaoToken 注册进模型广场看你打算用的模型 ID。这个列表会调整所以别抄别人文章里的旧 ID以页面当时的展示为准。同一页面的控制台里可以创建 API Key本文一律用占位符YOUR_API_KEY表示真实 Key 只放在你自己机器的环境变量里不要写进 YAML 或提交到 Git。创建 Key 这一步和生产环境的 kubeconfig 要分开对待。排查 ingress 用的 Key 只服务于 Codex 这类消耗 Token 的工具它不会、也不应该被塞进集群里的任何 Secret。集群里该有的是 tls.crt/tls.key 这类证书 Secret两者不是一回事。2.2 ~/.codex/config.toml 里把 base_url 指向 TaoToken 通道Codex 的配置写在~/.codex/config.toml关键是改model_provider和 provider 段的base_url不要把 Claude Code 那套ANTHROPIC_*变量搬过来两者协议不一样。下面这份可以直接抄把模型 ID 换成你在模型广场看到的值model YOUR_MODEL_ID model_provider taotoken [model_providers.taotoken] name TaoToken base_url https://taotoken.net/api env_key TAOTOKEN_API_KEY wire_api chat然后在启动 Codex 的同一个 shell 里导出 Keyexport TAOTOKEN_API_KEYYOUR_API_KEY codex两个容易踩的点base_url末尾不要补/v1也不要往上面拼任何查询参数填https://taotoken.net/api就对了env_key写的是环境变量名不是 Key 本身。如果启动后报鉴权失败先确认导出变量的 shell 和跑 codex 的 shell 是同一个再确认 Key 没复制进多余空格。3. 把 ingress YAML、Service、controller 日志整理成三段对照材料3.1 三段材料怎么剪剪到什么粒度第一段是 ingress 全文包含ingressClassName、annotations、spec.tls和spec.rules。annotations 里可能藏着 rewrite-target 之类的改写规则它会改变最终匹配的路径剪材料时不能漏。第二段是 rule 指向的那个 Service 全文重点是metadata.name、metadata.namespace、spec.type、spec.ports和spec.selector。第三段是 ingress-controller 的日志。先拿到 controller Pod 名再取尾部若干行kubectl get pods -n ingress-nginx -o wide kubectl logs -n ingress-nginx controller-pod --tail200日志里值得留下的行包括带 upstream、no matches、SSL、certificate 的。为了减少干扰可以按关键字过滤后再贴kubectl logs -n ingress-nginx controller-pod --tail300 | grep -Ei upstream|no matches|ssl|certificate|404|503有一个边界要提前说清楚Codex 只能读你贴给它的文本它不会连你的集群也不该被要求去执行 kubectl。所有命令都在你本地或者跳板机上跑跑完把输出贴回对话。3.2 让 Codex 按 host → path → service:port 的顺序逐行对照材料凑齐后给 Codex 的指令要具体到步骤别只说「帮我看看哪错了」。可以直接用这段下面是我的 ingress YAML、对应的 Service YAML以及 ingress-controller 的日志片段。 请按四步逐项对照 1. 请求的 host 是否能命中 rules[].host含通配符写法 2. 请求的 path 与 pathType 是否匹配 3. backend.service.name 与 Service 的 metadata.name、namespace 是否一致 4. backend.service.port 与 Service 的 spec.ports 是否对得上。 每一步给出「一致 / 不一致」的结论不一致时给出最小修改建议和修改后的片段。 不要假设我已经改过任何内容也不要输出我没贴的字段。这个提示词的用意是把「找不一致」变成可核对的清单。Codex 返回 diff 建议后你本地改 YAML 再kubectl apply再看下一轮日志。第二轮如果 host 匹配上了但仍然 503焦点就转到端口和 Endpoints而不是继续怀疑 host。4. 四类高频错位NodePort、443、tls.crt/tls.key、default backend4.1 NodePort 与 80/443 的端口错位ingress-controller 自己也是 Pod它通过一个 Service 暴露出去。如果这个 Service 的类型是 NodePort对外监听的很可能是 30080、30443 这类端口你却拿 80 和 443 去访问当然连不上。这里有三层端口要分清客户端访问的端口NodePort 或云上负载均衡的 80/443、controller Service 的 port、controller Pod 容器里的监听端口。kubectl get svc -n ingress-nginx -o wide kubectl get pods -n ingress-nginx -o wide输出里PORT(S)列会明确写出80:30080/TCP这种映射关系。把这三层数字抄进对话里让 Codex 对照你的访问方式检查是否错位。顺带看EXTERNAL-IP如果一直是 pending说明负载均衡没起来访问入口本身就不存在。4.2 tls.crt / tls.key 没挂上或者 secretName 对不上证书这条线通常这样创建本地用 openssl 生成tls.crt和tls.key再用kubectl create secret tls把两个文件装进 Secret。kubectl create secret tls my-tls --certtls.crt --keytls.key -n namespace三个一致性必须检查Secret 的 namespace 与 Ingress 的 namespace 相同Ingress 里spec.tls[].secretName与 Secret 名完全一致spec.tls[].hosts包含 rule 里的 host。少了第三项SNI 匹配不上会回落到默认证书浏览器报证书域名不匹配。证书内容本身也可以本地核对openssl x509 -in tls.crt -noout -subject -dates openssl x509 -in tls.crt -noout -text | grep -A1 Subject Alternative Name如果 SAN 里没有你访问的域名问题不在 ingress 规则而在签发环节。日志侧常见的关键词是secret xxx not found、SSL_do_handshake() failed、no ssl_certificate is defined把这些行一起贴给 Codex它能帮你把日志关键词和配置项对应起来。4.3 default backend 8181 与「规则没命中」的关系不少 ingress-controller 的默认后端监听在 8181 端口任何没匹配上 rule 的请求都会被丢到这里返回一个 404 页面。看到 404、页面内容还带 default backend 字样基本可以判断请求根本没进任何 rule。这个信号很有价值说明 Service 和 Pod 可能是好的排查方向应该留在 host 和 path 上而不是去重启后端。如果 404 页面不是默认后端的样子而是应用自己吐的那说明请求已经打到 Pod问题在应用路由或者 rewrite 规则上方向完全不同。区分这两种 404能省掉不少无效操作。5. 验证本地执行 kubectl 和 curl把输出贴回对话5.1 本地命令清单改完 YAML 并 apply 之后不要只在浏览器里刷新。按顺序跑下面这组命令把每一条的输出留好kubectl get ingress -n namespace -o yaml kubectl describe ingress ingress-name -n namespace kubectl get svc -n namespace -o wide kubectl get endpoints -n namespace kubectl get pods -n ingress-nginx -o wide kubectl logs -n ingress-nginx controller-pod --tail200然后用 curl 从集群外部打一次注意用-H Host: ...或--resolve把域名指到实际入口避免本地 DNS 干扰curl -I -H Host: api.example.com http://node-ip:nodeport/ curl -k -I --resolve api.example.com:443:node-ip https://api.example.com/这些命令全部由你在本地执行。Codex 不接触你的集群也不执行任何命令。5.2 把输出贴回 Codex 做第二轮对照第二轮对话的开场可以这样写这是修改后的 ingress YAML 和 Service YAML以及执行上述命令的输出。 请只对照两件事host/path 是否已经命中backend 指向的 Service 和端口是否解析到非空 Endpoints。 如果 Endpoints 为空请只从 selector 与 Pod labels 的匹配关系上给出检查建议。之所以把范围收窄是因为第二轮如果继续泛泛地看很容易被 annotations 里无关的配置带跑。Endpoints 为空是很典型的一类Service 的spec.selector和 Pod 的 labels 对不上ingress 规则再正确也转不过去。这一步不需要动 ingress 本身改的是 Service 或工作负载的标签。6. 跑通之后去控制台对一下这次调用6.1 同一把 Key 继续用在下一轮 ingress 检查ingress 排障往往不止一轮先修 host再修端口再看证书最后确认 default backend 不再出现。这个过程里 Codex 会反复读长 YAML 和日志Token 消耗比日常问答高。同一把YOUR_API_KEY可以继续用于后续检查比如让 Codex 对照kubectl get svc的输出确认 NodePort 与 80/443 的映射是否一致或者让它解释一段SSL_do_handshake() failed的日志含义。它做的事始终是读文本、给对照结论命令还是你本地跑。6.2 该去哪个页面创建下一把 Key、看用量如果打算把这类排查固定成日常流程建议顺手做两件事。一是到 TaoToken 模型对话 用同一把 Key 发一条测试消息确认模型 ID 和 Base URL 没填错再回头跑 Codex 会更稳。二是打开 控制台 API Keys 看一下这次排查消耗了多少顺便决定要不要为长期使用单独建一把 Key如果写代码的频率上来了Coding Plan 页面上有当前的套餐说明自己对着用量估一下就行。至于 ingress 本身的字段细节还是以你集群里 controller 版本对应的文档为准Codex 给的只是对照结论最终 apply 前请再看一眼 diff。最后留一个自己的习惯每次贴给 Codex 的材料里一定夹带一条出错时的原始日志和一条正常时的日志两者对照着看比只贴一堆配置要快得多。ingress 这层的问题八成都藏在这种「同一条规则、两种结果」的差异里。