【问题标题】:Appending files to a StringIO Tar archive one at a time一次将文件附加到 StringIO Tar 存档
【发布时间】:2018-02-18 20:27:59
【问题描述】:

我正在编写利用StringIO 对象和rubygems/package 的代码,其中包括TarWriterTarReader

我的最终目标是能够调用方法 add_file 将文件添加/附加到存档,然后调用方法 read_all_files 来读回添加文件的文件名和内容。

我目前的两种方法是:

require "rubygems/package"

def add_file(io)
  Gem::Package::TarWriter.new(io) do |tar|
    puts "What is the name of the file you wish to add?"
    print "> "
    filename = gets.chomp
    puts

    tar.add_file(filename, 0755) do |file|
      puts "Enter the file contents"
      print "> "
      contents = gets.chomp

      file.write contents
    end
  end
end

def read_all_files(io)
  Gem::Package::TarReader.new(io) do |tar|
    tar.each do |tarfile|
      puts "File Name> #{tarfile.full_name}"
      puts tarfile.read
    end
  end
end

#usage:

io = StringIO.new

add_file(io)
add_file(io)
add_file(io)
io.rewind
read_all_files(io)

输出:

What is the name of the file you wish to add?
> test1

Enter the file contents
> this is the first test
What is the name of the file you wish to add?
> test2

Enter the file contents
> this is the second test
What is the name of the file you wish to add?
> test3

Enter the file contents
> this is the third test
File Name> test1
this is the first test

当前发生的问题是,出于某种原因read_all_files 只读取一个文件,尽管我应该迭代所有三个文件。

我尝试了各种想法,例如在每次add_file 调用后回退文件,但这每次都会覆盖 tar 文件。我也尝试寻找到 io 对象的末尾并添加文件,但这也无法正常工作。

我最初以为TarWriter会读取头部并自动将新文件附加到tar存档中的正确位置,但似乎并非如此。

这似乎我需要将所有文件从StringIO tar 存档读取到变量,然后在每次添加新文件时重新添加所有文件。这是正确的行为吗?有没有办法解决这个问题?

谢谢

【问题讨论】:

    标签: ruby tar stringio


    【解决方案1】:

    问题是因为每次调用 add_file 时都会创建一个新的 TarWriter。您需要在对 add_file 的调用之间保留 TarWriter 对象。例如

    require "rubygems/package"
    
    def add_file(io, tar=nil)
    
      tar = Gem::Package::TarWriter.new(io) if tar.nil?
    
      puts "What is the name of the file you wish to add?"
      print "> "
      filename = gets.chomp
      puts
    
      tar.add_file(filename, 0755) do |file|
        puts "Enter the file contents"
        print "> "
        contents = gets.chomp
    
        file.write contents
      end
    
      tar
    end
    
    def read_all_files(io)
      Gem::Package::TarReader.new(io) do |tar|
        puts 'TarReader created'
        tar.each do |tarfile|
          puts "File Name> #{tarfile.full_name}"
          puts tarfile.read
        end
      end
    end
    
    io = StringIO.new
    
    tar1 = add_file(io)
    tar1 = add_file(io, tar1)
    tar1 = add_file(io, tar1)
    io.rewind
    read_all_files(io)
    

    这个输出:

       C:\Users\Administrator\test>ruby tarwriter.rb
       What is the name of the file you wish to add?
       > x.txt
       Enter the file contents
       > xxx
       What is the name of the file you wish to add?
       > z.txt
       Enter the file contents
       > zzz
       What is the name of the file you wish to add?
       > y.txt
       Enter the file contents
       > yyy
       TarReader created
       File Name> x.txt
       xxx
       File Name> z.txt
       zzz
       File Name> y.txt
       yyy
    

    【讨论】:

      猜你喜欢
      • 2012-04-03
      • 2012-10-05
      • 2020-04-04
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-02-28
      相关资源
      最近更新 更多