第六步 Vue2 集成全家桶 vue-router vuex axios 和 element-ui

介紹

  • Vue Router
    是Vue.js官方提供的路由管理庫,用于實現(xiàn)前端應(yīng)用的路由功能。它可以將前端路由映射到Vue組件,實現(xiàn)頁面的切換和導(dǎo)航等功能。Vue Router支持嵌套路由款慨、路由參數(shù)、路由守衛(wèi)等高級功能谬莹,能夠滿足各種復(fù)雜的路由需求檩奠。

  • Vuex
    是Vue.js官方提供的狀態(tài)管理庫桩了,用于集中管理應(yīng)用程序中的狀態(tài)。它將應(yīng)用程序中的數(shù)據(jù)存儲在一個全局的store中埠戳,并提供了一些API來改變狀態(tài)和獲取狀態(tài)井誉。Vuex的核心概念包括state(存儲應(yīng)用程序的狀態(tài))、mutations(用于改變狀態(tài)的方法)整胃、actions(用于異步操作和提交mutations的方法)等颗圣。通過Vuex,可以實現(xiàn)狀態(tài)在組件間的共享和管理屁使,提供了更好地組織和協(xié)調(diào)組件間的通信和數(shù)據(jù)流動在岂。

  • Axios
    是一個基于Promise的HTTP客戶端庫,用于在瀏覽器和Node.js中發(fā)起HTTP請求蛮寂。它提供了一系列的API來發(fā)送請求蔽午、攔截請求和響應(yīng)、處理錯誤等酬蹋。Axios支持瀏覽器的XMLHttpRequest和Node.js的http模塊及老,提供了更簡潔、易用和可配置的接口范抓。在Vue.js開發(fā)中骄恶,Axios通常用于與后端API進行通信,發(fā)送異步請求獲取數(shù)據(jù)匕垫。

  • Element UI
    是一套基于 Vue.js 的桌面端 UI 組件庫僧鲁,它提供了豐富的可復(fù)用組件,方便開發(fā)者快速構(gòu)建現(xiàn)代化象泵、美觀的 Web 應(yīng)用程序寞秃。

安裝

項目根目錄下打開終端或命令行工具,運行以下命令來安裝相關(guān)依賴包:

npm install vue-router@3.0.1 vuex@3.0.1 axios element-ui --save

vue-router

1. 在 src/ 目錄下新建 views 目錄单芜。在此目錄中新建一個名為 404.vue 的文件,并添加以下內(nèi)容:
<template>
  <div class="error">
    <div class="imgWrapper">
      <img src="@img/errorPages/404.png" alt="404">
    </div>
  </div>
</template>

<style lang="less" scoped>
  .error {
    display: grid;
    place-items: center;
    height: 100vh;
  }
</style>

404.png 圖片如果未添加會編譯報錯犁柜,找一張圖片放上去或者刪除圖片放入自己的文字即可洲鸠。

2. 在 src/ 目錄下找到并打開 App.vue 文件,用以下內(nèi)容直接覆蓋現(xiàn)有內(nèi)容:
<template>
  <div id="app">
    <router-view></router-view>
  </div>
</template>

<script>
export default {
  name: 'App'
}
</script>

<router-view> 是 Vue Router 提供的組件馋缅,用于在 Vue 應(yīng)用中展示當(dāng)前路由對應(yīng)的組件內(nèi)容扒腕。它作用類似于一個占位符,它定義了一個容器萤悴,在路由切換時瘾腰,會根據(jù)不同的路由匹配,動態(tài)渲染對應(yīng)的組件內(nèi)容覆履。

3. 在 src/ 目錄下新建 router 目錄蹋盆。在此目錄中新建一個名為 index.js 的文件费薄,并添加以下內(nèi)容:
import Vue from 'vue'
import VueRouter from 'vue-router'

Vue.use(VueRouter)

const pages = [
  {
    path: '/home',
    component: (resolve) => require(['@/components/HelloWorld.vue'], resolve)
  },
  {
    path: '/errorPage/404',
    component: (resolve) => require(['@/views/404.vue'], resolve)
  }
]

const router = new VueRouter({
  routes: [
    // 默認路由
    {
      path: '/',
      redirect: '/home'
    },
    // 頁面路由
    ...pages,
    // 沒有匹配的路由重定向到404頁面
    {
      path: '*',
      redirect: '/errorPage/404'
    }
  ]
})

// 路由跳轉(zhuǎn)前
router.beforeEach((to, from, next) => {
  // 可用于攔截導(dǎo)航并執(zhí)行一些操作,例如驗證用戶身份栖雾、權(quán)限控制等楞抡。
  next()
})

// 路由跳轉(zhuǎn)后
router.afterEach((to, from) => {
  window.scrollTo(0, 0) // 每次路由改變滾動條都回到頂部
})

export default router

