Redux 核心:Middleware


Posted by s103071049 on 2021-11-23

Redux 核心:Middleware

react 與 redux 是兩個不同的東西。可以直接操作 REDUX 忽略 REACT!

  1. REACT 藉由 STATE 儲存狀態
  2. REDUX 藉由 STORE(一個 JS 物件) 儲存狀態

Redux Toolkit

Redux 的 boilerplate(樣板) 讓人詬病:也就是寫 redux 之前要設置 store、actionType、action、reducer、provider、selector ...,有這麼多的前置作業。

基本設置烙賽多。為了降低 boiler plate,redux 就出了 redux toolkit (RTK)。 RTK 將工具打包好,幫你用一些更簡潔的語法建立 action, reducer ... 之類的東西。底層還是 redux 只是幫你使用更多方便的 function。

tookit 跟 react-redux 還是要進行結合

createSlice 整合了之前的 reducer, action, actionTypes。因為使用了 immer,所以用一些語法進行轉換,就可以用直接去改變的方式去改變他,比方說可以用 push 不用再點點點。依據你的名稱自動產生 action,他會同時是 action 也是 actionTypes

也提供 createReducer, createActions

基本上就是幫你把東西包好,學習一個新的 library 使用

Redux middleware(中間件)

express 發 req 到 express 的 server,經過一系列 express 的 middleware 的轉換最後才發 response 回去。

Redux middleware

action 進到 store 之前,透過 middleware 的轉換。所以如果我的 middleware 可以做非同步,就可以 dispatch 一個 promise 或 fetch 的 funct 出去。他就可以在 middleware 幫我完成 call api 這件事情,然後再把 api 的 response 存到 store 去。

  1. 點 ui
  2. eventHandler dispatch 一個 action
  3. 經過 middleware,在 middleware call api,完成後再用 dispatch 的方式將他送出去,類似 action 的轉換
  4. action 就會到 store 裡面去,經過 reducer 結合產生出新的 state 更新回 ui

Redux thunk

功能:處理 action 用,action 在 redux 裡面只是 js 的物件。但透過 middleware action 可以不只是 obj

好處:action 的操作擴大,他可以先做一些事情再操作 store 裡面的資料。redux thunk 將功能性擴大。

thunk is a funct,透過 thunk 這個 middleware 可以回傳一個 funct,
redux thunk 這個 middleware 就只是幫我執行這個 function,把 dispatch 給我,所以我可以在 function 裡面用 dispatch。

const INCREMENT_COUNTER = 'INCREMENT_COUNTER'

function increment() {
// action is obj
  return {
    type: INCREMENT_COUNTER
  }
}

function incrementAsync() {
// action is funct, redux thunk 幫我執行的 funct
  return dispatch => {
    setTimeout(() => {
      // Yay! Can invoke sync or async actions with `dispatch`
      dispatch(increment())
    }, 1000)
  }
}

我的 actionCreator

const incrementAsync1 = amount => dispatch => {
  setTimeout(() => {
    dispatch(incrementByAmount(amount))
  }, 1000)
} 
function incrementAsync1(amount) {
  return function handle(dispatch) {
    setTimeout(() => {
      dispatch(incrementByAmount(amount))
    }, 1000) // 一秒過後會 dispatch 一個 action
  }
}

function incrementAsync1(amount) {
  return function (dispatch) {
    setTimeout(() => {
      dispatch(incrementByAmount(amount))
    }, 1000) // 一秒過後會 dispatch 一個 action
  }
}
// 裡外一起改成箭頭函式
 const incrementAsync1 = (amount) =>  {
  return  dispatch => {
    setTimeout(() => {
      dispatch(incrementByAmount(amount))
    }, 1000) // 一秒過後會 dispatch 一個 action
  }
}
// 將括號拿掉 return 也拿掉,簡化成一行
 const incrementAsync1 = (amount) => dispatch => {
    setTimeout(() => {
      dispatch(incrementByAmount(amount))
    }, 1000)
  }

原本 action creator 會 return js obj 作為 action,透過 redux thunk return 的會是 funct,redux thunk 會去執行 funct,所以可以達到非同步的目的。
redux thunk 就只是一個執行 funct 的 middleware。與之前的差異在 dispatch 出來的 funct 不是 pure js obj, 他是一個 funct,透過 redux thunk 幫你執行

ex 將 response 寫到 response 的 store 裡面去

 const incrementAsync1 = (amount) => dispatch => {
    fetch(...).then(() => {
      dispatch(setUser(...))
    })
  }

#
#

redux saga 與 redux observable

(學習曲線很陡)

用途:處理一些 side-effect,通常 redux 的 middleware 都是處理一些非同步變同步的東西。

  • thunk:dispatch 的 action 是一個 funct,然後 middleware 幫你執行
  • saga :saga dispatch 的東西一個 action,實際 call api 會在 middleware 那邊
  • observale:dispatch 一個 action,經過處理 call api,api 回來再 dipatch 一個 action 送出。透過這樣去 setResult。action in action out。









Related Posts

用 D3.js v4 看 Pokemon 屬性表

用 D3.js v4 看 Pokemon 屬性表

[http] 不只是簡單的跨域請求 Preflight Request

[http] 不只是簡單的跨域請求 Preflight Request

[week9] 給自己看的 PHP 和 MySQL 溝通

[week9] 給自己看的 PHP 和 MySQL 溝通


Comments