webpack-dev-server 从入门到实战

9,153 阅读4分钟

xr.png

古有云:“工欲善其事,必先利其器”。作为一个前端开发,搭建一个便捷的开发环境,将会为我们的开发工作带来极大的效率提升。而Webpack作为如今前端工程打包必不可少的工具,很多人却不知道从Webpack 4开始提供的DevServer功能。

让我们一起来学习下吧!

1 什么是webpack-dev-server

DevServerWebpack 3开放的一个实验功能,使用webpack-dev-middleware中间件,提供热更新的开发服务器,旨在帮助开发者在开发阶段快速进行环境搭建。

最新Webpack 5还支持反向代理、防火墙、Socketgzip压缩等功能。

2 反向代理配置

Nginx类似,webpack-dev-server也是通过url正则匹配的方式进行url代理配置,常用配置参考如下代码:

{
  "/rest/": {
    "target": "http://127.0.0.1:8080",
    "secure": false
  }
}

还可以通过用JavaScript定义此配置,把多个条目代理到同一个目标。将代理配置文件设置为proxy.conf.js(代替proxy.conf.json),并指定如下例子中的配置文件。

module.exports = {
    //...
    devServer: {
        proxy: [
            {
                context: ['/auth''/api'],
                target'http://localhost:3000',
            },
        ],
    },
};

2.1 基本配置项介绍

  • proxydevServer代理配置
  • /api: 表示需要代理的请求url
  • target:反向代理的地址
  • pathRewrite:请求地址重写,类似NginxRewite功能

其他写法参考:

"pathRewrite": {
  "^/old/api""/new/api"
}

 // remove path
pathRewrite: {
  '^/remove/api'''
}

// add base path
pathRewrite: {
  '^/': '/basepath/'
}

// custom rewriting
pathRewritefunction (path, req) {
  return path.replace('/api''/base/api');
}

// custom rewriting, returning Promise
pathRewriteasync function (path, req) {
  const should_add_something = await httpRequestToDecideSomething(path);
  if (should_add_something) path += 'something';
  return path;
}

2.2 其他配置参考

  • logLevel:日志打印等级,支持['debug', 'info', 'warn', 'error', 'silent']silent不打印日志
  • logProvider: 自定义日志打印中间件
  • secure:是否关闭https安全认证
  • changeOrigin:修改代理请求host
  • protocolRewrite:协议重写,httphttps请求互转
  • cookieDomainRewrite:修改cookieDomain的值
  • headers:给所有请求添加headers配置
  • proxyTimeout:请求超时时间

2.3 高级代理机制

  • onError:  对请求状态码进行处理
function onError(err, req, res, target) {
    res.writeHead(500, {
        'Content-Type''text/plain',
    });
    res.end('Something went wrong. And we are reporting a custom error message.');
}
  • onProxyRes: 对代理接口的Response处理,这里常用来获取cookie、重定向等
function onProxyRes(proxyRes, req, res) {
    proxyRes.headers['x-added'] = 'foobar'// 添加一个header
    delete proxyRes.headers['x-removed']; // 删除一个header
}
  • onProxyReq:对代理接口request处理,执行在请求前,常用来设置cookieheader等操作
function onProxyReq(proxyReq, req, res) {
    // add custom header to request
    proxyReq.setHeader('x-added''foobar');
    // or log the req
}

3 域名白名单配置

配置该配置后,只有匹配的host地址才可以访问该服务,常用于开发阶段模拟网络网络防火墙对访问IP进行限制。当该配置项被配置为all时,会跳过host检查,但不建议这样做,因为有DNS攻击的风险。

  1. webpack配置项配置
module.exports = {
  //...
  devServer: {
    allowedHosts: [
      'host.com',
      'subdomain.host.com',
      'subdomain2.host.com',
      'host2.com',
    ],
  },
};
  1. cli 启动命令配置
npx webpack serve --allowed-hosts .host.com --allowed-hosts host2.com

4 端口配置

  1. webpack配置项配置
module.exports = {
  //...
  devServer: {
    port8080,
  },
};
  1. cli 启动命令配置
   npx webpack serve --port 8080

5 Angular 实战 —— 通过webpack devServer代理REST接口到本地服务器

在Angular框架中,由于对webpack进行了封装,proxy配置文件默认使用的是proxy.config.json。(js格式配置文件需要到angular.json配置文件中修改),这里以proxy.config.json为例。

  1. 代理所有以/rest/开头的接口到127.0.0.1:8080,并且将/rest/请求地址转为/
{
  "/rest/": {
    "target": "http://127.0.0.1:8080",
    "secure": false,
    "pathRewrite": {
      "/rest/": "/"
    },
    "changeOrigin": true,
    "logLevel": "debug",
    "proxyTimeout": 3000
  }
}

访问启动地址测试{{ host地址}}/rest/testApi

  1. 给所有的/rest/接口加上cftk的header

这个需要使用js格式的proxy配置文件,修改angular.json中的proxyConfig为 proxy.config.js,在proxy.config.js中添加如下内容:

const PROXY_CONFIG = [
    {
        "target""http://127.0.0.1:8080",
        "secure"false,
        "pathRewrite": {
            "/rest/""/"
        },
        "changeOrigin"true,
        "logLevel""debug",
        "proxyTimeout"3000,
        "onProxyReq"(request, req, res) => {
            request.setHeader('cftk''my cftk');
        }
    },
];
module.exports = PROXY_CONFIG;

6 webpack-dev-server 与 nginx 的对比

      webpack-dev-server   nginx
 使用场景   本地开发  全场景 
 网络支持   https/http/http2/ws  https/http/http2/ws/ftp等 
 加载方式   编译代码后加载到内存,性能更好,可以结合webpack进行热更新,项目较大时会占据过多内存  读取硬盘中的内容,适合大项目 
 gzip支持   支持  支持 
 线程   单线程  多线程 
 正向代理   不支持  支持 
 反向代理   支持  支持,功能更强大 
 服务支持   单点支持  支持多服务,负载均衡 
 上手难度   易  难 
 总结   非常适合本地开发态,其中代码都是读取到内存中,性能更好,减少了每次更改后编译的时间,上手简单学习成本较低,在一些鉴权场景下不需要其他第三方插件就可以获取cookie等信息,对开发者更友好。但由于编译和代理绑定,每次修改配置的成本较大  十项全能,是一款非常优秀的服务器,功能非常强大,但配置也较为复杂,有一定的学习成本,本地联调需要借助浏览器插件才可以获取cookie等浏览器信息,配置文件维护涉及团队沟通成本