DEV Community

Cover image for Share Your AWS S3 Private Content With Others, Without Making It Public

Share Your AWS S3 Private Content With Others, Without Making It Public

Idris Rampurawala on March 24, 2020

Amazon Web Services (AWS) S3 objects are private by default. Only the object owner has permission to access these objects. Optionally we can set bu...
Collapse
 
detstartups profile image
Detroit Startups

Hi - if you were planning to deploy this as a Flask app - per your github repo - would it make sense to do that via AWS Lambda? And to do that via Zappa, or AWS Sam to build the Lambda stack, or something else?

Thanks so much for making this post!

Collapse
 
idrisrampurawala profile image
Idris Rampurawala • Edited

Hi,

Thanks for reading the article.

You can definitely deploy it as a Serverless app like AWS Lambda, totally depends on your use-case.
The article is just a demonstration of achieving the problem statement at hand, you can plug it into either your existing codebase or design a standalone serverless API (as per your need).

P.S. Hit ❤️ or 🦄 if you like this post.

Collapse
 
l222p profile image
l222p

Is it safe to share pre-signed URLs? Because I have noticed that the AccessKey and Token are present in the URL, can be this considered a vulnerability?

Collapse
 
idrisrampurawala profile image
Idris Rampurawala

Hey, it is safe in the sense that you decide the users who will get access to the resource, but do evaluate on the following points:

  • Restrict access by ensuring Limiting presigned URL capabilities
  • Always generate a URL with an expiry
  • The access key and token shared in the presigned-url are generated at runtime and one cannot easily manipulate the url (check was docs)
  • Try not to disclose your S3 path in the URL (use CloudFront)
  • Lastly, avoid sharing your S3 files if it contains sensitive information. Rather mask if for the end-users.

Hope it solves your queries.

Collapse
 
l222p profile image
l222p

Thanks,

Want I want to display images on my site, those images are located in S3 and they're encrypted. Right now, what I do is download the image in the backend using the S3 GetObject API, but I don't like it since the front-end should download them. So, I pre-signed them and send it this way and then I realized they contain ApiAccess and ApiToken.

I don't think this is ok haha, What should I do? How can I use CloudFront to "hide" the s3 path?

Thanks

Thread Thread
 
idrisrampurawala profile image
Idris Rampurawala

Hi,

If your front-end is using resources from S3, then I would suggest you add S3 bucket permissions to restrict the access outside your domain.

You can then directly expose that S3 bucket containing images on the front-end via Cloudfront. I do not see any use-case of using a pre-signed URL here as ur images might be restricted to your own domain and optionally authenticated users.

Hope it answers your queries.

P.S. Check this post for using CloudFront in front of S3

Collapse
 
thegardenman profile image
TheGardenMan

Hi thanks for the article.I am quite new to this.But in boto3,where should I specify my access_key,secret_key etc?
One can't simply generate a signed right?
I am new to this.So I maybe wrong!

Collapse
 
idrisrampurawala profile image
Idris Rampurawala

Hey, it is not recommended to use AWS secrets for any AWS SDK (boto3 in your case). The recommended method is to install AWS CLI in your local machine and configure it with your IAM secret keys. Now, in this project you only need to add this profile-name (gets generated by AWS CLI setup) in .env against AWS_PROFILE_NAME key and your AWS SDK should work then.

Collapse
 
mannysayah profile image
Manny Sayah

Great post! Could I do something like only make them public if the files are accessed through a certain route?

Let's say I have a myVideo file in my S3 bucket.
The video file is private. So no direct access to s3/bucket/myVideo
But the video is accessible if any public user goes to mywebsite.com/player?file=myVideo

Cheers

Collapse
 
frumkinariel profile image
Ariel Frumkin

Hi!
is there a way to share an s3 folder to non s3 users?
thank you

Collapse
 
idrisrampurawala profile image
Idris Rampurawala • Edited

Hey Ariel, thanks for reading the post.

AWS S3 does not have a true concept of folder structures. They are just a logical separation of actual objects. Hence, you cannot directly create a signed URL of a folder in S3.

There is a way I can think of accomplishing your task is by creating a signed URL with custom policy. The link will help you achieve your use-case. Please do share if you are able to achieve this :)

P.S. Make sure you have proper conditions in your custom policy to restrict public access.

Collapse
 
sumaximize profile image
sumaximize • Edited

The generated url is then given to the user without making our bucket private.

Maybe a slip, I think you mean "without making our bucket public".

Thanks for the post 🎉