从 vuex 模块中监听动作/突变

Posted

技术标签:

【中文标题】从 vuex 模块中监听动作/突变【英文标题】:Listen to actions/mutations from within a vuex modules 【发布时间】:2019-04-15 14:07:42 【问题描述】:

我有一个包含多个模块的 vuex 存储,我希望能够在模块内收听“全局”dispatchcommit 调用(也称为操作和突变)。例如,在auth 模块中有登录和注销等操作。每当调度这些操作时,我希望另一个模块 ui 也执行一些操作,例如根据登录用户设置语言。

我知道我可以从 auth 模块的登录和注销操作中分派 ui 操作。但我宁愿让它反过来,这样ui 正在监听auth 中发送的事件(动作和/或突变)。这样我就可以轻松创建副作用,而无需更改“原始”vuex 模块。

也许我需要使用手表,但有些动作不会改变状态,所以我不能总是使用它们。创建插件也是一种选择,但我不想每次想创建这样的副作用时都创建一个额外的插件。

所以我的问题;在一个 vuex 模块中,我如何监听从其他模块发送的动作/突变?

【问题讨论】:

Vue listen for Vuex commit?的可能重复 也许你可以在模块内订阅 谢谢还没有找到,但它建议使用插件。我想知道是否有另一种方式来收听(或订阅)模块中的操作 我想一个插件会为你解决它 将其用作插件是可选的。 Subscribe API 可以在商店实例创建后注册。无法从模块内监听,因为模块被编译到单个存储实例中。 【参考方案1】:

我为自己创建了一个 vuex 插件,它可以触发所有商店中的所有刷新操作。但是你可以做任何我称之为刷新的事情。

插件:

const onModuleAValueChange= (store) => 
    store.watch(
        state => state.moduleA.value,
        (val, oldVal) => 
            // Don't do anything on init state
            if (!oldVal) return;

            // This will trigger all refresh actions on all store. But you can add anything here
            // Essentially does: 
            // store.dispatch(`moduleA/refresh`); 
            // store.dispatch(`moduleB/refresh`); 
            // store.dispatch(`moduleC/refresh`);
            for (let state in store.state) 
                const action = `$state/refresh`;
                // If the store does not have an refresh action ignore
                if (store._actions[action]) store.dispatch(`$state/refresh`);
            

            // Additional action 
            store.dispatch(`moduleC/moduleC_Action`);
        
    );
;

存储核心:

export const store = new Vuex.Store(
    modules: 
        moduleA,
        moduleB,
        moduleC
    ,
    plugins: [onModuleAValueChange]
);

【讨论】:

以上是关于从 vuex 模块中监听动作/突变的主要内容,如果未能解决你的问题,请参考以下文章

Vuex |如何在模块操作中提交全局突变?

注册模块中的vuex未知突变类型

尝试从 Vuex 模块调度操作不起作用。 [vuex] 未知动作类型

Vuex:为啥我们用大写字母编写突变、动作和吸气剂?

在命名空间模块中调用使用方括号(计算机属性名称)定义的 Vuex 操作

如何从 javascript/typescript 模块文件(导入/导出)访问 Vuex 商店?