文档

通过RRSA配置ServiceAccount的RAM权限实现Pod权限隔离

更新时间:

基于适用于服务账户的RAM角色(RAM Roles for Service Accounts,简称RRSA)功能,您可以在集群内实现Pod维度的OpenAPI权限隔离,从而实现云资源访问权限的细粒度隔离,降低安全风险。本文介绍RRSA功能的使用方法。

索引

背景信息

ECS实例元数据包含ECS实例(ECI实例基于ECS实例实现)在阿里云系统中的信息。您可以在运行中的实例内查看实例元数据,并基于实例元数据配置或管理实例。通过实例元数据,Kubernetes集群内应用可以获取实例RAM角色策略所生成的STS临时凭证,然后通过该临时凭证访问云资源OpenAPI。更多信息,请参见ECS实例元数据概述

1

但ECS实例元数据无法满足多租场景下集群内应用Pod间的云资源访问权限隔离需求,也无法满足ACK Serverless或ECI场景下使用STS临时凭证的需求(ECI实例无法绑定用户的RAM角色)。因此,阿里云容器服务ACK联合RAM访问控制服务推出了RRSA功能。基于RRSA功能,您可以在集群内实现应用隔离的RAM角色功能。各个应用可以扮演独立的RAM角色并使用获取的临时凭证访问云资源,以实现应用RAM权限最小化。

在多租场景下,RRSA功能可以实现集群内应用Pod间云资源访问权限的细粒度隔离;在ACK Serverless或ECI场景下,RRSA功能可以满足使用STS临时凭证控制凭证有效期的需求。

3

从用户侧视角来看,RRSA功能的工作流程如下。

  1. 用户提交使用了服务账户令牌卷投影功能的应用Pod。

  2. 集群将为该应用Pod创建和挂载相应的服务账户OIDC Token文件。

  3. Pod内程序使用挂载的OIDC Token文件访问STS服务的AssumeRoleWithOIDC接口,获取扮演指定RAM角色的临时凭证。

    说明

    请提前修改RAM角色配置,允许Pod使用的服务账户扮演该RAM角色。更多信息,请参见AssumeRoleWithOIDC

  4. Pod内程序使用获取到的临时凭证访问云资源OpenAPI。

使用限制

RRSA功能目前仅支持1.22及以上版本的集群,即ACK集群基础版ACK集群Pro版ACK Serverless集群基础版ACK Serverless集群Pro版

启用RRSA功能

  1. 登录容器服务管理控制台

  2. 在控制台左侧导航栏,单击集群

  3. 集群列表页面,单击目标集群名称或者目标集群右侧操作列下的详情

  4. 在集群详情页面,单击基本信息页签,然后在集群信息区域单击RRSA OIDC对应的启用RRSA

  5. 在弹出的启用RRSA对话框,单击确定

    基本信息区域,当集群状态由更新中变为运行中后,表明该集群的RRSA特性已变更完成,RRSA OIDC右侧将显示OIDC提供商的URL链接和ARN信息。

集群开启RRSA功能后,ACK将在后台执行如下操作。

  • 自动创建一个集群专用的OIDC Issuer服务。该服务由ACK托管,无需您运维。更多信息,请参见OIDC Issuer

  • 为您的集群开启服务账户令牌卷投影功能。更多信息,请参见部署服务账户令牌卷投影

    说明

    如果您的集群此前已开启服务账户令牌卷投影功能,本次操作将使用本次创建的OIDC Issuer配置合并您此前设置的service-account-issuer参数的值。

  • 在您的账号下创建一个使用该OIDC Issuer的OIDC身份提供商,名称为ack-rrsa-<cluster_id>,其中 <cluster_id>为您的集群ID。更多信息,请参见管理OIDC身份提供商

使用RRSA功能

集群开启RRSA功能后,您可以参考以下内容,赋予集群内应用通过RRSA功能获取访问云资源OpenAPI的临时凭证的能力。

使用示例

本示例部署的应用将使用RRSA功能扮演指定角色,获取当前账号下集群列表信息。

示例配置

  • 命名空间:rrsa-demo

  • 服务账户:demo-sa

  • RAM角色:demo-role-for-rrsa

示例流程

