三亩地 三亩地SAN MU DI · CODE DIARY
ARTICLE DETAIL

日记详情

真实记录编程学习的某一天,欢迎挑你感兴趣的翻一翻。

kube-rbac-proxy 授权原理深度解读:SubjectAccessReview 是如何工作的?

kube-rbac-proxy 授权原理深度解读:SubjectAccessReview 是如何工作的?

kube-rbac-proxy 授权原理深度解读:SubjectAccessReview 是如何工作的?

【免费下载链接】kube-rbac-proxyKubernetes RBAC authorizing HTTP proxy for a single upstream.项目地址: https://gitcode.com/gh_mirrors/ku/kube-rbac-proxy

kube-rbac-proxy 是一个面向单一上游服务的 Kubernetes RBAC 授权 HTTP 代理,其授权核心正是 Kubernetes 的SubjectAccessReview(SAR)机制。本文带你从源码角度深度解读 kube-rbac-proxy 工作原理:一次 HTTP 请求如何被翻译成一次 RBAC 授权检查,TokenReview 与 SubjectAccessReview 两次 API 调用如何协同,以及结果缓存、静态授权器、请求重写等进阶机制的真实实现,帮你彻底搞懂这套侧车代理的授权链路。


为什么普通服务需要 SubjectAccessReview 代理?🚪

在默认配置下,Kubernetes 集群内任何 Pod 都能访问其他 Pod 的网络端口。如果你的应用(比如 Prometheus 的 metrics 端点)希望只允许持有合法 RBAC 权限的调用方访问,就需要一个"门卫":

  • 校验调用方身份(你是谁?)
  • 校验调用方权限(你能做这件事吗?)
  • 通过后才把请求转发给真正的上游应用

kube-rbac-proxy 正是扮演这个门卫角色。它不自己实现权限判断,而是把判断委托给 Kubernetes API Server 的 SubjectAccessReview 接口,因此你的 RBAC 策略只维护一份,规则完全统一。

kube-rbac-proxy 完整工作流程:认证 → 授权 → 转发

一次请求从进入到转发,需要依次穿过三个过滤器(见pkg/filters/auth.go),顺序至关重要:

顺序过滤器作用失败返回
1WithAuthentication身份认证401 Unauthorized
2WithAuthorizationRBAC 授权403 Forbidden
3WithAuthHeaders注入用户信息到请求头

在入口处(cmd/kube-rbac-proxy/app/kube-rbac-proxy.goRun函数),处理器会按照WithAuthHeaders → WithAuthorization → WithAuthentication的顺序层层包裹,也就是先认证、再授权、最后才放行。此外--ignore-paths配置的路径可以完全跳过认证授权直接转发。

第一次 API 调用:TokenReview 完成身份认证 🎫

当客户端携带 Bearer Token 访问时,kube-rbac-proxy 调用authentication.k8s.ioTokenReview接口,把 token 交给 API Server 校验签名、有效期和 audiences,换取一个标准的 Kubernetes 用户对象(用户名 + 组)。

