现如今在处理http请求的时候,由于请求的资源较多,如果不启用压缩的话,那么页面请求的流量将会非常大。启用gzip压缩,在一定程度上会大大的提高页面性能。
因此这写一个使用Node.js实现在http客户端与服务端传输压缩数据的实例代码。在HTTP服务器端与HTTP客户端之间传输压缩数据时,在客户端请求头中需要使用accept-encoding字段指定服务端压缩数据时使用的压缩算法,在服务端响应头中使用content-encoding字段声明服务器端响应数据的压缩算法。
首先来看服务端代码吧,这段代码,首先创建了一个HTTP服务器,当HTTP服务器接收到客户端请求时,获取客户端请求头中的accept-encoding字段,如果字段值包含'deflate'字段,创建Deflate对象并使用该对象压缩应用程序根目录下的test.txt文件,在服务器端响应头中使用content-encoding字段值指定为'deflate',然后将压缩后的数据返回给客户端。如果accept-encoding字段值包含'gzip'字符串,使用同样的方式来创建一个Gzip对象来压缩应用程序根目录下的test.txt文件,在服务器端响应头中使用content-encoding字段值指定为'gzip',然后将压缩后的数据返回给客户端。如果accept-encoding字段值中不包含上述两种字符串,则直接将应用程序根目录下的test.txt文件中的数据返回给客户端。
完整的server代码如下:
var fs = require('fs'); var zlib = require('zlib'); var http = require('http'); http.createServer(function (req, res){ var raw = fs.createReadStream('test.txt'); var acceptEncoding = req.headers['accept-encoding']; if (!acceptEncoding){ acceptEncoding = ''; } if (acceptEncoding.match(/deflate/)){ res.write(200, {'content-encoding': 'deflate'}); raw.pipe(zlib.createDeflate()).pipe(res); } else if (acceptEncoding.match(/gzip/)){ res.write(200, {'content-encoding': 'gzip'}); raw.pipe(zlib.createGzip()).pipe(res); } else{ res.write(200, {}); raw.pipe(res); } }).listen(1337, '127.0.0.1');
创建了服务端之后,我们来看看创建的HTTP客户端,在下面的客户端实例代码中我们创建了一个HTTP客户端请求数据,将客户端请求头重的accept-encoding字段值设定为‘gzip, deflate',在接受到客户端请求后,获取响应头中的content-encoding字段值,如果字段值为’gzip',创建Gunzip对象并使用该对象解压缩服务端响应数据,并将其写入到应用程序根目录下的test1.txt文件中。如果content-encoding字段值为'deflate',创建Inflate对象并使用对象解压缩服务端响应数据,并将其写入到应用程序根目录下的test1.txt文件中。如果content-encoding字段值不包含上述两个字符串,则会将服务端相应的数据直接写入应用程序根目录下的test1.txt文件中。
完整的client代码如下:
var fs = require('fs'); var zlib = require('zlib'); var http = require('http'); var options = { host: 'localhost', path: '/', port: 1337, headers: {'accept-encoding': 'gzip, deflate'} }; var request = http.get(options) ; request.on('response', function (res){ var output = fs.createWriteStream('test2.txt'); var codeStr = res.headers['content-encoding']; switch (codeStr){ case 'gzip': res.pipe(zlib.createGunzip()).pipe(output); break; case 'deflate': res.pipe(zlib.createInflate()).pipe(output); break; default : res.pipe(output); break } });