3、统一身份认证:IAM角色与权限模型、跨云SSO集成、OAuth2.0与SAML协议实践

说实话,跨云协同最让人头疼的,往往不是网络怎么通,而是「谁是谁」的问题。

你想想看,AWS 有 IAM,Azure 有 Entra ID,阿里云有 RAM。每个云都有自己的用户体系。如果每个平台都单独建账号、单独配权限,运维同学光管理密码就得疯掉。

我最早做混合云项目时,就踩过这个坑。当时三个云平台,每个平台 50 多个子账号,光权限变更就得发邮件审批,效率极低。后来我下定决心,必须搞统一身份认证。

3.1 IAM 角色与权限模型:最小权限原则

先聊最基础的东西——IAM 角色。

很多人分不清「用户」和「角色」。我简单解释一下:用户是具体的人,角色是一组权限的集合。你把人加到角色里,他就有了对应的权限。这样管理起来灵活得多。

核心原则:最小权限

只给用户完成工作所需的最小权限。多一个权限都不要给。

我在项目中遇到过这样的情况:某位开发同学为了调试方便,直接给了管理员权限。结果不小心删了生产环境的数据库表……嗯,从那以后,我们团队严格执行最小权限原则。

具体怎么做?我建议分三步:

  1. 梳理业务场景:列出所有需要跨云访问的场景,比如「开发人员需要读取 AWS S3 和 Azure Blob 的日志」。
  2. 定义角色模板:按职责划分角色,比如「只读角色」、「运维角色」、「管理员角色」。
  3. 绑定策略:每个角色绑定对应的权限策略,策略用 JSON 写,清晰明了。

举个例子,AWS 的 IAM 策略长这样:

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": "s3:GetObject",
      "Resource": "arn:aws:s3:::my-bucket/*"
    }
  ]
}

说白了,这就是告诉 AWS:「允许这个角色读取 my-bucket 里的所有对象。」其他操作?不行。

3.2 跨云 SSO 集成:一次登录,到处访问

SSO(单点登录)是跨云协同的基石。用户只需要登录一次,就能访问所有云平台。

我常用的方案是:用企业 IdP(身份提供商)作为中心,比如 Okta、Azure AD 或者自建的 Keycloak。所有云平台都信任这个 IdP。

我的经验:不要自己写 SSO 实现。直接用现成的 IdP 产品,省心省力。我曾经试过自己写 SAML 断言生成器,结果被各种签名问题折磨了两周。

跨云 SSO 的架构大致如下:

跨云 SSO 集成架构 用户 企业 IdP AWS Azure 阿里云 登录请求 SAML/OAuth 断言 SAML/OAuth 断言

流程很简单:用户登录企业 IdP,IdP 生成一个令牌(Token),然后把这个令牌发给各个云平台。云平台验证令牌后,允许用户访问资源。

3.3 OAuth2.0 与 SAML 协议实践

说到协议,目前主流的就是 OAuth2.0 和 SAML。很多人搞不清两者的区别,我简单说说。

特性 OAuth2.0 SAML
适用场景 API 授权、移动端、单页应用 企业级 SSO、Web 应用
数据格式 JSON(轻量) XML(较重)
令牌类型 Access Token + Refresh Token SAML Assertion
安全性 依赖 HTTPS + 签名 内置签名 + 加密

我个人习惯:如果是新项目,优先用 OAuth2.0。它更轻量、更灵活。但如果是和已有的企业系统对接,比如对接 Active Directory,那 SAML 更合适。

OAuth2.0 实践:授权码模式

OAuth2.0 有四种授权模式,最常用的是「授权码模式」。我拿一个实际场景举例:

假设你的应用需要读取用户在 AWS 上的 S3 文件。流程是这样的:

  1. 用户点击「登录 AWS」按钮
  2. 应用把用户重定向到 AWS 的授权页面
  3. 用户同意授权
  4. AWS 返回一个授权码给应用
  5. 应用用授权码去换 Access Token
  6. 应用拿着 Access Token 去读取 S3 文件

代码示例(Python 伪代码):

# 第一步:获取授权码(用户浏览器操作)
redirect_url = "https://aws.amazon.com/oauth2/authorize?response_type=code&client_id=YOUR_CLIENT_ID&redirect_uri=YOUR_CALLBACK_URL"

# 第二步:用授权码换 Token
import requests
token_response = requests.post(
    "https://aws.amazon.com/oauth2/token",
    data={
        "grant_type": "authorization_code",
        "code": "AUTHORIZATION_CODE",
        "client_id": "YOUR_CLIENT_ID",
        "client_secret": "YOUR_CLIENT_SECRET",
        "redirect_uri": "YOUR_CALLBACK_URL"
    }
)
access_token = token_response.json()["access_token"]

# 第三步:用 Token 访问资源
headers = {"Authorization": f"Bearer {access_token}"}
s3_response = requests.get("https://s3.amazonaws.com/my-bucket/file.txt", headers=headers)

注意:Client Secret 绝对不能暴露在前端代码里。我曾经见过有人把 Secret 写在 JavaScript 里,结果被爬虫抓了个正着……

SAML 实践:企业级 SSO

SAML 的流程稍微复杂一些,但核心思想是一样的:用户通过 IdP 认证,IdP 生成一个 SAML 断言,然后发给 SP(服务提供商)。

我举个例子,用 AWS 作为 SP,Azure AD 作为 IdP:

  1. 用户访问 AWS 控制台
  2. AWS 发现用户未登录,重定向到 Azure AD
  3. 用户在 Azure AD 输入凭证
  4. Azure AD 生成 SAML 断言,发回给 AWS
  5. AWS 验证断言,允许用户登录

SAML 断言长这样(简化版):

<saml:Assertion>
  <saml:Subject>
    <saml:NameID>user@company.com</saml:NameID>
  </saml:Subject>
  <saml:AttributeStatement>
    <saml:Attribute Name="Role">
      <saml:AttributeValue>admin</saml:AttributeValue>
    </saml:Attribute>
  </saml:AttributeStatement>
</saml:Assertion>

避坑指南:我曾经在配置 SAML 时,因为证书过期导致 SSO 突然失效。后来我养成了习惯:在证书到期前 30 天设置自动提醒。另外,建议用自动化工具管理证书轮换,别手动操作。

3.4 统一权限模型设计

最后,聊聊权限模型的设计。跨云环境下,权限模型要能「翻译」不同云的权限语言。

我常用的方法是:抽象一个中间层。比如定义一套通用的权限标签:

  • read:storage:读取存储
  • write:compute:创建计算资源
  • admin:all:管理员权限

然后写一个适配器,把这些标签映射到各个云平台的权限策略。比如:

# 通用标签 -> AWS 策略
mapping = {
    "read:storage": "s3:GetObject, s3:ListBucket",
    "write:compute": "ec2:RunInstances, ec2:StartInstances",
    "admin:all": "*"
}

这样,你只需要在中间层管理权限,不用每个云都配一遍。省事多了。

总结一下:统一身份认证的核心就三件事——角色建模、SSO 集成、协议选型。做好这三件事,跨云协同的身份管理基本就稳了。


公众号:蓝海资料掘金营,微信deep3321