Ruby Net :: FTP storbinary从管道输入写入损坏的文件

时间:2015-02-07 22:14:54

标签: ruby ftp

我想使用Ruby的Net :: FTP类存储二进制文件。该文件的内容由先前的进程放入管道中。我需要从管道(IO类)中获取字节并将其存储(在飞/无临时文件中)到ftp服务器。

如果我这样做的话

ftp = Net::FTP.new(@@host, @@user, @@password)
ftp.debug_mode = true 
ftp.passive = true
ftp.binary = true
ftp.storbinary("STOR #{name}", pipe, Net::FTP::DEFAULT_BLOCKSIZE)
ftp.close

存储文件的大小比它应该小约500kb(正确的大小约为6.8 MB)。该文件包含gpg加密数据。如果尝试解密,我会收到错误。

直接从管道存储到本地文件会生成具有正确大小和正在解密的文件。

我对红宝石比较新,有人可以给我一个提示吗?调试的一些想法?我可以提供其他信息吗?

感谢您的帮助


Net :: FTP的调试输出:

put: PASV
get: 227 Entering Passive Mode (80,237,136,162,233,60).
put: STOR test-ftp.tar.gz.gpg
get: 150 Opening BINARY mode data connection for test-ftp.tar.gz.gpg
get: 226 Transfer complete

Ruby版本:ruby 2.1.5p273

操作系统:debian linux

环境:ruby脚本直接从bash执行

更多代码:

p_out, p_in = IO.pipe
@@thread = Thread.new {
  cmd = "gpg --no-tty --cipher-algo AES256 --compress-level 0 --passphrase-file #{@@cmd.results[:gpg_passphrase_file]} --symmetric" 
  # Execute gpg
  Open3.popen3 ( cmd )  { |stdin, stdout, stderr, wait_thr|   

    Thread.new {
      cnt = IO::copy_stream pipe, stdin
      @@output.debug "GPG_Encryption::execute copied #{(Float(cnt)/1024/1024).round(2)} MiB bytes to gpg"
      pipe.close
      stdin.close
    }

    Thread.new {
      cnt = IO::copy_stream stdout, p_in
      @@output.debug "GPG_Encryption::execute copied #{(Float(cnt)/1024/1024).round(2)} MiB bytes from gpg"
    }

    # wait for gpg finished
    wait_thr.join

    # Close pipe (sends eof)
    p_in.close

    # check result
    if 0 == wait_thr.value 
      @@output.info "gpg finished..."                    
    else
      @@output.error "gpg returned an error"
      @@output.raw stderr.readlines.join
      exit 1
    end
  }
}

ftp = Net::FTP.new(@@host, @@user, @@password)
ftp.debug_mode = true 
ftp.passive = true
ftp.binary = true
ftp.storbinary("STOR #{name}", pipe, Net::FTP::DEFAULT_BLOCKSIZE)
ftp.close

1 个答案:

答案 0 :(得分:0)

您可能在文件完全发送之前关闭了FTP连接。尝试删除明确的ftp.close。您可能无论如何都不需要它,因为当ftp被垃圾收集时,连接将自动关闭。