【发布时间】:2019-05-04 23:53:39
【问题描述】:
我在 Vue 中使用全局事件总线已经有一段时间了——比如const bus = new Vue()。工作正常,但是订阅的处理可能会变得非常冗长。
假设我订阅了组件中的一个事件:
mounted() {
bus.$on('some.event', callback)
}
我必须跟踪回调并在beforeDestroy 中正确处理它。这可以使用全局 mixin 稍微简化,但由于我使用的是 <keep-alive>,因此我必须区分在 mounted 和 activated 回调中进行的订阅。
所以我想我会给 Vuex 一个机会来管理这个,因为观察者是由框架处理的。我提出了以下建议。
只要发布了对象或数组,似乎就可以正常工作。原始数据似乎不会触发反应,尽管被包裹在外部对象中,即{ data: 123 }
我正在寻找有关通知订阅者的替代解决方案。到目前为止我所看到的只是内部的notify 方法,使用起来感觉不太安全。
eventstore.js
import Vue from 'vue'
const state = {
events: {}
}
const actions = {
publish({commit}, payload) {
commit('publish_event', payload)
}
}
const mutations = {
publish_event(state, payload) {
if(!state.events[payload.key]) {
Vue.set(state.events, payload.key, { data: payload.data })
} else {
state.events[payload.key] = { data: payload.data }
}
}
}
const getters = {
events: state => state.events
}
export default {
state,
actions,
mutations,
getters
}
globalmixin.js
methods: {
publish(key, data) {
this.$store.dispatch('publish', { key, data })
}
}
somecomponent.vue
function mapEventGetters(eventKeys) {
return _.reduce(eventKeys, (result, current) => {
result[current] = function() {
return _.get(this, `$store.getters.events.${current}.data`)
}
return result
}, {})
}
computed: {
...mapEventGetters(['foo_bar'])
},
watch: {
'foo_bar'(value) {
console.log(`foo_bar changed to ${value}`)
}
}
【问题讨论】:
-
什么是“内部通知方法”?指的是观察者吗?
-
@RichardMatsen 这是一个例子:github.com/vuejs/vue/blob/dev/src/core/observer/array.js#L42
-
好的,谢谢。这没有出现在 API 文档中,所以我同意使用起来可能很狡猾(
ob = this.__ob__也许它是一个可以改变的内部?) -
我只是在组件中使用计算属性来代替观察者或显式订阅。为了获得对商店项目的深度引用,我将添加一个提取深度值的商店 getter。
-
@RichardMatsen 确实,依赖内部结构似乎是个坏主意 :)
标签: javascript vue.js vuex