Keycloak
[top]
Keycloak为Web应用和Restful服务提供了一站式的单点登录解决方案。它的目标就是让应用的安全管理变得简单,让开发人员可以轻松地保护他们的应用程序和服务。并且Keycloak为登录、注册、用户管理提供了可视化管理界面,你可以借助于该界面来配置符合你需要的安全策略和进行用户管理。
主要功能
Keycloak实现了业内常见的认证授权协议和通用的安全技术,主要有:
- 浏览器应用程序的单点登录(SSO)。
- OIDC认证授权。
- OAuth 2.0。
- SAML。
- 多租户支持。
- 身份代理 - 使用外部 OpenID Connect 或 SAML 身份提供商进行身份验证。
- 第三方登录。
- 用户联盟 - 从 LDAP 和 Active Directory 服务器同步用户。
- Kerberos 网桥 - 自动验证登录到 Kerberos 服务器的用户。
- 用于集中管理用户、角色、角色映射、客户端和配置的管理控制台。
- 用户账户集中管理的管理控制台。
- 自定义主题。
- 两段身份认证。
- 完整登录流程 - 可选的用户自注册、恢复密码、验证电子邮件、要求密码更新等。
- 会话管理 - 管理员和用户自己可以查看和管理用户会话。
- 令牌映射 - 将用户属性、角色等映射到令牌和语句中。
- 安全策略恢复功能。
- CORS 支持 - 客户端适配器具有对 CORS 的内置支持。
- 自定义SPI接口扩展。
- JavaScript 应用程序、WildFly、JBoss EAP、Fuse、Tomcat、Jetty、Spring 等客户端适配器。
- 支持任何具有 OpenID Connect Relying Party 库或 SAML 2.0 Service Provider 库的平台/语言。
概念
- Realm:
realm
是管理用户和对应应用的空间,有点租户的味道,可以让不同realm
之间保持逻辑隔离的能力。Keycloack提供了一个叫Master
的realm
,这个Master
不承担具体应用和用户的管理,它只用来管理其它realm
的生命周期。 - User:
User
是能够登录到应用系统的实体,其实可以理解为账户。 - Authentication:识别和验证用户的过程。证明“你说的这个你就是你”。
- Authorization:授予用户访问权限的过程。标明“你可以干什么、不可以干什么”。
- Credentials:证明用户身份的凭证。可能是密码、一次性密码、数字证书以及指纹。
- Roles:角色是RBAC的重要概念,用于表明用户的身份类型。
- user role mapping:用户角色映射关系。通常一个用户可能有多个角色,一个角色也可以对应不同的人。
- composite roles:复合角色,听起来很玄乎,其实就是角色的从属关系或者说继承关系。
B
角色从属于A
角色,那么你拥有了A
角色就一定拥有B
角色的权限。 - Groups:用户组,你可以将一系列的角色赋予定义好的用户组,一旦某用户属于该用户组,那么该用户将获得对应组的所有角色权限。
- Clients:客户端。通常指一些需要向keycloak请求以认证一个用户的应用或者服务,甚至可以说寻求keycloak保护并在keycloak上注册的请求实体都是客户端。
- client adapters:keycloak为了支持多语言和跨平台而设计的适配器,比如适配Java的、适配Python的。有些是内置的实现,有些需要我们按照keycloak的抽象定义来实现。后续我们主要和Spring Boot Adapter打交道。
- identity provider:用来认证用户的服务,简称
IDP
。keycloak本身就是一个IDP
。这个类似Spring Security中的AuthenticationProvider
接口。 - 资源服务器(Resource Server):资源服务器通常依赖某种信息来决定是否授权。该授权信息通常包含在安全令牌或用户会话中。任何可信的Keycloak客户端都可以作为资源服务器。这些客户端的资源及范围由一系列的授权策略保护。
- 资源:资源是应用或者组织的资产。它们可以是一些列的端点、一个典型的HTML页面等等。在授权策略语境中,资源指的就是被保护的对象。每个资源或者每组资源都有着唯一标识。
- 范围:资源的范围扩展了资源的访问界限。在授权语义中,范围是可以应用在资源上的许多动词之一。它通常表示对指定资源可施加的动作。如查看、编辑、删除等等。但是范围也可以表示资源的其它关联信息。如工程资源和造价范围,这里的造价范围被用来定义用户访问工程造价的特定策略及权限。
- 权限:权限将被保护的对象与必须评估的策略关联起来,以确定是否允许访问。语法** X 可以在资源 Z 上施加 Y**。这里X指可以是用户、角色、用户组,或者其组合。在这里你可以使用声明和上下文。Y指代一个动作,如写、读等等。Z指代被保护的资源,如 “/accounts”。
- 策略:策略定义了授予对象访问权时必须满足的条件。与权限不同,策略不指定受保护的对象,而是指定访问制定对象(如资源、范围或两者)时必须满足的条件。策略与用来保护资源的访问控制机制(ACMs)密切相关。使用策略可以实现基于属性的访问控制(ABAC)、基于角色的访问控制(RBAC)、基于上下文的访问控制以及其任何组合。
- 策略提供者(Policy Provider):策略提供者是特定策略类型的具体实现。Keycloak提供的内置策略都是由不同的提供者来支持的。Keycloak允许添加自定义的策略类型。Keyclaok提供了SPI(Service Provider Interface),你可以使用SPI来添加自定义策略提供者。
- 权限许可(Permission Ticket):权限许可(权限ticket)是由UMA定义的特殊token类型,它的不透明结构由授权服务器所决定。这种结构代表了客户端请求的资源或者范围、访问上下文,以及要执行的策略。在UMA中,权限许可是人与人、人与组织之间共享的关键。在授权工作流中使用权限ticket可以支持一系列从简单到复杂的场景,让资源所有者和资源服务器细粒度地控制资源访问。
概念架构
授权
Keycloak支持细粒度的授权策略,并可以对这些策略进一步组合,如:
- 基于属性(ABAC)
- 基于角色(RBAC)
- 基于用户(UBAC)
- 基于上下文(CABC)
- 基于规则(Rule-based)
- 通过JavaScript
- 使用Jboss Drools
- 基于时间(Time-based)
- 通过SPI自定义访问控制策略(ACM)
Keycloak提供了一组管理界面和RESTful API,用于创建权限、关联权限与授权策略,以及在应用程序中执行授权决策。
资源服务器需要依据一些信息才能判断权限。对于REST的资源服务器来说这些信息通常来自于一个加密的token,如在每个访问请求中携带bearer token。对于依赖于session的Web应用来说,这些信息就来自于每个request对应的用户session。
资源服务器通常执行的是基于角色的访问控制(RBAC)策略,即检查用户所拥有的角色是否关联了要访问的资源。虽然这种方式非常有用,但是它们也有一些限制:
- 资源和角色紧耦合,角色的更改(如添加、删除或更改访问上下文)可能影响多个资源。
- 基于RBAC的应用程序无法很好地响应安全性需求的调整。
- 项目规模扩大时,复杂的角色管理会很困难而且容易出错。
- 不够灵活。角色并不能有效代表用户身份,即缺乏上下文信息。客观上来说被授予了角色的用户,至少会拥有某些访问权限。
当下的项目中,我们需要考虑不同地区、不同本地策略、使用不同设备、以及对信息共享有较高需求的异构环境。Keycloak授权服务可以通过以下方式帮助您提高应用程序和服务的授权能力:
- 不同的访问控制机制以及细粒度的授权策略。
- 中心化的资源、权限以及策略管理。
- 中心化的策略决策。
- REST风格的授权服务。
- 授权工作流以及用户访问管理。
- 可作为快速响应您项目中安全需求的基础设施。
架构
从设计的角度来看,授权服务基于一组授权模式,提供了以下功能:
- 策略管理点(PAP)
在Keycloak Admin的基础上提供了UI界面来管理资源服务器、资源、范围、权限以及策略。其中的部分功能也可以通过Protection API来实现。
- 策略决策点(PDP)
为和权限请求相应的授权请求以及策略评估,提供了分布式的策略决策点。更多信息请查看获取权限章节。
- 策略执行点(PEP)
为资源服务器端实际执行授权决策,Keycloak提供了用于不同环境的一些内置策略执行器。
- 策略信息点(PIP)
基于Keycloak的认证服务器,可以在策略评估时从身份认证信息以及上下文环境中获取一些其它属性。
授权过程
Keycloak的细粒度授权主要有三个必要步骤:
- 资源管理
- 权限及策略管理
- 执行策略
资源管理
资源管理定义了什么是被保护的对象。
首先,需要定义被保护的资源服务器,通常是一个web应用或一组服务。有关资源服务器的更多信息请参考术语。
资源服务器可以使用Keycloak管理员控制台来管理。在那里,您可以将任何已注册的客户端启用为资源服务器,并管理其资源和范围。
资源可以是web页面、Rest资源、文件系统上的一个文件、一个EJB等等。它们可以是一组资源(如Java中的一个Class),也可以是一个特定的资源。
举例来说,你可以用Bank Account来代表所有的银行账户,并且用它来定义对全部银行账户的通用授权。但同时你也可以为Alice的私有账户来单独设置权限,使得只有Alice本人能够对其账户进行某些操作。
资源可以通过Keycloak控制台或者Protection API来管理。利用Protection API的方式,资源服务器可以远程管理资源。
范围(Scope)通常用来表示在资源上执行的动作,还可以使用范围来代表资源中的一个或者多个属性。
权限及策略管理
定义好了资源服务器和其上的资源,下一步就是定义权限和策略。
定义策略的步骤图示如下:
策略定义了在资源或者范围上执行某些动作的先决条件,但是请记住它们并不和被保护的资源直接绑定。策略是通用的,可以通过再次组合来构造更复杂的权限及策略。
举例来说,要获取“User Premium”角色下的资源组访问权限,你可以使用RBAC策略。
Keycloak为常用场景提供了一些内置的策略类型。你可以使用JavaScript或者JBoss的Drools来编写自己的策略。
定义了策略之后就可以来定义权限了。权限与被保护的资源紧耦合,它们由被保护对象及策略组合而成。
执行策略
策略的执行包含了对资源服务器实际实施授权决策的必要步骤。实现方式是在资源服务器上启用策略执行点(PEP),PEP能够与授权服务器通信,请求授权数据,并根据服务器返回的决策来控制对受保护资源的访问。
授权服务
授权服务包括下列三种REST端点:
- Token Endpoint
- Resource Management Endpoint
- Permission Managerment Endpoint
上边的各个端点涵盖了授权服务的各个步骤。
Token Endpoint
Oauth2客户端(如前端应用)可以通过token endpoint获取访问令牌(access token),然后使用这些令牌来获取资源服务器(如后端应用)上被保护的资源。同样,Keycloak授权服务扩展了OAuth2,允许基于配置好的策略发放访问令牌。这意味着资源服务器可以利用关联了权限的令牌来对资源进行保护。在Keycloak中,带有权限的访问令牌被称作请求方令牌(Requesting Party Token),或者缩写为RPT。
更多的信息请查看获取权限章节。
保护API
保护API指提供的一系列UMA兼容的操作,用来帮助资源服务器管理资源、范围、权限及相关策略。只有资源服务器才能被允许访问这些API,前提是资源服务器有内置的uma_protection范围。
提供给资源服务器的API可以分为两组:
- 资源管理
创建资源、删除资源、根据ID查询、其他查询
- 权限管理
发放权限Ticket
远程管理资源的功能默认是开启的。可以通过Keycloak管理员控制台来关闭此功能。
如果使用了UMA协议,Protection API对权限Ticket的发放是整个授权流程的重要组成部分。后面会讲到,它们表示着在整个授权过程中客户端所申请的权限及向服务器申请包含着权限的最终令牌。
更多信息请查看保护API章节。
参考资料
- 官网文档:https://www.keycloak.org/docs/latest/getting_started/index.html
- OpenAPI官方文档:https://openid.net/specs/openid-connect-core-1_0.html#CodeFlowAuth
- 网关鉴权的集成案例:https://blog.csdn.net/weixin_39797912/article/details/110507580
- SpringCloud Gateway集成OAuth:https://blog.jdriven.com/2019/11/spring-cloud-gateway-with-openid-connect-and-token-relay/
- Spring Gateway和KeyCloak构建一个OIDC认证系统:https://zhuanlan.zhihu.com/p/138578359
- keycloak+istio实现基于jwt的服务认证授权:https://zhuanlan.zhihu.com/p/231500100
- Kubernetes +keycloak单点登录详解:https://blog.csdn.net/tao12345666333/article/details/117458401
- 通过Keycloak API理解OAuth2与OpenID Connect: https://cookcode.blog.csdn.net/article/details/112706006
- OneLogin-参考产品:https://developers.onelogin.com
- 浅析 kubernetes 的认证与鉴权机制:https://www.jianshu.com/p/78005787f558
- Keycloak简单几步实现对Spring Boot应用的权限控制:https://segmentfault.com/a/1190000040332863
- IDAAS-参考产品:https://help.aliyun.com/document_detail/112299.html