示例

压缩或解压缩一个文件可以通过导流一个 fs.ReadStream 到一个 zlib 流,然后到一个 fs.WriteStream 来完成。

const gzip = zlib.createGzip();
const fs = require('fs');
const inp = fs.createReadStream('input.txt');
const out = fs.createWriteStream('input.txt.gz');

inp.pipe(gzip).pipe(out);

一步压缩或解压缩数据可以通过快捷方法来完成。

const input = '.................................';
zlib.deflate(input, (err, buffer) => {
    if (!err) {
        console.log(buffer.toString('base64'));
    } else {
        // handle error
    }
});

const buffer = new Buffer('eJzT0yMAAGTvBe8=', 'base64');
zlib.unzip(buffer, (err, buffer) => {
    if (!err) {
        console.log(buffer.toString());
    } else {
        // handle error
    }
});

要在 HTTP 客户端或服务器中使用此模块,请在请求中使用 accept-encoding 和在响应中使用 content-encoding 头。

注意:这些例子只是极其简单地展示了基础的概念。Zlib 编码消耗非常大,其结果应当被缓存。详见 优化内存占用 中更多的关于 Zlib 用法中对速度 / 内存 / 压缩的权衡取舍。

// client request example
const zlib = require('zlib');
const http = require('http');
const fs = require('fs');
const request = http.get({
    host: 'izs.me',
    path: '/',
    port: 80,
    headers: {
        'accept-encoding': 'gzip,deflate'
    }
});
request.on('response', (response) => {
    var output = fs.createWriteStream('izs.me_index.html');

    switch (response.headers['content-encoding']) {
        // or, just use zlib.createUnzip() to handle both cases
    case 'gzip':
        response.pipe(zlib.createGunzip()).pipe(output);
        break;
    case 'deflate':
        response.pipe(zlib.createInflate()).pipe(output);
        break;
    default:
        response.pipe(output);
        break;
    }
});

// server example
// Running a gzip operation on every request is quite expensive.
// It would be much more efficient to cache the compressed buffer.
const zlib = require('zlib');
const http = require('http');
const fs = require('fs');
http.createServer((request, response) => {
    var raw = fs.createReadStream('index.html');
    var acceptEncoding = request.headers['accept-encoding'];
    if (!acceptEncoding) {
        acceptEncoding = '';
    }

    // Note: this is not a conformant accept-encoding parser.
    // See http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.3
    if (acceptEncoding.match(/\bdeflate\b/)) {
        response.writeHead(200, {
            'content-encoding': 'deflate'
        });
        raw.pipe(zlib.createDeflate()).pipe(response);
    } else if (acceptEncoding.match(/\bgzip\b/)) {
        response.writeHead(200, {
            'content-encoding': 'gzip'
        });
        raw.pipe(zlib.createGzip()).pipe(response);
    } else {
        response.writeHead(200, {});
        raw.pipe(response);
    }
}).listen(1337);

默认情况下,Zlib 方法在截断解压缩数据时,会抛出一个错误。然而,如果已知该数据是不完整的,或仅仅是希望检查一个压缩文件的开始部分,通过改变用于压缩输入数据最后一个数据块的 flushing 方法,有可能可以抑制默认的错误处理程序:

// This is a truncated version of the buffer from the above examples
const buffer = new Buffer('eJzT0yMA', 'base64');

zlib.unzip(buffer, {
    finishFlush: zlib.Z_SYNC_FLUSH
}, (err, buffer) => {
    if (!err) {
        console.log(buffer.toString());
    } else {
        // handle error
    }
});

这不会改变其他情况下抛出错误的行为,例如,当输入无效格式的数据。使用该方法,这将不可能确定输入是否提前结束或是否缺乏完整性检查,因此有必要手动检查该解压缩结果的有效性。

results matching ""

    No results matching ""