2010-04-25 5 views
12

Ich bin auf Rails 2.3.5 und Ruby 1.8.6 und versuchen herauszufinden, wie ein Benutzer über meine Rails App eine Datei auf einen FTP-Server auf einem anderen Rechner hochladen kann. Auch meine Rails-App wird auf Heroku gehostet, was das Schreiben von Dateien in das lokale Dateisystem nicht erleichtert.Rails Upload-Datei auf FTP-Server

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 

Derzeit Ich versuche nur die Rails-Anwendung zu bekommen auf meinem Windows-Laptop zu arbeiten. Mit dem obigen Code bekomme ich diesen Fehler

Ich versuche, eine CSV-Datei hochladen, wenn das einen Unterschied macht. Weiß jemand was los ist?

Antwort

18

Nach viel Forschung und Kopf hämmerte ich den Quellcode für putbinaryfile-Methode zu lesen, um eine Abhilfe für die Begrenzung von putbinaryfile herauszufinden. Hier ist der Arbeits Code, ersetzen Sie diese Zeile

ftp.putbinaryfile(file.read, File.basename(file.original_filename)) 

mit

ftp.storbinary("STOR " + file.original_filename, StringIO.new(file.read), Net::FTP::DEFAULT_BLOCKSIZE) 

Und falls Sie sich fragen, STOR ist ein roher FTP-Befehl, ja es kam zu dem. Ich bin ziemlich überrascht, dass dieses Szenario von Ruby-Standardbibliotheken nicht einfacher gehandhabt wird, es war sicherlich nicht offensichtlich, was getan werden musste.

Und wenn Ihre Anwendung auf Heroku ist, fügen sich diese Zeile

ftp.passive = true 

Heroku Firewall Setup nicht für FTP Aktiv-Modus erlauben, auch sicherstellen, dass der FTP-Server im passiven Modus unterstützt.

+0

Funktioniert 'ftp.putbinaryfile (StringIO.new (file.read), datei.original_filename, Net :: FTP :: DEFAULT_BLOCKSIZE)? –

+0

Nein, das hat nicht funktioniert, wirft den Fehler "kann StringIO nicht in String konvertieren". – Bob

+0

Hey, behandelt Rails 3 das besser? – fatfrog

1

scheint mir, dass ftp.putbinaryfile nur den Pfad und den Namen der Datei als ersten Parameter will.

+0

Dies hat 2 andere gute Optionen: http://stackoverflow.com/questions/5223763/how-to-ftp-in-ruby-without-first-saving-the-text-file – Josh

+0

Der Pfad ist genug, damit es funktioniert . –