web-dev-qa-db-ja.com

vuexストアの状態をクリアする方法は?

Vuexストアでの私の状態は巨大です。

すべてを手動でnullに設定する代わりに、状態のすべてのデータを一度にリセットする方法はありますか?

27
KaliCharan

私はちょうど私のために働く素晴らしいソリューションを見つけました。

const getDefaultState = () => {
  return {
    items: [],
    status: 'empty'
  }
}

// initial state
const state = getDefaultState()

const actions = {
  resetCartState ({ commit }) {
    commit('resetState')
  },
  addItem ({ state, commit }, item) { /* ... */ }
}

const mutations = {
  resetState (state) {
    // Merge rather than replace so we don't lose observers
    // https://github.com/vuejs/vuex/issues/1118
    Object.assign(state, getDefaultState())
  }
}

export default {
  state,
  getters: {},
  actions,
  mutations
}

Vuexモジュールの状態をプロのようにリセットする

素晴らしいソリューションを提供してくれたTaha Shashtariに感謝します。

マイケル、

31

以下のソリューションをもう少し使用した後に更新する

そのため、空のオブジェクト({})でreplaceStateを使用すると、状態の小道具がなくなるため、最終的にブリックの反応性になります。したがって、本質的には、状態のすべてのプロパティを実際にリセットしてから、store.replaceState(resetStateObject)を使用する必要があります。モジュールなしのストアの場合、基本的に次のようなことを行います。

let state = this.$store.state;
let newState = {};

Object.keys(state).forEach(key => {
  newState[key] = null; // or = initialState[key]
});

this.$store.replaceState(newState);

更新(コメントから):1つのモジュールのみをリセット/定義し、残りをそのまま維持する必要がある場合はどうなりますか?

すべてのモジュールをリセットしたくない場合は、必要なモジュールをリセットし、他のリセットを現在の状態のままにしておくことができます。

たとえば、複数のモジュールがあり、aと呼ぶ上記のメソッドを使用して、モジュールresetStateAを初期状態にのみリセットしたいとします。次に、元の状態(すべてのモジュールを含むbefore resetting)を複製します。

var currentState = deepClone(this.state)

ここで、deepCloneは、選択するディープクローン方法です( lodashには良い方法があります )。このクローンの現在の状態はA before resetです。それを上書きしましょう

var newState = Object.assign(currentState, {
  a: resetStateA
});

その新しい状態をreplaceStateで使用します。これには、初期状態のaモジュールを除く、すべてのモジュールの現在の状態が含まれます。

this.$store.replaceState(newState);

元のソリューション

Vuex.storeでこの便利なメソッドを見つけました。次のようにreplaceStateを使用すると、すべての状態をすばやく簡単にクリアできます。

store.replaceState({})

単一のストアまたはモジュールで動作し、すべての状態プロパティの反応性を保持します。 Vuex APIドキュメントページ を参照し、replaceStateのページを見つけます。

モジュール用

ストアをモジュールに置き換える場合、各モジュールに空の状態オブジェクトを含める必要があります。したがって、たとえば、モジュールaおよびbがある場合、次のようにします。

store.replaceState({
  a: {},
  b: {}
})
7
seebiscuit

プロパティごとに初期状態を宣言し、その状態にリセットできます。 state = initialStateを実行したり、反応を失ったりすることはできません。

私が取り組んでいるアプリケーションでそれを行う方法は次のとおりです。

let initialState = {
    "token": null,
    "user": {}
}

const state = Vue.util.extend({}, initialState)

const mutations = {
    RESET_STATE(state, payload) {
       for (let f in state) {
        Vue.set(state, f, initialState[f])
       }
    }
}
5
For the Name

State = {}を実行すると、プロパティの反応性が削除され、ゲッターの突然変異が突然機能しなくなります。

次のようなサブプロパティを持つことができます。

state: {
  subProperty: {
    a: '',
    lot: '',
    of: '',
    properties: '',
    .
    .
    .
  }
}

State.subProperty = {}を実行すると、反応性を失うことなく役立ちます。

状態が大きすぎて、異なるモジュールに分割して、次のようにvuexストアにインポートしないでください。

import Vue from 'vue'
import Vuex from 'vuex'
import authorization from './modules/authorization'
import profile from './modules/profile'

Vue.use(Vuex)

export const store = new Vuex.Store({
  modules: {
    authorization,
    profile
  }
})

今、あなたの個々のファイルに:

// modules/authorization.js
import * as NameSpace from '../NameSpace'
import { someService } from '../../Services/something'

const state = {
  [NameSpace.AUTH_STATE]: {
    auth: {},
    error: null
  }
}

const getters = {
  [NameSpace.AUTH_GETTER]: state => {
    return state[NameSpace.AUTH_STATE]
  }
}

const mutations = {
  [NameSpace.AUTH_MUTATION]: (state, payload) => {
    state[NameSpace.AUTH_STATE] = payload
  },
}

const actions = {
  [NameSpace.ASYNC_AUTH_ACTION]: ({ commit }, payload) => {
    someService.login(payload.username, payload.password)
      .then((user) => {
        commit(NameSpace.AUTH_MUTATION, {auth: user, error: null})
      })
      .catch((error) => {
        commit(NameSpace.AUTH_MUTATION, {auth: [], error: error})
      })
  }
}

export default {
  state,
  getters,
  mutations,
  actions
}

状態をクリアする必要がある場合は、突然変異を実装するだけで済みます。

