Cropping with Paperclip and the S3
15 Jul 2010
Paperclip is good. I pulled my hair out for several hours over this issue though. I had successfully implemented the custom cropping technique as demonstrated in railscast #182 but when I tried storing my images on the s3 I ran into a couple issues. The first was retrieving the image geometry. Instead of reading the geometry from the file I chose to read it out of the data we declare :styles option of the has_attached_file macro. This works for all but the original image - for that I use open-uri. It is probably pre-optimization but I didn't want to download every version just to find out their dimensions. My geometry methods look like this:
require 'open-uri' def avatar_geometry(style=:large) return file_geometry if style == :original w, h = avatar.options[:styles][style].gsub("#","").split("x") Paperclip::Geometry.new(w, h) end def file_geometry @geometry ||= {} @geometry[avatar.url] ||= Paperclip::Geometry.from_file(open(avatar.url)) end
My next issue manifested itself by not working and this error message appearing in my logs.
paperclip No such file or directory @ blob.c/OpenBlob
I spent several hours searching for solutions but nothing came up. I started brute-force debugging where you start changing things just to see what makes a difference. It turns out I don't understand why the change I made that fixed the problem but for now I'm happy with a solution.
As I was messing with the transformation_command method of the Cropper processor I noticed that the super class implementation returns an array. The version from railscasts joins the array then substitutes the crop dimensions for our new dimensions. Returning a string works when the files are stored locally but I tried splitting it back into an array and it totally works. I don't know why!
def transformation_command if crop_command cmd = crop_command + super.join(" ").sub(/ -crop \S+/, '') cmd.split(" ") else super end end