使用示例流程
  • 如果您希望通过不安装ack-pod-identity-webhook组件的方式使用RRSA功能,您可以手动修改应用模板挂载应用所需的OIDC Token文件并配置相关环境变量。具体操作,请参见手动修改应用模板使用RRSA功能

  • 如果您希望使用已存在的RAM角色,不创建新的RAM角色,您可以为已有RAM角色新增相关权限。具体操作,请参见使用已存在的RAM角色并授权

  1. 安装ack-pod-identity-webhook组件。

    1. 集群列表页面,单击目标集群名称,然后在左侧导航栏,选择运维管理 > 组件管理

    2. 组件管理页面,单击安全页签,找到ack-pod-identity-webhook组件,单击组件右下方的安装

    3. 在提示对话框确认组件信息后,单击确定

  2. 创建一个名为demo-role-for-rrsa的RAM角色。

    1. 使用阿里云账号登录RAM控制台

    2. 在左侧导航栏,选择身份管理 > 角色,然后在角色页面,单击创建角色

    3. 创建角色面板,选择可信实体类型为身份提供商,然后单击下一步

    4. 配置角色页面,配置如下角色信息后,单击完成

      本示例配置如下。

      配置项

      描述

      角色名称

      demo-role-for-rrsa。

      备注

      选填有关该角色的备注信息。

      身份提供商类型

      OIDC

      选择身份提供商

      ack-rrsa-<cluster_id>。其中,<cluster_id>为您的集群ID。

      限制条件

      • oidc:iss:保持默认。

      • oidc:aud:选择sts.aliyuncs.com

      • oidc:sub:条件判定方式选择StringEquals,值的格式为system:serviceaccount:<namespace>:<serviceAccountName>

        • <namespace>:应用所在的命名空间。

        • <serviceAccountName>:服务账户名称。

        根据测试应用的信息,此处需要填入system:serviceaccount:rrsa-demo:demo-sa

  3. 步骤2创建的角色授予测试应用所需的AliyunCSReadOnlyAccess系统策略权限。具体操作,请参见为RAM角色授权

  4. 部署测试应用。关于测试应用的参考代码,请参见阿里云官方SDK使用RRSA OIDC Token的参考代码

    1. 使用以下内容,创建demo.yaml文件。

      如下YAML示例中,为命名空间增加标签pod-identity.alibabacloud.com/injection: 'on',并为服务账号增加注解pod-identity.alibabacloud.com/role-name: demo-role-for-rrsa,启用ack-pod-identity-webhook组件的配置自动注入功能。关于ack-pod-identity-webhook组件配置的更多说明,请参见ack-pod-identity-webhook

      展开查看示例代码

      ---
      apiVersion: v1
      kind: Namespace
      metadata:
        name: rrsa-demo
        labels:
          pod-identity.alibabacloud.com/injection: 'on'
      
      ---
      apiVersion: v1
      kind: ServiceAccount
      metadata:
        name: demo-sa
        namespace: rrsa-demo
        annotations:
          pod-identity.alibabacloud.com/role-name: demo-role-for-rrsa
      
      ---
      apiVersion: v1
      kind: Pod
      metadata:
        name: demo
        namespace: rrsa-demo
      spec:
        serviceAccountName: demo-sa
        containers:
          - image: registry.cn-hangzhou.aliyuncs.com/acs/ack-ram-tool:1.0.0
            imagePullPolicy: "Always"
            args:
              - rrsa
              - demo
            name: demo
        restartPolicy: OnFailure
    2. 执行以下命令,部署测试应用。

      kubectl apply -f demo.yaml
  5. 执行以下命令,查看测试应用Pod,确认ack-pod-identity-webhook组件已为Pod自动注入所需的配置。

    kubectl -n rrsa-demo get pod demo -o yaml

    展开查看预期输出

    apiVersion: v1
    kind: Pod
    metadata:
      name: demo
      namespace: rrsa-demo
    spec:
      containers:
      - args:
        - rrsa
        - demo
        env:
        - name: ALIBABA_CLOUD_ROLE_ARN
          value: acs:ram::1***:role/demo-role-for-rrsa
        - name: ALIBABA_CLOUD_OIDC_PROVIDER_ARN
          value: acs:ram::1***:oidc-provider/ack-rrsa-c***
        - name: ALIBABA_CLOUD_OIDC_TOKEN_FILE
          value: /var/run/secrets/ack.alibabacloud.com/rrsa-tokens/token
        image: registry.cn-hangzhou.aliyuncs.com/acs/ack-ram-tool:1.0.0
        imagePullPolicy: Always
        name: demo
        volumeMounts:
        - mountPath: /var/run/secrets/kubernetes.io/serviceaccount
          name: kube-api-access-4bwdg
          readOnly: true
        - mountPath: /var/run/secrets/ack.alibabacloud.com/rrsa-tokens
          name: rrsa-oidc-token
          readOnly: true
      restartPolicy: OnFailure
      serviceAccount: demo-sa
      serviceAccountName: demo-sa
      volumes:
      - name: kube-api-access-4bwdg
        projected:
          defaultMode: 420
          sources:
          - serviceAccountToken:
              expirationSeconds: 3607
              path: token
          - configMap:
              items:
              - key: ca.crt
                path: ca.crt
              name: kube-root-ca.crt
          - downwardAPI:
              items:
              - fieldRef:
                  apiVersion: v1
                  fieldPath: metadata.namespace
                path: namespace
      - name: rrsa-oidc-token
        projected:
          defaultMode: 420
          sources:
          - serviceAccountToken:
              audience: sts.aliyuncs.com
              expirationSeconds: 3600
              path: token

    预期输出表明,ack-pod-identity-webhook组件已为Pod自动注入了如下配置。

    类别

    配置项名称

    配置项说明

    环境变量

    ALIBABA_CLOUD_ROLE_ARN

    需要扮演的RAM角色ARN。

    ALIBABA_CLOUD_OIDC_PROVIDER_ARN

    OIDC身份提供商的ARN。

    ALIBABA_CLOUD_OIDC_TOKEN_FILE

    包含OIDC Token的文件路径。

    VolumeMount

    rrsa-oidc-token

    挂载OIDC Token的配置。

    Volume

    rrsa-oidc-token

    挂载OIDC Token的配置。

  6. 执行以下命令,查看测试应用日志。

    kubectl -n rrsa-demo logs demo

    预期输出集群列表信息:

    cluster id: cf***, cluster name: foo*
    cluster id: c8***, cluster name: bar*
    cluster id: c4***, cluster name: foob*
  7. 可选:移除角色被授予的AliyunCSReadOnlyAccess系统策略权限。具体操作,请参见为RAM角色移除权限

    等待30秒左右,执行以下命令,再次查看测试应用日志。

    kubectl -n rrsa-demo logs demo

    预期输出无权限的错误日志:

       StatusCode: 403
       Code: StatusForbidden
       Message: code: 403, STSToken policy Forbidden for action cs:DescribeClusters request id: E78A2E2D-***
       Data: {"accessDeniedDetail":{"AuthAction":"cs:DescribeClusters","AuthPrincipalDisplayName":"demo-role-for-rrsa:ack-ram-tool","AuthPrincipalOwnerId":"11***","AuthPrincipalType":"AssumedRoleUser","NoPermissionType":"ImplicitDeny","PolicyType":"ResourceGroupLevelIdentityBasedPolicy"},"code":"StatusForbidden","message":"STSToken policy Forbidden for action cs:DescribeClusters","requestId":"E78A2E2D-***","status":403,"statusCode":403}

