더하기 버튼을 눌렀을 때 바로 +1을 더하지 않고 3초 기다렸다가 +1이 되도록 미들웨어를 사용해 구현할 수 있다.dispatch(함수) -> 함수실행 -> 함수안에서 diuspatch(객체)
createAsyncThunk api를 사용해 thunk 함수를 생성할 수 있다.
이 api는 첫번째 인자에 action value, 두번째 인자에 함수가 들어간다.
이 함수에 하고싶은 작업들을 구현하면 된다.
두번쨰 들어가는 함수에서도 인자를 꺼낼 수 있는데, 첫번째 인자(arg)는 이 thunk 함수ㅜ가 외부에서 사용되었을 때 넣은 값을 여기에서 조회할 수 있고, 두번째 인자에서는 thunk가 제공하는 여러가지 api 기능들이 담긴 객체를 꺼낼 수 있다.
// thunk 함수는 createAsyncThunk 라는 툴킷 API를 사용해서 생성
// __가 함수 이름에 붙는 이유는 이 함수가 thunk 함수라는 것을 표시하기 위한
// 개인의 convention. 함수의 이름은 본인이 편한 이름으로 명명
export const __addNumber = createAsyncThunk(
"ADD_NUMBER_WAIT",
(arg, thunkAPI)=>{},
);
처음 예시로 했던 3초 기다렸다가 실행하는 함수를 만들어보자.
// src/redux/modules/counterSlice.js
import { createSlice, createAsyncThunk } from "@reduxjs/toolkit";
export const __addNumber = createAsyncThunk(
// 첫번째 인자 : action value
"addNumber",
// 두번째 인자 : 콜백함수
(payload, thunkAPI) => {
setTimeout(() => {
thunkAPI.dispatch(addNumber(payload));
}, 3000);
}
);
const initialState = {
number: 0,
};
const counterSlice = createSlice({
name: "counter",
initialState,
reducers: {
addNumber: (state, action) => {
state.number = state.number + action.payload;
},
minusNumber: (state, action) => {
state.number = state.number - action.payload;
},
},
});
export const { addNumber, minusNumber } = counterSlice.actions;
export default counterSlice.reducer;
함수안에 setTimeout web api를 이용해 3초 지연했다. 그 다음에 thunkAPI 안에 있는 dispatch를 통해 원래 하려고 했던 addNumber라는 action creator를 넣었다.
App.jsx 파일도 봐보자
// src/App.jsx
import React from "react";
import { useState } from "react";
import { useDispatch, useSelector } from "react-redux";
import { minusNumber, __addNumber } from "./redux/modules/counterSlice";
const App = () => {
const dispatch = useDispatch();
const [number, setNumber] = useState(0);
const globalNumber = useSelector((state) => state.counter.number);
const onChangeHandler = (evnet) => {
const { value } = evnet.target;
setNumber(+value);
};
// thunk 함수를 디스패치한다. payload는 thunk함수에 넣어주면,
// 리덕스 모듈에서 payload로 받을 수 있다.
const onClickAddNumberHandler = () => {
dispatch(__addNumber(number));
};
const onClickMinusNumberHandler = () => {
dispatch(minusNumber(number));
};
return (
<div>
<div>{globalNumber}</div>
<input type="number" onChange={onChangeHandler} />
<button onClick={onClickAddNumberHandler}>더하기</button>
<button onClick={onClickMinusNumberHandler}>빼기</button>
</div>
);
};
export default App;
기존에 addNumber 라는 action creator를 dispatch 했다면, 이젠 __addNumber라는 thunk 함수를 dispatch 한다.
createAsyncThunk를 이용한다.createAsyncThunk()의 첫번째 자리에는 action value, 두번째에는 함수가 들어간다.