egg.js 动态转发代理

时间:2022-07-26
本文章向大家介绍egg.js 动态转发代理,主要内容包括其使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。
  • 需求背景利用nodejs和consul实现注册中心和网关
  • egg.js在获取配置信息与节点后进行服务转发与路径管理
  • 实现难点没有成行的技术博客去解决这个问题

解决方案

  • 依赖http-proxy-middleware和koa2-connect
  • 重点问题application/x-www-form-urlencoded 转发代理要定制解决否则活转发失败
  • 配置文件中添加代理配置信息
  • // 忽略安全威胁csrf的防范 config.security = { csrf:{ enable: false } } //代理配置信息 config.proxyConfig = {}; // add your middleware config here config.middleware = ['proxy'];
  • 在中间件中添加代理js
  • proxy.js /*
* @Description: api 网关代理 
* @Author: 吴文周
* @Github: http://gitlab.yzf.net/wuwenzhou 
* @Date: 2020-06-28 13:38:19 
* @LastEditors: 吴文周
* @LastEditTime: 2020-08-13 18:14:32 
*/
const { createProxyMiddleware } = require('http-proxy-middleware');
const k2c = require('koa2-connect');
module.exports = (options,app) => {  
return async function(ctx,next) {  let proxy= app.config.proxyConfig;  
  try {      
    const Proxy = k2c(createProxyMiddleware('/api',{ 
    target: proxy.target,// 动态设置可以从缓存中获取更新       
    pathRewrite:proxy.Rewrite,// 动态设置可以从缓存中获取更新        
    changeOrigin: true,        
    secure: false,        
    body:ctx.request.body,        
    onProxyReq:(proxyReq, req, res, options)=>{          
    const contentType = proxyReq.getHeader('Content-Type'); 
    // 特殊判断如果类型是application/x-www-form-urlencoded 转发代理需要特殊处理      
    try {           
     if (contentType && contentType.indexOf('application/x-www-form-urlencoded')>=0) {
              let body = Object.keys(options.body).map(function(key) {   
               return encodeURIComponent( key ) + '=' + encodeURIComponent(options.body[key])
              }).join('&');              
 //Update header              
proxyReq.setHeader('content-type', 'application/x-www-form-urlencoded');              
proxyReq.setHeader('content-length', body.length );             
 // Write out body changes to the proxyReq stream              
proxyReq.write(body);              
// proxyReq.end();           
 }       
   } catch (error) {      
      console.log(error);          }        }      }));     
 await Proxy(ctx,next);    }else{      next()    }    } catch (error) {      console.log(error)      next()    }  };};