> 只有 Vue Router 2 是與 Vue 2 相互兼容的,所以如果你更新了 Vue ,你也需要更新 Vue Router 。這也是我們在主文檔中將遷移路徑的詳情添加進來的原因。
有關使用 Vue Router 2 的完整教程,請參閱 [Vue Router 文檔](https://router.vuejs.org/zh-cn/)。
## Router 初始化
### `router.start` <sup>替換</sup>
不再會有一個特殊的 API 用來初始化包含 Vue Router 的 app ,這意味著不再是:
``` js
router.start({
template: '<router-view></router-view>'
}, '#app')
```
你只需要傳一個路由屬性給 Vue 實例:
``` js
new Vue({
el: '#app',
router: router,
template: '<router-view></router-view>'
})
```
或者,如果你使用的是運行時構建 (runtime-only) 方式:
``` js
new Vue({
el: '#app',
router: router,
render: h => h('router-view')
})
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>router.start</code> 被調用的示例。</p>
</div>
```
## Route 定義
### `router.map` <sup>替換</sup>
路由現在被定義為一個在 router 實例里的一個 [`routes` 選項](https://router.vuejs.org/zh-cn/essentials/getting-started.html#javascript)數組。所以這些路由:
``` js
router.map({
'/foo': {
component: Foo
},
'/bar': {
component: Bar
}
})
```
會以這種方式定義:
``` js
var router = new VueRouter({
routes: [
{ path: '/foo', component: Foo },
{ path: '/bar', component: Bar }
]
})
```
考慮到不同瀏覽器中遍歷對象不能保證會使用相同的鍵值,這種數組的語法可以保證更多可預測的路由匹配。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>router.map</code> 被調用的示例。</p>
</div>
```
### `router.on` <sup>移除</sup>
如果你需要在啟動的 app 時通過代碼生成路由,你可以動態地向路由數組推送定義來完成這個操作。舉個例子:
``` js
// 普通的路由
var routes = [
// ...
]
// 動態生成的路由
marketingPages.forEach(function (page) {
routes.push({
path: '/marketing/' + page.slug
component: {
extends: MarketingComponent
data: function () {
return { page: page }
}
}
})
})
var router = new Router({
routes: routes
})
```
如果你需要在 router 被實例化后增加新的路由,你可以把 router 原來的匹配方式換成一個包括你新添的加路由的匹配方式:
``` js
router.match = createMatcher(
[{
path: '/my/new/path',
component: MyComponent
}].concat(router.options.routes)
)
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>router.on</code> 被調用的示例。</p>
</div>
```
### `router.beforeEach` <sup>changed</sup>
`router.beforeEach` 現在是異步工作的,并且攜帶一個 `next` 函數作為其第三個參數。
``` js
router.beforeEach(function (transition) {
if (transition.to.path === '/forbidden') {
transition.abort()
} else {
transition.next()
}
})
```
``` js
router.beforeEach(function (to, from, next) {
if (to.path === '/forbidden') {
next(false)
} else {
next()
}
})
```
### `subRoutes` <sup>換名</sup>
出于 Vue Router 和其他路由庫一致性的考慮,重命名為[`children`](https://router.vuejs.org/zh-cn/essentials/nested-routes.html)
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>subRoutes</code> 選項的示例。</p>
</div>
```
### `router.redirect` <sup>替換</sup>
現在用一個[路由定義的選項](https://router.vuejs.org/zh-cn/essentials/redirect-and-alias.html)作為代替。舉個例子,你將會更新:
``` js
router.redirect({
'/tos': '/terms-of-service'
})
```
成像下面的`routes`配置里定義的樣子:
``` js
{
path: '/tos',
redirect: '/terms-of-service'
}
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>router.redirect</code> 被調用的示例。</p>
</div>
```
### `router.alias` <sup>替換</sup>
現在是你進行 alias 操作的[路由定義里的一個選項](https://router.vuejs.org/zh-cn/essentials/redirect-and-alias.html)。舉個例子,你需要在你的`routes`定義里將:
``` js
router.alias({
'/manage': '/admin'
})
```
配置這個樣子:
``` js
{
path: '/admin',
component: AdminPanel,
alias: '/manage'
}
```
如果你需要進行多次 alias 操作,你也可以使用一個數組語法去實現:
``` js
alias: ['/manage', '/administer', '/administrate']
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行<a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a>找到 <code>router.alias</code> 被調用的示例。</p>
</div>
```
### 任意的 Route 屬性 <sup>替換</sup>
現在任意的 route 屬性必須在新 meta 屬性的作用域內,以避免和以后的新特性發生沖突。舉個例子,如果你以前這樣定義:
``` js
'/admin': {
component: AdminPanel,
requiresAuth: true
}
```
你現在需要把它更新成:
``` js
{
path: '/admin',
component: AdminPanel,
meta: {
requiresAuth: true
}
}
```
如果在一個路由上訪問一個屬性,你仍然會通過 meta 。舉個例子:
``` js
if (route.meta.requiresAuth) {
// ...
}
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到任意的路由不在 meta 作用域下的示例。</p>
</div>
```
### URL 中的 Query 數組 [] 語法 <sup>移除</sup>
當傳遞數組給 query 參數時,URL 語法不再是 `/foo?users[]=Tom&users[]=Jerry`,取而代之,新語法是 `/foo?users=Tom&users=Jerry`,此時 `$route.query.users` 將仍舊是一個數組,不過如果在該 query 中只有一個參數:`/foo?users=Tom`,當直接訪問該路由時,vue-router 將無法知道我們期待的 `users` 是個數組。因此,可以考慮添加一個計算屬性并且在每個使用 `$route.query.users` 的地方以該計算屬性代替:
```javascript
export default {
// ...
computed: {
// 此計算屬性將始終是個數組
users () {
const users = this.$route.query.users
return Array.isArray(users) ? users : [users]
}
}
}
```
## Route 匹配
路由匹配現在使用 [path-to-regexp](https://github.com/pillarjs/path-to-regexp) 這個包,這將會使得工作與之前相比更加靈活。
### 一個或者更多的命名參數 <sup>改變</sup>
語法稍微有些許改變,所以以`/category/*tags`為例,應該被更新為`/category/:tags+`。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到棄用路由語法的示例。</p>
</div>
```
## 鏈接
### `v-link` <sup>替換</sup>
`v-link` 指令已經被一個新的 [`<router-link>` 組件](https://router.vuejs.org/zh-cn/api/router-link.html)指令替代,這一部分的工作已經被 Vue 2 中的組件完成。這將意味著在任何情況下,如果你擁有這樣一個鏈接:
``` html
<a v-link="'/about'">About</a>
```
你需要把它更新成:
``` html
<router-link to="/about">About</router-link>
```
注意:`<router-link>`不支持`target="_blank"`屬性,如果你想打開一個新標簽頁,你必須用`<a>`標簽。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>v-link</code> 指令的示例。</p>
</div>
```
### `v-link-active` <sup>替換</sup>
`v-link-active` 也因為指定了一個在 [`<router-link>` 組件](https://router.vuejs.org/zh-cn/api/router-link.html)上的 tag 屬性而被棄用了。舉個例子,你需要更新:
``` html
<li v-link-active>
<a v-link="'/about'">About</a>
</li>
```
成這個寫法:
``` html
<router-link tag="li" to="/about">
<a>About</a>
</router-link>
```
`<a>`標簽將會成為真實的鏈接 (并且可以獲取到正確的跳轉),但是激活的類將會被應用在外部的`<li>`標簽上。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>v-link-active</code> 指令的示例</p>
</div>
```
## 編程導航
### `router.go` <sup>改變</sup>
為了與 [HTML5 History API](https://developer.mozilla.org/en-US/docs/Web/API/History_API) 保持一致性,`router.go` 已經被用來作為 [后退/前進導航](https://router.vuejs.org/zh-cn/essentials/navigation.html#routergon),[`router.push` ](https://router.vuejs.org/zh-cn/essentials/navigation.html#routerpushlocation) 用來導向特殊頁面。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> ,找到 <code>router.go</code> 和 <code>router.push</code> 指令被調用的示例。</p>
</div>
```
## 路由選擇:Modes
### `hashbang: false` <sup>移除</sup>
Hashbangs 將不再為谷歌需要去爬去一個網址,所以他們將不再成為哈希策略的默認選項。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>hashbang: false</code> 選項的示。</p>
</div>
```
### `history: true` <sup>替換</sup>
所有路由模型選項將被簡化成一個單個的[`mode` 選項](https://router.vuejs.org/zh-cn/api/options.html#mode)。你需要更新:
``` js
var router = new VueRouter({
history: 'true'
})
```
成這個寫法:
``` js
var router = new VueRouter({
mode: 'history'
})
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>history: true</code> 選項的示。</p>
</div>
```
### `abstract: true` <sup>替換</sup>
所有路由模型選項將被簡化成一個單個的[`mode` 選項](https://router.vuejs.org/zh-cn/api/options.html#mode)。你需要更新:
``` js
var router = new VueRouter({
abstract: 'true'
})
```
成這個寫法:
``` js
var router = new VueRouter({
mode: 'abstract'
})
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>abstract: true</code> 選項的示例。</p>
</div>
```
## 路由選項:Misc
### `saveScrollPosition` <sup>替換</sup>
它已經被替換為可以接受一個函數的 [`scrollBehavior` 選項](https://router.vuejs.org/zh-cn/advanced/scroll-behavior.html),所以滑動行為可以完全的被定制化處理 - 甚至為每次路由進行定制也可以滿足。這將會開啟很多新的可能,但是簡單的復制舊的行為:
``` js
saveScrollPosition: true
```
你可以替換為:
``` js
scrollBehavior: function (to, from, savedPosition) {
return savedPosition || { x: 0, y: 0 }
}
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移路徑</a> 找到 <code>saveScrollPosition: true</code> 選項的示例。</p>
</div>
```
### `root` <sup>換名</sup>
為了與 [HTML 的`<base>` 標簽](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/base)保持一致性,重命名為 `base`。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移路徑</a> 找到 <code>root</code> 選項的示例。</p>
</div>
```
### `transitionOnLoad` <sup>移除</sup>
由于 Vue 的過渡系統 [`appear` transition control](transitions.html#初始渲染的過渡) 的存在,這個選項將不再需要。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移路徑</a> 找到 <code>transitionOnLoad: true</code> 選項的示例。</p>
</div>
```
### `suppressTransitionError` <sup>移除</sup>
出于簡化鉤子的考慮被移除。如果你真的需要抑制過渡錯誤,你可以使用 [`try`...`catch`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/try...catch) 作為替代。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移指令</a> 找到 <code>suppressTransitionError: true</code> 選項的示例。</p>
</div>
```
## 路由掛鉤
### `activate` <sup>替換</sup>
使用 [`beforeRouteEnter`](https://router.vuejs.org/zh-cn/advanced/navigation-guards.html#組件內的鉤子) 這一組件進行替代。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移路徑</a> 找到 <code>beforeRouteEnter</code> 鉤子的示例。</p>
</div>
```
### `canActivate` <sup>替換</sup>
使用[`beforeEnter`](https://router.vuejs.org/en/advanced/navigation-guards.html#perroute-guard) 在路由中作為替代。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移路徑</a> 找到 <code>canActivate</code> 鉤子的示例。</p>
</div>
```
### `deactivate` <sup>移除</sup>
使用[`beforeDestroy`](../api/#beforeDestroy) 或者 [`destroyed`](../api/#destroyed) 鉤子作為替代。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移路徑</a> 找到 <code>deactivate</code> 鉤子的示例。</p>
</div>
```
### `canDeactivate` <sup>替換</sup>
在組件中使用[`beforeRouteLeave`](https://router.vuejs.org/zh-cn/advanced/navigation-guards.html#組件內的鉤子) 作為替代。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移路徑</a> 找到 <code>canDeactivate</code> 鉤子的示例。</p>
</div>
```
### `canReuse: false` <sup>移除</sup>
在新的 Vue 路由中將不再被使用。
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>canReuse: false</code> 選項的示例。</p>
</div>
```
### `data` <sup>替換</sup>
`$route`屬性是響應式的,所以你可以就使用一個 watcher 去響應路由的改變,就像這樣:
``` js
watch: {
'$route': 'fetchData'
},
methods: {
fetchData: function () {
// ...
}
}
```
```
<div class="upgrade-path">
<h4>升級路徑</h4>
<p>運行 <a href="https://github.com/vuejs/vue-migration-helper">遷移助手</a> 找到 <code>data</code> 鉤子的示例。</p>
</div>
```
### `$loadingRouteData` <sup>移除</sup>
定義你自己的屬性 (例如:`isLoading`),然后在路由上的 watcher 中更新加載狀態。舉個例子,如果使用 [axios](https://github.com/mzabriskie/axios) 獲取數據:
``` js
data: function () {
return {
posts: [],
isLoading: false,
fetchError: null
}
},
watch: {
'$route': function () {
var self = this
self.isLoading = true
self.fetchData().then(function () {
self.isLoading = false
})
}
},
methods: {
fetchData: function () {
var self = this
return axios.get('/api/posts')
.then(function (response) {
self.posts = response.data.posts
})
.catch(function (error) {
self.fetchError = error
})
}
}
```
- 寫在前面
- 基礎
- 安裝
- 介紹
- Vue實例
- 模板語法
- 計算屬性和偵聽器
- Class 與 Style 綁定
- 條件渲染
- 列表渲染
- 事件處理
- 表單輸入綁定
- 組件基礎
- 深入了解組件
- 組件注冊
- Prop
- 自定義事件
- 插槽
- 動態組件 & 異步組件
- 處理邊界情況
- 過渡 & 動畫
- 進入/離開 & 列表過渡
- 狀態過渡
- 可復用性 & 組合
- 混入
- 自定義指令
- 渲染函數 & JSX
- 插件
- 過濾器
- 工具
- 生產環境部署
- 單文件組件
- 單元測試
- TypeScript 支持
- 規模化
- 路由
- 狀態管理
- 服務端渲染
- 內在
- 深入響應式原理
- 遷移
- 從 Vue 1.x 遷移
- 從 Vue Router 0.7.x 遷移
- 從 Vuex 0.6.x 遷移到 1.0
- 更多
- 對比其他框架
- 加入 Vue.js 社區
- 開發團隊