JS Store pattern i Vue

Når man utvikler en JS app med et moderne rammeverk har man i de fleste tilfellene behovet for å lagre og hente ut informasjon på tvers av applikasjonens struktur. Eksempelvis har man ofte behov for å lagre den innloggede brukeren slik at denne kan hentes ut der den trengs.

Ofte vil det også være et behov for at denne dataen skal lagres i nettleseren og ikke forsvinne etter hver økt, til dette brukes ofte localStorage. Da oppstår det et naturlig behov for å synkronisere dataen sentralt lagret i applikasjonen og informasjoen lagret i nettleseren, dette er kode man gjerne vil isolere og kun skrive en gang. Et såkalt store pattern vil kunne hjelpe med dette.

Kjernen i store mønsteret er at man lager et store-objekt som inneholder dataens tilstand og funksjoner som har som ansvar å modifisere denne tilstanden. Det er viktig at man kun bruker disse funksjonene når man skal modifisere data, det gjør det lettere og debugge og forstå i tracet hvor modifiseringen kom fra.

Store-objekt

For store-objectekt lager vi en egen fil som vi kan kalle store.js, her setter vi opp for lagring av en bruker og en token til bruk for autentisering i API-kall:

export default {
    state: {
        user: null,
        token: null
    },

    setToken: function (token) {
        this.state.token = token
    },
    setUser: function (user) {
        this.state.user = user
    },
    clear() {
        this.state.user = null;
        this.state.token = null;
    }
}

Legge til storen i Vue

For å få tilgang til den globale storen overalt importer vi den i main.js og legger den til som en variabel på Vues prototype:

import store from '@/store'

Vue.prototype.$store = store;

Vi kan da bruke storen slik:

this.$store.setToken(.token);
this.$store.setUser(user)

localStorage støtte

For å legge til støtte for localStorage modifiserer vi først store.js ved å innkludere funksjoner som oppdaterer localStoragedataen hver gang vi oppdaterer tilstanden.

export default {
    state: {
        user: null,
        token: null
    },

    setToken: function (token) {
        this.state.token = token
        localStorage.state = JSON.stringify(this.state)
    },
    setUser: function (user) {
        this.state.user = user
        localStorage.state = JSON.stringify(this.state)
    },
    clear() {
        this.state.user = null;
        this.state.token = null;
        localStorage.removeItem('state');
    }
}

Vi må også modifisere main.js til å hente ut data fra localStorage hvis den finnes og opprette et tomt dataobjekt hvis den ikke finnes.

import store from '@/store'

if ( localStorage.hasOwnProperty("state") ) {
    store.state = JSON.parse(localStorage.state);
}
else {
    localStorage.state = JSON.stringify(store.state);
}

Vue.prototype.$store = store;