AWS Lambda:Lambda 函数 S3 到 S3 复制的跨账户策略

问题描述 投票:0回答:3

我们正在尝试实现 lambda 函数,该函数将根据源 S3 存储桶事件将对象从一个 S3 复制到跨账户中的另一个 S3 存储桶。目前,我们能够在同一 SAG 内的源和目标之间复制文件。但是当我们尝试跨账户实现相同的逻辑时,得到了 CopyObject 操作:Access Denied 问题。我已经给出了以下存储桶策略。您能否帮助我获取正确的 IAM 和存储桶策略来解决此问题。

{
    "Version": "2012-10-17",
    "Id": "Policy1603404813917",
    "Statement": [
        {
            "Sid": "Stmt1603404812651",
            "Effect": "Allow",
            "Principal": {
                "AWS": "arn:aws:iam::6888889898:role/Staff"
            },
            "Action": [
                "s3:GetObject",
                "s3:GetObjectAcl",
                "s3:ListBucket",
                "s3:PutObject",
                "s3:PutObjectAcl"
            ],
            "Resource": [
                "arn:aws:s3:::source-bucktet-testing-lambda/*",
                "arn:aws:s3:::source-bucktet-testing-lambda"
            ]
        }
    ]
}

基于

https://www.lixu.ca/2016/09/aws-lambda-and-s3-how-to-do-cross_83.html
链接,是的,我们可以借助源和目标的访问 ID 和访问密钥来实现相同的逻辑。但我正在尝试实现相同的逻辑,而不是源和目标的访问 ID 和访问密钥,通过适当的策略授予源和目标存储桶的访问权限,并使其像同一帐户一样工作。

amazon-web-services amazon-s3 aws-lambda amazon-iam
3个回答
11
投票

为了重现您的情况,我执行了以下操作:

  • 帐户-A中:
    • 创建了 Amazon S3 存储桶 (
      Bucket-A
      )
    • 创建了 IAM 角色 (
      Role-A
      )
    • 创建了 AWS Lambda 函数 (
      Lambda-A
      ) 并将
      Role-A
      分配给该函数
    • Bucket-A 上配置了
      Amazon S3 事件
      以触发
      Lambda-A
      的“所有对象创建事件”
  • 帐户-B中:
    • 使用存储桶策略创建了 Amazon S3 存储桶 (
      Bucket-B
      )(见下文)

IAM 角色

Role-A
具有
AWSLambdaBasicExecutionRole
托管策略,以及此内联策略,该内联策略为 Lambda 函数分配读取
Bucket-A
和写入
Bucket-B
的权限:

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

目标存储桶的存储桶策略

Bucket-B
上的存储桶策略允许从
Role-A
IAM 策略进行访问:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Principal": {
                "AWS": "arn:aws:iam::ACCOUNT-A:role/role-a"
            },
            "Action": [
                "s3:PutObject",
                "s3:PutObjectAcl"
            ],
            "Resource": "arn:aws:s3:::bucket-b/*"
        }
    ]
}

Lambda 函数

当在

Lambda-A

中创建对象时会触发
Bucket-A
,并将其复制到
Bucket-B

import boto3
import urllib

TARGET_BUCKET = 'bucket-b'

def lambda_handler(event, context):
    
    # Get incoming bucket and key
    source_bucket = event['Records'][0]['s3']['bucket']['name']
    source_key = urllib.parse.unquote_plus(event['Records'][0]['s3']['object']['key'])

    # Copy object to different bucket
    s3_resource = boto3.resource('s3')
    copy_source = {
        'Bucket': source_bucket,
        'Key': source_key
    }
    target_key = source_key # Change if desired

    s3_resource.Bucket(TARGET_BUCKET).Object(target_key).copy(copy_source, ExtraArgs={'ACL': 'bucket-owner-full-control'})

我同意

ACL=bucket-owner-full-control
,因为将对象复制到不同帐户拥有的存储桶有时会导致对象仍然由原始帐户“拥有”。使用此 ACL 向拥有目标存储桶的账户授予所有权。

测试

我已将文件上传到

Bucket-A
中的
Account-A

文件已正确复制到

Bucket-B
中的
Account-B

评论

该解决方案不需要需要:

  • Bucket-A
    上的存储桶策略,因为
    Role-A
    授予必要的权限
  • 关闭 S3 阻止公共访问,因为分配的权限不会授予“公共”访问权限

0
投票

假设如下

  1. 上述策略适用于源存储桶
  2. 6888889898 是目标 AWS 账户
  3. 用于复制文件的 Lambda 位于目标 AWS 账户中,并附加有员工角色。

即使正确设置了所有这些,复制操作也可能会失败。这是因为策略允许您获取/放置 s3 对象,但不允许与这些 s3 对象关联的标签。

您还需要允许以下操作“s3:GetObjectTagging”和“s3:PutObjectTagging”


0
投票

谢谢您的本指南,它非常适合小文件,但当我上传大文件(~200mb)时,它无法复制。 你能帮我解决这个问题吗

© www.soinside.com 2019 - 2024. All rights reserved.