這段代碼是一個基于Vue Router的路由配置。

以下是對代碼的解釋:

  • Vue.use(VueRouter) 是通過Vue.use()方法來全局注冊 Vue Router 插件析藕,使得我們可以在 Vue 實例中使用 Vue Router 的功能召廷。

  • const pages = [... ] 定義了一個數(shù)組變量pages,用于存儲頁面路由配置账胧。每個頁面路由配置以對象表示竞慢,對象中包括一個路由路徑path和對應(yīng)的組件component
    這里使用了一個按需加載的方式治泥,可以在需要時異步加載組件:
    (resolve) => require(['xxx.vue'], resolve) 表示在路由激活時動態(tài)加載組件筹煮,并將解析后的組件傳遞給resolve回調(diào)函數(shù)。換言之车摄,當(dāng)訪問對應(yīng)的路由路徑時寺谤,路由系統(tǒng)會動態(tài)加載組件并渲染到匹配的路由視圖中。

  • const router = new VueRouter({...}) 是創(chuàng)建一個 Vue Router 實例吮播,并配置其中的路由变屁。在這里,路由配置包含三部分:
    默認路由:將根路徑/重定向到/home路徑意狠。
    頁面路由:使用展開運算符...pages數(shù)組中的頁面路由配置添加到路由配置中粟关。
    沒有匹配的路由重定向到404頁面:當(dāng)用戶訪問不存在的路徑時,將自動重定向到/errorPage/404路徑环戈。

  • router.beforeEach((to, from, next) => {...}) 是路由跳轉(zhuǎn)前的鉤子函數(shù)闷板。在其中可以執(zhí)行一些操作,例如驗證用戶身份院塞、權(quán)限控制等遮晚。在這段代碼中,鉤子函數(shù)邏輯為空拦止,即不執(zhí)行任何操作县遣。

  • router.afterEach((to, from) => {...}) 是路由跳轉(zhuǎn)后的鉤子函數(shù)。在這里汹族,使用window.scrollTo(0, 0)將滾動條位置重置為頂部萧求,以確保每次路由改變時都會回到頂部。

4. 打開 src/main.js 文件顶瞒,掛載到Vue實例:
import router from './router'

new Vue({
  router
})

修改后的代碼如下:

import Vue from 'vue'
import App from './App.vue'
import router from './router'
import '@css/index.less'

// 禁用生產(chǎn)環(huán)境提示
Vue.config.productionTip = false

new Vue({
  router,
  render: (h) => h(App)
}).$mount('#app')

vuex

1. 在 src/ 目錄下新建 store 目錄夸政。在此目錄中新建一個名為 index.js 的文件,并添加以下內(nèi)容:
import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

// 本地存儲-修改
const storageSet = (key, value) => {
  localStorage.setItem(key, JSON.stringify(value))
}

// 本地存儲-獲取
const storageGet = (key) => {
  return JSON.parse(localStorage.getItem(key))
}

export default new Vuex.Store({
  // 數(shù)據(jù)源 使用:this.$store.state.xxx
  state: {
    user: {} // 用戶信息
  },
  // 派生數(shù)據(jù) 使用:this.$store.getters.xxx
  getters: {
    // 獲取當(dāng)前-用戶對象
    GET_USER(state) {
      state.user = storageGet('STORE_USER') || {}
      return state.user
    }
  },
  // 更改數(shù)據(jù)-同步 使用:this.$store.commit('xxx', data)
  mutations: {
    // 保存當(dāng)前-用戶對象
    SET_USER(state, data) {
      state.user = data
      storageSet('STORE_USER', data)
    }
  },
  // mutations裝飾器-異步
  actions: {
  }
})

這段代碼是一個基于 Vue 和 Vuex 的狀態(tài)管理工具的配置榴徐。以下是對代碼的解釋:

  • Vue.use(Vuex) 是通過Vue.use()方法來全局注冊 Vuex 插件守问,使得我們可以在 Vue 實例中使用 Vuex 的功能匀归。

  • const storageSet = (key, value) => {...} 和 const storageGet = (key) => {...} 是兩個輔助函數(shù),用于將數(shù)據(jù)存儲在本地的localStorage中酪碘,并且可以在需要時獲取該數(shù)據(jù)朋譬。

  • new Vuex.Store({...}) 是創(chuàng)建一個 Vuex 的 Store 實例。這個實例將包含 Vuex 的核心架構(gòu)和一些選項來定義應(yīng)用程序的狀態(tài)管理兴垦。

  • state 屬性用于定義倉庫store的初始狀態(tài)徙赢,其中user是一個空對象,用于存儲用戶信息探越。

  • getters 屬性是派生狀態(tài)的計算屬性狡赐,允許我們從倉庫的數(shù)據(jù)中獲取一些衍生狀態(tài)。GET_USER getter用于獲取當(dāng)前用戶對象钦幔。

  • mutations 屬性定義了一些同步方法枕屉,用來修改倉庫的狀態(tài)。在這里鲤氢,只有一個SET_USER mutation方法用于保存當(dāng)前用戶對象搀擂,并同時將其存儲在本地localStorage中。

  • actions 屬性中可以定義一些異步方法卷玉,在需要時執(zhí)行異步操作哨颂,并最終調(diào)用mutations中的方法來修改狀態(tài)。

