如何使用 aws sam cli 在 .yaml 中为 python lambda 编写策略以从 S3 读取

How to write a policy in .yaml for a python lambda to read from S3 using the aws sam cli

我正在尝试将 python lambda 部署到 aws。当给定存储桶名称和文件路径时,此 lambda 仅从 s3 存储桶读取文件。如果我 运行 以下命令,它在本地机器上工作正常:

sam build && sam local invoke --event testfile.json GetFileFromBucketFunction

文件中的数据被打印到控制台。接下来,如果我 运行 以下命令将 lambda 打包并发送到 my-bucket。

sam build && sam package --s3-bucket my-bucket --template-file .aws-sam\build\template.yaml --output-template-file packaged.yaml

下一步是在 prod 中部署,所以我尝试以下命令:

sam deploy --template-file packaged.yaml --stack-name getfilefrombucket --capabilities CAPABILITY_IAM --region my-region

lambda 现在可以在 lambda 控制台中看到,我可以 运行 它但没有返回任何内容,如果我手动将服务角色更改为允许 s3 get/put 那么 lambda作品。然而,这破坏了使用 aws sam cli 的全部意义。

我想我需要在 template.yaml 文件中添加一个策略。这个linkhere seems to say that I should add a policy such as one shown here。所以,我补充说:

Policies: S3CrudPolicy

在 'Resources:GetFileFromBucketFunction:Properties:' 下,然后我重建应用程序并重新部署,部署失败并在 cloudformation 中出现以下错误:

1 validation error detected: Value 'S3CrudPolicy' at 'policyArn' failed to satisfy constraint: Member must have length greater than or equal to 20 (Service: AmazonIdentityManagement; Status Code: 400; Error Code: ValidationError; Request ID: unique number

The following resource(s) failed to create: [GetFileFromBucketFunctionRole]. . Rollback requested by user.

我删除堆栈重新开始。我的想法是 'S3CrudPolicy' 不是我可以使用的现成策略,而是我必须在 template.yaml 文件中定义自己的东西?

我不确定该怎么做,而且文档似乎没有显示任何非常简单的用例示例(据我所知),如果有人知道该怎么做,您可以 post 解决方案?

我尝试了以下方法:

S3CrudPolicy:
  PolicyDocument:
    -
      Action: "s3:GetObject"
      Effect:  Allow
      Resource: !Sub arn:aws:s3:::${cloudtrailBucket}
      Principal:  "*"

但失败并出现以下错误:

Failed to create the changeset: Waiter ChangeSetCreateComplete failed: Waiter encountered a terminal failure state Status: FAILED. Reason: Invalid template property or properties [S3CrudPolicy] 

如果有人可以帮助从 s3 为 read/write 编写一个简单的策略,那会很棒吗?我需要再写一个这样让 lambdas 调用其他 lambdas 以及这里的解决方案(我想象类似的东西?)会很棒吗? - 或者关于如何编写这些政策声明的体面、易于使用的指南?

非常感谢您的帮助!

找到了!!如果其他人遇到这个问题,您需要将以下几行添加到 template.yaml 文件中的 Resources:YourFunction:Properties:

  Policies: 
    - S3CrudPolicy:
        BucketName: "*"

“*”将允许您的 lambda 与任何存储桶通信,如果需要,您可以切换为特定的东西。如果您遗漏 'BucketName' 则它不起作用,并且 returns CloudFormation 中的错误提示 S3CrudPolicy 无效。