流和压缩
- buffer
- 流
- 压缩
buffer
buffer 是二进制数据。我们都知道,计算机在处理数据时候,最终是转换成二进制来进行处理的。在 js 中,最终只能操作字符串。
nodejs 出现后,js 有了处理二进制数据的能力。
来看下面的例子:
const fs = require('fs');
fs.readFile('./test.txt',(err, data)=>{
if(err) throw err;
console.log(data);
});
在上面的例子中,我们使用 readFile 来读取文件,在没有添加指定编码的情况下,读取出来的就是 buffer 数据。
下面介绍一些关于 buffer 的简单操作。
// 创建 buffer
let buf = new Buffer.from([10,20,30]);
console.log(buf); // <Buffer 0a 14 1e>
流
在计算机中,数据是以流的形式来进行传输。
在 nodejs 中,可以针对流进行操作。
可读流
将一块数据以流的形式一点一点的读取。
const fs = require('fs');
// 创建一个可读流
let readablestream = fs.createReadStream('./test.txt');
readablestream.on('data',function(chunk){
console.log(chunk.toString());
console.log('--------------------------------------')
})
可写流
const fs = require('fs');
// 创建可读流
let readablestream = fs.createReadStream('./test.txt');
// 创建可写流
let writeablestream = fs.createWriteStream('./test2.txt');
readablestream.on('data',function(chunk){
writeablestream.write(chunk);
})
readablestream.on('end',function(){
writeablestream.end();
})
pipe 方法
pipe 方法就类似于在两个数据容器之间接了一根管子,数据流直接通过这跟管道流向另外一个容器,不需要在监听data事件。
const fs = require('fs');
// 创建可读流
let readablestream = fs.createReadStream('./test.txt');
// 创建可写流
let writeablestream = fs.createWriteStream('./test3.txt');
readablestream.pipe(writeablestream);
压缩
使用到了 nodejs 中内置的模块,zlib,可以通过这个模块来创建压缩文件。
快速入门的示例:
const zlib = require('zlib');
const fs = require('fs');
// 要对一个文件进行压缩
const gzib = zlib.createGzip(); // 压缩对象
const readablesteam = fs.createReadStream('./test.txt');
const output = fs.createWriteStream('./test.txt.gz');
readablesteam.pipe(gzib).pipe(output);
解压缩
const fs = require('fs'); // 引入文件模块
const zlib = require('zlib'); // 引入压缩模块
const gunzip = zlib.createGunzip(); // 解压缩文件创建的是 gunzip 对象
// 和压缩过程相比 , 就是一个反向操作 , 可读流为压缩文件 , 可写流为解压文件
const inFile = fs.createReadStream('./test.txt.gz');
const outFile = fs.createWriteStream('./Hello.txt');
// 同样也是调用可读流的 pipe() 方法 , 写入之前先传入 gunzip 对象进行一下解压 , 然后在进行写入
inFile.pipe(gunzip).pipe(outFile);
服务端解压缩
const http = require('http');
const zlib = require('zlib');
const fs = require('fs');
const filepath = './extra/fileForGzip.html'; // 要向客户端返回的文件
const server = http.createServer(function (req, res) {
const acceptEncoding = req.headers['accept-encoding']; // 获取 acceptEncoding 的值
// 判断是否需要 gzip 压缩
if (acceptEncoding.indexOf('gzip') != -1) {
// 进入 if 说明 acceptEncoding 里面包含 gzip 值
// 客户端的浏览器支持压缩文件
const gzip = zlib.createGzip();
// 记得响应 Content-Encoding,告诉浏览器:文件被 gzip 压缩过
res.writeHead(200, {
'Content-Encoding': 'gzip'
});
fs.createReadStream(filepath).pipe(gzip).pipe(res);
} else {
// 进入 else , 说明客户端的浏览器不支持压缩文件
// 直接返回该文件
fs.createReadStream(filepath).pipe(res);
}
});
server.listen(3000);