nodejs中http-proxy使用小結


    最近在寫xmocker的工具,用於開發前期的mock數據,不可避免的用到了代理的中間件。當然,github上有關於http-proxy封裝的中間件。畢竟是自己練手的項目,就自己寫了個中間件,方便定制功能。

    http-proxy庫用於koa中,是使用它的 proxy.web方法。常規的用法是:

proxy.web(req, res, { target: 'http://mytarget.com:8080' }, function(e) { ... });

    項目中的要求是將API代理到用戶填寫的網址上去。Koa提供了req和res,用戶提供了網址,這樣中間件就很容易寫了

function proxyTo({ status }) {
  return async function (ctx, next) {
    return next().then(async () => {
      if (status === undefined || ctx.status === status) {
        let data
        try {
          data = await proxy.web(ctx.req, ctx.res)
        } catch (e) {
          if (err) console.log(err)
          return
        }
      }
    })
  }
}

  設置訪問結果為404則進行代理,否則不進行代理。然后在koa的中間件中use這個函數就可以了。

  基礎應用這樣自然就可以了,可是遇到POST的時候就不行了,因為用到了koa-bodyparser,導致post的請求沒法發給服務器。在http-proxy的issue中到處找解決辦法,終於找到了讓req重新stream的方法。

 

proxy.on('proxyReq', function (proxyReq, req, res, options) {
    if (req.body) {
      let bodyData = JSON.stringify(req.body)
      // incase if content-type is application/x-www-form-urlencoded -> we need to change to application/json
      proxyReq.setHeader('Content-Type', 'application/json')
      proxyReq.setHeader('Content-Length', Buffer.byteLength(bodyData))
      // stream the content
      proxyReq.write(bodyData)
    }
  })

  嗯,這樣基本就完成了一個Proxy的中間件。

  剛開始用起來還不錯,至少普通的API都可以轉發了。於是試着代理到公司的API系統,網頁端也沒發現什么問題。然后用fiddler代理安卓客戶端,用正則代理鏈接至自己的服務,出現了亂碼。。。客戶端用的是okhttp發出的請求,fiddler上看轉發回來的json數據明明是正常的,結果在手機上中文就是不正確,都是十六進制代碼,根本沒解析。仔細對比:編碼?都是utf-8,這個沒問題。gzip?我明明是用的pipe過去,代碼原封不動啊。我試中捕獲了所有數據,用gzip解碼后,也是正確的,那為什么會出錯呢?

  和別人交流了好久也沒找到問題。沒辦法,到代碼中找找。對於請求的header,發現cookie貌似少了一條,就看看header轉發時候怎么處理的。結果發現,header全是進行轉換的。issue中有提到set-cookie多條的問題,我這也是這個情況,嘗試着看看這個文件改動記錄,意外發現了一個Option項 :preserveHeaderKeyCase。

  nodejs中header都是小寫的形式,所以http-proxy中就進行了轉換,將請求全部header轉為小寫。於是改了了true,這樣就不再轉換了。然后,客戶端正常了!!!哈哈,仔細一看,cookie還是不是多條。算了,先不管cookie了,至少普通登錄沒啥問題了。

  另外加個changeOrigin為true可以防止有些服務器path取的是初始域名,出現404的問題。暫時就這么多啦。proxy插件的地址在:

https://github.com/wenlonghuo/xmocker/blob/master/app/plugin/proxy.js

歡迎試用我的Mock工具:

https://github.com/wenlonghuo/xmocker-cli

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM