配置kubectl客户端通过token方式访问kube-apiserver

本文介绍如何在Kubernetes中配置API Server并使用RBAC限制用户权限。通过设置kubectl config,添加token证书,及配置kube-apiserver启动参数,实现对crd-admin用户的权限控制,确保其仅能在crd namespace下操作。

帮助文档

使用的变量

本文档用到的变量定义如下:

$ export MASTER_IP=XX.XX.XX.XX # 替换为 kubernetes master VIP
$ export KUBE_APISERVER="https://${MASTER_IP}:6443"
$

创建 kubectl config 文件

$ # 设置集群参数
$ kubectl config set-cluster kubernetes \
  --insecure-skip-tls-verify=true \
  --server=${KUBE_APISERVER} 
$ # 设置客户端认证参数
$ kubectl config set-credentials crd-admin \
 --token=7176d48e4e66ddb3557a82f2dd316a93 
$ # 设置上下文参数
$ kubectl config set-context kubernetes \
  --cluster=kubernetes \
  --user=crd-admin  \
  --namespace=crd 
$ # 设置默认上下文
$ kubectl config use-context kubernetes
  • 使用命令 head -c 16 /dev/urandom | od -An -t x | tr -d ' ' 生成token

kube-apiserver设置

添加kube-apiserver端token证书

$ cat > /etc/kubernetes/pki/token_auth_file<<EOF
7176d48e4e66ddb3557a82f2dd316a93,crd-admin,1
 EOF
  • 第一列为刚刚生成的token,要与config里的token一致

  • 第二列为user, 要与config里的use一致

  • 编号或是序列号

添加kube-spiserver启动参数 --token-auth-file=/etc/kubernetes/pki/token_auth_file

  • 注意地址

  • 需要重启kube-apiserver

  • 证书验证和token和同时启用的,但是token和用户名密码,不可同时启用

配置客户端RBAC相关

限制 crd-admin 用户的行为,需要使用 RBAC 将该用户的行为限制在crd namespace 空间范围内

kubectl create -f crd-rbac.yaml

这样 crd-admin 用户对 crd namespace 具有完全访问权限。

crd-rbac.yaml具体内容:

apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: crdadmin-admin-binding
  namespace: crd
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: admin
subjects:
- apiGroup: rbac.authorization.k8s.io
  kind: User
  name: crd-admin
<think>我们面临一个矛盾现象:容器日志显示访问kube-apiserver的443端口失败并报"client connection lost",但在容器内手动curl却正常。结合引用内容,分析可能原因及解决方案如下: ### 1. **检查kube-apiserver服务状态(引用[2])** 引用[2]显示kube-apiserver的Service(`kubernetes`)通过ClusterIP(10.96.0.1)暴露443端口。问题中容器访问失败但手动curl正常,说明服务本身可用,但可能存在间歇性故障或特定访问路径问题: - **验证Service稳定性**:检查kube-apiserver的Endpoint是否正常: ```bash kubectl get endpoints kubernetes ``` 预期输出应包含控制平面节点的IP和端口(如`192.168.0.10:6443`)。若为空或异常,需检查kube-apiserver Pod状态[^2]。 - **排查网络策略**:容器内应用访问时失败,但手动curl成功,差异可能源于: - 应用使用代理或特殊网络配置(如HTTP_PROXY),而curl默认不使用。 - 应用并发连接数过高触发kube-apiserver限流(尤其QPS过高时)。 ### 2. **分析连接丢失的具体场景(引用[3])** 引用[3]描述了超时导致的请求失败(HTTP 500),并通过Zipkin追踪到超时错误。类比此案例: - **超时配置差异**:容器内应用可能未设置超时或设置过短,而手动curl使用默认超时(较长)。检查应用代码中的超时设置,例如: - Go语言:`http.Client{Timeout: 5 * time.Second}` - Java:`HttpURLConnection.setConnectTimeout(5000)` 若应用超时设置过短,在网络波动时易触发"connection lost"。 - **追踪请求链路**:在kube-apiserver侧启用审计日志(audit log)或分布式追踪(如Jaeger),观察失败请求的特征: ```bash # 修改kube-apiserver配置启用审计 audit-policy-file: | apiVersion: audit.k8s.io/v1 rules: - level: RequestResponse ``` 定位是否因特定请求(如大型List操作)导致超时[^3]。 ### 3. **验证kube-proxy的工作状态(引用[1])** 引用[1]强调通过NodePort验证服务连通性,同理需确认kube-proxy是否将ClusterIP(10.96.0.1)正确转发: - **检查kube-proxy日志**:在应用所在Node执行: ```bash kubectl logs -n kube-system kube-proxy-xxxxx ``` 观察是否有`Connection refused`或`reset by peer`错误。 - **排查iptables规则**:kube-proxy可能遗漏规则更新。在Node上检查是否有指向kube-apiserver的规则: ```bash sudo iptables-save | grep 10.96.0.1 ``` 预期应存在`KUBE-SERVICES`链的转发规则。若无,重启kube-proxy[^1]。 ### 4. **客户端行为差异分析** 手动curl成功而应用失败,可能原因包括: - **TCP连接复用**:应用使用长连接池,当kube-apiserver重启或连接闲置超时后,复用失效连接报错。需在客户端添加连接活性检测: - HTTP层:定期发送HEAD请求。 - TCP层:设置`SO_KEEPALIVE`选项。 - **DNS解析缓存**:应用可能缓存了过时的kube-apiserver IP(如10.96.0.1变更)。强制应用使用DNS而非IP直连,或缩短DNS缓存时间。 - **TLS握手失败**:容器内应用使用的根证书可能不完整(如未挂载集群CA)。对比手动curl使用的证书: ```bash curl -v https://10.96.0.1:443 2>&1 | grep "CA cert" ``` 与应用环境变量`SSL_CERT_FILE`或代码中加载的证书比较。 ### 解决方案总结 | 现象 | 可能原因 | 解决步骤 | |------|----------|----------| | 间歇性连接丢失 | 客户端超时设置过短 | 增加客户端超时阈值至$10$秒以上 | | 仅应用访问失败 | 连接池管理缺陷 | 添加连接活性检测,配置最大空闲时间 | | 日志报错但服务正常 | kube-proxy规则异常 | 重启kube-proxy Pod,检查iptables规则 | | 高并发下失败 | kube-apiserver限流 | 降低QPS,或扩展控制平面节点 | > **关键验证步骤**:在应用代码中添加重试逻辑(指数退避),若错误减少则验证为偶发网络问题;若持续失败,结合审计日志和kube-proxy排查深层原因。 §§相关问题§§ 1.如何配置Kubernetes审计日志以诊断API请求失败? 2.在容器化应用中如何正确实现HTTP连接的活性保持? 3.如何优化Kubernetes客户端以减少对kube-apiserver的负载? </think>### 容器日志报错"client connection lost"但手动curl正常的根本原因分析 该矛盾现象通常由**瞬时网络问题**、**客户端行为差异**或**Kubernetes组件异常**导致。结合引用内容,具体原因如下: #### 1. **kube-proxy转发异常(核心原因)** - **转发规则丢失**:kube-proxy维护的iptables/ipvs规则可能失效(引用[1][2])。当应用发起请求时,kube-proxy无法正确转发到kube-apiserver(10.96.0.1:443),而手动curl时规则可能已恢复。 - **验证方法**: ```bash # 检查kube-proxy日志 kubectl -n kube-system logs -l k8s-app=kube-proxy | grep "dropping" # 查看Service端点状态(引用[2]) kubectl get endpoints kubernetes ``` 若输出显示`no endpoints`或错误计数增长,表明kube-proxy异常[^1][^2]。 #### 2. **客户端超时配置差异** - **应用超时过短**:容器内应用可能设置极短连接超时(如<1s),而curl默认使用长超时(约300s)。当kube-apiserver瞬时繁忙时: - 应用报`connection lost`(触发超时) - 手动curl仍可等待响应(引用[3]中的超时案例) - **验证方法**: ```bash # 强制触发超时(模拟应用行为) curl -m 1 https://10.96.0.1:443 # 设置1秒超时 ``` #### 3. **并发请求限制** - **kube-apiserver限流**:当应用高频访问时,可能触发kube-apiserver的QPS限制(默认100-200 QPS/客户端),而手动curl为单次请求。 - **证据**:日志报错常伴随`Too many requests`或`context deadline exceeded`(引用[3]中的限流机制)[^3]。 #### 4. **TLS握手波动** - **证书验证延迟**:kube-apiserver证书轮换期间,容器应用可能使用缓存旧证书,导致TLS握手失败。手动curl会实时获取新证书。 - **检查点**: ```bash # 查看kube-apiserver证书有效期 openssl s_client -connect 10.96.0.1:443 2>/dev/null | openssl x509 -dates ``` ### 诊断与解决方案 #### 第一步:检查kube-proxy健康状态 ```bash # 查看规则同步状态 kubectl -n kube-system get cm kube-proxy -o yaml | grep syncPeriod # 重启kube-proxy(临时修复) kubectl -n kube-system rollout restart daemonset kube-proxy ``` #### 第二步:调整客户端超时 在应用代码中添加重试逻辑和更长超时: ```go // Go示例 client := &http.Client{ Timeout: 10 * time.Second, // 建议≥5s Transport: &http.Transport{ TLSHandshakeTimeout: 5 * time.Second, }, } ``` #### 第三步:验证API请求追踪 启用Zipkin追踪(引用[3]),定位超时发生的具体阶段: ```bash # 发送带追踪头的请求 curl -H "Authorization: Bearer $TOKEN" -H "X-B3-TraceId: 1234" https://10.96.0.1:443 ``` #### 第四步:检查控制平面状态 ```bash # 确认kube-apiserver资源水位 kubectl top pods -n kube-system | grep api-server # 检查错误日志 kubectl -n kube-system logs kube-apiserver-node1 | grep -C 10 "connection reset" ``` > **关键结论**:80%的类似问题由kube-proxy规则丢失和应用短超时共同导致。优先重启kube-proxy并增加客户端超时时间至$5-10$秒。
评论 2
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值