基于IAM开发自有API
“SiX统一认证/授权”提供多租户授权模型,向客户(开发者)公开其功能,以构建自己的安全 API。
客户(开发者)可以使用“分层组织”、“自定义角色/权限”、“组”和“自定义属性”等来创建满足其特定要求的 API,而无需自行实现复杂的授权模型。
架构
基本步骤
根据如上架构并利用以下步骤,客户(开发人员)可以快速构建自己的被保护的API。
1. 创建身份应用程序用户或集成密钥
对于身份应用程序用户
“SiX统一认证/授权”创建的 IdP 开箱即用地支持 OIDC/OAuth2,创建 IdP 后,您应该使用 OIDC 客户端与 “SiX统一认证/授权” 进行交互。客户端将处理授权流程,例如authorization_code为您的应用程序执行自动授予流程,更多信息请参阅:
由“SiX统一认证/授权”创建的IdP可以配置为与同一客户拥有的微信小程序联合,在小程序用户通过微信平台的身份验证服务器进行身份验证后,同一用户将被授予由“SiX统一认证/授权”生成的访问令牌,并自动为该小程序用户创建一个影子用户,更多信息请参阅:
对于集成密钥
“SiX统一认证/授权”扩展了创建集成密钥的功能,该密钥本质上是 RSA256 密钥对,客户(开发人员)可以使用密钥交换访问令牌,然后使用它们访问API,更多信息请参阅:
2. 验证访问实体并获取访问令牌
请使用 创建身份应用程序用户或集成密钥 中的链接了解如何获取访问实体的访问令牌。
3. 检索访问实体的授权配置
创建访问实体后,您可以使用控制台为它们分配授权,例如将应用用户或集成密钥放入一些自定义组中或为实体设置差异化属性。
一个授权分配示例如下,请注意JWT(访问令牌)声明中突出显示的部分。
{
"sub": "13888888888",
"aud": "iot_sample_client",
"nbf": 1728714570,
"role": [
{
"ROLE_customer-role": [
"perm-read-travels"
]
}
],
"org": {
"level": 2,
"orgId": "0a2a0090-8bf6-1c88-818b-feb6072c00e1"
},
"openId": "0a2a00f9-8faf-17bf-818f-aff3de430000",
"scope": [
"openid",
"profile"
],
"iss": "https://08d7db.app.shuhenglianchang.com",
"property": [
{
"name": "custom-prop",
"value": "123456"
},
{
"name": "salesforce_fed_id",
"value": "aaabbbccc"
}
],
"exp": 1728732570,
"iat": 1728714570,
"jti": "265181fa-9228-4b39-bb58-fe9061208d20"
}
4. 使用访问令牌访问 API
获取访问令牌后,您可以使用访问令牌 (JWT) 调用您开发的 API,例如,您可以将令牌放在Restful API请求的标头中。
5. 通过 JWK 验证访问令牌
获取 JWK 后,您的资源服务器可以使用它来验证 JWT (访问令牌)。
对于IdP用户
对于在“SiX统一认证/授权”中创建的每个 IdP,将为该IdP分配一个子域名,您可以在“.well-known/openid-configuration”端点中检查 JWK 信息。
对于集成密钥
对于集成密钥,请使用平台中的 JWK。
6 验证声明(Authz 检查)
您的资源服务器可以验证 JWT(访问令牌)中封装的声明。
我们推荐的方法是将声明统一转换为您的API函数调用拦截器,然后像下面示例中展示的那样解释权限。
//The accessing entity should have the permission to update the specific "resource" entity.
@PreAuthorize(hasPermission(#resourceId, 'resource', 'update'))
public Map<String, Object> resource(String resourceId) {
//the implementation of the API
}
//The accessing entity should have the property(six_iot_product = #resourceId) and property(purpose = device_reg) set in the claims to access the API.
@PreAuthorize(@attributeMethodSecurity.matchAttributeValue(authentication, #resourceId, 'six_iot_product') and @attributeMethodSecurity.matchAttributeValue(authentication, 'device_reg', 'purpose'))
public Map<String, Object> controller(String resourceId) {
//the implementation of the API
}