Serverless: S3 – S3BucketPermissions – Action does not apply to any resource(s) in statement
I’ve been playing around with S3 buckets with Serverless, and recently wrote the following code to create an S3 bucket and put a file into that bucket:
const AWS = require("aws-sdk"); let regionParams = { 'region': 'us-east-1' } let s3 = new AWS.S3(regionParams); let s3BucketName = "marks-blog-bucket"; console.log("Creating bucket: " + s3BucketName); let bucketParams = { Bucket: s3BucketName, ACL: "public-read" }; s3.createBucket(bucketParams).promise() .then(console.log) .catch(console.error); var putObjectParams = { Body: "<html><body><h1>Hello blog!</h1></body></html>", Bucket: s3BucketName, Key: "blog.html" }; s3.putObject(putObjectParams).promise() .then(console.log) .catch(console.error);
When I tried to cURL the file I got a permission denied exception:
$ curl --head --silent https://s3.amazonaws.com/marks-blog-bucket/blog.html HTTP/1.1 403 Forbidden x-amz-request-id: 512FE36798C0BE4D x-amz-id-2: O1ELGMJ0jjs11WCrNiVNF2z2ssRgtO4+M4H2QQB5025HjIpC54VId0eKZryYeBYN8Pvb8GsolTQ= Content-Type: application/xml Transfer-Encoding: chunked Date: Fri, 29 Sep 2017 05:42:03 GMT Server: AmazonS3
I wrote the following code to try and have Serverless create a bucket policy that would make all files in my bucket publicly accessible:
serverless.yml
service: marks-blog frameworkVersion: ">=1.2.0 <2.0.0" provider: name: aws runtime: python3.6 timeout: 180 resources: Resources: S3BucketPermissions: Type: AWS::S3::BucketPolicy Properties: Bucket: marks-blog-bucket PolicyDocument: Statement: - Principal: "*" Action: - s3:GetObject Effect: Allow Sid: "AddPerm" Resource: arn:aws:s3:::marks-blog-bucket ...
Let’s try to deploy it:
./node_modules/serverless/bin/serverless deploy Serverless: Packaging service... Serverless: Excluding development dependencies... Serverless: Uploading CloudFormation file to S3... Serverless: Uploading artifacts... Serverless: Uploading service .zip file to S3 (1.3 KB)... Serverless: Validating template... Serverless: Updating Stack... Serverless: Checking Stack update progress... ........ Serverless: Operation failed! Serverless Error --------------------------------------- An error occurred: S3BucketPermissions - Action does not apply to any resource(s) in statement.
D’oh! That didn’t do what I expected.
I learnt that this message means:
Some services do not let you specify actions for individual resources; instead, any actions that you list in the Action or NotAction element apply to all resources in that service. In these cases, you use the wildcard * in the Resource element.
To fix it we need to use the wildcard * to indicate that the s3:GetObject permission should apply to all values in the bucket rather than to the bucket itself.
Take 2!
serverless.yml
service: marks-blog frameworkVersion: ">=1.2.0 <2.0.0" provider: name: aws runtime: python3.6 timeout: 180 resources: Resources: S3BucketPermissions: Type: AWS::S3::BucketPolicy Properties: Bucket: marks-blog-bucket PolicyDocument: Statement: - Principal: "*" Action: - s3:GetObject Effect: Allow Sid: "AddPerm" Resource: arn:aws:s3:::marks-blog-bucket/* ...
Let’s deploy again and try to access the file:
$ curl --head --silent https://s3.amazonaws.com/marks-blog-bucket/blog.html HTTP/1.1 200 OK x-amz-id-2: uGwsLLoFHf+slXADGYkqW0bLfQ7EPG/kqzV3l2k7SMex4NlMEpNsNN/cIC9INLPohDtVFwUAa90= x-amz-request-id: 7869E21760CD50F1 Date: Fri, 29 Sep 2017 06:05:11 GMT Last-Modified: Fri, 29 Sep 2017 06:01:33 GMT ETag: "57bac87219812c2f9a581943da34cfde" Accept-Ranges: bytes Content-Type: application/octet-stream Content-Length: 46 Server: AmazonS3
Success! And if we check in the AWS console we can see that the bucket policy has been applied to our bucket:
Published on Java Code Geeks with permission by Mark Needham, partner at our JCG program. See the original article here: Serverless: S3 – S3BucketPermissions – Action does not apply to any resource(s) in statement Opinions expressed by Java Code Geeks contributors are their own. |