手写Node静态资源服务器的实现方法(2)

  1. gzip方法用于实现压缩
  2. gunzip方法用于实现解压
  3. 其中文件msg.txt是同级目录
  4. 为什么需要这么写:gzip(path.join(__dirname,'msg.txt'));
  5. 因为console.log(process.cwd());打印出当前工作目录是根目录,并不是文件所在目录,如果这么写gzip('msg.txt');找不到文件就会报错
  6. basename 从一个路径中得到文件名,包括扩展名的,可以传一个扩展名参数,去掉扩展名
  7. extname 获取扩展名
  8. 压缩的格式和解压的格式需要对上,否则会报错

有些时候我们拿到的字符串不是一个流,那怎么解决呢

let zlib=require('zlib');
let str='hello';
zlib.gzip(str,(err,buffer)=>{
  console.log(buffer.length);
  zlib.unzip(buffer,(err,data)=>{
    console.log(data.toString());
  })
});

有可能压缩后的内容比原来还大,要是内容太少的话,压缩也没什么意义了

文本压缩的效果会好一点,因为有规律

在http中应用压缩和解压

下面实现这样一个功能,如图:

客户端向服务器发起请求的时候,会通过accept-encoding(比如:Accept-Encoding:gzip,default)告诉服务器我支持的解压缩的格式

  1. 服务器端需要根据Accept-Encoding显示的格式进行压缩,没有的格式就不能压缩,因为浏览器无法解压
  2. 如果客户端需要的Accept-Encoding中的格式服务端没有,也无法实现压缩
let http = require("http");
let path = require("path");
let url = require("url");
let zlib = require("zlib");
let fs = require("fs");
let { promisify } = require("util");
let mime = require("mime");
//把一个异步方法转成一个返回promise的方法
let stat = promisify(fs.stat);
http.createServer(request).listen(8080);
async function request(req, res) {
 let { pathname } = url.parse(req.url); 
 let filepath = path.join(__dirname, pathname); 
 // fs.stat(filepath,(err,stat)=>{});现在不这么写了,异步的处理起来比较麻烦
 try {
  let statObj = await stat(filepath);
  res.setHeader("Content-Type", mime.getType(pathname));
  let acceptEncoding = req.headers["accept-encoding"];
  if (acceptEncoding) {
   if (acceptEncoding.match(/\bgzip\b/)) {
    
    res.setHeader("Content-Encoding", "gzip");
    fs
     .createReadStream(filepath)
     .pipe(zlib.createGzip())
     .pipe(res);
   } else if (acceptEncoding.match(/\bdeflate\b/)) {
    res.setHeader("Content-Encoding", "deflate");
    fs
     .createReadStream(filepath)
     .pipe(zlib.createDeflate())
     .pipe(res);
   } else {
    fs.createReadStream(filepath).pipe(res);
   }
  } else {
   fs.createReadStream(filepath).pipe(res);
  }
 } catch (e) {
  res.statusCode = 404;
  res.end("Not Found");
 }
}

      

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/42.html