state[NameSpace.AUTH_STATE] = {
  auth: {},
  error: null
}
3

あなたがどのようなケースを使用しているかはわかりませんが、似たようなことをしなければなりません。ユーザーがログアウトしたら、アプリの状態全体を消去したいので、window.reloadを実行しました。たぶん正確にあなたが求めたものではないかもしれませんが、これがあなたが店をクリアしたい理由であるなら、多分代替案。

2
xenetics

router.go()またはthis.$router.go()を呼び出します

ページが更新され、状態はユーザーが最初にアプリをロードしたときの状態にリセットされます。

1
Amol J

これらの2つの答えに基づいて( #1#2 )実行可能なコードを作成しました。

Vuexのindex.jsの私の構造:

import Vue from 'vue'
import Vuex from 'vuex'
import createPersistedState from 'vuex-persistedstate'

import { header } from './header'
import { media } from './media'

Vue.use(Vuex)

const store = new Vuex.Store({
  plugins: [createPersistedState()],

  modules: {
    header,
    media
  }
})

export default store

各モジュール内で、すべての状態を別々のvar initialStateに移動し、突然変異で関数resetStateを定義する必要があります(以下のmedia.jsのように)。

const initialState = () => ({
  stateOne: 0,

  stateTwo: {
    isImportedSelected: false,
    isImportedIndeterminate: false,

    isImportedMaximized: false,
    isImportedSortedAsc: false,

    items: [],

  stateN: ...
  }
})

export const media = {
  namespaced: true,

  state: initialState, // <<---- Our States

  getters: {
  },

  actions: {
  },

  mutations: {
    resetState (state) {
      const initial = initialState()
      Object.keys(initial).forEach(key => { state[key] = initial[key] })
    },
  }

}

Vueコンポーネントでは、次のように使用できます。

<template>
</template>

<script>
  import { mapMutations } from 'vuex'

  export default {
    name: 'SomeName',

    data () {
      return {
        dataOne: '',
        dataTwo: 2
      }
    },

    computed: {
    },

    methods: {
      ...mapMutations('media', [ // <<---- define module
        'resetState' // <<---- define mutation
      ]),

      logout () {
        this.resetState() // <<---- use mutation
        // ... any code if you need to do something here
      }
    },

    mounted () {
    }
  } // End of 'default'

</script>

<style>
</style>
1
TitanFighter

状態全体をリセットする場合は、組み込みの replaceState メソッドを使用できます。

Index.jsに設定された状態を考えます:

    const state = { user: '', token: '', products: [] /* etc. */ }
    const initialStateCopy = JSON.parse(JSON.stringify(state))

    export const store = new Vuex.Store({ state, /* getters, mutations, etc. */ })

    export function resetState() {
      store.replaceState(initialStateCopy)
    }

次に、vueコンポーネント(または任意の場所)でresetStateをインポートします。

    import { resetState } from '@/store/index.js'

    // vue component usage, for example: logout
    {
      // ... data(), computed etc. omitted for brevity
      methods: {
        logout() { resetState() }
      }
    }
1
hitautodestruct

私自身は上記を読み、解決策を実装しました。あなたも助けることができます!!

すべてのオブジェクトはVueに格納され、observableとして機能します。したがって、値の参照変更/変更の場合、変更される実際の値がトリガーされます。

そのため、resetの状態は初期ストアモジュール値としてコピーである必要があります。

ユーザーからログアウトするとき、コピーとして同じ値を各モジュールに割り当てられるにする必要があります。

これは次のように実現できます。

ステップ1:初期モジュールのコピーを作成します。

// store.ts

// Initial store with modules as an object
export const initialStoreModules = {
    user,
    recruitment,
};

export default new Vuex.Store({
    /**
     * Assign the modules to the store 
     * using lodash deepClone to avoid changing the initial store module values
     */
    modules: _.cloneDeep(initialStoreModules),
    mutations: {
        // reset default state modules by looping around the initialStoreModules
        [types.RESET_STATE](state: any) {
        _.forOwn(initialStoreModules, (value: IModule, key: string) => {
            state[key] = _.cloneDeep(value.state);
        });
        },
    }
});

ステップ2:アクションを呼び出して、状態を初期状態に変更します。

// user_action.ts
const logout = ({ commit }: any) => {
    commit(types.LOGOUT_INIT);
    new UserProxy().logout().then((response: any) => {
      router.Push({
        name: 'login',
      });
      // reset the state
      commit(types.RESET_STATE);
    }).catch((err: any) => {
      commit(types.LOGOUT_FAIL, err);
    });
};
0
Mukundhan

これが私のアプリで動作するソリューションです。 defaultState.jsという名前のファイルを作成しました。

//defaultState.js
//the return value is the same as that in the state
const defaultState = () => {
    return {
       items: [],
       poles: {},
       ...
    }
}

export default defaultState

そして、それを使用したい場所

//anywhere you want to use it
//for example in your mutations.js
//when you've gotten your store object do

import defaultState from '/path/to/defaultState.js'

let mutations = {
    ...,
    clearStore(state){
        Object.assign(state, defaultState())
    },
}

export default mutations

次に、store.jsで

import Vue from 'vue';
import Vuex from 'vuex';

import actions from './actions';
import getters from './getters';
import mutations from './mutations'; //import mutations
import state from './state';

Vue.use(Vuex);


export default new Vuex.Store({
    actions,
    mutations,
    state,
    getters,
});

以上です

0
david oyinbo