微服务安全:访问控制、XACML 及安全边车模式
1. 访问控制基础
授权是一项重要的业务功能,每个微服务都能自行确定允许访问其操作的标准。在最基本的授权形式中,我们会检查特定用户是否有权限在特定资源上执行特定操作。这种操作与资源的组合被称为权限。授权检查的目的是评估用户是否具备访问特定资源所需的最低权限集。
资源可以明确规定谁能够执行操作以及可以执行哪些操作。声明资源所需权限的方式有多种,最常见的是为资源附加策略或访问控制列表(ACL)。目前有多种策略语言用于表达这些访问控制要求,例如亚马逊网络服务(AWS)使用的基于 JSON 的策略语言,示例如下:
{
"Version": "2012-10-17",
"Statement": {
"Effect": "Allow",
"Action": "s3:ListBucket",
"Resource": "arn:aws:s3:::example_bucket"
}
}
此外,开放策略代理(Open Policy Agent,OPA)引入了另一种策略语言,主要针对云原生环境的基于策略的控制。以下是一个在 OPA 中定义的策略示例,允许访问所有 HTTP 请求:
package http.authz
allow = true
可扩展访问控制标记语言(XACML)则提供了另一种定义访问控制策略的方式,它是目前唯一由 OASIS 制定的策略语言标准。
2. XACML 详解
XACML 是细粒度访问控制的事实标准,它采用基于 XML 的领域特定语言(DSL),以非常精细的方式表示访问资源所需的权限集。
XACML 提供了参考架构、请求响应协议和策略语言。其参考架构包含策略管理点(PAP)、策略决策点(PDP)、策略执行点(PEP)和策略信息点(PIP)。这是一个高度分布式的架构,各组件之间没有紧密耦合。
-
PAP
:是编写策略的地方。
-
PDP
:负责评估策略并做出决策。在评估策略时,如果 XACML 请求中缺少某些无法推导出来的信息,PDP 会调用 PIP。
-
PIP
:其作用是为 PDP 提供缺失的信息,这些信息可以是用户属性或其他所需细节。
-
PEP
:位于客户端和服务之间,拦截所有请求。它从客户端请求中提取主题、资源和操作等属性,构建标准的 XACML 请求并发送给 PDP,然后接收 PDP 的 XACML 响应。
以下是 XACML 组件架构的工作流程 mermaid 图:
graph LR
classDef process fill:#E5F6FF,stroke:#73A6FF,stroke-width:2px;
A(PAP):::process -->|定义并存储策略| B(策略存储):::process
C(客户端):::process -->|请求访问| D(PEP):::process
D -->|创建 XACML 请求| E(PDP):::process
B -->|提供策略| E
E -->|请求信息| F(PIP):::process
F -->|提供信息| E
E -->|返回 XACML 响应| D
D -->|允许/拒绝访问| C
将策略决策点(PDP)引入微服务架构主要有两种方式:
-
集中式/远程 PDP
:将 PDP 视为一个单一的远程端点,所有微服务都连接到该端点以授权访问请求。每个微服务创建自己的 XACML 请求,并通过通信通道将其传递给 PDP,PDP 评估请求并返回 XACML 响应。
-
嵌入式 PDP
:远程或集中式 PDP 模型存在一些缺点,例如性能成本高、策略信息点(PIP)所有权问题和整体式 PDP 问题。嵌入式 PDP 会与每个微服务一起运行,采用事件驱动的策略分发模型。每个微服务订阅感兴趣的主题,从 PAP 获取适当的访问控制策略并更新嵌入式 PDP。这种方法不会违反微服务中的不可变服务器概念。
3. 安全边车模式
安全边车模式源自摩托车边车的概念。在微服务领域,微服务类似于摩托车,安全处理层类似于边车。微服务和边车通过远程通道通信,它们部署在同一物理或虚拟机中,无需通过网络路由。边车本身也是一个微服务。
实现安全边车模式在微服务架构中有诸多好处:
- 微服务实现无需担心安全实现的内部细节,且两者无需使用相同的编程语言。
- 安全功能可以被其他微服务复用,无需关注具体实现细节。
- 安全边车的所有权可以由在安全领域有专业知识的不同团队负责,而微服务开发人员专注于特定领域的业务功能。
安全边车通常具有以下四个主要功能:
-
令牌验证(自省)
:微服务的拦截器拦截请求并与令牌验证端点通信,检查提供的令牌是否足以访问相应的微服务。建议暴露 OAuth 2.0 自省端点来验证令牌,示例请求和响应如下:
POST /introspect HTTP/1.1
Host: sidecar.local
Accept: application/json
Content-Type: application/x-www-form-urlencoded
token=2YotnFZFEjr1zCsicMWpAA
HTTP/1.1 200 OK
Content-Type: application/json
{
"active": true,
"client_id": "l238j323ds-23ij4",
"username": "jdoe",
"scope": "read write dolphin",
"sub": "jdoe",
"aud": "https://foo.com",
"iss": "https://issuer.example.com/",
"exp": 1419356238,
"iat": 1419350238
}
- 获取用户信息(userinfo) :微服务可以与安全边车暴露的 userinfo 端点通信,以获取调用服务的最终用户的更多信息。这是 OpenID Connect 规范中定义的标准端点,示例请求和响应如下:
GET /userinfo HTTP/1.1
Host: sidecar.local
Authorization: Bearer SlAV32hkKG
HTTP/1.1 200 OK
Content-Type: application/json
{
"sub": "jdoe",
"name": "Jane Doe",
"given_name": "Jane",
"family_name": "Doe",
"preferred_username": "j.doe",
"email": "janedoe@example.com"
}
- 令牌颁发(token) :微服务可以调用安全边车的 token 端点获取新令牌,以与下游微服务通信。该端点可基于 OAuth 2.0 令牌端点进行标准化,并支持 OAuth 2.0 令牌交换配置文件,示例请求和响应如下:
POST /token HTTP/1.1
Host: sidecar.local
Content-Type: application/x-www-form-urlencoded
grant_type=urn:ietf:params:oauth:grant-type:token-exchange
&resource=foo
&subject_token=SlAV32hkKG
&subject_token_type=urn:ietf:params:oauth:token-type:access_token
HTTP/1.1 200 OK
Content-Type: application/json
Cache-Control: no-cache, no-store
{
"access_token":"eyJhbGciOiJFUzI1NiIsImtpZCI6Ijllc",
"issued_token_type": "urn:ietf:params:oauth:token-type:access_token",
"token_type":"Bearer",
"expires_in":60
}
- 授权访问请求(pdp) :拦截器或微服务本身可以调用 pdp 端点,以确定传入请求是否足以执行其预期的操作。该请求和响应可以基于 XACML 的 JSON 配置文件和 REST 配置文件进行标准化,示例请求和响应如下:
POST /pdp HTTP/1.1
Host: sidecar.local
Accept: application/json
Content-Type: application/x-www-form-urlencoded
[xacml request in json, see figure 11-4]
HTTP/1.1 200 OK
Content-Type: application/json
{
"Response": [{
"Decision": "Permit"
}]
}
4. 微服务安全实现
在典型的微服务部署中,OAuth 2.0 用于边缘安全。API 网关会验证 OAuth 2.0 访问令牌,并向下游微服务颁发自己的令牌。如果是自包含的访问令牌(如 JSON Web Token),微服务可以自行验证令牌的签名;否则,它需要与安全令牌服务暴露的令牌验证端点通信。
由于 OAuth 2.0 令牌是承载令牌,容易被窃取并被用于冒充令牌所有者访问资源,因此在使用承载令牌时,必须通过安全的通信通道进行传输,这就需要为所有通信通道启用传输层安全(TLS)。
启用 TLS 的步骤如下:
1.
创建公钥/私钥对
:使用 Java 自带的 keytool 工具生成密钥对,并将其存储在 keystore.jks 文件中。示例命令如下:
keytool -genkey -alias spring -storetype JKS -keyalg RSA -keysize 2048 -keystore keystore.jks -validity 3650
执行此命令后,会提示输入密钥库密码和生成证书所需的数据。
2.
配置 Spring Boot 微服务
:将生成的 keystore.jks 文件复制到示例的主目录(如 ch12/sample01/),并在 [SAMPLE_HOME]/src/main/resources/application.properties 中添加以下配置:
server.port: 8443
server.ssl.key-store: keystore.jks
server.ssl.key-store-password: springboot
server.ssl.keyAlias: spring
- 验证配置 :在 ch12/sample01/ 目录下使用以下命令启动 TokenService 微服务:
mvn spring-boot:run
如果看到输出显示 HTTPS 端口为 8443,则说明配置成功。
综上所述,理解微服务安全的基础知识是构建生产就绪的微服务部署的关键。通过合理运用访问控制、XACML 和安全边车模式,并正确配置 TLS 和 OAuth 2.0,我们可以有效保障微服务的安全性。
微服务安全:访问控制、XACML 及安全边车模式
5. 不同访问控制模型对比
为了更清晰地了解集中式 PDP 和嵌入式 PDP 这两种访问控制模型,我们可以通过以下表格进行对比:
| 模型类型 | 优点 | 缺点 | 适用场景 |
| ---- | ---- | ---- | ---- |
| 集中式 PDP | 策略集中管理,便于统一维护和更新;所有微服务使用相同的决策逻辑,保证决策一致性 | 性能成本高,每次访问控制检查都需通过网络与 PDP 通信;PIP 所有权集中,不利于各微服务自主管理数据;PDP 易形成单体应用,修改策略可能影响所有服务 | 对策略一致性要求高,微服务数量相对较少且对性能要求不苛刻的场景 |
| 嵌入式 PDP | 性能较好,减少网络通信开销;各微服务可自主管理 PIP,符合微服务架构原则;避免 PDP 成为单体应用,策略修改影响范围小 | 策略分发和管理相对复杂,需要事件机制支持;新容器启动时需从 PAP 获取策略,可能存在短暂延迟 | 微服务数量众多,对性能和自主性要求高的场景 |
6. 安全边车模式的深入应用
安全边车模式在实际应用中还可以结合其他技术进一步提升微服务的安全性。例如,与 Istio 结合使用时,Istio 引入的边车代理可以为微服务提供强大的身份验证、策略管理、透明 TLS 加密以及认证、授权和审计(AAA)工具。
下面是安全边车与 Istio 结合的 mermaid 流程图:
graph LR
classDef process fill:#E5F6FF,stroke:#73A6FF,stroke-width:2px;
A(客户端):::process -->|请求| B(安全边车):::process
B -->|验证、授权等处理| C(Istio 边车代理):::process
C -->|TLS 加密、身份验证等| D(微服务):::process
D -->|响应| C
C -->|处理响应| B
B -->|返回响应| A
在这个流程中,客户端的请求首先经过安全边车进行基本的令牌验证和授权检查,然后传递给 Istio 边车代理进行更高级的安全处理,如 TLS 加密和身份验证,最后到达微服务。微服务的响应则沿着相反的路径返回给客户端。
7. 微服务安全的持续优化
微服务安全是一个持续的过程,需要不断地进行优化和改进。以下是一些持续优化微服务安全的建议:
-
定期更新策略
:随着业务需求的变化和安全威胁的演变,定期审查和更新访问控制策略,确保其有效性和适应性。
-
监控和审计
:建立完善的监控和审计机制,实时监测微服务的安全状态,及时发现和处理异常行为。例如,记录所有的访问请求和授权决策,以便进行事后分析和合规性检查。
-
漏洞扫描
:定期对微服务进行漏洞扫描,及时发现和修复潜在的安全漏洞。可以使用专业的漏洞扫描工具,如 Nmap、Burp Suite 等。
-
员工培训
:对开发人员和运维人员进行安全培训,提高他们的安全意识和技能,确保他们在开发和运维过程中遵循安全最佳实践。
8. 总结与展望
在微服务架构中,安全是至关重要的。通过本文介绍的访问控制、XACML、安全边车模式以及 TLS 和 OAuth 2.0 的配置,我们可以构建一个较为安全的微服务环境。
集中式 PDP 和嵌入式 PDP 两种访问控制模型各有优缺点,需要根据具体的业务场景和需求进行选择。安全边车模式为微服务提供了一种灵活、可复用的安全解决方案,能够有效降低微服务与安全逻辑的耦合度。
未来,随着微服务架构的不断发展和安全威胁的日益复杂,微服务安全技术也将不断创新和完善。例如,人工智能和机器学习技术可能会被应用于安全领域,帮助我们更准确地识别和防范安全威胁。同时,区块链技术也可能为微服务的安全提供新的解决方案,如实现更可靠的身份验证和数据完整性保护。
总之,微服务安全是一个不断发展和演进的领域,我们需要持续关注和学习新的安全技术和方法,以保障微服务系统的稳定运行和数据安全。
超级会员免费看
22

被折叠的 条评论
为什么被折叠?



