资讯动态

K8S 安装 Ingress 踩坑记:从 404 到把 endpoint 改到 TaoToken

发布时间:2026/10/17 23:40:20 来源:尧图企业网站定制
1. 从 404 开始K8S Ingress 装完为什么还是打不开服务K8S 安装 Ingress 之后访问域名返回 404这个场景几乎每个刚接触 Kubernetes 的人都会撞上一次。Ingress 本身不是一个能直接跑起来的组件它是一组转发规则的声明真正干活的是 Ingress Controller也就是集群里那个跑着 Nginx或 Traefik的 Pod。你写了一条 Ingress 规则Controller 读到它生成对应的 Nginx 配置reload 之后才会把流量按域名和路径转发到后端 Service。这条链路上任何一环错位浏览器看到的都是 404而且 404 的页面长得还挺像容易让人误以为「装成功了」。先把三种对外暴露方式摆清楚方便你判断自己该用哪种。LoadBalancer 依赖云厂商本地集群基本拿不到外部 IPNodePort 会在每个节点开一个 30000–32767 的高位端口能用但端口号难看、也不好做域名Ingress 则是用七层规则把域名和路径映射到 Service配合一个 Controller 统一入口。所以「K8S 安装 Ingress」这件事准确说是「部署 Ingress Controller 写 Ingress 规则」两件事缺一不可。404 的成因通常落在四个位置Controller 没真正就绪、Ingress 的 ingressClassName 没对上、规则里的 host/path 和你请求的不一致、后端 Service 的端口写错。还有一种更隐蔽的情况Controller 正常、规则也匹配上了但上游 endpoint 指向了一个不可用的地址Nginx 返回 502 或 503而某些配置下会表现为 404。这篇就按「先让 Controller 跑起来再让规则匹配上最后把上游 endpoint 换到统一通道复测」的顺序走一遍每一步都给可复制的 YAML 和 kubectl 命令。我试过在本地 kind 集群和一台单机 k3s 上分别装踩的坑不太一样但排查思路是共通的。下面所有命令你都可以直接粘到终端里跑注意把命名空间和 Service 名字换成你自己的。2. 前置准备部署 Ingress Controller 与 TaoToken 统一通道在写 Ingress 规则之前得先确认 Controller 真的在跑。社区版 nginx ingress controller 的部署方式这几年变过几次老教程里的mandatory.yaml单文件已经拆分了现在推荐用官方提供的 deploy 目录。下面这套在 1.24 以上的集群实测可用。kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.10.1/deploy/static/provider/cloud/deploy.yaml如果你在本地 kind 或 minikube 上provider/cloud会尝试申请 LoadBalancer 类型的 Service可能一直 Pending。本地环境换成provider/baremetal/deploy.yaml或者干脆用 NodePort 方式暴露kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.10.1/deploy/static/provider/baremetal/deploy.yaml装完先看 Pod 状态这一步别跳过Controller 没 Ready 后面全是白搭kubectl get pods -n ingress-nginx kubectl get svc -n ingress-nginx正常应该看到ingress-nginx-controller-xxxx处于 RunningService 那一列有 80 和 443 的映射。如果 Pod 一直 ContainerCreating多半是镜像拉不下来检查节点网络或换镜像源如果 CrashLoopBackOff看日志kubectl logs -n ingress-nginx deploy/ingress-nginx-controllerController 就绪后再准备一个后端服务。这里我用一个简单的 echo 服务做演示它会把你请求的路径原样返回方便确认路由到底有没有生效kubectl create deployment echo --imagehashicorp/http-echo -- /http-echo -listen:5678 -texthello from echo kubectl expose deployment echo --port80 --target-port5678注意--port80是 Service 端口--target-port5678是容器实际监听的端口。这两个数字后面写 Ingress 规则时会用到写反了就是 404 或 502 的经典来源。接下来是 TaoToken 统一通道的接入。TaoToken 提供 OpenAI 兼容的 API 入口把上游 endpoint 统一到https://taotoken.net/api这样你的应用不用为每个模型改一遍地址。先在控制台创建一个 API Key然后把它放进 K8S 的 Secret 里别硬编码在 YAML 中kubectl create secret generic taotoken-secret \ --from-literalapi-keysk-你的Key如果你还没拿到 Key去控制台新建一个即可https://taotoken.net/console?utm_sourcetaotoken_aicg_blog_endutm_mediumcsdnutm_campaignrewrite 。创建时注意权限范围只勾选需要的模型最小权限原则在集群里尤其重要。把上游 endpoint 指向 TaoToken 的意义在于Ingress 负责集群内的七层路由TaoToken 负责集群外模型调用的统一出口两者职责分开排查问题时边界清晰。当你的服务需要调用大模型时请求链路是「外部域名 → Ingress → Service → Pod → TaoToken API」任何一段断了都能单独定位。3. 可复制配置Ingress YAML 与上游 endpoint 改写先写一条最小可用的 Ingress 规则。把下面内容存成echo-ingress.yaml注意ingressClassName这一行1.18 之后社区版 Controller 默认用nginx这个 class 名老教程里用注解kubernetes.io/ingress.class: nginx的写法已经废弃两者混用会导致规则被忽略、直接 404。apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: echo-ingress namespace: default annotations: nginx.ingress.kubernetes.io/rewrite-target: / spec: ingressClassName: nginx rules: - host: echo.local http: paths: - path: / pathType: Prefix backend: service: name: echo port: number: 80几个容易写错的点pathType必填Prefix表示前缀匹配Exact表示精确匹配写错会导致路径对不上service.port.number是 Service 的端口不是容器的 targetPort这里填 80 对应前面kubectl expose的--port80rewrite-target: /会把请求路径重写成根路径如果你的后端对路径敏感去掉这行注解。应用它kubectl apply -f echo-ingress.yaml kubectl get ingress kubectl describe ingress echo-ingressdescribe的输出里会有一行Rules:确认 host 和 path 和你预期一致。如果describe里看到Default backend: default-http-backend:80说明规则没被解析多半是ingressClassName或 apiVersion 的问题。现在处理上游 endpoint。假设你的应用 Pod 里有个环境变量指向模型服务地址把它从原来的直连地址改成 TaoToken 的统一入口。用 ConfigMap 管理配置改的时候不用重建 PodapiVersion: v1 kind: ConfigMap metadata: name: app-config namespace: default data: OPENAI_BASE_URL: https://taotoken.net/api OPENAI_MODEL: gpt-4o-mini然后在 Deployment 里引用apiVersion: apps/v1 kind: Deployment metadata: name: app namespace: default spec: replicas: 1 selector: matchLabels: app: app template: metadata: labels: app: app spec: containers: - name: app image: your-app:latest envFrom: - configMapRef: name: app-config - secretRef: name: taotoken-secret注意envFrom会把 ConfigMap 和 Secret 里的所有键注入成环境变量Secret 里的api-key会变成API_KEY大写、连字符转下划线。如果你的应用读的是OPENAI_API_KEY在 Secret 里就用这个键名别指望 K8S 帮你做映射。改完配置滚动更新kubectl apply -f app-config.yaml kubectl rollout restart deployment/app kubectl rollout status deployment/app如果你用的是 Claude Code 这类需要 Anthropic 兼容入口的工具TaoToken 也提供对应通道Base URL 同样是https://taotoken.net/apiKey 和 Model ID 三件套配齐即可。Cline、CC Switch 这类客户端在设置里填的也是这三项缺一个都会报认证失败。4. 验证请求链路从 curl 到确认路由生效配置写完必须验证别靠「看起来对」就收工。第一步先绕过 Ingress直接打 Service确认后端本身是通的kubectl run curl-test --imagecurlimages/curl --rm -it --restartNever -- \ curl -s http://echo.default.svc.cluster.local/如果这一步就失败问题在 Service 或 Pod跟 Ingress 无关。返回hello from echo说明后端没问题继续往下。第二步验证 Ingress。本地集群没有外部 IP用端口转发把 Controller 的 80 端口映射到本机kubectl port-forward -n ingress-nginx svc/ingress-nginx-controller 8080:80另开一个终端带上 Host 头请求curl -H Host: echo.local http://localhost:8080/返回hello from echo就说明 Ingress 规则匹配成功、路由生效了。如果返回 404看 Controller 的访问日志kubectl logs -n ingress-nginx deploy/ingress-nginx-controller --tail50日志里会打印实际匹配到的 location 和 upstream对照你的规则看差在哪。常见的是 Host 头没带、path 写成了/echo但请求的是/、或者pathType用了Exact导致子路径不匹配。第三步验证上游 endpoint 改写是否生效。进到应用 Pod 里直接请求 TaoToken 的接口kubectl exec -it deploy/app -- sh curl -s https://taotoken.net/api/v1/models \ -H Authorization: Bearer $API_KEY能列出模型列表就说明统一通道通了。如果返回 401检查 Secret 里的 Key 是否正确注入、环境变量名是否匹配如果返回连接超时检查集群的出网策略或 NetworkPolicy 是否放行了 443 出站。第四步做一次端到端复测。让应用通过 Ingress 暴露的域名调用模型观察完整链路。这一步能同时验证 Ingress 路由和 TaoToken 通道任何一段出问题都会在日志里留下痕迹。实测下来把这两段分开验证比一上来就端到端调要快得多因为你能立刻知道是集群内路由的问题还是外部 API 的问题。5. 常见报错排查401、local proxy failed、reading choices、OAuth排障时先看报错原文不同错误指向完全不同的层。下面这几个是我在 K8S 装 Ingress 并接 TaoToken 过程中真实遇到过的。404 Not FoundNginx 页面Controller 正常但规则没匹配上。检查三处ingressClassName是否为nginx、kubectl get ingressclass里有没有这个 class、Host 头是否和规则里的host完全一致包括大小写。用kubectl describe ingress看 Events如果提示ingress class not found就是 class 名写错了。401 Unauthorized请求到了 TaoToken 但 Key 无效。先确认 Secret 注入的环境变量名kubectl exec进去env | grep -i key看一眼。常见错误是 Secret 里键名写成api-key应用读的却是OPENAI_API_KEY两边对不上。另外检查 Key 有没有多余空格从控制台复制时容易带上换行。local proxy failed这个报错通常出现在客户端工具Cline、Claude Code 等配置了本地代理但代理没起来或者 Base URL 填成了localhost而容器里根本没有这个服务。在 K8S 场景下如果你在 Pod 里配了HTTP_PROXY环境变量指向一个不存在的地址就会看到这个。检查 Deployment 的 env把不必要的代理变量删掉Base URL 直接用https://taotoken.net/api。reading choices 相关报错形如error reading choices: unexpected end of JSON input说明请求发出去了但响应体不是预期的 JSON。多半是 Base URL 少了/v1或者多了斜杠比如写成https://taotoken.net/api/v1/末尾带斜杠某些客户端拼接后会变成双斜杠导致 404。统一写成https://taotoken.net/api让客户端自己拼路径。OAuth 相关报错如果你用的是需要 OAuth 登录的工具报OAuth token expired或invalid_grant说明凭证过期了。这类工具通常有自己的凭证缓存目录清掉重新登录即可。注意 K8S 里 Pod 重启后临时目录会丢长期运行的服务应该用 API Key 而不是 OAuth 交互式登录。502 Bad GatewayIngress 匹配上了但后端连不上。检查 Service 的targetPort和容器实际监听端口是否一致用kubectl get endpoints echo看有没有后端地址。如果 endpoints 为空说明 Service 的 selector 没匹配到任何 Pod。503 Service Temporarily UnavailableController 找不到可用的 upstream。和 502 类似重点看 endpoints 和 Pod 的 readiness 探针。探针没通过时 Pod 不会进 endpoints流量自然过不去。排查顺序建议固定成先kubectl get pods -n ingress-nginx确认 Controller再kubectl get endpoints确认后端然后kubectl describe ingress确认规则最后看 Controller 日志确认匹配过程。这个顺序能覆盖九成以上的 404 场景。6. 把链路固定下来接入文档与后续验证入口配置跑通之后建议把 Ingress YAML、ConfigMap、Secret 的创建命令整理成一个deploy.sh下次换集群直接跑一遍。Secret 不要提交到 Git用kubectl create secret命令或者 SealedSecrets 这类方案管理。Ingress 规则里的 host 建议用变量替换方便在测试和生产环境之间切换。后续要验证模型调用是否正常可以直接在模型对话页面发一条测试请求确认 Key 和通道都没问题https://taotoken.net/model-chat?utm_sourcetaotoken_aicg_blog_endutm_mediumcsdnutm_campaignrewrite 。如果你要长期跑编码类 AgentCoding Plan 的额度模型更适合持续调用https://taotoken.net/coding-plan?utm_sourcetaotoken_aicg_blog_endutm_mediumcsdnutm_campaignrewrite 。需要新建或轮换 Key 时在控制台操作https://taotoken.net/api-keys?utm_sourcetaotoken_aicg_blog_endutm_mediumcsdnutm_campaignrewrite 。完整的接入参数和示例在文档里https://taotoken.net/doc?utm_sourcetaotoken_aicg_blog_endutm_mediumcsdnutm_campaignrewrite 。最后留一个实用习惯每次改完 Ingress 或 ConfigMap先kubectl rollout status等滚动更新完成再用curl -H Host: ...打一次别直接刷新浏览器。浏览器有缓存容易让你误判规则有没有生效。把验证命令写进 CI 的 smoke test每次部署自动跑一遍404 这类问题就能在合并前拦住。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