「Vue × Docker」服務(wù)器部署Vue遇到的那些坑

項(xiàng)目之前一直在電腦本地做的,廢棄了很久才想起來部署到服務(wù)器上。因?yàn)槭堑谝淮斡胿ue,發(fā)布時(shí)遇到了很多問題,用了5個(gè)小時(shí)才解決掉。
主要問題有兩個(gè):

  1. 不清楚如何發(fā)布vue項(xiàng)目,服務(wù)器上npm run dev只能本地測試使用。
  2. 數(shù)據(jù)接口的代理加載不出資源。

服務(wù)器環(huán)境:

linux 7.0 x86_64
npm 6.1.0
vue 2.9.6
docker 17.12.0-ce
開放端口8003(前端)和3000(接口)
注:以下過程為已安裝好npm/vue-cli/docker且數(shù)據(jù)接口正常工作為前提。

vue在本地測試運(yùn)行時(shí)是使用 $ npm run dev。
但vue環(huán)境真正的部署是要通過webpack構(gòu)建成html后通過nginx等web服務(wù)解析工作的。
首先看vue的配置文件config/index.js,生產(chǎn)環(huán)境部署vue時(shí)網(wǎng)上的案例常遇到資源加載404的問題,根本原因是在構(gòu)建配置時(shí)“assetsPublicPath”的問題,webpack會(huì)根據(jù)這一項(xiàng)配置修改資源引用的路徑。

module.exports = {
  ...
  build: {
    index: path.resolve(__dirname, '../dist/index.html'),
    assetsRoot: path.resolve(__dirname, '../dist'),
    assetsSubDirectory: 'static',
    assetsPublicPath: '/',
    ...
  }
}

如果是配置“assetsPublicPath: '/'”,那么就要把構(gòu)建出來的內(nèi)容放到nginx的html根目錄下(不是服務(wù)器的根目錄),這樣資源才能正常加載。因?yàn)榉?wù)器沒有直接安裝nginx,所以借用了docker環(huán)境。

$ sudo npm run build // vue項(xiàng)目打包

打包后生成的html文件是在項(xiàng)目的dist目錄下,會(huì)產(chǎn)生一個(gè)index.html和static文件夾。也可以直接在計(jì)算機(jī)本地打包后,只將dist文件夾傳到服務(wù)器上。
第二個(gè)問題是我的vue項(xiàng)目中請(qǐng)求數(shù)據(jù)使用了代理,即.get('/api/......'),而不是.get('http://......')。
在本地測試時(shí)可以直接在vue的配置文件config/index.js的dev部分配置代理,用/api替換掉了 http: //localhost:3000/。

module.exports = {
  dev: {
    assetsSubDirectory: 'static',
    assetsPublicPath: '/',
    proxyTable: {
      '/api': {
        target: 'http://localhost:3000/',
        changeOrigin: true,
        pathRewrite: {
          '^/api': '/',
        },
      },
    },
    ...
}

但在服務(wù)器上該方法不適用,所以如果不修改nginx配置的話,是無法請(qǐng)求到/api/......的數(shù)據(jù)的。創(chuàng)建一個(gè)nginx配置文件default.conf,內(nèi)容如下:

server {
    listen       80;
    server_name  localhost;
    location / {
        root   /usr/share/nginx/html;
        index  index.html index.htm;
    }
    location ^~/api/ {        
        rewrite ^/api/(.*)$ /$1 break;        
        proxy_set_header   Host             $host;        
        proxy_set_header   x-forwarded-for  $remote_addr;        
        proxy_set_header   X-Real-IP        $remote_addr;        
        proxy_pass http://127.0.0.1:3000;
    }
    error_page   500 502 503 504  /50x.html;
    location = /50x.html {
        root   /usr/share/nginx/html;
    }
}

關(guān)鍵部分在于 location ^~/api/{...},是將原本寫在index.js配置文件中的代理用nginx來實(shí)現(xiàn)。當(dāng)nginx接收到 http: //xxx.xxx.xxx.xxx:8003/api/... 的請(qǐng)求時(shí)自動(dòng)轉(zhuǎn)發(fā)到3000端口。
準(zhǔn)備完畢后,docker拉取nginx的鏡像,我使用的版本是nginx@latest。不用編寫dockerfile,直接實(shí)例化容器:

$ sudo docker run -d --name vue -p 8003:80 -v /mnt/donghan/default.conf:/etc/nginx/conf.d/default.conf -v /mnt/donghan/vue/dist:/usr/share/nginx/html nginx:latest

在這里要注意的幾個(gè)參數(shù):

-p 8003:80 // 容器內(nèi)的80端口映射到外部主機(jī)8003端口
-v /mnt/donghan/vue/dist:/usr/share/nginx/html // 將vue生成的html文件直接導(dǎo)入到容器中nginx的根目錄下,前面的是我服務(wù)器上存放dist的目錄
-v /mnt/donghan/default.conf:/etc/nginx/conf.d/default.conf // 導(dǎo)入nginx環(huán)境配置文件

經(jīng)過這么一折騰,vue才能夠在服務(wù)器上真正部署起來。整個(gè)流程做下來還是踩了不少坑,網(wǎng)上的那些博客解決方案都很零散。在沒有描述詳細(xì)服務(wù)器環(huán)境的情況下,很難根據(jù)一句話兩句話搞定問題。所以在這里也希望大家以后寫博客的時(shí)候能更詳細(xì)的說說服務(wù)器上的環(huán)境和問題的描述,一起加油。

題外話

這次做的是express+vue+mongodb的一個(gè)站,基本核心都是nodejs,然!而!就在部署完之后我得到了這個(gè)很難過的消息:「Node之父Ryan Dahl說:Node 失誤太多無力回天,Deno 前景明朗?!?/a>
nodejs零零散散接觸了有一年,現(xiàn)在已經(jīng)慢慢熟悉了,居然有種老友訣別之感。但也確實(shí)也存在各種各樣的問題,Ry的PPT上的這張圖相信大家都深有感觸。


希望下一代的Nodejs——Deno能越走越遠(yuǎn),也祝js家族更加壯大。

相關(guān)閱讀更多精彩內(nèi)容

  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務(wù)發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,569評(píng)論 19 139
  • 又吵架了,去找?guī)熃懔奶?,覺得自己真的很不成熟。 如果兩個(gè)人真的相愛的話,需要很多很多理解和包容,才能長相守。 誰對(duì)...
    百里晴閱讀 285評(píng)論 0 0
  • 1、公司背景 重慶市中旅安信小額貸款有限公司是中國旅游集團(tuán)旗下的全國互聯(lián)網(wǎng)小額貸款公司。公司注冊資本3億元人民幣,...
    Teroy閱讀 744評(píng)論 0 0

友情鏈接更多精彩內(nèi)容