6
votes

I have an authentication on my nuxt web-app, using the nuxt/auth module. I also use modular vuex stores to handle different states. After I login, everything is fine and I can navigate through the app normally. But when I try to reload the page or access it directly through a URL, the user is not accessible, thus, the whole web-app becomes unusable. I try to access the user object with this.context.rootState.auth.user, which is null after page-reload or direct access. Strangely enough, this only happens in production.

I already tried to add an if-guard, but sadly the getter is not reactive. Probably because it´s a nested object. This is my current getter:

 get someGetter() {
    if (!this.context.rootState.auth.user) {
      return []
    }
    const userId = this.context.rootState.auth.user.id as string
    const arr = []
    for (const item of this.items) {
        // Using userId to add something to arr
    }
    return arr
  }

Is there a way to force nuxt to finish the authentication before initialising the vuex-modules, or to make this getter reactive, so it will trigger again, when the user object is accessible?

This is what my auth-config looks like in nuxt.config.ts:

auth: {
  strategies: {
    local: {
      _scheme: '@/auth/local-scheme',
      endpoints: {
        login: {
          url: '/api/authenticate',
          method: 'post',
          propertyName: false
        },
        logout: { url: '/api/logout', method: 'post' },
        user: { url: '/api/users/profile', propertyName: false }
      }
    },
    // This dummy setting is required so we can extend the default local scheme
    dummy: {
      _scheme: 'local'
    }
  },
  redirect: {
    logout: '/login'
  }
}

EDIT

I resolved this by following Raihan Kabir´s answer. Using vuex-persistedstate in an auth-plugin, which is triggered every time the server renders the page. The plugin saves the userId in a cookie, so the store can use it as a fallback, if the auth-module isn´t ready.

1
Same problem here.Leon Braun

1 Answers

5
votes

The thing is, the vuex clears data on reload/refresh to keep credentials secure. That's what vuex is. If you want to store data for long time without being interrupted after reloading, you should use localstorage for that. But localstorage is not recommended for storing credentials.

If you need only user_id to keep in the vuex, use Cookie instead. And try something like this in your store's index.js file -

export const actions = {
    // This one runs on the beginning of reload/refresh
    nuxtServerInit ({ commit }, { req }) {
        if (req.headers.cookie) {
              const parsed = cookieparser.parse(req.headers.cookie)
              try {
                  // get user id that you would set on auth as Cookie
                  user_id = parsed.uid
              } catch (err) {
                  // error here...
              }
        }

        // perform login and store info on vuex store
        commit('authUserOnReload', user_id)
    },
}

// Define Mutations
export const mutations = {
    authUserOnReload (state, user_id) {
        // perform login here and store user
    }
}