# UPDATE
It turns out the method below works unless your file is below a certain file size (which I haven’t figured out yet but it’s around 15k). If your file is too small it will be StringIO not a Tempfile. So how do we check it then? By the file size, if it’s 0 then don’t run the image upload code.
Replace
@image = Image.create params[:image] unless params[:image][:file_data].kind_of? StringIO
with
@image = Image.create params[:image] unless params[:image][:file_data].size == 0
# END UPDATE
Coming from PHP getting file uploads to work with Rails was a bit of a mind funk.
The biggest issue is that a file upload field returns different objects depending on if you browsed for a file or left it blank. If you browsed and chose a file the object will be a ‘Tempfile’, if it’s blank it will be ‘StringIO’. That took a couple of hours to figure out.
The next step was figuring out how to check the object type, that’s when I stumbled upon some beauty Ruby code
object.kind_of?
Simple once you know how.
The file field from the form in my view:
<%= file_field(“image”, “file_data”) %>
Here’s my controller code for updating data from the form (the controller is products_controller.rb so I’m setting a relationship to the Image ‘product_id’):
def update params[:image][:product_id] = params[:id]
@image = Image.create params[:image] unless params[:image][:file_data].kind_of? StringIO @product = Product.find(params[:id])
if @product.update_attributes(params[:product])
flash[:notice] = ‘Product was successfully updated.’ redirect_to :controller => ‘cms’, :action => ‘index’ else render :action => ‘edit’ end end
The line to notice is
@image = Image.create params[:image] unless params[:image][:file_data].kind_of? StringIO
It translates to; save the image model unless file_data is a StringIO object (if it’s not StringIO then it’s a Tempfile)