kube-apiserver鉴权源码简析
创始人
2024-02-02 10:40:44
0

1 概述

1.1 环境

版本信息如下:
a、操作系统:centos 7.6
b、kubernetes版本:v1.15.0


1.2 鉴权Authorization

4A包括账号Account、认证Authentication、鉴权Authorization、审计Audit,是一个IT系统的一个基础的非业务性的通用功能。后台鉴权一般分为接口权限和数据权限,接口权限在在controller层的拦截器中实现,数据权限在dao层中实现。
kube-apiserver是一个http web服务,显然接口鉴权的工作也是在controller层的拦截器中实现。

1.3 kube-apiserver中的RBAC鉴权思路

kube-apiserver支持ABAC和RBAC,但RBAC往往使用得最广泛,因此本文只讨论RBAC。
对于RBAC而言,kubernetes的Role对象和ClusterRole对象,保存着一组权限,而权限就是谓语(action,或者叫verb)和宾语(object)(例如:get是谓语,pod是宾语)。kube-apiserver从http request对象的tls信息中获得主语(subject),从http mechod和http path推断出谓语和宾语,具备了主语、谓语和宾语后,遍历所有ClusterRole对象和Role对象中的权限信息,逐一对比,匹配正确则放行请求,不匹配则返回403响应。

2 源码

2.1 在拦截器链中注册鉴权相关的两个拦截器

鉴权拦截器是genericapifilters.WithAuthorization( ),而推断了主语、谓语和宾语的拦截器是genericapifilters.WithRequestInfo( )。在拦截器链中,因为genericapifilters.WithRequestInfo( )是较后配置的,因此是较先执行的。

# kubernetes/staging/src/k8s.io/apiserver/pkg/server/config.go
func DefaultBuildHandlerChain(apiHandler http.Handler, c *Config) http.Handler {handler := genericapifilters.WithAuthorization(apiHandler, c.Authorization.Authorizer, c.Serializer)/*其他拦截器*/handler = genericapifilters.WithRequestInfo(handler, c.RequestInfoResolver)/*其他拦截器*/return handler
}

2.2 拦截器genericapifilters.WithRequestInfo( )

将http request的信息解析之后,得到k8s对象的gvr信息、namespace、verb等信息,并保存到名称为info且类型为RequestInfo结构体的对象中,这些信息会在authorize阶段中被使用到。

func WithRequestInfo(handler http.Handler, resolver request.RequestInfoResolver) http.Handler {return http.HandlerFunc(func(w http.ResponseWriter, req *http.Request) {ctx := req.Context()// 解析http请求的path和query参数,形成info对象,info对象会在authorize阶段中被使用到info, err := resolver.NewRequestInfo(req)if err != nil {responsewriters.InternalError(w, req, fmt.Errorf("failed to create RequestInfo: %v", err))return}// 将info对象放入http request中的ctx对象中req = req.WithContext(request.WithRequestInfo(ctx, info))handler.ServeHTTP(w, req)})
}
// RequestInfo holds information parsed from the http.Request
type RequestInfo struct {IsResourceRequest boolPath stringVerb stringAPIPrefix  stringAPIGroup   stringAPIVersion stringNamespace  stringResource stringSubresource stringName stringParts []string
}

2.3 拦截器genericapifilters.WithAuthorization( )

func WithAuthorization(handler http.Handler, a authorizer.Authorizer, s runtime.NegotiatedSerializer) http.Handler {return http.HandlerFunc(func(w http.ResponseWriter, req *http.Request) {ctx := req.Context()// 从request的ctx对象中提取数据attributes, err := GetAuthorizerAttributes(ctx)// 使用鉴权器进行鉴权,这行代码是重点authorized, reason, err := a.Authorize(attributes)// 鉴权结果是通过,则放行请求if authorized == authorizer.DecisionAllow {handler.ServeHTTP(w, req)return}// 服务器内部发生错误,返回5xx响应if err != nil {responsewriters.InternalError(w, req, err)return}// 鉴权结果是不通过,返回403响应responsewriters.Forbidden(ctx, attributes, w, req, reason, s)})
}

RBAC鉴权器的主要逻辑如下:

func (r *RBACAuthorizer) Authorize(requestAttributes authorizer.Attributes) (authorizer.Decision, string, error) {ruleCheckingVisitor := &authorizingVisitor{requestAttributes: requestAttributes}// VisitRulesFor(  )从http request的ctx对象中拿出info对象,然后遍历ClusterRoleBinding和RoleBinding找出所有role// 最终逐一进行比对role中表示的权限r.authorizationRuleResolver.VisitRulesFor(requestAttributes.GetUser(), requestAttributes.GetNamespace(), ruleCheckingVisitor.visit)// 鉴权结果是一个布尔值,放在ruleCheckingVisitor的属性allowed中if ruleCheckingVisitor.allowed {return authorizer.DecisionAllow, ruleCheckingVisitor.reason, nil}/*其他代码*/return authorizer.DecisionNoOpinion, reason, nil
}

3 小结

kube-apiserver是一个普通web http服务,鉴权逻辑清晰易懂,先是从http request中提取主语、谓语和宾语,在鉴权阶段就拿着刚获得的主谓宾信息去逐一匹配所有ClusterRole和Role对象中包含的权限信息。

相关内容

热门资讯

【NI Multisim 14...   目录 序言 一、工具栏 🍊1.“标准”工具栏 🍊 2.视图工具...
银河麒麟V10SP1高级服务器... 银河麒麟高级服务器操作系统简介: 银河麒麟高级服务器操作系统V10是针对企业级关键业务...
不能访问光猫的的管理页面 光猫是现代家庭宽带网络的重要组成部分,它可以提供高速稳定的网络连接。但是,有时候我们会遇到不能访问光...
AWSECS:访问外部网络时出... 如果您在AWS ECS中部署了应用程序,并且该应用程序需要访问外部网络,但是无法正常访问,可能是因为...
Android|无法访问或保存... 这个问题可能是由于权限设置不正确导致的。您需要在应用程序清单文件中添加以下代码来请求适当的权限:此外...
北信源内网安全管理卸载 北信源内网安全管理是一款网络安全管理软件,主要用于保护内网安全。在日常使用过程中,卸载该软件是一种常...
AWSElasticBeans... 在Dockerfile中手动配置nginx反向代理。例如,在Dockerfile中添加以下代码:FR...
AsusVivobook无法开... 首先,我们可以尝试重置BIOS(Basic Input/Output System)来解决这个问题。...
ASM贪吃蛇游戏-解决错误的问... 要解决ASM贪吃蛇游戏中的错误问题,你可以按照以下步骤进行:首先,确定错误的具体表现和问题所在。在贪...
月入8000+的steam搬砖... 大家好,我是阿阳 今天要给大家介绍的是 steam 游戏搬砖项目,目前...