WebpackDevServer多API代理配置

配置說明:

提早配置多個API代理目標, 在開發環境下可快速切換API代理目標.javascript

演示:

(鼠標移至前端界面右下角位置, 輸入預先配置的目標來切換API代理) css

基於你項目的HTML模板文件, 複製一份出來, 加上style, span#current-env, input#modify-proxy, script. 樣式及形式可隨意修改, 反正是dev環境_(:з」∠)_html

/templates/dev.html前端

<!DOCTYPE html>
<html lang="zh-CN">
<head>
	<meta charset="UTF-8">
	<meta http-equiv="X-UA-Compatible" content="IE=Edge,chrome=1" >
	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
	<meta name="format-detection" content="telephone=no"/>
	<link rel="icon" href="/static/build/logo-mini.png" type="image/x-icon">
    <title>Title</title>
    <style> #modify-proxy { position: fixed; width: 150px; right: -149px; bottom: 12px; } #current-env { position: fixed; right: 10px; bottom: 13px; opacity: 0.2; pointer-events: none; } #modify-proxy:hover, #modify-proxy:focus { right: 0; } </style>
</head>
<body>
    <div id="app"></div>
    <span id="current-env"></span>
    <input id="modify-proxy" placeholder="修改代理" onchange="changeProxy(this)"/>
    <script> document.getElementById('modify-proxy').value = window.localStorage.getItem('proxy').slice(1) document.getElementById('current-env').innerHTML = 'API 環境: ' + (window.localStorage.getItem('proxy').slice(1) || '默認') function changeProxy(el) { var value = el.value.trim() window.localStorage.setItem('proxy', value ? ('/' + value) : '') document.getElementById('current-env').innerHTML = 'API 環境: ' + (value || '默認') } </script>
</body>
</html>
複製代碼

修改webpack配置文件. HtmlPlugin配置, 開發環境使用咱們剛剛寫的dev.html模板:java

const isProduction = process.env.mode && process.env.mode.trim() === 'production'
// ...
{
    plugins: [
        /* ... other plugins */
        new HtmlPlugin({
            title: 'Demo',
            filename: 'index.html',
            template: path.join(__dirname, 'src', isProduction ? 'templates/default.html' : 'templates/dev.html'), // 看這裏!
            chunks: ['index', 'manifest'],
            hash: false,
        }),
        /* ... other plugins */
]
}
複製代碼

新建 proxy-config.js 文件, 提早配置多個API代理目標:webpack

const proxyTargets = [
    {
        targetName: 'dev',
        target: 'https://dev-xxx.xxx.com',
    },
    {
        targetName: 'test',
        target: 'https://test-xxx.xxx.com',
        baseURL: '/api-manage',
    },
    {
        targetName: 'caspian',
        target: 'http://192.168.5.39:9003',
    },
    {
        targetName: '小明',
        target: 'http://192.168.5.116:9003',
    },
    {
        targetName: '小紅',
        target: 'http://192.168.5.117:9003',
    },
]

const proxies = {}
const BASE_URL = process.env.BASE_URL || ''

proxyTargets.forEach((proxyTarget) => {
    proxies[`/${proxyTarget.targetName}${BASE_URL}`] = {
        target: proxyTarget.target,
        pathRewrite: { [`/${proxyTarget.targetName}${BASE_URL}`]: proxyTarget.baseURL || BASE_URL || '' },
        changeOrigin: true,
        toProxy: false,
        prependPath: false,
    }
})

module.exports = proxies

複製代碼

修改WebpackDevServer的啓動文件:web

const path = require('path')
const WebpackDevServer = require('webpack-dev-server')
const webpack = require('webpack')
const config = require('./webpack.config.js')
const proxies = require('./proxy-config') // 引入代理配置文件

const devPort = process.env.port

const options = {
    hot: true,
    historyApiFallback: true,
    contentBase: path.join(__dirname, './'),
    compress: false,
    disableHostCheck: true,
    host: '0.0.0.0', // 容許經過其餘ip訪問
    proxy: Object.assign(proxies, { // !!!把配置扔這裏, 順便給個默認代理
        '/**': {
            target: 'https://default-xxx.com',
            changeOrigin: true,
            toProxy: false,
            prependPath: false,
            secure: false, // 接受 運行在 https 上的服務
        },
    }),
}

WebpackDevServer.addDevServerEntrypoints(config, options)
const compiler = webpack(config)
const server = new WebpackDevServer(compiler, options)

server.listen(devPort, '0.0.0.0', () => {
    global.console.log(`dev server listening on port ${devPort}`)
})

複製代碼

utils.js 在本身的工具庫上加上getBaseURL方法:chrome

const baseUrl = process.env.BASE_URL || ''
const isProduction = process.env.mode && process.env.mode.trim() === 'production'

getBaseURL() {
    if (isProduction) {
        return baseUrl
    }
    const proxy = window.localStorage.getItem('proxy') || ''
    return proxy + baseUrl
}
複製代碼

在本身所用的HTTP請求工具類上改動, 在 URL 前加上getBaseURL():api

async request(_url: string, options = {}) {
    const url = utils.getBaseURL() + _url // 加上getBaseURL()
    let fetchOptions = Object.assign(fetchOptions, this.defaultOptions, options)
    const res = await fetch(url, fetchOptions)
}
複製代碼

完成!app

最後:

不適用於全部的項目及團隊開發模式, 這裏只是分享一下本身在項目實踐上的一些小技巧, 但願對你有所幫助!

相關文章
相關標籤/搜索