Search code examples
javascriptvuexnuxt.js

Routing 404's with NuxtJS and Vuex - should components call mutations or can actions return promises?


I am trying to figure out how to handle external validation of my routes in NuxtJS.

Let's say I have a Posts page which loads dynamically

{ path: '/posts/:id?', name: 'posts-id', component: Post }

Then to check if there is an actual post with that given id, I need to call my API and either get the post or handle a 404.

AsyncData gives me this possibility by example below

export default {
  asyncData ({ params, error }) {
    return axios.get(`https://my-api/posts/${params.id}`)
    .then((res) => {
      return { title: res.data.title }
    })
    .catch((e) => {
      error({ statusCode: 404, message: 'Post not found' })
    })
  }
}

However, it sets the data on the component BUT I want this to be set in my Vuex store. This is solved by changing asyncData to fetch and allowing me to directly mutate and call actions. Directly mutating is wrong, but if I use an action I can't handle a 404 error.

So how do I go about doing this?


Solution

  • I overlooked the fact that you could simply return a promise from the action. This allowed me to handle the 404 state in the component itself while keeping my request in my store.


    Post page

    async fetch ({ store, params, error }) {
      await store.dispatch('article/GET', params).catch((e) => {
        error({ statusCode: 404, message: 'Post not found' })
      })
    },
    

    Store Action

    async GET({commit}, params) {
      return new Promise((resolve, reject) => {
        axios.get('/posts/' params[0).then((res) => {
          let data = res.data
          commit('SET', data)
          resolve()
        }).catch((e) => {
          reject(e)
        })
      })
    },