2. 打開 src/main.js 文件相种,掛載到Vue實例:
import store from './store'

new Vue({
  store
})

修改后的代碼如下:

import Vue from 'vue'
import App from './App.vue'
import router from './router'
import store from './store'
import '@css/index.less'

// 禁用生產(chǎn)環(huán)境提示
Vue.config.productionTip = false

new Vue({
  router,
  store,
  render: (h) => h(App)
}).$mount('#app')

axios

src/目錄下新建 api 目錄威恼。在此目錄中新建一個名為 index.js 的文件,并添加以下內(nèi)容:

import Vue from 'vue'
import axios from 'axios'

// 設(shè)置超時時長
axios.defaults.timeout = '60000'

// request攔截器
axios.interceptors.request.use((config) => {
  return config
}, (error) => {
  return Promise.reject(error)
})

// responese攔截器
axios.interceptors.response.use((res) => {
  return res
}, (error) => {
  return Promise.reject(error)
})

/**
 * 設(shè)置請求header
 * @param {Object} headers
 */
const setHeader = (headers) => {
  for (const key in headers) {
    axios.defaults.headers[key] = headers[key]
  }
}

/**
 * POST請求
 * @param {String} url 地址
 * @param {Object} params 參數(shù)
 * @param {Object} headers headers
 */
export const methodPost = (url, params, headers = {}) => {
  return new Promise((resolve, reject) => {
    setHeader(headers)
    axios.post(url, params).then((response) => {
      resolve(response.data)
    }).catch((error) => {
      reject(error)
    })
  })
}

/**
 * 文件上傳
 * @param {String} url 地址
 * @param {File} file 文件
 */
export const methodUpload = (url, file) => {
  return new Promise((resolve, reject) => {
    const formData = new FormData()
    formData.append('file', file)
    formData.append('currentDate', Date.now())
    axios.post(url, formData, {
      headers: {
        'Content-Type': 'multipart/form-data'
      }
    }).then((response) => {
      resolve(response.data)
    }).catch((error) => {
      reject(error)
    })
  })
}

這段代碼是一個配置了axios 網(wǎng)絡(luò)請求庫的請求攔截器和響應(yīng)攔截器寝并,以及一些封裝的請求方法箫措。
以下是對代碼的解釋:

  • axios.defaults.timeout = '60000' 設(shè)置了axios的默認超時時長為60秒。

  • axios.interceptors.request.use((config) => {...}, (error) => {...}) 是請求攔截器衬潦,用于在發(fā)送請求之前對請求進行一些處理斤蔓。在這里,通過config來獲取請求配置镀岛,可以對請求進行一些修改或處理弦牡,然后返回修改后的請求配置。如果在請求發(fā)送過程中發(fā)生錯誤哎媚,將會被catch到并返回一個rejected狀態(tài)的Promise喇伯。

  • axios.interceptors.response.use((res) => {...}, (error) => {...}) 是響應(yīng)攔截器喊儡,用于在接收到響應(yīng)后對響應(yīng)進行一些處理拨与。在這里,通過res來獲取響應(yīng)數(shù)據(jù)艾猜,可以對響應(yīng)進行一些修改或處理买喧,然后返回修改后的響應(yīng)數(shù)據(jù)捻悯。如果在響應(yīng)過程中發(fā)生錯誤,將會被catch到并返回一個rejected狀態(tài)的Promise淤毛。

  • const setHeader = (headers) => {...} 是一個工具函數(shù)今缚,用于設(shè)置請求的header。將傳入的header參數(shù)遍歷低淡,并將其設(shè)置到axios的默認headers中姓言。

  • export const methodPost = (url, params, headers = {}) => {...} 是一個封裝的POST請求方法。該方法接收一個url蔗蹋、一個params對象和一個可選的headers對象作為參數(shù)何荚,使用axios.post方法發(fā)送POST請求,并返回一個Promise對象猪杭。如果請求成功餐塘,將會將響應(yīng)數(shù)據(jù)作為resolved狀態(tài)返回;如果請求失敗皂吮,將會將錯誤作為rejected狀態(tài)返回戒傻。

  • export const methodUpload = (url, file) => {...} 是一個文件上傳方法。該方法接收一個url和一個file對象作為參數(shù)蜂筹,使用FormDatafile對象附加到請求體中需纳,并將請求發(fā)送到指定的url。同樣狂票,該方法也返回一個Promise對象候齿,在上傳成功時將響應(yīng)數(shù)據(jù)作為resolved狀態(tài)返回,失敗時將錯誤作為rejected狀態(tài)返回闺属。

