有什么理由不使用操作从通量存储中获取数据吗?
Is there any reason why not to use actions to get data from a flux store?
我对视图和商店如何在不断变化中相互作用的理解一直在发展。在我看来是三种模式。
此处的代码是为 angular-flux 编写的,但我认为这些想法通常适用于 flux。
模式 1 - 存储 getter 是同步的
// Get my data from the store
data = store.get();
// If store has data then do stuff with it
if (data !== undefined) {
handleUpdate(data);
} else { // load the data from the server
actionCreator.getData();
}
scope.$listenTo(store, "UPDATE", function (data) {
// Listen to updates to the data
handleUpdate(data);
})
模式 2 - 存储 getter 是异步的
// store will call the server and get the data for you if it doesn't have it
store.get().promise().then(handleUpdate(data));
scope.$listenTo(store, "UPDATE", function (data) {
// Listen to updates to the data
handleUpdate(data);
})
模式 3 - 使用操作和事件从存储中获取数据,因此异步处理只发生在一个地方
scope.$listenTo(store, "UPDATE", function (data) {
// Listen to updates to the data
handleUpdate(data);
})
flux.dispatch("GET")
在模式 3 中,商店看起来像这样:
store.handler["GET"] = function () {
if (this.state.data) {
this.emit("GET", this.state.data);
} else {
dataResource.get().$promise.then(function(data) {
flux.dispatch("UPDATE", data);
});
}
}
store.handler["UPDATE"] = function (data) {
this.state.set("data", data);
this.emit("GET", this.state.data);
}
我喜欢模式 3 因为
- 它保留了从商店中的服务器获取数据的复杂性
(至少在使用该商店的所有地方都没有重复)
- 组件只需要在一处处理异步事件
问题是它打破了存储只在它们改变时发出事件的想法,在这种情况下它可能会在它没有改变时发出一个事件,这样请求数据的组件就可以通过事件监听系统。
他们这样做有什么根本上的问题吗,以后会把我赶出去吗?因为它不遵循纯通量方法。
我做了类似于模式3的事情。入口应用程序调用一个动作来初始化api并调用初始数据。 Api 获取数据的操作由 api.store 处理。 api.store 是唯一为请求调用 api 的对象。 api 在收到数据时调用其他操作。这些电话由相关商店处理。
app.js
'use strict';
import React from 'react';
import ReactDom from 'react-dom';
import AppCtrl from './components/app.ctrl.js';
import Actions from './actions/api.Actions';
import ApiStore from './stores/Api.Store';
window.ReactDom = ReactDom;
Actions.apiInit();
ReactDom.render( <AppCtrl />, document.getElementById('react') );
api.store.js
import Reflux from 'reflux';
import Actions from '../actions/api.Actions';
import ApiFct from '../utils/sa.api';
let ApiStoreObject = {
newData: {
"React version": "0.14",
"Project": "ReFluxSuperAgent",
"currentDateTime": new Date().toLocaleString()
},
listenables: Actions,
apiInit() { ApiFct.setData(this.newData); },
apiInitDone() { ApiFct.getData(); },
apiSetData(data) { ApiFct.setData(data); }
}
const ApiStore = Reflux.createStore(ApiStoreObject);
export default ApiStore;
sa.api.js
import request from 'superagent';
import apiActions from '../actions/api.Actions';
import saActions from '../actions/sa.Actions';
module.exports = {
getData() { request.get('/routes/getData').end((err, res) => { this.gotData(res.body); }); },
gotData(data) { saActions.gotData1(data); saActions.gotData2(data); saActions.gotData3(data); },
setData(data) { request.post('/routes/setData').send(data).end((err, res) => { apiActions.apiInitDone(); }) },
};
basic.store.js
import Reflux from 'reflux';
import Actions from '../actions/sa.Actions';
import AddonStore from './Addon.Store';
import MixinStoreObject from './Mixin.Store';
function _GotData(data) { this.data1 = data; BasicStore.trigger('data1'); }
let BasicStoreObject = {
init() { this.listenTo(AddonStore, this.onAddonTrigger); },
data1: {},
listenables: Actions,
mixins: [MixinStoreObject],
onGotData1: _GotData,
onAddonTrigger() { BasicStore.trigger('data2'); },
getData1() { return this.data1; },
getData2() { return AddonStore.data2; },
getData3() { return this.data3; }
}
const BasicStore = Reflux.createStore(BasicStoreObject);
export default BasicStore;
我对视图和商店如何在不断变化中相互作用的理解一直在发展。在我看来是三种模式。
此处的代码是为 angular-flux 编写的,但我认为这些想法通常适用于 flux。
模式 1 - 存储 getter 是同步的
// Get my data from the store
data = store.get();
// If store has data then do stuff with it
if (data !== undefined) {
handleUpdate(data);
} else { // load the data from the server
actionCreator.getData();
}
scope.$listenTo(store, "UPDATE", function (data) {
// Listen to updates to the data
handleUpdate(data);
})
模式 2 - 存储 getter 是异步的
// store will call the server and get the data for you if it doesn't have it
store.get().promise().then(handleUpdate(data));
scope.$listenTo(store, "UPDATE", function (data) {
// Listen to updates to the data
handleUpdate(data);
})
模式 3 - 使用操作和事件从存储中获取数据,因此异步处理只发生在一个地方
scope.$listenTo(store, "UPDATE", function (data) {
// Listen to updates to the data
handleUpdate(data);
})
flux.dispatch("GET")
在模式 3 中,商店看起来像这样:
store.handler["GET"] = function () {
if (this.state.data) {
this.emit("GET", this.state.data);
} else {
dataResource.get().$promise.then(function(data) {
flux.dispatch("UPDATE", data);
});
}
}
store.handler["UPDATE"] = function (data) {
this.state.set("data", data);
this.emit("GET", this.state.data);
}
我喜欢模式 3 因为
- 它保留了从商店中的服务器获取数据的复杂性 (至少在使用该商店的所有地方都没有重复)
- 组件只需要在一处处理异步事件
问题是它打破了存储只在它们改变时发出事件的想法,在这种情况下它可能会在它没有改变时发出一个事件,这样请求数据的组件就可以通过事件监听系统。
他们这样做有什么根本上的问题吗,以后会把我赶出去吗?因为它不遵循纯通量方法。
我做了类似于模式3的事情。入口应用程序调用一个动作来初始化api并调用初始数据。 Api 获取数据的操作由 api.store 处理。 api.store 是唯一为请求调用 api 的对象。 api 在收到数据时调用其他操作。这些电话由相关商店处理。
app.js
'use strict';
import React from 'react';
import ReactDom from 'react-dom';
import AppCtrl from './components/app.ctrl.js';
import Actions from './actions/api.Actions';
import ApiStore from './stores/Api.Store';
window.ReactDom = ReactDom;
Actions.apiInit();
ReactDom.render( <AppCtrl />, document.getElementById('react') );
api.store.js
import Reflux from 'reflux';
import Actions from '../actions/api.Actions';
import ApiFct from '../utils/sa.api';
let ApiStoreObject = {
newData: {
"React version": "0.14",
"Project": "ReFluxSuperAgent",
"currentDateTime": new Date().toLocaleString()
},
listenables: Actions,
apiInit() { ApiFct.setData(this.newData); },
apiInitDone() { ApiFct.getData(); },
apiSetData(data) { ApiFct.setData(data); }
}
const ApiStore = Reflux.createStore(ApiStoreObject);
export default ApiStore;
sa.api.js
import request from 'superagent';
import apiActions from '../actions/api.Actions';
import saActions from '../actions/sa.Actions';
module.exports = {
getData() { request.get('/routes/getData').end((err, res) => { this.gotData(res.body); }); },
gotData(data) { saActions.gotData1(data); saActions.gotData2(data); saActions.gotData3(data); },
setData(data) { request.post('/routes/setData').send(data).end((err, res) => { apiActions.apiInitDone(); }) },
};
basic.store.js
import Reflux from 'reflux';
import Actions from '../actions/sa.Actions';
import AddonStore from './Addon.Store';
import MixinStoreObject from './Mixin.Store';
function _GotData(data) { this.data1 = data; BasicStore.trigger('data1'); }
let BasicStoreObject = {
init() { this.listenTo(AddonStore, this.onAddonTrigger); },
data1: {},
listenables: Actions,
mixins: [MixinStoreObject],
onGotData1: _GotData,
onAddonTrigger() { BasicStore.trigger('data2'); },
getData1() { return this.data1; },
getData2() { return AddonStore.data2; },
getData3() { return this.data3; }
}
const BasicStore = Reflux.createStore(BasicStoreObject);
export default BasicStore;