I have an image in my AWS S3 bucket. Is it safe to include this image in my website by placing the AWS URL in an <img>
tag? The URL includes parameters such as "Amz-Signature", "Amz-Credential", and "amz-security-token. Could these be used maliciously to get to access other files in my S3 bucket?
Here is an example URL:
https://s3.amazonaws.com/MyBucketName/FileName.jpg?X-Amz-Date=20160126T141139Z&X-Amz-Expires=300&X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Signature=Lots_of_letters_and_Numbers2&X-Amz-Credential=MYAMAZON_CREDENTIALS/20160126/us-east-1/s3/aws4_request&X-Amz-SignedHeaders=Host&x-amz-security-token=REALLY_LONG_SECURITYTOKEN
Alternatively, I can generate an expiry URL from my C# code using the AWS SDK. Something like:
var expiryUrlRequest = new GetPreSignedUrlRequest
{
BucketName = WebConfigurationManager.AppSettings["AWSBucketName"],
Key = fileName,
Expires = DateTime.Now.AddHours(3)
};
This yields a URL that has "AWSAccessKeyId" as a parameter.
Are either of these URL's safe to use in my webpage? What risks would be involved in using them on my site?
Thank you very much for your time. Please let me know if you need additional information or if I am being unclear.
EDIT: To provide some further insight into my application, users are uploading a file to an S3 bucket. I'm using SignalR to confirm that the image is in the bucket by displaying the image from S3 on my webpage for the user to see.
Easiest thing to do is make them public in s3, at least read-only. If you don't want them to be public on s3, for whatever reason, you could add a cloudfront distribution that will serve the images from your s3 bucket, and you can give cloudfront access to the files, without making the images public in s3.
There is an access check on the S3 side but that only checks whether the signer entity is allowed to get the file. You can remove that permission but that invalidates all signed URLs. Signed URLs provide secure a way to distribute private content without streaming them through the backend.
The more efficient and cost-effective option is to use AWS's S3 service for storing the image files. Using S3 is a very low-cost option. Effectively, all you are paying for is transferring files into an S3 bucket and serving those images to your users.
Do not make the bucket public. If you do, then potentially user1 could see user2's uploaded files.
You can allow users to retrieve single files for a specific period of time using pre-signed URLs.
GetPreSignedUrlRequest
to generate a pre-signed URL for the file you want the user to download.<img>
tag.Using this technique is safe:
GetPreSignedUrlRequest
call)The URL uses a hashing technique to ensure the URL cannot be modified, nor can it be abused to get other files.
If displaying the access key ID is a concern, you can either (a) create an IAM user specifically for the purpose of downloading the files from S3, or (b) use an IAM role on your EC2 instance to generate the pre-signed URL.
References:
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With