Rails upload file to ftp server - ruby-on-rails

I'm on Rails 2.3.5 and Ruby 1.8.6 and trying to figure out how to let a user upload a file to a FTP server on a different machine via my Rails app. Also my Rails app will be hosted on Heroku which doesn't facilitate the writing of files to the local filesystem.
index.html.erb
<% form_tag '/ftp/upload', :method => :post, :multipart => true do %>
<label for="file">File to Upload</label> <%= file_field_tag "file" %>
<%= submit_tag 'Upload' %>
<% end %>
ftp_controller.rb
require 'net/ftp'
class FtpController < ApplicationController
def upload
file = params[:file]
ftp = Net::FTP.new('remote-ftp-server')
ftp.login(user = "***", passwd = "***")
ftp.putbinaryfile(file.read, File.basename(file.original_filename))
ftp.quit()
end
def index
end
end
Currently I'm just trying to get the Rails app to work on my Windows laptop. With the above code, I'm getting this error
Errno::ENOENT in FtpController#upload
No such file or directory -.... followed by a dump of the file contents
I'm trying to upload a CSV file if that makes any difference. Anyone knows what's going on?

After much research and head banging, I ended up reading the source code for putbinaryfile method to figure out a workaround for the limitation of putbinaryfile. Here's the working code, replace this line
ftp.putbinaryfile(file.read, File.basename(file.original_filename))
with
ftp.storbinary("STOR " + file.original_filename, StringIO.new(file.read), Net::FTP::DEFAULT_BLOCKSIZE)
And in case you are wondering, STOR is a raw FTP command, yeah it came to that. I'm rather surprised this scenario isn't more easily handled by Ruby standard libraries, it certainly wasn't obvious what needed to be done.
And if your app is on Heroku, add this line
ftp.passive = true
Heroku's firewall setup does not allow for FTP active mode, also make sure that your FTP server supports passive mode.

Seems to me that ftp.putbinaryfile just wants the path and name of the file as the first parameter.

Related

Content for doesn't work in production mode

On one of application's page there is:
<% content_for :head do %>
<%= tag :meta, property: "fb:app_id", content: ENV["FACEBOOK_APP_ID"] %>
<% content_for :title, #check.title %>
<% end %>
And it worked in development, while I was running server at my localhost.
After that I deployed application on heroku. And that simply doesn't work.
What means doesn't work. I load page in development at localhost:
<title>Tenta</title>
<meta content="*****************" property="fb:app_id">
When I load this page deployed at heroku host, these tags are simply absent.
Why?
Also, If you don't know this particular issue solution, I would appreciate if you adivce me, how can I look what is going on - heroku logs and watching last 150 logs in inconvinient windows console doesn't give me a lot of helpful information.

Rails 4, asset pipeline causes user downloadable files to be downloaded twice

I have a folder in my app directory named "uploads" where users can upload files and download files. I don't want the uploads folder to be in the public directory because I want to control download authorization.
In my controller, I have:
send_file Rails.root.join('app', 'uploads', filename), :type => 'application/zip', :disposition => 'inline', :x_sendfile=>true
This actually works fine. The problem is that when I'm on the production server, when I run the rake assets:precompile, and have an assets directory, the file downloads twice. The first time the file downloads, the browser acts as if nothing is going on (no loading spinning), but I see data being transferred in the Google Chrome web developer Network tab. Then after the file has been downloaded, a prompt comes up asking the user if he/she wants to download the file.
Removing the assets folder in the public directory gets rid of this problem, but I want to use the asset pipeline. I also tried changing the asset pipeline requires from require_tree to require_directory.
Does anyone know how to get send_file working properly with the asset pipeline?
Thanks.
For anyone having this problem, I solved it. Pass
'data-no-turbolink' => true
into the link_to helper to stop Turbolinks from messing with the download.
https://github.com/rails/turbolinks/issues/182
But if you are using a form with turbooboost = true, instead of link_to, or even with a link_to you can do it like this:
Inside your controller, and inside your action put:
def download
respond_to do |format|
format.html do
data = "Hello World!"
filename = "Your_filename.docx"
send_data(data, type: 'application/docx', filename: filename)
end
format.js { render js: "window.location.href = '#{controller_download_path(params)}';" }
end
end
Replace controller_download_path with a path to your download action,
and place in your routes both post and get for the same path:
post '/download' => 'your_controller#download', as: :controller_download
get '/download' => 'your_controller#download', as: :controller_download

ckeditor in rails with mongodb

