В проекте React-Redux люди обычно создают несколько действий и уменьшителей для каждого подключенного компонента.Однако это создает много кода для простых обновлений данных.
Рекомендуется ли использовать одно универсальное действие и редуктор для инкапсуляции всех изменений данных, чтобы упростить и ускорить разработку приложений .
Какие бы были недостатки или потеря производительности при использовании этого метода.Потому что я не вижу существенного компромисса, и это значительно облегчает разработку, и мы можем поместить их все в в один файл! Пример такой архитектуры:
// Say we're in user.js, User page
// state
var initialState = {};
// generic action --> we only need to write ONE DISPATCHER
function setState(obj){
Store.dispatch({ type: 'SET_USER', data: obj });
}
// generic reducer --> we only need to write ONE ACTION REDUCER
function userReducer = function(state = initialState, action){
switch (action.type) {
case 'SET_USER': return { ...state, ...action.data };
default: return state;
}
};
// define component
var User = React.createClass({
render: function(){
// Here's the magic...
// We can just call the generic setState() to update any data.
// No need to create separate dispatchers and reducers,
// thus greatly simplifying and fasten app development.
return [
<div onClick={() => setState({ someField: 1 })}/>,
<div onClick={() => setState({ someOtherField: 2, randomField: 3 })}/>,
<div onClick={() => setState({ orJustAnything: [1,2,3] })}/>
]
}
});
// register component for data update
function mapStateToProps(state){
return { ...state.user };
}
export default connect(mapStateToProps)(User);
Редактировать
Итак, типичная архитектура Redux предлагает создавать:
- Централизованные файлы со всеми действиями
- Централизованные файлы со всеми редукторами
Вопрос в том, почему двухэтапный процесс ?Вот еще одно архитектурное предложение:
Создать 1 набор файлов , содержащий все setXField()
, которые обрабатывают все изменения данных .А другие компоненты просто используют их для запуска изменений.Легко.Пример:
/** UserAPI.js
* Containing all methods for User.
* Other components can just call them.
*/
// state
var initialState = {};
// generic action
function setState(obj){
Store.dispatch({ type: 'SET_USER', data: obj });
}
// generic reducer
function userReducer = function(state = initialState, action){
switch (action.type) {
case 'SET_USER': return { ...state, ...action.data };
default: return state;
}
};
// API that we export
let UserAPI = {};
// set user name
UserAPI.setName = function(name){
$.post('/user/name', { name }, function({ ajaxSuccess }){
if (ajaxSuccess) setState({ name });
});
};
// set user picture URL
UserAPI.setPicture = function(url){
$.post('/user/picture', { url }, function({ ajaxSuccess }){
if (ajaxSuccess) setState({ url });
});
};
// logout, clear user
UserAPI.logout = function(){
$.post('/logout', {}, function(){
setState(initialState);
});
};
// Etc, you got the idea...
// Moreover, you can add a bunch of other User related methods,
// like some helper methods unrelated to Redux, or Ajax getters.
// Now you have everything related to User available in a single file!
// It becomes much easier to read through and understand.
// Finally, you can export a single UserAPI object, so other
// components only need to import it once.
export default UserAPI
Пожалуйста, прочитайте комментарии в разделе кода выше.
Теперь вместо множества действий / диспетчеров / редукторов.У вас есть файл 1, содержащий все необходимое для концепции пользователя . Почему это плохая практика ?IMO, это делает жизнь программиста намного проще , а другие программисты могут просто прочитать файл сверху вниз, чтобы понять бизнес-логику , им не нужно переключаться назад и впередмежду файлами действий / редукторов.Черт, даже redux-thunk
не нужен!И вы даже можете проверить функции по одной.Так что тестируемость не теряется.