2009-09-01 73 views
42

Zlib :: GzipReader可以采用“IO或类似IO的对象”。因为它是输入,正如文档中所述。如何解压缩红宝石中的Gzip字符串?

Zlib::GzipReader.open('hoge.gz') {|gz| 
    print gz.read 
    } 

    File.open('hoge.gz') do |f| 
    gz = Zlib::GzipReader.new(f) 
    print gz.read 
    gz.close 
    end 

我应该如何解压一个字符串?

回答

105

上述方法对我来说没有工作。
我不断收到incorrect header check (Zlib::DataError)错误。显然它假设你默认有一个标题,但并不总是这样。

,我实现的解决办法是:

require 'zlib' 
require 'stringio' 
gz = Zlib::GzipReader.new(StringIO.new(resp.body.to_s))  
uncompressed_string = gz.read 
+3

谢谢,我得到了同样的错误,这解决了我的问题! – 2013-03-24 01:07:40

+0

Mucho help here – simonmorley 2014-01-17 10:27:10

+0

is calling body.to_s redundant? – Blaskovicz 2014-06-26 17:50:15

15

你需要Zlib::Inflate一个字符串的解压缩和zlib ::放气进行压缩

def inflate(string) 
    zstream = Zlib::Inflate.new 
    buf = zstream.inflate(string) 
    zstream.finish 
    zstream.close 
    buf 
    end 
17

的Zlib由您的压缩数据中包含一个头默认asumes。 如果您的数据不包含头文件,则会引发Zlib :: DataError失败。

你可以告诉的Zlib承担数据必须通过以下解决方法没有头:

def inflate(string) 
    zstream = Zlib::Inflate.new(-Zlib::MAX_WBITS) 
    buf = zstream.inflate(string) 
    zstream.finish 
    zstream.close 
    buf 
end 
+0

这不再有效。 – jm3 2017-11-23 23:14:09

5

使用(-Zlib::MAX_WBITS),我得到了ERROR: invalid code lengths setERROR: invalid block type
唯一以下为我的作品了。

Zlib::GzipReader.new(StringIO.new(response_body)).read 
2

我用上面的答案使用的Zlib ::减缩

我一直得到破碎的文件(小文件),并花了很多时间来找出使用的问题可以是固定的:

buf = zstream.deflate(string,Zlib::FINISH) 

没有zstream.finish行!

def self.deflate(string) 
    zstream = Zlib::Deflate.new 
    buf = zstream.deflate(string,Zlib::FINISH) 
    zstream.close 
    buf 
end 
2

要gunzip文件的内容,使用下面的代码(在1.9.2测试)

Zlib::GzipReader.new(StringIO.new(content), :external_encoding => content.encoding).read 

谨防编码问题

4

我们不需要任何额外的参数,这些天。有deflateinflate类方法允许快速oneliners这样的:“我应该如何ungzip一个字符串”

>> data = "Hello, Zlib!" 
>> compressed = Zlib::Deflate.deflate(data) 
=> "x\234\363H\315\311\311\327Q\210\312\311LR\004\000\032\305\003\363" 
>> uncompressed = Zlib::Inflate.inflate(compressed) 
=> "Hello, Zlib!" 

我认为回答这个问题:最好的。 :)

+4

如果你压缩和解压缩,那么这将是很好,但它不会被gzip压缩。只需在gzip压缩数据上运行Zlib :: Inflate.inflate(压缩)将承担错误的压缩并引发“不正确的头部检查”异常。 – philwhln 2012-11-04 22:20:49

5

的zstream =的Zlib :: Inflate.new(16 +的Zlib :: MAX_WBITS)

+1

不错的一个。从[文档](http://www.ruby-doc.org/stdlib-2.1.5/libdoc/zlib/rdoc/Zlib/Inflate.html)“或添加16来仅解码gzip格式(一个Zlib: :DataError将针对非gzip流引发)“ – iain 2014-12-10 13:39:14

4

在Rails中你可以使用:

  • ActiveSupport::Gzip.compress("my string")
  • ActiveSupport::Gzip.decompress()