vueSSR: 從0到1構建vueSSR項目 --- 路由的構建

vue開發依賴的相關配置

Vue SSR 指南

今天先做客戶端方面的配置,明天再做服務端的部分。
那麼馬上開始吧~

修改部分代碼

腳手架生成的代碼肯定是不適合我們所用的 所以要修改一部分代碼

//App.vue
<template>
    <div id="app">
        <router-view></router-view>
    </div>
</template>

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

<style>
    html,body,#app,#app>*{
        width: 100%;
        height: 100%;
    }
    body{
        font-family: 'Avenir', Helvetica, Arial, sans-serif;
        -webkit-font-smoothing: antialiased;
        -moz-osx-font-smoothing: grayscale;
        text-align: center;
        color: #2c3e50;
        font-size: 16px;
        margin: 0;
        overflow-x: hidden;
    }

    img{
        width: 200px;
    }
</style>

修改main.js
爲什麼要這麼做?爲什麼要避免狀態單例
main.js 是我們應用程序的「通用 entry」。
在純客戶端應用程序中,我們將在此文件中創建根 Vue 實例,並直接掛載到 DOM。
但是,對於服務器端渲染(SSR),責任轉移到純客戶端 entry 文件。
main.js 簡單地使用 export 導出一個 createApp 函數:

import Vue from 'vue';
Vue.config.productionTip = false;
import App from './App.vue';
//router store 實例
//這麼做是避免狀態單例
export function createApp() {

    const app = new Vue({
        //掛載router,store
        render: h => h(App)
    })
    //暴露app實例
    return { app };
}

添加Vue.config.js配置

webpack的入口文件有兩個,一個是客戶端使用,一個是服務端使用。
爲何這麼做?
今天只做客戶端部分。

    src/vue.config.js
    module.exports = {
        css: {
            extract: false//關閉提取css,不關閉 node渲染會報錯
        },
        configureWebpack: () => ({
            entry: './src/entry/client'
        })
    }
    app.$mount('#app')

根目錄創建 entry 文件夾,以及webpack入口代碼

    mdkir  entry
    cd  entry
    創建 入口文件
        client.js 作爲客戶端入口文件。
        server,js 作爲服務端端入口文件。 //先創建不做任何配置
    entry/client.js

        import { createApp } from '../main.js';

        const { app } = createApp();

        app.$mount('#app');

路由和代碼分割

官方說明的已經很清楚了,我就不做過多介紹了,下面直接展示代碼

添加新路由,這裏將存放pages的相關路由

src/pages/router/index.js

/**
 *
 * @method componentPath 路由模塊入口
 * @param  {string} name 要引入的文件地址
 * @return {Object}
 */
function componentPath (name = 'home'){
    return {
        component:() => import(`../${name}/index.vue`)
    }
}

export default [
    {
        path: '/home',
        ...componentPath(),
        children: [
            {
                path: "vue",
                name: "vue",
                ...componentPath('home/vue')
            },
            {
                path: "vuex",
                name: "vuex",
                ...componentPath('home/vuex')
            },
            {
                path: "vueCli3",
                name: "vueCli3",
                ...componentPath('home/vueCli3')
            },
            {
                path: "vueSSR",
                name: "vueSSR",
                ...componentPath('home/vueSSR')
            }
        ]

    }
]

src/router.config.js作爲路由的總配置 易於管理


//路由總配置
    import Vue from 'vue';
    import VueRouter from 'vue-router';

    Vue.use(VueRouter);
    //爲什麼採用這種做法。
    //如果以後有了別的大模塊可以單獨開個文件夾與pages平級
    //再這裏導入即可。這樣易於管理

    // pages
    import pages from './pages/router';

    export function createRouter() {
        return new VueRouter({
            mode: 'history',
            routes: [
                {
                    path: "*",
                    redirect: '/home/vue'
                },
                ...pages
            ]
        })
    }

更新main.js

import Vue from 'vue';
Vue.config.productionTip = false;
import App from './App.vue';
+ import { createRouter } from './router.config.js'
//router store 實例
//這麼做是避免狀態單例
export function createApp() {
+   const router = createRouter()
    const app = new Vue({
+       router,
        render: h => h(App)
    })
    //暴露app,router實例
    return { app, router };
}

更新 client.js
由於使用的路由懶加載,所以必須要等路由提前解析完異步組件,才能正確地調用組件中可能存在的路由鉤子。

// client.js
import { createApp } from '../main.js';

const { app, router } = createApp();

router.onReady( () => {
    app.$mount('#app');
})

最近有點事情 vuex 部分後續再做

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章