提问人:Jordan 提问时间:8/9/2018 最后编辑:mecographJordan 更新时间:8/25/2021 访问量:9119
将存储桶策略附加到无服务器生成的存储桶
Attach bucket policy to bucket generated by serverless
问:
我正在尝试使用无服务器创建一个 S3 存储桶,它可以工作,但是为了操作其中的文件,我需要一个存储桶策略。我很难理解在何处以及如何添加使用首次无服务器部署时创建的生成的 S3bucket 名称的策略
##serverless.yml
##
service: vcc-nametags-api
# Use the serverless-webpack plugin to transpile ES6
plugins:
- serverless-webpack
- serverless-offline
- serverless-ding
# serverless-webpack configuration
# Enable auto-packing of external modules
custom:
# Our stage is based on what is passed in when running serverless
# commands. Or fallsback to what we have set in the provider section.
stage: ${opt:stage, self:provider.stage}
# Set our DynamoDB throughput for prod and all other non-prod stages.
# Load our webpack config
webpack:
webpackConfig: ./webpack.config.js
includeModules: true
environment: ${file(env.yml):${self:custom.stage}, file(env.yml):default}
provider:
name: aws
runtime: nodejs8.10
stage: dev
region: us-east-1
# These environment variables are made available to our functions
# under process.env.
environment:
S3DBBucketName:
Ref: NametagsDatabaseBucket
functions:
# Defines an HTTP API endpoint that calls the main function in create.js
# - path: url path is /tags
# - method: POST request
# - cors: enabled CORS (Cross-Origin Resource Sharing) for browser cross
# domain api call
# - authorizer: authenticate using the AWS IAM role
create:
handler: create.main
events:
- http:
path: tags
method: post
cors: true
get:
# Defines an HTTP API endpoint that calls the main function in get.js
# - path: url path is /tags/{id}
# - method: GET request
handler: get.main
events:
- http:
path: tags/{id}
method: get
cors: true
list:
# Defines an HTTP API endpoint that calls the main function in list.js
# - path: url path is /tags
# - method: GET request
handler: list.main
events:
- http:
path: tags
method: get
cors: true
update:
# Defines an HTTP API endpoint that calls the main function in update.js
# - path: url path is /tags/{id}
# - method: PUT request
handler: update.main
events:
- http:
path: tags/{id}
method: put
cors: true
delete:
# Defines an HTTP API endpoint that calls the main function in delete.js
# - path: url path is /tags/{id}
# - method: DELETE request
handler: delete.main
events:
- http:
path: tags/{id}
method: delete
cors: true
# Create our resources with separate CloudFormation templates
resources:
# S3DB
- ${file(resources/s3-database.yml)}
##s3-database.yml
##
Resources:
NametagsDatabaseBucket:
Type: AWS::S3::Bucket
Properties:
# Set the CORS policy
CorsConfiguration:
CorsRules:
-
AllowedOrigins:
- '*'
AllowedHeaders:
- '*'
AllowedMethods:
- GET
- PUT
- POST
- DELETE
- HEAD
MaxAge: 3000
NametagsDatabaseBucketPolicy:
Type: AWS::S3::BucketPolicy
Properties:
Bucket:
Ref: NametagsDatabaseBucket
PolicyDocument:
Statement:
- Sid: PublicReadGetObject
Effect: Allow
Principal: "*"
Action:
- "s3:DeleteObject"
- "s3:GetObject"
- "s3:ListBucket"
- "s3:PutObject"
Resource:
Fn::Join: [
"", [
"arn:aws:s3:::",
{
"Ref": "NametagsDatabaseBucket"
},
"/*"
]
]
# Print out the name of the bucket that is created
Outputs:
NametagsDatabaseBucketName:
Value:
Ref: NametagsDatabaseBucket
我已经尝试了在互联网上找到的各种组合,并将其添加到文件中的属性中,但我似乎无法使任何事情正常工作iamroles
serverless.yml
答:
9赞
Matt D
8/9/2018
#1
资源引用名称似乎很重要,我一直不得不在资源名称中使用存储桶的名称。例如,具有 www.example.com 的存储桶需要引用名称 。S3BucketWwwexamplecom
但是,我还注意到您的示例中缺少 BucketName 元素。
这是来自具有存储桶策略的静态网站的工作示例:
resources:
Resources:
S3BucketWwwexamplecom:
Type: AWS::S3::Bucket
DeletionPolicy: Delete
Properties:
BucketName: ${self:custom.s3WwwBucket}
CorsConfiguration:
CorsRules:
- AllowedMethods:
- PUT
- GET
- POST
- HEAD
AllowedOrigins:
- "https://${self:custom.myDomain}"
AllowedHeaders:
- "*"
AccessControl: PublicRead
WebsiteConfiguration:
IndexDocument: index.html
BucketPolicyWwwexamplecom:
Type: 'AWS::S3::BucketPolicy'
Properties:
PolicyDocument:
Statement:
- Sid: PublicReadForGetBucketObjects
Effect: Allow
Principal: '*'
Action:
- 's3:GetObject'
Resource: arn:aws:s3:::${self:custom.s3WwwBucket}/*
Bucket:
Ref: S3BucketWwwexamplecom
-1赞
Alessandro Oliveira
8/9/2018
#2
由于您使用 lambda 进行上传,因此您应该为 Lambda 创建一个 IAM 角色和一个仅具有操作所需权限的 IAM 策略。您可以通过在云形成中使用以下摘录来实现此目的:
AWSTemplateFormatVersion: '2010-09-09'
Description: My Template
Resources:
LambdaRole:
Type: AWS::IAM::Role
Properties:
AssumeRolePolicyDocument:
Version: '2012-10-17'
Statement:
- Effect: Allow
Principal:
Service: lambda.amazonaws.com
Action: sts:AssumeRole
RoleName: !Sub ${AWS::StackName}-LambdaRole
S3Policy:
Type: AWS::IAM::Policy
Properties:
PolicyName: S3_Writer
PolicyDocument:
Version: '2012-10-17'
Statement:
- Effect: Allow
Action:
- s3:*
Resource: !Sub
- arn:aws:s3:::${BucketName}/*
- BucketName: !Ref NametagsDatabaseBucket
Roles:
- !Ref TaskRole
Outputs:
LambdaRole:
Value: !Sub "${LambdaRole.Arn}"
Export:
Name: !Sub ${AWS::StackName}-LambdaRole
然后,在您的serverless.yml中,只需引用使用类似这样的东西创建的任务角色来引用执行角色:
service: vcc-nametags-api
provider:
role: ${cf:${env:YOUR_STACK_ENV, 'YOUR_STACK_NAME'}.LambdaRole}
我们在几个项目中都有这样的设置,我希望它对你有用。
评论