Redux-reducers
Redux-レデューサー
レデューサーはReduxの純粋な機能です。 純粋な機能は予測可能です。 レデューサーは、Reduxで状態を変更する唯一の方法です。 ロジックと計算を記述できる唯一の場所です。 Reducer関数は、アプリの以前の状態とディスパッチされるアクションを受け入れ、次の状態を計算して新しいオブジェクトを返します。
次のいくつかのことは、レデューサー内で実行しないでください-
- 関数の引数の突然変異
- API呼び出しとルーティングロジック
- 非純粋関数の呼び出し Math.random()
以下は、レデューサーの構文です-
(state,action) => newState
アクションクリエーターモジュールで説明したWebページに製品アイテムのリストを表示する例を続けましょう。 その減速機を書く方法を以下に見てみましょう。
const initialState = {
isLoading: false,
items: []
};
const reducer = (state = initialState, action) => {
switch (action.type) {
case 'ITEMS_REQUEST':
return Object.assign({}, state, {
isLoading: action.payload.isLoading
})
case ‘ITEMS_REQUEST_SUCCESS':
return Object.assign({}, state, {
items: state.items.concat(action.items),
isLoading: action.isLoading
})
default:
return state;
}
}
export default reducer;
まず、状態を「initialState」に設定しない場合、Reduxは未定義の状態でreducerを呼び出します。 このコード例では、JavaScriptのconcat()関数が「ITEMS_REQUEST_SUCCESS」で使用されていますが、既存の配列は変更されません。代わりに、新しい配列を返します。
この方法で、状態の突然変異を回避できます。 州に直接書かないでください。 「ITEMS_REQUEST」では、受信したアクションから状態値を設定する必要があります。
レデューサーでロジックを記述し、論理データに基づいて分割できることは既に説明しました。 大規模なアプリケーションを扱う場合、レデューサーを分割してルートレジューサーとして組み合わせる方法を見てみましょう。
ユーザーが製品の注文ステータスにアクセスしてウィッシュリスト情報を表示できるWebページを設計するとします。 異なるレデューサーファイルでロジックを分離し、それらを独立して動作させることができます。 GET_ORDER_STATUSアクションがディスパッチされ、ある注文IDとユーザーIDに対応する注文のステータスを取得すると仮定しましょう。
/reducer/orderStatusReducer.js
import { GET_ORDER_STATUS } from ‘../constants/appConstant’;
export default function (state = {} , action) {
switch(action.type) {
case GET_ORDER_STATUS:
return { ...state, orderStatusData: action.payload.orderStatus };
default:
return state;
}
}
同様に、GET_WISHLIST_ITEMSアクションがディスパッチされ、ユーザーのウィッシュリスト情報を取得すると仮定します。
/reducer/getWishlistDataReducer.js
import { GET_WISHLIST_ITEMS } from ‘../constants/appConstant’;
export default function (state = {}, action) {
switch(action.type) {
case GET_WISHLIST_ITEMS:
return { ...state, wishlistData: action.payload.wishlistData };
default:
return state;
}
}
ReduxのcombinedReducersユーティリティを使用して、両方のレデューサーを結合できるようになりました。 composeReducersは値が異なるリデューサー関数であるオブジェクトを返す関数を生成します。 インデックスリデューサーファイルにすべてのリデューサーをインポートし、それらをそれぞれの名前を持つオブジェクトとして結合できます。
/reducer/index.js
import { combineReducers } from ‘redux’;
import OrderStatusReducer from ‘./orderStatusReducer’;
import GetWishlistDataReducer from ‘./getWishlistDataReducer’;
const rootReducer = combineReducers ({
orderStatusReducer: OrderStatusReducer,
getWishlistDataReducer: GetWishlistDataReducer
});
export default rootReducer;
さて、次のようにこのrootReducerをcreateStoreメソッドに渡すことができます-
const store = createStore(rootReducer);