amazon-dynamodb - 使用 Cognito 的 DynamoDB 细粒度访问

标签 amazon-dynamodb authorization amazon-cognito amazon-iam

我正在开发一项需要访问 DynamoDB 表的服务,该表必须通过授权用户访问表来管理。帐户管理由 Cognito 处理。我目前正在调查对 DynamoDB 表的直接访问,并根据具有相关 IAM 策略的用户组限制读/写访问。

表中存在多个组织,多个用户与一个组织相关联。该模型的示例如下。我还以多对一关系存储部门和部门信息。

用户的 Cognito Sub 作为用户 ID 存储在数据库中的 USR# 下。

+-------+-------+-----------------+------------+--------+
|  PK   |  SK   |      Name       |   GSI1PK   | GSI2PK |
+-------+-------+-----------------+------------+--------+
| ORG#1 | ORG#1 | Acme Inc        |            |        |
| ORG#1 | USR#1 | John Doe        |            |        |
| ORG#2 | ORG#2 | Globetex        |            |        |
| ORG#2 | USR#2 | Jane Doe        |            |        |
| ORG#1 | SEC#1 | Sector A1       | ORG#1SEC#1 | SEC#1  |
| DEP#1 | DEP#1 | Human Resources | ORG#1SEC#1 | DEP#1  |
+-------+-------+-----------------+------------+--------+

到目前为止,我可以在特定 IAM 策略中以硬编码方式限制对每个组织的访问。但是,这是不可扩展的。如果要存在一百个组织,则还必须存在一百个具有单独策略的用户组。此政策的示例如下。

有没有什么方法可以创建一个使用自定义 Cognito 变量的 IAM 策略,例如“organization”,它允许我创建一个单一的策略来限制对仅以该组织开头的行的访问?我无法使用以下代码使其正常工作。

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "dynamodb:GetItem",
                "dynamodb:PutItem",
                "dynamodb:Query"
            ],
            "Resource": [
                "arn:aws:dynamodb:region:id:table/TableName"
            ],
            "Condition": {
                "ForAllValues:StringEquals": {
                    "dynamodb:LeadingKeys": [
                        "${cognito-identity.amazonaws.com:org}"
                    ]
                }
            }
        }
    ]
}

编辑:为清楚起见,我的查询是在验证时将自定义 Cognito 变量动态插入到 IAM 策略中。

例如,用户 A 将 custom:org = Acme 作为 Cognito 属性,而用户 B 将 custom:org = Globex 作为其自定义 Cognito 属性。

上面代码中详述的单个策略可以将此属性直接插入到策略中,因此一个策略可以用于不同组织中的多个用户。

经过进一步研究后,我不确定这是否可行,但如果有人有任何尝试此类事情的经验,我很乐意听到。

最佳答案

根据 this article,我认为你很接近它应该是 StringLike 而不是 StringEquals

"Condition": {
              "ForAllValues:StringLike": {
                  "dynamodb:LeadingKeys": [
                      "{TENANTID}-*"
                  ]
              }

可能还想阅读 Multi-tenant SaaS Storage Strategies白皮书

编辑 我不相信静态策略有可能做你想做的事。

但是链接文章中的代码确实提供了“管理来自任何租户的用户的访问”的能力。

重点是role/AccessDynamoWithTenantContext的使用

    tenantPolicy = getPolicy(event['tenantID'])
    
    assumed_role = sts_client.assume_role(
        RoleArn="arn:aws:iam::<account-id>:role/AccessDynamoWithTenantContext",
        RoleSessionName="tenant-aware-product",
        Policy=tenantPolicy,
    )

并在getPolicy()中动态注入(inject)tenentId

policy = json.dumps(policyTemplate).replace("{TENANTID}", tenantID)

return policy

关于amazon-dynamodb - 使用 Cognito 的 DynamoDB 细粒度访问,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/64334798/

相关文章:

google-cloud-platform - GCP IAM 能否用于为我的业务应用程序的用户提供访问控制

c# - WP7 上的 TweetSharp 授权 (oAuth)

amazon-web-services - 如何为未经身份验证的用户使用 AWS Cognito?

amazon-web-services - amazon-cognito-identity-js - 通过电子邮件验证用户身份时遇到问题

amazon-web-services - Dynamodb- 添加非关键属性

python - 如何使用 Boto 使 dynamoDB 中的 key 过期?

amazon-web-services - 本地 DynamoDB

java - Quarkus 和 DynamoDBMapper - native 构建上的 "no mapping for HASH key"

node.js - 使用授权方法和新附加参数 : accessToken in Header? 有什么区别

javascript - 如何处理 Cognito Web 应用程序 session 刷新?