꾸준한프로그래밍

패스트캠퍼스 챌린지 19일차 - 리덕스 복습 본문

백엔드

패스트캠퍼스 챌린지 19일차 - 리덕스 복습

꾸준이 2021. 9. 24. 23:49

0. 공부 인증

공부 시작 20 : 24

공부 종료 23 : 48

 

오늘은 그동안 공부했던 핵심 기능들을 복습하려고 한다!

사실 진도를 빨리빨리 나가고 싶은데,
복습을 안하면 그동안 공부한 것이 헛것이 될 것같아 오늘은 진도를 나가는 것은 힘들 것 같고,

그 동안 진도를 나갔던 부분을 다시 체크를 해야할 것 같다...

 

그래서 우선 크게 2가지를 복습하려고 한다.

 - 1. 리덕스

 - 2. 소셜 로그인

기능 구현이다.

 

사실 오늘 다 끝낼 수 있을지 모르겠지만....

 

1. 리덕스 구현하기

먼저 리덕스 구조를 다시 파악해보자.

 - 액션, 디스패치, 리듀서, 스토어

가 있다.

 

구현을 하기 위해서 크게 두가지 방법이 있다.

 - 시작할 때부터 템플릿을 활용하는 방법

 - 리액트 앱 생성 후에 리덕스로 추가하는 방법. 

그렇지만 초보자가 보기에는 두번째 방법을 사용하는 것이 이해하기 필요할 수 있다.

 

그래서 프로세스는 

 - 디스패치 함수가 실행되면, 액션이 발생하고, 이를 리듀서를 통해서, 최종적인 상태가 된다!

 

Action 은  { TYPE : "some text" },

Reducer는 function reducer(state, action){ retrun changeState } ,

Store는 단하나가 존재하며, 그 값을 변화시킬 수 있음.

Dispatch는 스토어의 내장 함수로, 액션을 발생시키는 함수이다. dispatch(action)

 

일단 시작하려면,
파일 구조부터 만들자

 - store 폴더를 만들고, 그 쪽에 저장소 / 리듀서를 만들어야 한다.

    - index.js 에서 여러가지 모듈(스토어들)을 불러와서, combineReducers 로 관련 파일들을 출력해줘야한다.

// 여러 리듀서들을 합쳐주자 -> 이것이 루트 리듀서야 ~
import { combineReducers } from "redux";

// 리듀서를 임포트하자
import todo from "./modules/todo";


export default combineReducers({
    // 여러 리듀서들을 넣어줘 :: 서브 리듀서
    todo
})

그리고 모듈 아래, 스토어들은 아래와 같이 작성해줘야 한다.

 

액션 타입 -> 액션 생성 함수 -> 리듀서 (이 형식으로 파일이 출력된다.)

// 우리가 원하는 행동, 데이터의 변화를 각각의 액션으로 할당

// 액션 타입 (문자열) : 액션 타입을 보통 대문자로 하는 것이 관례
// todo/CREATE 가 된 이유는 todo의 CREATE 다 라는 것을 알려주기 위한 목적도 있음.(어디에 속해 있냐라는 것)
// todo/CREARTE 를 통해서 조금이나마 더 가독성이 좋게 그리고 에러 발생율을 줄일 수 있음. 
// 외부의 여러 곳에서 사용될 수도 있음
const CREATE = 'todo/CREATE' // 할 일 목록을 추가하는 액션
const DONE = 'todo/DONE' // 할 일 목록 중에서 완료 처리하는 것



// 액션 생성 함수 
// 무조건 객체 형태임. 그리고 객체에 type이 꼭 필요함.
// 어떤 값을 생성하기 위해서는 데이터가 필요함 그것이 payload라는 변수라고 하자.
// 현재 payload의 값에는 {id : 1, text : "hello"} 처럼 들어가 있음 
export function create (payload) {
    return{
        type : CREATE,
        payload
    }
}

export function done (id) {
    return{
        type : DONE,
        id
    }
}


// 초기 상태를 만들어주자
const initState = {
    list : [{
        id : 0,
        text : "척추 펴기",
        done : true
    },
    {
        id : 1,
        text : "물 마시기",
        done : false
    }],

    listColor : "red" // 이건 그냥 예시
}

// 마지막으로 리듀서라는 것을 만들어보자
// 리듀서 :::: 스토어를 변경 시키는 것
// 함수를 생성할 때에는 state와 action 을 무조건 주어야 함. 
// state의 기본 값으로 initState를 줄 수 있음
export default function todo(state = initState, action){
    // 리듀서 안에는 스위치 문이 들어감
    // 액션 함수의 타입을 가져와서 그것에 맞게 작동함.
    switch(action.type) {
        case CREATE: 
            return{
                // 우선 기본 상태를 가져와야함.
                ...state,
                list : state.list.concat({
                    id : action.payload.id,
                    text : action.payload.text,
                    done : false
                })
            }
        case DONE :
            return{
                ...state,
                list : state.list.map(item => 
                    item.id === action.id 
                    ? {...item, done : true}
                    : item
                )
            }
        default :
            return state // 디폴트에 아무것도 작성하지 않으면 에러가 발생해. 꼭 state를 리턴해줘
        
    }
}

 

그리고 컴포넌트에서 해당 리듀서를 사용하기 위해서는

react-redux에서 Provider 를,

redux 에서는 createStore를 임포트 해줘야해!

 

// 리덕스를 위한 코드들
// 1. 저장소를 만들어줘야함
import { createStore } from "redux"
import rootReducer from './store'

// 2. 프로바이더를 가져오자
import { Provider } from "react-redux"

...
<Provider store = {store}>
	<App />
</Provider>

 

컴포넌트에서 리덕스를 사용하자.

우선, react-redux 에서는 useDispatch, useSelector를, 

제작한 스토어에는 create, done 을 임포트해와서 사용이 가능하다.

 

import { useRef } from 'react'
import { useDispatch, useSelector } from "react-redux"
import { create, done } from '../store/modules/todo'

export default function AllTodoList() {
    const list  = useSelector(state => state.todo.list)
    const inputRef = useRef()
    const dispatch = useDispatch()

    return(
        <section>
            <h1>할 일 목록</h1>
            <div>
                <input type = "text" ref = {inputRef} />
                <button
                    onClick = {() => {
                        dispatch(create({id : list.length, text : inputRef.current.value }))
                    }}
                >확인</button>
            </div>

            <ul>
                {list.map(item => (
                    <li key = {item.id}> {item.text} </li>
                ))}
            </ul>
        </section>
    )
}

 

환급 챌린지 (19/30)

 

 

본 포스팅은 패스트캠퍼스 환급 챌린지 참여를 위해 작성되었습니다.

https://bit.ly/37BpXiC

 

패스트캠퍼스 [직장인 실무교육]

프로그래밍, 영상편집, UX/UI, 마케팅, 데이터 분석, 엑셀강의, The RED, 국비지원, 기업교육, 서비스 제공.

fastcampus.co.kr

#패스트캠퍼스 #패캠챌린지 #직장인인강 #직장인자기계발 #패스트캠퍼스후기 #한번에끝내는Node.js웹프로그래밍초격차패키지