우당탕탕 개발일기
[REDUX] 초간단한 카운터로 Redux-toolkit 연습 본문
redux를 설치했더니 store를 생성하는 createStore에 취소선이 그어져있었다.
최신 버전의 redux가 redux-toolkit을 추천하고 redux-toolkit에서는 createStore가 사용되지 않기 때문이라고 했다.
프로젝트에서도 redux-toolkit을 쓸 예정이라, redux-toolkit을 드디어 배워보기로 했다.
redux로 골머리를 앓았던 기억이 생생하여... 😇 조금 겁이 났으나, 조금 만지작거리고나니 redux보다 훨씬 쉬운 것 같다..!
나는 붕어라서, 내가 했던 거를 기록해보려고 한다.
설치
// NPM
npm install @reduxjs/toolkit
폴더 구조는
📂 src
|-- index.js
|-- App.js
|-- store
|-- store.js
|-- counterSlice.js
일단 UI 먼저 구성하기
// App.js
import React, { useState } from "react";
function App() {
const [value, setValue] = useState("");
function onClickPlus() {
// 1씩 더하기 버튼
}
function onClickMinus() {
// 1씩 빼기 버튼
}
function onIncrease() {
// 입력값만큼 더하기 버튼
}
return (
<div>
<p>현재 숫자는 0입니다.</p>
<button onClick={onClickPlus}>+</button>
<button onClick={onClickMinus}>-</button>
<div>
<input onChange={(e) => setValue(e.target.value)}></input>
<button onClick={onIncrease}>더하기</button>
</div>
</div>
);
}
export default App;
나는 1씩 더하는 +버튼, 1씩 빼는 -버튼, input에 숫자 입력한만큼 더해주는 버튼 총 세가지를 만들었다.
변수명도 막 지은 진짜 초초초간단 컴포넌트
Slice 정의하기
// counterSlice.js
import { createSlice } from "@reduxjs/toolkit";
let initialState = {
now: 0
};
const counterSlice = createSlice({
name: "counter",
initialState,
reducers: {
plus: (state, action) => {
// 1씩 증가하기
state.now += 1;
},
minus: (state, action) => {
// 0 이상일 때, 1씩 감소하기
if (state.now > 0) state.now -= 1;
},
plusInput: (state, action) => {
// 입력값만큼 증가시키기
state.now += Number(action.payload);
}
}
});
export const counterActions = counterSlice.actions; // dispatch 할 때 사용할 actions export
export default counterSlice;
initialState를 정의해주기. (현재값이라는 뜻으로 변수명을 'now'로 했다.)
counterSlice를 정의해주면 되는데, 이 때 counterSlice에는 name, initialState, reducers를 필수로 가져야한다.
store 만들기
// store.js
import { configureStore } from "@reduxjs/toolkit";
import counterSlice from "./counterSlice";
const store = configureStore({
// 여기는 단수형태인 'reducer'!
reducer: {
counter: counterSlice.reducer
}
});
export default store;
store에는 reducer가 필요하므로 import 해 온 counterSlice.reducer를 counter라는 이름으로 넣어줌.
다른 이름의 파일로 slice가 만들어지면 저기다가 추가로 넣어주어야함.
productSlice라는 파일이 생기고 그 안에 createSlice해주면, (변수): productSlice.reducer 이렇게 추가!
index 파일에 Provider로 감싸주기
// index.js
import React from "react";
import ReactDOM from "react-dom/client";
import "./index.css";
import App from "./App";
import reportWebVitals from "./reportWebVitals";
// Provider와 Provider에 연결해줄 store import
import { Provider } from "react-redux";
import store from "./store/store";
const root = ReactDOM.createRoot(document.getElementById("root"));
root.render(
// store라는 이름으로 import 해 온 store 넣어주기
<Provider store={store}>
<App />
</Provider>
);
...
Provider는 state를 어떤 컴포넌트들에게 제공할 지를 정하는 울타리.
상태 관리는 전역적으로 가능해야하니까 최상단 파일(index)에서 Provider로 감싸주기! 그래야 어디에서든 reducer를 쓸 수 있다.
이 때, store를 반드시 정의해주어야 해당 범위 안에서 store에 있는 reducer들을 사용할 수 있다.
dispatch 사용하기
// App.js
import React, { useState } from "react";
import { useSelector, useDispatch } from "react-redux";
import { counterActions } from "./store/counterSlice";
function App() {
const [value, setValue] = useState("");
const number = useSelector((state) => state.counter.now); // 뭘 넣어야할지 잘 모르겠으면 콘솔 찍어보기!
const dispatch = useDispatch();
function onClickPlus() {
dispatch(counterActions.plus());
}
function onClickMinus() {
dispatch(counterActions.minus());
}
function onIncrease() {
dispatch(counterActions.plusInput(value));
}
return (
<div>
<p>현재 숫자는 {number}입니다.</p>
<button onClick={onClickPlus}>+</button>
<button onClick={onClickMinus}>-</button>
<div>
<input onChange={(e) => setValue(e.target.value)}></input>
<button onClick={onIncrease}>더하기</button>
</div>
</div>
);
}
export default App;
counterSlice.js에서 export했던 counterActions를 import 해와서, action type 즉 slice의 reducers에서 함수로 정의했던 action type들을 불러오면 dispatch끝!
개인적으로 이 부분이 제일 심플해서 좋았다!
'What I Learned > etc.' 카테고리의 다른 글
input/text-area 아닌 태그에서 커서 깜빡임 (0) | 2023.04.21 |
---|---|
[Eslint] import 자동 정렬은 Eslint로! (0) | 2023.02.16 |
[VSCode] live server 에러 : Something is went wrong! Please check into Developer Console or report on GitHub. (0) | 2022.12.29 |
[git] 커밋 메시지 컨벤션(Commit Message Convention) (0) | 2022.12.27 |
VS Code 확장 프로그램 (0) | 2022.12.27 |