How to upload image to S3 using paperclip gem

Throughout my life, I have been unable to figure out how a basic paperclip example works . There is only one line in the controller and that is

@user = User.create( params[:user] )


I just don't understand how this is all it takes to upload an image to s3. I modified this example a bit because I wanted to use the jquery file loader and not the default headliners, so I'm at where the image is being sent to my controller, but I can't figure out how I should take the image from the parameters and assign it as an attachment ... This is what I see in the logs:

Parameters: {"files"=>[#<ActionDispatch::Http::UploadedFile:0x132263b98 @tempfile=#<File:/var/folders/5d/6r3qnvmx0754lr5t13_y1vd80000gn/T/RackMultipart20120329-71039-1b1ewde-0>, @headers="Content-Disposition: form-data; name=\"files[]\"; filename=\"background.png\"\r\nContent-Type: image/png\r\n", @content_type="image/png", @original_filename="background.png">], "id"=>"385"}

My JS is very simple:

 ` $('#fileupload').fileupload({
    dataType: 'json',
    url: '/my_url',
    done: function (e, data) {


What I would like to know is how I can remove the file data from the above POSTed parameters and pass it to a paperclip. I'm sure I'll have to assign the attachment attribute to (...), but I don't know which source of my file is.

I've wasted a ridiculous time trying to figure this out and I can't get it. I tried to load directly to s3, but the event chain was terribly convoluted, so I want this simple walk-through example to be done first. Thanks so much for any help you give at cna!


source to share

3 answers

You need a few more and it will help if you can show the exact code you are using.

A paperclip can be sent to S3 using:

When your controller creates a User model, it sends all parameters. This is called "bulk assignment" (be sure to read about attr_accessible).

When your model receives parameters, it uses the APC Paperclip processor to load it.

You need an AWS gem, a valid S3 bucket, and a config file.

Try this blog post and let us know if it helps you:

UPDATE 2013-04-03: Glad to see Chloe's comment below - you may need an additional parameter and the blog post may be out of date.



If you want to do it manually, approach it like this:

# In order to get contents of the POST request with the photo,
# you need to read contents of request
upload = params[:file].is_a(String)
file_name = upload ? params[:file] : params[:file].original_filename
extension = file_name.split('.').last

# We have to create a temp file which is going to be used by Paperclip for
# its upload
tmp_file = "#{Rails.root}/tmp/file.#{extension}"
file_id = 0

# Check if file with the name exists and generate unique path
while File.exists?(tmp_file) do
  tmp_file_path = "#{Rails.root}/tmp/file#{file_id}.#{extension}"
  id += 1

# Let write the file from post request to unique location, 'wb') do |f|
  if upload
    f.write params[:file].read

# Now that file is saved in temp location, we can use Paperclip to mimic one file
# upload
@photo = :photo =>

# We'll return javascript to say that the file is uploaded and put its thumbnail in
# HTML or whatever else you wanted to do with it
respond_to do |format|
    render :text => "Success"
    render :text => @photo.errors


You can rewrite yours create

or whatever you use as the url you submit the form to.



This bit:

"files"=>[#<ActionDispatch::Http::UploadedFile:0x132263b98 @tempfile=#     <File:/var/folders/5d/6r3qnvmx0754lr5t13_y1vd80000gn/T/RackMultipart20120329-71039-1b1ewde-0>


is the part (I think) that contains the content of the file posted on the form.

In Rails, the User model will have a helper: has_attached_file

Passing [: params] to the User.create method allows this helper to collect the file's content, do any processing (like resizing, etc. based on the attributes provided to the helper), and then push the image (s) to your store (like , S3 or whatever - the S3 credentials are passed to the helper).

Hope this explains how he does it? question

re a bit of jQuery .. not sure if the code should be in there, but why not use a Rails form with: remote => true and process the response in jquery?



All Articles