Reputation: 57
I'm currently developping my own application using RoR 4.1.1.
My aim is to create a platform to store .zip files and I want users to be able to download those files. The issue is that my boss wants me to store the files into the database directly and not into a filesystem.
Therefore I did this in my ItemsController:
def create
@item = Item.new(item_params)
@item.file = params[:item][:file].read
if @item.save
redirect_to @item
else
render 'new'
end
end
And this in my new.html.erb view:
<%= f.label :application %>
<%= f.file_field :file %>
<p>
<%= f.submit %>
</p>
This is supposed to make me able to upload things to my DB.
Now I have a file column in my database with binary files in it. But how can I get these downloaded?
Upvotes: 1
Views: 2378
Reputation: 13521
You can initiate a download with the send_data
controller method. Docs here: http://api.rubyonrails.org/classes/ActionController/DataStreaming.html#method-i-send_data
So let's say you create a route for your download action:
get '/items/:id/download', as: :item_download
And provide your users with a link to your items:
link_to 'Download', item_download_path(@item), disable_with: 'Downloading...'
Now your controller initiates the download to the user:
def download
item = Item.find params[:id]
send_data item.file, filename: item.name, type: 'zip', disposition: 'attachment'
end
As soon as the user clicks the Download
link it will grey out and change to Downloading...
then the browser will open its download dialog and begin downloading the zip file.
Note: I assumed your item
has a name
method but it can be anything you want. The important options are type: 'zip', disposition: 'attachment'
. Type is the file type and helps your browser know what it is and disposition is for the browser to either download the file or to render it on the page. For example if you're downloading a pdf file, passing disposition: 'inline'
would make the browser display the pdf rather than download it directly.
Upvotes: 5