Vue-Router
有兩種模式,默認是 hash
模式,另一種是 history
模式。html
#
符號。好比 http://www.example/#/hello
,hash 的值爲 #/hello
。特色:hash 雖然出現 URL 中,但不會被包含在 HTTP 請求中,對後端不會產生什麼影響,改變 URL 不會重載頁面。pushState()
和 replaceState()
方法,來完成 URL 跳轉而無須從新加載頁面。(須要特定瀏覽器支持)hash 和 history 兩種模式都是基於瀏覽器自身的屬性,vue-router
只是利用了這兩個特性(底層仍是瀏覽器提供的接口)來實現前端路由。前端
通常來講,兩種模式都是能夠的。除非在乎不太漂亮的 #
,只能選擇 history。vue
這兩種模式在開發環境下都沒有什麼太大的問題,可是當部署到生產環境中後,二者有所不一樣。nginx
hash 模式部署沒有什麼問題,只要訪問到服務器上的 index.html,就能夠訪問網站了。
history 模式下,前端的 URL 必須和實際向後端發起請求的 URL 一致,如 http://www.example.com/user/id
。若是後端缺乏對 /user/id
的路由處理,將返回 404 錯誤。web
不過這種模式要玩好,還須要後臺配置支持……因此呢,你要在服務端增長一個覆蓋全部狀況的候選資源:若是 URL 匹配不到任何靜態資源,則應該返回同一個 index.html 頁面,這個頁面就是你 app 依賴的頁面。- Vue-Router
在作「年度帳單」項目的時候,項目部署的時候,用的是 hash 模式。APP安卓端分享出去的連接對於 #
作了特殊處理,encode 轉義成了 %23
,因此路由只能換成 history 的模式。vue-router
所以,現把解決的思路總結下,雖然 官網 上給出瞭解決方案,但在實際的編碼中也遇到了一些問題。後端
當項目在根目錄下部署的時候(如 http://www.example.com/
),vue
的相關文件默認不須要修改,修改的是後端,這裏以 nginx 爲例。api
location / { try_files $uri $uri/ /index.html; }
$uri
就是訪問的 url,不包含 域名
和 querystring
。例如 /test/hello
當訪問 $uri
時,若是存在,則訪問 $uri/
, 不存在就訪問 /index.html
這樣配置好,訪問 http://example.com/
時就能夠訪問到網站了,進入多級目錄後刷新頁面也不會存在問題。瀏覽器
這裏涉及到修改 vue
項目幾個配置文件。
先定義幾個環境bash
http://www.example.com:8080/
home/web/
home/web/h5-year-bill/
http://www.example/h5-year-bill/
http://www.example/h5-year-bill/static/
1. 打包後的靜態資源路徑須要修改
找到 build/config/index.js
,代碼以下:
... build: { ... - assetsPublicPath // 訪問路徑,修改爲絕對路徑 + assetsPublicPath: '/h5-year-bill/' }
2. 路由文件Vue-Router
有一個 base
屬性, 傳送門
base 類型: string 默認值: "/" 應用的基路徑。例如,若是整個單頁應用服務在 /app/ 下,而後 base 就應該設爲 "/app/"
所以,找到 src/router/index.js
,代碼以下:
// 不影響本地開發,兼容性作了處理 const isHistoryMode = process.env.NODE_ENV === 'production' ? { mode: 'history', base: '/h5-year-bill/' } : { mode: 'hash' }; const router = new Router({ ...isHistoryMode, routes });
至此,打包配置的相關修改已所有完成,項目也可以正常訪問。
但仍是會有一個問題,跳轉到某個路由後,刷新頁面,就會出現頁面空白,或者路由不通,此時就要修改 nginx 的配置了。
3. nginx 配置相關修改
nginx部署路徑/conf/nginx.conf
,修改以下:
#h5-year-bill location ^~ /h5-year-bill { root /home/web; index index.html; try_files $uri $uri/ /h5-year-bill/index.html last; }
/h5-year-bill/
就是部署的網站目錄。
這樣幾項配置後,就能夠在子目錄下訪問網站,刷新也沒有問題。