Search code examples
vue.jsvuexvue-router

VueJS get AJAX data before routing / mounting componenents


I want to initialize some base data once before having VueJS does any routing / mounting.

Now I found out about the Global Navigation Guard router.beforeEach. But It triggers not only on the initial load (page load), but every route that is triggered. Now I could put in some sort of if-statement to have the code run only once, but that's not my preferred way of solving this:

// pseudo:
router.beforeEach((to, from, next) => {
    if (state.initialized === false) {
        await store.dispatch(init)
    }

    // the rest of my routing guard logic....
})

I'd prefer not having the if-statement run everytime (knowing it's only going to be true once, and false forever after).

Is there an official way to have (ajax) code run only once, AFTER vue is initialized (so I have access to vuex state, etc.), BEFORE any routing has started.


Solution

  • You can easily perform an asynchronous task before mounting your root Vue instance.

    For example

    // main.js
    import Vue from 'vue'
    import store from 'path/to/your/store'
    import router from 'path/to/your/router'
    import App from './App.vue'
    
    store.dispatch('init').then(() => {
      new Vue({
        store,
        router,
        render: h => h(App)
      }).$mount('#app')
    })
    

    It would be a good idea to show something in index.html while that's loading, eg

    <div id="app">
      <!-- just an example, this will be replaced when Vue mounts -->
      <p>Loading...</p>
    </div>