Express
代理本地请求
一般前端使用的都是
webpack
或者vite
这种成熟构建工具,代理其实只需要配置一下就好了,但是有些情况可能需要搭配koa
或者express
去代理本地请求,像这种情况,一般会搭配http-proxy-middleware
一起使用,接下来介绍一下express
使用http-proxy-middleware
代理本地请求到指定域名请求的一种方法
前置环境搭建
# 配置express最轻量的启动脚本服务
var express = require('express');
var { createProxyMiddleware } = require('http-proxy-middleware');
var app = express();
var port = process.env.PORT || config.dev.port;
module.exports = app.listen(port, function(err) {
if (err) {
console.log(err);
return;
}
console.log('Listening at http://localhost:' + port + '\n');
});
使用 http-proxy-middleware
配置代理
1. 安装 http-proxy-middleware
npm install --save-dev http-proxy-middleware
2. 配置middleware
var express = require('express');
var { createProxyMiddleware } = require('http-proxy-middleware');
var app = express();
var port = process.env.PORT || config.dev.port;
# 如果env需要proxy,那就代理到指定环境
if (process.env.proxy) {
app.use(createProxyMiddleware({
// 要代理的目标地址
target: process.env.proxy,
changeOrigin: true,
secure: false,
logLevel: 'debug',
timeout: 5000,
proxyTimeout: 6000,
// pathFilter 可以配置那些地址可以走代理
// 这里可以是 string,string[], (path):Boolean 等等,具体可以按照官方的来写就好了
pathFilter: pathname => {
console.log('pathname :>> ', pathname);
return !(pathname.match('html') || pathname === '/');
},
headers: { referer: process.env.proxy },
logger: console,
on: {
proxyReq: (proxyReq, req, res) => {
console.log('proxyReq :>> ', proxyReq.path);
proxyReq.setHeader('referer', process.env.proxy);
},
error: (err, req, res) => {
console.log('error', err);
}
}
}));
}
module.exports = app.listen(port, function(err) {
if (err) {
console.log(err);
return;
}
console.log('Listening at http://localhost:' + port + '\n');
});
到此简单的代理就配置完成了
但是遇到一个问题,接下来简单描述一下,如果有遇到的朋友可以参考一下
- 现象:get请求ok,post请求无返回会报错
- 排查:bodyParser 导致的代理转发带有 body 数据的 post 请求会失败
- 结论:去掉中间件 bodyParser
这里贴一下完整的代码,如果大家碰到相似问题可以试一下,希望可以帮到类似问题的朋友
var express = require('express');
var webpack = require('webpack');
var config = require('../config');
var { createProxyMiddleware } = require('http-proxy-middleware');
var webpackConfig = process.env.NODE_ENV === 'testing' ? require('./webpack.prod.conf') : require('./webpack.dev.conf');
var { mock } = require('./dev-api');
var app = express();
var compiler = webpack(webpackConfig);
var port = process.env.PORT || config.dev.port;
var devMiddleware = require('webpack-dev-middleware')(compiler, {
publicPath: webpackConfig.output.publicPath,
stats: {
colors: true,
chunks: false
}
});
var hotMiddleware = require('webpack-hot-middleware')(compiler, { log: () => {} });
// force page reload when html-webpack-plugin template changes
// 当html-webpack-plugin模版改变时重新加载页面
compiler.plugin('compilation', function(compilation) {
compilation.plugin('html-webpack-plugin-after-emit', function(data, cb) {
hotMiddleware.publish({ action: 'reload' });
cb();
});
});
// serve webpack bundle output
app.use(devMiddleware);
app.use(hotMiddleware);
app.get('/', (_, res) => res.redirect('/html/index.html'));
// var proxyConfig = config.dev.proxy;
// // 使用代理数据
// if (proxyConfig.open) {
// // 解析req.body
// var bodyParser = require('body-parser');
// // parse application/x-www-form-urlencoded
// app.use(bodyParser.urlencoded({ extended: true }));
// // parse application/json
// app.use(bodyParser.json());
// }
if (process.env.proxy) {
app.use(createProxyMiddleware({
target: process.env.proxy,
changeOrigin: true,
secure: false,
logLevel: 'debug',
timeout: 5000,
proxyTimeout: 6000,
pathFilter: pathname => {
console.log('pathname :>> ', pathname);
return !(pathname.match('html') || pathname === '/');
},
headers: { referer: process.env.proxy },
logger: console,
on: {
proxyReq: (proxyReq, req, res) => {
console.log('proxyReq :>> ', proxyReq.path);
proxyReq.setHeader('referer', process.env.proxy);
},
error: (err, req, res) => {
console.log('error', err);
res.writeHead(504, {
code: 504,
message: 'Gateway Timeout'
});
}
}
}));
} else {
// 使用mock数据
app.use(mock);
}
module.exports = app.listen(port, function(err) {
if (err) {
console.log(err);
return;
}
console.log('Listening at http://localhost:' + port + '\n');
});
写在最后
因为时间问题,我没有研究具体原因,知道的同学可以评论区科普一下,