Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Understanding State and Getters in Nuxt.js: Getters won't working

i'm new to Vue and Nuxt and i'm building my first website in Universal mode with these framework.

I'm a bit confused on how the store works in nuxt, since following the official documentation i can't achieve what i have in mind.

In my store folder i have placed for now only one file called "products.js", in there i export the state like this:

export const state = () => ({

  mistica: {
    id: 1,
    name: 'mistica'
    }
})

(The object is simplified in order to provide a cleaner explanation)

In the same file i set up a simple getter, for example:

export const getters = () => ({

    getName: (state) => {
      return state.mistica.name
    }
})

Now, according to the documentation, in the component i set up like this:

computed: {
 getName () {
  return this.$store.getters['products/getName']
 }
}

or either (don't know what to use):

computed: {
 getName () {
  return this.$store.getters.products.getName
 }
}

but when using "getName" in template is "undefined", in the latter case the app is broken and it says "Cannot read property 'getName' of undefined"

Note that in the template i can access directly the state value with "$store.state.products.mistica.name" with no problems, why so?

What am i doing wrong, or better, what didn't i understand?

like image 352
sintj Avatar asked Jul 17 '19 10:07

sintj


2 Answers

Using factory function for a state is a nuxt.js feature. It is used in the SSR mode to create a new state for each client. But for getters it doesn't make sense, because these are pure functions of the state. getters should be a plain object:

export const getters = {
  getName: (state) => {
    return state.mistica.name
  }
}

After this change getters should work.


Then you can use the this.$store.getters['products/getName'] in your components.

You can't use this.$store.getters.products.getName, as this is the incorrect syntax.

But to get simpler and more clean code, you can use the mapGetters helper from the vuex:

import { mapGetters } from "vuex";

...

computed: {
  ...mapGetters("products", [
    "getName",
    // Here you can import other getters from the products.js
  ])
}
like image 103
Nina Lisitsinskaya Avatar answered Oct 27 '22 17:10

Nina Lisitsinskaya


Couple of things. In your "store" folder you might need an index.js for nuxt to set a root module. This is the only module you can use nuxtServerInit in also and that can be very handy.

In your products.js you are part of the way there. Your state should be exported as a function but actions, mutations and getters are just objects. So change your getters to this:

export const getters = {
    getName: state => {
      return state.mistica.name
    }
}

Then your second computed should get the getter. I usually prefer to use "mapGetters" which you can implement in a page/component like this:

<script>
import {  mapGetters } from 'vuex'
export default {
  computed: {
    ...mapGetters({
      getName: 'products/getName'
    })
}
</script>

Then you can use getName in your template with {{ getName }} or in your script with this.getName.

like image 42
Andrew1325 Avatar answered Oct 27 '22 18:10

Andrew1325