Os arquivos de formato Gzip (criados com o gzipprograma, por exemplo) usam o algoritmo de compressão "deflate", que é o mesmo algoritmo de compressão que o zlib usa. No entanto, ao usar zlib para aumentar um arquivo compactado gzip, a biblioteca retorna um Z_DATA_ERROR.
Como posso usar o zlib para descompactar um arquivo gzip?
Para descompactar um arquivo no formato gzip com zlib, chame inflateInit2com o windowBitsparâmetro as 16+MAX_WBITS, assim:
inflateInit2(&stream, 16+MAX_WBITS);
Se você não fizer isso, o zlib reclamará de um formato de stream incorreto. Por padrão, o zlib cria fluxos com um cabeçalho zlib e, ao inflar, não reconhece o cabeçalho gzip diferente, a menos que você diga isso. Embora isso seja documentado a partir da versão 1.2.1 do zlib.harquivo de cabeçalho, não está no manual zlib . Do arquivo de cabeçalho:
windowBitstambém pode ser maior que 15 para decodificação gzip opcional. Adicione 32 a windowBitspara habilitar a decodificação zlib e gzip com detecção automática de cabeçalho ou adicione 16 para decodificar apenas o formato gzip (o formato zlib retornará a Z_DATA_ERROR). Se um fluxo gzip está sendo decodificado, strm->adleré um crc32 em vez de um adler32.
Obrigado, isso era muito frustrante até encontrar este post.
Alex
Nossa, essa é a pergunta de 2009. Obrigado @Greg Hewgill
YuAn Shaolin Maculelê Lai
Talvez você possa fornecer algumas diretrizes para a descompressão iterativa do fluxo gzip. Em uma descompressão gzip única, em que o fluxo de saída e o tamanho devem ser fixos e suficientes para armazenar toda a saída descompactada. Este valor depende da eficácia da descompressão gzip, que pode variar de acordo com a entropia dos dados. Existe uma maneira de alocar dinamicamente mais espaço para o buffer de saída quando necessário? Obrigado
por que essa peça de ouro não está nos documentos exatamente neste formato?
Ramon Moraes
sinta-se à vontade para enviar uma solicitação / patch de pull contra cpython usando qualquer uma dessas respostas.
dnozay
ótima resposta para strings, alguma ideia de como fazer isso para um stream sem ler o arquivo inteiro na memória?
Josh J
Obrigado. Posso resolver meu problema de descompactação no meu código-fonte com sua resposta.
Bethlee
incrível, esta é uma pepita de ouro .. no entanto, não posso deixar de sentir que isso é equivalente a 'números mágicos'? onde na documentação isso é mencionado? Eu olhei, mas realmente não devo ter verificado o suficiente .. também, a notação eu não sigo totalmente. O que o | quer dizer, isso é opcional? e porque deflate é negativo .. é MAX_WBITS uma constante .. 🙁
m1nkeh
3
A estrutura do zlib e do gzip é diferente. zlib usa RFC 1950 e gzip usa RFC 1952 , portanto, tem cabeçalhos diferentes, mas o restante tem a mesma estrutura e segue o RFC 1951 .
zlib.decompress(data, 15 + 32)
Pitão
zlib
suporte de biblioteca :zlib
formato compactado)deflate
formato compactado)gzip
formato compactado)O
zlib
módulo python também oferece suporte a eles.escolhendo windowBits
Mas
zlib
pode descompactar todos esses formatos:deflate
formato, usewbits = -zlib.MAX_WBITS
zlib
formato, usewbits = zlib.MAX_WBITS
gzip
formato, usewbits = zlib.MAX_WBITS | 16
Consulte a documentação em http://www.zlib.net/manual.html#Advanced (seção
inflateInit2
)exemplos
dados de teste:
teste óbvio para
zlib
:teste para
deflate
:teste para
gzip
:os dados também são compatíveis com o
gzip
módulo:detecção automática de cabeçalho (zlib ou gzip)
adicionar
32
awindowBits
irá acionar a detecção de cabeçalhousando ao
gzip
invésPara
gzip
dados com cabeçalho gzip, você pode usar ogzip
módulo diretamente; mas lembre-se de que sob o capô ,gzip
usazlib
.fonte
A estrutura do zlib e do gzip é diferente. zlib usa RFC 1950 e gzip usa RFC 1952 , portanto, tem cabeçalhos diferentes, mas o restante tem a mesma estrutura e segue o RFC 1951 .
fonte