Read and write gzip files easily.

Kamil Slowikowski kslowikowski at gmail.com
Wed Feb 19 21:14:43 PST 2014


On Thursday, 20 February 2014 at 04:03:45 UTC, Adam D. Ruppe 
wrote:
> On Thursday, 20 February 2014 at 03:58:01 UTC, Kamil 
> Slowikowski wrote:
>>    auto compressed = comp.compress(mem.data);
>>    //comp.flush(); // Does not fix the problem.
>
> You need to write each compressed block and the flush. So more 
> like:
>
> writeToFile(comp.compress(mem.data)); // loop over all the data 
> btw
> writeToFile(comp.flush());
>
> and that should do it.
>
>
> flush returns the remainder of the data.

Hey Adam, thanks for the tip.

Next problem: the output has strange characters, as shown:

- - -
./zfile.d test.gz out.gz
hi there
here's some text in a file
-K

Thu Feb 20 00:07:52 kamil W530 ~/work/dlang
zcat out.gz
	hi there
here's some text in a file
-K

zcat test.gz | wc -c
39

zcat out.gz | wc -c
63

zcat test.gz | hexdump
0000000 6968 7420 6568 6572 680a 7265 2765 2073
0000010 6f73 656d 7420 7865 2074 6e69 6120 6620
0000020 6c69 0a65 4b2d 000a
0000027

zcat out.gz | hexdump
0000000 0009 0000 0000 0000 6968 7420 6568 6572
0000010 1b0a 0000 0000 0000 6800 7265 2765 2073
0000020 6f73 656d 7420 7865 2074 6e69 6120 6620
0000030 6c69 0a65 0003 0000 0000 0000 4b2d 000a
000003f
- - -


Code:

- - -
#!/usr/bin/env rdmd
import std.stdio,
        std.stream,
        std.zlib,
        std.c.process,
        std.process,
        std.file;

void main(string[] args)
{
     if (args.length != 3) {
         writefln("Usage: ./%s <file> <output>", args[0]);
         exit(0);
     }

     // Read command line arguments.
     string filename = args[1];
     string outfile = args[2];
     auto len = filename.length;

     std.file.File input;
     // Automatically decompress the file if it ends with "gz".
     if (filename[len - 2 .. len] == "gz") {
         auto pipe = pipeShell("gunzip -c " ~ filename);
         input = pipe.stdout;
     } else {
         input = std.stdio.File(filename);
     }

     // Write data to a stream in memory
     auto mem = new MemoryStream();
     string line;
     while ((line = input.readln()) !is null) {
         mem.write(line);
         // Also write the line to stdout.
         write(line);
     }

     // Put the data into a new gz file.
     auto comp = new Compress(HeaderFormat.gzip);
     // See the raw compressed bytes.
     //writeln(cast(ubyte[])compressed);

     // Write compressed output to a file.
     with (new std.stream.File(outfile, FileMode.OutNew)) {
         auto compressed = comp.compress(mem.data);
         writeExact(compressed.ptr, compressed.length);
         // Get any remaining data.
         compressed = comp.flush();
         writeExact(compressed.ptr, compressed.length);
     }
}
- - -


More information about the Digitalmars-d mailing list