手动修改应用模板使用RRSA功能

您可以通过手动修改应用模板挂载应用所需的OIDC Token文件以及配置相关环境变量,在不安装ack-pod-identity-webhook组件的情况下使用RRSA功能。

应用模板示例代码如下。

展开查看应用模板示例代码

apiVersion: v1
kind: Pod
metadata:
  name: demo
  namespace: rrsa-demo
spec:
  containers:
  - args:
    - rrsa
    - demo
    env:
    - name: ALIBABA_CLOUD_ROLE_ARN
      value: <role_arn>
    - name: ALIBABA_CLOUD_OIDC_PROVIDER_ARN
      value: <oid_provider_arn>
    - name: ALIBABA_CLOUD_OIDC_TOKEN_FILE
      value: /var/run/secrets/ack.alibabacloud.com/rrsa-tokens/token
    image: registry.cn-hangzhou.aliyuncs.com/acs/ack-ram-tool:1.0.0
    imagePullPolicy: Always
    name: demo
    volumeMounts:
    - mountPath: /var/run/secrets/ack.alibabacloud.com/rrsa-tokens
      name: rrsa-oidc-token
      readOnly: true
  restartPolicy: OnFailure
  serviceAccount: demo-sa
  serviceAccountName: demo-sa
  volumes:
  - name: rrsa-oidc-token
    projected:
      defaultMode: 420
      sources:
      - serviceAccountToken:
          audience: sts.aliyuncs.com
          expirationSeconds: 3600
          path: token