這些封裝的請求方法可以方便地在應(yīng)用中進行網(wǎng)絡(luò)請求慌盯,并對請求和響應(yīng)進行統(tǒng)一的處理。

通過下面的方式便可引入調(diào)用:

import { methodPost } from '@/api'

methodPost('接口地址', {}).then((res) => {
  // 請求成功
}).catch((err) => {
  // 請求失敗
})

element-ui

1. 打開 src/main.js 文件掂器,掛載到Vue實例:
import Element from 'element-ui'
import "element-ui/lib/theme-chalk/index.css"

// Element掛載到Vue
Vue.$message = Element.Message
Vue.use(Element)

修改后的代碼如下:

import Vue from 'vue'
import Element from 'element-ui'
import 'element-ui/lib/theme-chalk/index.css'

import App from './App.vue'
import router from './router'
import store from './store'
import '@css/index.less'

// 禁用生產(chǎn)環(huán)境提示
Vue.config.productionTip = false

// Element掛載到Vue
Vue.$message = Element.Message
Vue.use(Element)

new Vue({
  router,
  store,
  render: (h) => h(App)
}).$mount('#app')
2. 打開之前創(chuàng)建的 src/api/index.js 文件亚皂,找到以下代碼塊:
// responese攔截器
axios.interceptors.response.use((res) => {
  return res
}, (error) => {
  return Promise.reject(error)
})

在添加 Vue.$message.error(error.toString())代碼, 如下:

// responese攔截器
axios.interceptors.response.use((res) => {
  return res
}, (error) => {
  Vue.$message.error(error.toString())
  return Promise.reject(error)
})

這樣響應(yīng)時的錯誤信息就能通過 Element 的 Message 組件來顯示了。

更多組件的使用方式国瓮,可到 element-ui 官方文檔 中查看灭必。



框架搭建整體流程

點擊下載步驟 1-7 配置完成的完整 Demo

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末乃摹,一起剝皮案震驚了整個濱河市禁漓,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌孵睬,老刑警劉巖播歼,帶你破解...
    沈念sama閱讀 206,311評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異掰读,居然都是意外死亡秘狞,警方通過查閱死者的電腦和手機叭莫,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,339評論 2 382
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來烁试,“玉大人雇初,你說我怎么就攤上這事〖跸欤” “怎么了靖诗?”我有些...
    開封第一講書人閱讀 152,671評論 0 342
  • 文/不壞的土叔 我叫張陵,是天一觀的道長支示。 經(jīng)常有香客問我呻畸,道長,這世上最難降的妖魔是什么悼院? 我笑而不...
    開封第一講書人閱讀 55,252評論 1 279
  • 正文 為了忘掉前任伤为,我火速辦了婚禮,結(jié)果婚禮上据途,老公的妹妹穿的比我還像新娘绞愚。我一直安慰自己,他們只是感情好颖医,可當(dāng)我...
    茶點故事閱讀 64,253評論 5 371
  • 文/花漫 我一把揭開白布位衩。 她就那樣靜靜地躺著,像睡著了一般熔萧。 火紅的嫁衣襯著肌膚如雪糖驴。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,031評論 1 285
  • 那天佛致,我揣著相機與錄音贮缕,去河邊找鬼。 笑死俺榆,一個胖子當(dāng)著我的面吹牛感昼,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播罐脊,決...
    沈念sama閱讀 38,340評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼定嗓,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了萍桌?” 一聲冷哼從身側(cè)響起宵溅,我...
    開封第一講書人閱讀 36,973評論 0 259
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎上炎,沒想到半個月后恃逻,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 43,466評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 35,937評論 2 323
  • 正文 我和宋清朗相戀三年辛块,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片铅碍。...
    茶點故事閱讀 38,039評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡润绵,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出胞谈,到底是詐尸還是另有隱情尘盼,我是刑警寧澤,帶...
    沈念sama閱讀 33,701評論 4 323
  • 正文 年R本政府宣布烦绳,位于F島的核電站卿捎,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏径密。R本人自食惡果不足惜午阵,卻給世界環(huán)境...
    茶點故事閱讀 39,254評論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望享扔。 院中可真熱鬧底桂,春花似錦、人聲如沸惧眠。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,259評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽氛魁。三九已至暮顺,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間秀存,已是汗流浹背捶码。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留或链,地道東北人宙项。 一個月前我還...
    沈念sama閱讀 45,497評論 2 354
  • 正文 我出身青樓,卻偏偏與公主長得像株扛,于是被迫代替她去往敵國和親尤筐。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 42,786評論 2 345

推薦閱讀更多精彩內(nèi)容