Rails direct upload to Amazon S3 using Activeadmin + Paperclip - ruby-on-rails

I am using Activeadmin and Paperclip to make images upload on my Rails app. When I try to upload big files to S3 the timeout error occurs, so I have to implement the direct upload to S3.
Does anyone know how can I make it? I could't figure it out...

There is a really nice article I've used when was first time setting up the AA+s3+Paperclip.
It has decent explanations + example app on Github, so you can check it live.
In AA the form would look something like this:
form multipart: true do |f|
# f.semantic_errors *f.object.errors.keys
f.inputs do
f.input :image_name #or whatever field is called
end
f.has_many :attachments do |a|
if a.object.persisted?
link_to image_tag(a.object.encoded_url, class: 'image-preview'), a.object.encoded_url, target: "_blank"
else
a.inputs do
a.s3_file_field(:attachment, as: :file, class: 'js-s3_file_field')
end +
a.inputs do
a.input(:s3_url, as: :hidden, input_html: { class: "s3_url" })
end
end
end
f.actions
end

The answer appears to be in the comments. Thanks Andrey for the tutorial link.
http://blog.littleblimp.com/post/53942611764/direct-uploads-to-s3-with-rails-paperclip-and

Related

active storage prevent client reupload file when form error validation

I have a form with many inputs, and one is a kbis, an file input.
My model:
class Company < ApplicationRecord
validates :name, presence: true
validate :presence_kbis
has_one_attached :kbis
private
def presence_kbis
errors.add(:kbis, :blank) unless kbis.attached?
end
end
I created a classic form, and one input is:
<%= f.input :kbis %>
My problem is if an other field contains an error, I lost the file, and I ask again to the user to select again a file.
I understood that for security reasons, the navigator can not select the file.
But the file is already uploaded to the rails server.
My question:
There is a way to use the file already uploded? In CarrierWawe we could do something like this:
<%= f.file_field :avatar %>
<%= f.hidden_field :avatar_cache %>
I tried to do this:
<%= f.hidden_field :kbis, value: f.object.kbis.signed_id if f.object.kbis.attached? %>
<%= f.input :kbis %>
but when I submit I have in exception: ActiveSupport::MessageVerifier::InvalidSignature
I think I have correcty understood how data is stored when succesfully, but I am not clear with differents step. It is store before or after validation? Where is the file is validation failed? It is removed after http request? If not when it is remove?
CONTEXT:
ruby 3.0.1
rails 6.1.3.1
environement: development
disk storage: local
I use simple_form

How to manage photos uploaded with refile gem hosted on AWS within Activeadmin. Rails

I have a rails application using refile to upload multiple images. I want to be able to manage these images for all the users in Activeadmin so if someone were to upload an offensive photo I can remove it from their profile through activeadmin. I don't know if its important to mention that these photos are being hosted on AWS.
f.inputs "Attachment", :multipart => true do
f.input :images, :hint => image_tag(f.object.images.each_with_index do |image, index|
attachment_image_tag(image, :file, :fit, 600, 600)
end)
end
I have been trying this code and am just getting all the details of the photos back like when it was uploaded, the id, and when it was last updated. This is the only bit of help I was finding online however its not getting me as far as I need. https://github.com/activeadmin/activeadmin/wiki/Showing-an-uploaded-image-in-the-form
Any help with this problem would be great. Thank you!
I ended up figuring it out.
f.inputs "Images" do
ul do
f.label "Click on the images you want to delete, The page will not automatically refresh however the image is being deleted!!"
f.object.images.each do |img|
li do
link_to img, remote: true, label: :remove_image, method: :delete do
attachment_image_tag(img, :file, :fill, 100, 100)
end
end
end
end
end
and in the model I put:
def edit
#images = Ambassador.images
end

Paperclip functional test giving NoHandlerError [duplicate]