重要

请替换应用模板示例代码中的如下字段。

  • <oid_provider_arn>:替换为当前集群的OIDC提供商ARN。该ARN可在容器服务管理控制台集群信息页面的基本信息页签获取。

  • <role_arn>需要替换为当前应用使用的RAM角色ARN。该ARN可在RAM控制台角色页面的角色详情页面获取。

  • audience:字段值需为 sts.aliyuncs.com

  • expirationSeconds:单位为秒,取值范围为[600, 43200],即10分钟~12小时。如果设置的值大于43200(12小时),实际的OIDC Token的过期时间仍为12小时。

部署修改后的应用模板后,应用内程序可以使用容器内挂载的OIDC Token(环境变量ALIBABA_CLOUD_OIDC_TOKEN_FILE指向的文件内容)、角色的ARN(环境变量ALIBABA_CLOUD_ROLE_ARN配置的值)以及OIDC身份提供商的ARN(环境变量ALIBABA_CLOUD_OIDC_PROVIDER_ARN配置的值),调用STS的AssumeRoleWithOIDC接口,获取一个扮演指定RAM角色的临时凭证,然后使用该临时凭证访问云资源OpenAPI。应用参考代码,请参见阿里云官方SDK使用RRSA OIDC Token的参考代码。更多信息,请参见AssumeRoleWithOIDC

使用已存在的RAM角色并授权

如果您的应用需要使用已存在的RAM角色,而非创建新的单独RAM角色,您可以修改RAM角色的信任策略,新增一条允许使用指定的服务账户的应用有权限通过扮演此RAM角色获取临时凭证的信任策略。更多信息,请参见修改RAM角色的信任策略

RAM角色信任策略中新增的Statement条目内容示例如下。

{
  "Action": "sts:AssumeRole",
  "Condition": {
    "StringEquals": {
      "oidc:aud": "sts.aliyuncs.com",
      "oidc:iss": "<oidc_issuer_url>",
      "oidc:sub": "system:serviceaccount:<namespace>:<service_account>"
    }
  },
  "Effect": "Allow",
  "Principal": {
    "Federated": [
      "<oidc_provider_arn>"
    ]
  }
}
重要

请替换Statement条目内容示例中的如下字段。

  • <oidc_issuer_url>:替换为当前集群的OIDC提供商URL。该URL可在容器服务管理控制台集群信息页面的基本信息页签获取。

  • <oidc_provider_arn>:替换为当前集群的OIDC提供商ARN。该ARN可在容器服务管理控制台集群信息页面的基本信息页签获取。

  • <namespace>:替换为应用所在的命名空间。

  • <service_account>:替换为应用使用的服务账户。

您也可以使用命令行工具ack-ram-tool通过自动化的方式配置该策略。对应的命令行示例如下。

ack-ram-tool rrsa associate-role --cluster-id <cluster_id> \
    --namespace <namespace> --service-account <service_account> \
    --role-name <role_name> --create-role-if-not-exist

阿里云官方SDK使用RRSA OIDC Token的参考代码

目前,部分阿里云官方SDK已经内置了支持使用RRSA OIDC Token进行OpenAPI认证的功能。支持此功能的SDK版本信息和参考代码如下。

编程语言

支持认证的SDK版本

使用示例

Go

Alibaba Cloud Credentials for Go 1.2.6及以上版本

GO SDK使用示例

Java

Alibaba Cloud Credentials for Java 0.2.10及以上版本

Java SDK使用示例

Python 3

Alibaba Cloud Credentials for Python 0.3.1及以上版本

Python 3 SDK使用示例

Node.js和TypeScript

Alibaba Cloud Credentials for TypeScript/Node.js 2.2.6及以上版本

Node.js和TypeScript使用示例

相关文档

  • 本页导读 (1)