iT邦幫忙

2

React 學習筆記_24(認識Redux)

簡介

在開發專案中,隨著專案的大小越來越大與複雜,我們的程式需要管理高於以往的state,這些state可能包含伺服器回應或快取的資料,管理這個不斷變化的state是非常困難的,這時候就需要一個module來統一管理state,讓state的變化更具有可預測性。

從圖看Redux

https://ithelp.ithome.com.tw/upload/images/20200515/20124767c2eyjjTBdS.png
(圖片來源 : Redux + React-Router 的入門教學和配置教程)

  • React Component利用Action Creater建立了一個Action。
  • 利用dispath將action傳送給Store。
  • Store接收到action後會自動調用reducers,並傳入兩個參數(state,action),而reducers會對指定的動作做出回應並且回傳一個新的state。
  • Store將新的state渲染在React Component中。

利用動圖可以更清楚的了解Redux整的作業流程。

(圖片來源 : Redux + React-Router 的入門教學和配置教程)

三大原則

Redux 可以用三個基本的原則來描述:

唯一真相來源

整個應用程式的state會被儲存到一個樹狀的物件並且被放在唯一的一個store裡。

State 是唯讀的

改變state的唯一方式是發出一個action,也就是一個描述將要發生什麼事情的物件。

pure function 的 Reducer

要指定state tree如何藉由action來改變,必須撰寫一個Reducer Function,而這個Fucntion必須是pure function,而pure function的定義可以參考純粹的好,Pure Function 知道這篇文章,裡面對於pure function描述得很清楚。

基礎

Action

Action是從程式中傳遞到store的資訊payload,他是store唯一個數據來源,藉由store.dispatch()來傳替它,action本身是個告訴store該做什麼動作的物件

{
      type: ADD_TODO,
      text: 'Build my first Redux app'
}

上面是一個簡易且標準的action模型,它是一個JavaScript的物件,值得注意的是action中必須擁有一個type屬性,通常被定義成字串,它用來明確的告訴store該做什麼。

Action Creater

Action Creater就是一個產生action的function。

const addTodo = (text) => {
    return{
        type:"ADD_TODO",
        text
    }
};

addTodo("Build my first Redux app"); 

在需要建構不同且數量多的action的時候,action creater便可以體現出其方便性,由於action creater return一個action的物件,所以可以直接使用dispatch(addTodo("Build my first Redux app"))直接傳遞action。


Reducer

Action是描述發生的事情並不會指定程式中的state該如何應對,處理state是reducer的工作,注意!!reducer是一個pure function,它接收兩個參數,state與action然後回傳一個新的State。

const todoApp = (state = {},action) => {
    switch(action.type){ //使用action的type來決定該做什麼動作
        case "TODO_1" : 
            return Object.assign({},state,{
                //...更新的state物件
            })
            
        case "TODO_2" : 
            return Object.assign({},state,{
                //...更新的state物件
            })
            
            //...
            
        default:
            return state; //當沒有合適的動作則回傳原本的state
    } 
};

上面建立了一個簡易且標準的reducers,它可以裡用switch case達到一次判定多種動作的reducers,而我們使用Object.assign為的是不直接寫入原本的state,取而代之的是回傳一個新的物件,以保持舊state的完整度。

在開發專案的時候隨著專案越來越複雜,Reducers也會越來越多越來越複雜,可以以不同功能且互不影響的原則下將reducers拆分成多個小的reducers,而Redux提供了一個utility combineReducers(),他會產生一個function,將每一個值都是不同的reducer function轉換成一個可以傳遞給createStore的單一 reducers function。

const Reacer_1 = (state = {},action) => {
    swtich(action.type){
        case "TODO_1" : 
            return NewState;
            
        //...
        
        defualt :
            return state;
    }
};

const Reacer_2 = (state = {},action) => {
    swtich(action.type){
        case "TODO_1" : 
            return NewState;
            
        //...
        
        defualt :
            return state;
    }
};

const Reducers = combineReducers({
    Reacer_1,
    Reacer_2
})

Store

Store簡單來說就是將action與reducers結合起來的物件,store將會負責以下事件:

  • 管理應用程式狀態
  • 允許藉由getState()取得state
  • 允許藉由dispatch(action)傳遞action已更新State。

注意!!在專案中無論資料處理的邏輯多麼複雜,應該使用combineReducers()將多個reducers function合併成一個,而不是建立多個store。

若已經有了一個reducer後便可以使用redux中的createStore()來建立store。

let store = createStore(Reducers);

參考資料 :
從Redux 的作者學習它
Redux + React-Router 的入門教學和配置教程


尚未有邦友留言

立即登入留言