Using Paperclip 3.0.1 in rails 3.2.2 I got this error:
**Paperclip::AdapterRegistry::NoHandlerError**
(No handler found for "2009-11-29-133527.jpg"):
In my model I have:
class Product < ActiveRecord::Base
...
has_many :assets
accepts_nested_attributes_for :assets
end
class Asset < ActiveRecord::Base
belongs_to :product
has_attached_file :image,
:path => ":rails_root/public/system/:attachment/:id/:style/:filename",
:url => "/system/:attachment/:id/:style/:filename",
:styles => { :medium => "300x300>", :thumb => "100x100>" }
end
The exception is raised at:
def create
**#product = Product.new params[:product]**
...
end
with params:
{...,
"product"=>{"title"=>"wibble1",
**"assets_attributes"=>{"0"=>{"image"=>"2009-11-29-133527.jpg"}
},**
"description"=>"Who is wibble...",
"price"=>"23.45"
},
"commit"=>"Create Product",
...}
Anyone know what's going on?
This Error is raised because you aren't giving Paperclip a correct class. It's a just a String.
You should receive something like this in params
"asset"=>
{"image"=>
#<ActionDispatch::Http::UploadedFile:0x000000056679e8
#content_type="image/jpg",
#headers= "Content-Disposition: form-data; name=\"asset[image]\";
filename=\"2009-11-29-133527.jpg\"\r\nContent-Type: image/jpg\r\n",
#original_filename=""2009-11-29-133527.jpg"",
#tempfile=#<File:/tmp/RackMultipart20120619-1043-yvc9ox>>}
And you should have something like this in yout View (in HAML, very simplified):
= form_for #product, html: { multipart: true } do |f|
= f.fields_for :asset do |asset_form|
= asset_form.file_field :image
Remember to set your form to multipart: true.
I just ran into this problem myself. In my case it was caused by skipping the multipart form declaration in the markup.
I was using formtastic so I added this and got it working:
semantic_form_for #picture, :html => {:multipart => true} do |f|
Note there is a situation when working with an HTML5 canvas that is worth noting. Getting the canvas data as a DataURI string and sending that to server can cause this error. Canvas .toDataURL() will give something like "data:image/png;base64,iVBORw0KGg..." which you can send to server with other information, so its different than a standard multi-part form upload. On the server side if you just set this to the paperclip attachment field you will get this error. You need to conver it to a file or IO object. You could write a temp file like this:
data_uri = params[:canvasDataUri]
encoded_image = data_uri.split(",")[1]
decoded_image = Base64.decode64(encoded_image)
File.open("signature.png", "wb") { |f| f.write(decoded_image) }
or use Ruby's StringIO which acts like an in memory file interface
#docHolder.document = StringIO.new(decoded_image)
Hope this helps.
I had <input type="file" ... multiple="multiple"> on file input, so paperclip attachment data was in an array.
I solved this simply by removing multiple attribute on file input.
my problem was not accepting get method in routes so i changed it as patch method and it work fine.
<%= form_for #product, :url => "/products/#{#product.id}/upload",:method => :patch, :html => { :multipart => true } do |f| %>
I'm pretty sure your problem is with the form_for in the view,
try something like this:
<%= form_for #restaurante, :html => { :multipart => true } do |form| %>
Nome:<%= form.text_field :nome%>
Endereço:<%= form.text_field :endereco %>
Especialidade:<%= form.text_field :especialidade %>
Foto:<%= form.file_field :foto %>
<%= form.submit 'create'%>
<% end %>
In my case I was passing String, as in #MauricioPasquierJuan's answer, but I wasn't using a form so the rest of the answer doesn't apply.
I couldn't find any documentation of how to programatically update an attachment - what types can be assigned, and why assigning and saving the modified record does not save modified attachments. This question was the closest thing I found.
Inside a function that process files inside an uploaded zip file, after saving extracted files to temp files, this is my solution:
record.attachment = File.new( tempfile_path_as_string ) ## probably not the only option
record.attachment.save ## next line doesn't update attachment without this
record.save
Make sure you migrate the database after you install Paperclip ('rake db:migrate')... Also, you might need to add the new data fields generated by Paperclip to your 'attr_accessible' line in the model.
I had a similar problem when I was trying to get Paperclip workin on one of my projects.
I have met the same problem, I think it is because there are two tables sharing the same attached_file_name... In my case, I add a :photo column both to activities and tweets, then the case seems to be that the system can find one of them but not the other. Because the files are saved in /public/photo/:id/:id path, if you have two columns both named as photo, then the problem occurs I think.
for me the problem was like this:
I used such line in controller, as saw it in some answers:
#image = User.find(params[:id]).image.<b>path</b>(:small)
and I had the problem "no handler for the file"
so, I just removed "path" and it worked:
#image = User.find(params[:id]).image(:small)
When we upgraded from 4.2.x to 4.3.x, we had to change the main paperclip field attribute (picture, image, etc) from a relative URL to a full URL to eliminate this error.

Use Carrierwave with Active Admin

Did any of you guys manage to get Active Admin with Carrierwave working?
When I installed AA everything worked fine but the image file upload
fields were plain text fields so added following:
ActiveAdmin.register Club do
form do |f|
f.inputs "Club" do
f.input :league
f.input :name
f.input :image, :as => :file
f.input :approved
end
f.buttons
end
end
Now it's displayed as a file upload field and I can select a file but
after I submitted the form nothing changed. There's still no image and
the image field is empty. Anyone knows what else to do to get it
working?
Finally found the problem.
form do |f|
needs to become:
form(:html => { :multipart => true }) do |f|
I still don't know why console is not working but well, at least I can upload new images now :) Thanks a lot for the help, bruno077!
Yes, it works without an issue, remember to set the attr_accessible if you haven't. According to your configuration, you should have the following code in your model:
#app/models/club.rb
class Club < ActiveRecord::Base
attr_accessible (previous list), :image #If exists
mount_uploader :image, ImageUploader
end
And of course you should have generated the Image uploader with
rails generate uploader image
Edit: you can follow Ryan's railscast if you have any issue. That's what I did for my ActiveAdmin app with Carrierwave

Image file input with Formtastic and ActiveAdmin

I started to use formstatic but I need to make a file field with image preview. I mean, when i edit an object, i want to see the image already linked.
How can I do that?
Thank you !
The answer is to use the hint attribute :
ActiveAdmin.register Event do
form :html => { :enctype => "multipart/form-data" } do |f|
f.input :map, :as => :file, :hint => f.template.image_tag(f.object.map.url(:thumb))
end
end
Bye
Use paperclip with formtastic
Formtasitc's github page mentions that it supports paperclip:
:file – a file field. Default for file-attachment attributes matching: paperclip or attachment_fu.
Here are some useful screencasts that will get you going:
Paperclip
Cropping images
EDIT:
To display an image in a column of a grid in ActiveAdmin you need to make a custom column (This is untested and could be flawed, I'm extrapolating this from the documentation):
index do
column "Title" do |post|
link_to image_tag("path to file", :alt => "post image"), admin_post_path(post)
end
end
Two Gems and one plugin can help your case:
Make sure you look at:
Gems:
Paperclip: https://github.com/thoughtbot/paperclip
RailsCast on PaperClip: http://railscasts.com/episodes/134-paperclip
CarrierWave: https://github.com/carrierwaveuploader/carrierwave
RailsCast on CarrierWave: http://railscasts.com/episodes/253-carrierwave-file-uploads
Jquery File Upload: https://github.com/blueimp/jQuery-File-Upload
Jquery File Upload RailsCast: http://railscasts.com/episodes/381-jquery-file-upload (Need a Pro Account for RailsCast)
As #ianpetzer said, in Rails 4.2 / ActiveAdmin master the current answer causes an object reference to be written out as well. The correct answer for 2016 should be similar to this answer:
form :html => { :multipart => true } do |f|
f.inputs do
#...
f.input :image, required: false, hint: image_tag(object.image.url(:medium)).html_safe
#...
end
end

Resources