这一逻辑位于pkg/authn/delegating.go,通过authenticatorfactory.DelegatingAuthenticatorConfig构建,其中:

  • 匿名访问被强制关闭(Anonymous.Enabled = false
  • TokenReview 结果缓存 2 分钟(CacheTTL
  • 如果配置了--client-ca-file,客户端 TLS 证书也是合法的认证方式

认证成功后,用户对象被写入请求上下文,供下一步授权使用。

第二次 API 调用:SubjectAccessReview 完成授权 ✅

认证通过后,kube-rbac-proxy 调用authorization.k8s.ioSubjectAccessReview接口,把"用户 + 请求属性"打包发送给 API Server,由 API Server 基于 RBAC 规则做出 Allow / Deny / NoOpinion 的判断。

创建 SAR 授权器的核心代码在pkg/authz/auth.goNewSarAuthorizer

  • 设置SubjectAccessReviewClient指向 Authorization V1 接口
  • 允许结果缓存 5 分钟AllowCacheTTL
  • 拒绝结果缓存 30 秒DenyCacheTTL

正是这两个缓存 TTL,让高频请求不必每次都打到 API Server,性能大幅提升。

SubjectAccessReview 的关键:请求如何被翻译成授权属性 🔑

API Server 只认 RBAC 属性,不认识 HTTP 请求。kube-rbac-proxy 的核心魔法就在pkg/proxy/proxy.goGetRequestAttributes:把 HTTP 请求翻译成authorizer.Attributes

HTTP 方法到 RBAC 动词的映射表

HTTP 方法RBAC 动词
POSTcreate
GETget
PUTupdate
PATCHpatch
DELETEdelete
其他*(任意)

资源请求与非资源请求

RBAC 授权区分两类请求:

  • 非资源请求:不配置resourceAttributes时,代理直接使用 URL 路径(如/metrics)构造属性,对应 RBAC 中的nonResourceURLs规则。
  • 资源请求:配置resourceAttributes后,通过 namespace、apiGroup、resource、subresource、name 构造属性,对应 RBAC 中的resources规则。

例如examples/resource-attributes示例中,要求调用方对 Servicekube-rbac-proxy拥有services/proxy子资源的get权限,SAR 请求就会携带这组资源属性去校验。

双保险:静态授权器与 SAR 授权器如何叠加 🛡️

细心的读者会发现:Run函数中创建了两个授权器,并通过union.New组合:

  1. 静态授权器NewStaticAuthorizer):在本地配置里做精确匹配,支持用户名、动词、命名空间、资源、路径等字段,全部匹配才放行。命中即返回 Allow,不命中返回 NoOpinion,不会拒绝。
  2. SAR 授权器NewSarAuthorizer):走 SubjectAccessReview 委托 API Server 判断。

两个授权器按"先静态、后 SAR"的顺序求并集,只要其中一个允许,请求就放行。这种设计既支持纯本地白名单(性能最好),也支持完全交给 Kubernetes RBAC 管理(策略最统一)。

高级配置:按请求重写 SubjectAccessReview ✍️

kube-rbac-proxy 还支持根据请求参数动态改写 SAR 内容(见examples/rewrites示例),适用于多租户场景:

  • rewrites.byQueryParameter:从 URL 查询参数取值
  • rewrites.byHTTPHeader:从请求头取值
  • resourceAttributes中支持 Go 模板{{ .Value }},把参数值注入属性字段

比如把 URL 中的?namespace=foo映射到 SAR 的 namespace 字段,这样同一个代理就可以服务不同命名空间的授权校验,灵活度极高。

部署前必看的 RBAC 权限配置 📋

kube-rbac-proxy 自身需要两个 API 的创建权限才能工作:

rules: - apiGroups: ["authentication.k8s.io"] resources: ["tokenreviews"] verbs: ["create"] - apiGroups: ["authorization.k8s.io"] resources: ["subjectaccessreviews"] verbs: ["create"]

完整可运行的 Deployment、Service、ConfigMap 与 RBAC 清单可以直接参考examples/resource-attributes/deployment.yamlexamples/rewrites/deployment.yaml

另外提醒一句:使用 Token 认证时,接收方可以冒充调用方身份。请只在调用方 token 权限足够低、或接收方权限本身更高的情况下使用 Token 认证;生产环境更推荐 mTLS 客户端证书方案。

总结:理解 SubjectAccessReview 是掌握 kube-rbac-proxy 的关键 🎯

回顾全文,kube-rbac-proxy 的授权原理可以浓缩为一句话:它把"HTTP 请求"翻译成"RBAC 属性",再通过 SubjectAccessReview 委托 API Server 裁决,并辅以静态白名单和结果缓存来提升性能与灵活性。

  • 认证靠TokenReview(你是谁),授权靠SubjectAccessReview(你能做什么)
  • 属性翻译逻辑在pkg/proxy/proxy.go,授权器在pkg/authz/auth.go,过滤器链在pkg/filters/auth.go
  • 允许缓存 5 分钟、拒绝缓存 30 秒,是性能优化的关键参数

掌握了这条链路,你就能自信地在生产集群里部署 kube-rbac-proxy,并针对业务场景定制资源属性与重写规则了。如果你正准备保护自己的 metrics 端点或内部服务,不妨按照上面的流程亲手搭建一遍,感受"一次认证、二次授权"的完整闭环。

【免费下载链接】kube-rbac-proxyKubernetes RBAC authorizing HTTP proxy for a single upstream.项目地址: https://gitcode.com/gh_mirrors/ku/kube-rbac-proxy

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

← 返回列表