I am using ck editor in rails having database mongo db. I followed the link https://github.com/galetahub/ckeditor . I am succes in doing work with the help of ckeditor.
since my view.html.erb code is like this
<%= f.cktext_area :description, :toolbar => 'Easy', :width => 800, :height => 200 %><br>
and my show page is
<%= raw#department.description %>
it does not works for file cases.
I have my model attachment_file.rb is
class Ckeditor::AttachmentFile < Ckeditor::Asset
has_mongoid_attached_file :data,
:url => "/ckeditor_assets/attachments/:id/:filename",
:path => ":rails_root/public/ckeditor_assets/attachments/:id/:filename"
validates_attachment_size :data, :less_than => 100.megabytes
validates_attachment_presence :data
def url_thumb
#url_thumb ||= Ckeditor::Utils.filethumb(filename)
end
end
It is working for image cases but not working for zip file or any attachement. when it comes to the file cases it can upload file successfully with its path. but to download that file by user it doesnot work. I mean backend works properly for all features. But lacks to download that uploaded file stops by
`javascript:void(0)/*130*/
i have found the answer of this problem . First run this in terminal.
$ sudo chmod -R 777 /usr/share/ruby-rvm/gems/ruby-1.9.3-p194/gems/ckeditor-3.7.1
follow this path in your computer since i am using linux and my gem file locates here.
/usr/share/ruby-rvm/gems/ruby-1.9.3-p194/gems/ckeditor-3.7.1/vendor/assets/javascripts/ckeditor/plugins/attachment/dialogs
and open attachement.js file and edit it with the code that u find from tha above link.
click
Now ck editor will works for file attachment also.
Seem like you encounter this bug in CKeditor:
It sugests adding before filter as fix eg:
# app/model/department.rb
before_save :fix_ckeditor_attachment_paths
def fix_ckeditor_attachment_paths
if self.description.index(/_cke_saved_href/)
self.description = self.body.gsub(/_cke_saved_href/, 'href')
end
end

How to the use the image_tag with a remote URL?

I've got a rake task which uploads images I've cached from an API to my S3 bucket. In my view, I try to output the image but it just doesn't appear to work. What I want to do is cache the images onto my filesystem, send them to S3 and I want to use the location of the image from my S3 bucket rather than my filesystem. My code looks like below:
In my rails console, I do this just to check the image url:
1.9.3p125 :002 > a.image
=> http:://s3-eu-west-1.amazonaws.com/ramen-hut/pictures/1.jpg?1343645629
1.9.3p125 :003 >
I use Paperclip in my app, is it supposed to add the url as "http:://"? Seems rather weird. The code in my index.html.erb looks like this:
<li>
<%= movie.title %>
<%= image_tag movie.image.url %>
</li>
But this results in the following html:
<li>
Cowboy Bebop
<img alt="1" src="/assets/http:://s3-eu-west-1.amazonaws.com/ramen-hut/pictures/1.jpg?1343645629">
</li>
Why does it include the '/assets'/ before my URL?
I configured Paperclip to set up the image url for my European S3 Bucket following a tutorial. So in my environment.rb, I've got this:
#Signature correction for Paperclip and AWS
AWS::S3::DEFAULT_HOST = "s3-eu-west-1.amazonaws.com"
And I've got an aws-signature.rb file in my initialisers directory with this code:
#Makes Paperclip use the correct URL for images
Paperclip.interpolates(:s3_eu_url) { |attachment, style|
"#{attachment.s3_protocol}://s3-eu-west-1.amazonaws.com/#{attachment.bucket_name}/#{attachment.path(style).gsub(%r{^/}, "")}"
}
There's a problem with the URL : http::// instead of http:// so image_tag doesn't know it's an absolute URL.
How do you generate these URLs? Gem or your own code?

Why is Paperclip failing silently in production + development?

I'm clueless as to what's going on with this because I have another app on the same server that receives and saves uploads just fine.
No error messages, Paperclip even say's in the log it's saving the attachments.
But the attachments don't get saved.
Thoughts anyone?
Also how would I test for this using RSpec/Capybara, because apparently my tests don't cover this.
Running Paperclip 2.3.12, Rails 3.0.9, REE1.8.7
Production on RHEL5 / Apache , but runs on a different user than my other app's user.
Update I get the same silent fail on development too!
But my test's pass and I can see the image being uploaded with the tests.
I believe you forget to add multipart option to your form
:html => {:multipart => true}
so
<%= form_for #my_object, :html => {:multipart => true} do |f| -%>
...
<% end %>

Resources