I'm going to be using S3 to store user uploaded photos. Obviously, I wont be serving the image files to user agents without resizing them down. However, not one size would do, as some thumbnails will be smaller than other larger previews. So, I was thinking of making a standard set of dimensions scaling from the lowest 16x16 to some highest 1024x1024. Is this a good way to solve this problem? What if I need a new size later on? How would you solve this?
2 Answers
Pre-generating different sizes and storing them in S3 is a fine approach, especially if you know what sizes you need, are likely to use all of the sizes for all of the images, and don't have so many images and sizes that the storage cost is excessive.
Here's another approach I use when I don't want to pre-generate and store all the different sizes for every image, or when I don't know what sizes I will want to use in the future:
Store the original size in S3.
Run a web server that can generate any desired size from the original image on request.
Stick a CDN (CloudFront) in front of the web server.
Now, your web site or application can request a URL like /16x16/someimage.jpg from CloudFront. The first time this happens, CloudFront will get the resized image from your web server, but then CloudFront will cache the image and serve it for you, greatly reducing the amount of traffic that hits your web server.
Here's a service that resizes images from arbitrary URLs, serving them through CloudFront: http://filter.to

- 22,089
- 5
- 66
- 75
-
Using CloudFront or filter.to infront of my image URIs is a good idea. I could even do this with my S3 partition, no? – Sam Oct 24 '12 at 23:22
-
Sure, CloudFront is great to stick in front of any static content, and even some dynamic content. Filter.to (run by a friend) is free for a reasonable amount of usage. – Eric Hammond Oct 25 '12 at 11:42
-
Is it possible to have my dynamic resizing script respond with a 301 HTTP code and a Location header pointing to the AWS S3 URI, and my image HTML elements will still load the resources properly? – Sam Oct 27 '12 at 03:18
-
A redirect will reduce load on your server for each request, but I don't think it will be cached be CloudFront, so your server will still need to handle all the requests. – Eric Hammond Oct 28 '12 at 01:06
-
I'll redirect for now. Then serve directly once/if I decide to use CloudFront. – Sam Oct 28 '12 at 06:14
-
So when this happens, does the resized image remain on the server, or in an S3 bucket? Can/should the image be deleted from the web server if it's residing on Cloudfront? Seems the server will fill up quickly with images otherwise... – bentedder Aug 05 '13 at 15:38
-
@bentedder: You can cache the generated image on the server or on S3 if you want to save some cpu the next time CloudFront asks for it, but otherwise ClodFront is generally serving it directly out of the end point caches. – Eric Hammond Aug 08 '13 at 19:16
This sounds like a good approach. Depending on your application you should define a set of thumbnail sizes that you always generate. But also store the original user file, if your requirements change later. When you want to add a new thumbnail size, you can iterate over all original files and generate the new thumbnails from it. This option gives you flexibilty for later.

- 8,041
- 3
- 37
- 40
-
Right, I was thinking of giving each photo a unique hash as a folder in S3, then store original.png and 128.png, 256.png, etc. If I ever need new sizes or cropped versions or any other transformations on the images, I can always iterate over the original.png's. – Sam Oct 24 '12 at 23:20