React를 사용하면서 Redux
라는 말을 들어봤을것이다. 필자 또한 그랬다. 그리고 이 단어를 들었을때 항상 꼬리표 처럼 달려 오는 말도 있었다.
엄청 어렵다.
그래서 일까 이것을 배우기 시작전부터 설렘 보다는 두려움이 컸다.
"현재 내가 리액트를 제대로 마스터 하지도 않았는데 이걸 내가 소화 할 수 있을까?" ,"내가 잘할 수 있을까?"
그리고 Redux
의 개념을 배우고 역시나 머리가 터질거 같은 느낌을 받았다.
그치만 이렇게 너무 어렵고 새로운 기술을 배우거나 접목 할때마다 멘토님들이 이야기 해주신 이야기로 생각을 정리한다.
"기술의 명세보다 그 기술이 주고자 하는 가치를 생각하면 보다 쉽게 이해될 수 있다."
쉽게 정리하면 이게 무엇이냐? 라는 것보다 이걸 왜 써야 하는지에 초점을 맞추면 오히려 본질이 쉽게 다가올 수 있다는 뜻이다.
그래서 나같은 사람들한테 처음부터 지레 겁부터 먹은 상태에서 울며 겨자먹기인채로 알아가는 것이 아니라 이걸 왜 알아야하고 왜 써야하는지에 대해 중요성을 알게하고, 그 다음 본론으로 넘어가는게 맞다고 판단하여 이 글을 작성한다.
리덕스가 등장하기전에 프론트엔드에서 데이터 흐름을 관리하는 방식은 MVC
패턴이었다.
MODEL
- 애플리케이션의 정보,데이터를 나타낸다.(데이터베이스, 처음 정의하는 상수, 초기화값, 변수 등) 또한 이러한 DATA, 정보들의 가공을 책임지는 컴포넌트를 말한다.View
- input 텍스트, 체크박스 항목 등과 같은 사용자 인터페이스 요소를 나타낸다. 즉, 데이터 및 객체의 입력, 그리고 보여주는 출력을 담당한다.Controller
- 데이터와 사용자인터페이스 요소들을 잇는 다리역할. 즉, 사용자가 데이터를 클릭하고, 수정하는 것에 대한 "이벤트"들을 처리하는 부분을 뜻한다. MVC
패턴의 특징은 양방향 데이터 흐름이다.
모델이 변경되면 뷰도 변경되고, 사용자에 의해 뷰가 변경되면 모델 또한 변경된다.
MVC 패턴의 장,단점은 아래와 같다.
한개의 모델이 여러 뷰를 조작하고, 한개의 뷰가 여러 개의 모델을 조작한다면 데이터 흐름을 읽기 힘들어진다.
프로젝트가 커질수록 버그를 찾기 어려워지고, 흐름을 추적하는데 많은 시간 소요
이러한 MVC 패턴으로 데이터 흐름을 관리하는데 많은 어려움을 겪고 있었고, 2014년 페이스북에서 이러한 문제의 대안으로 FLUX
라는 새로운 아키텍처 패턴을 개발 하였다.
기존의 애플리케이션과 달리 페이스북은 굉장히 많은 뷰와 모델이 필요했고, 사용자의 인터렉션 또한 기존 서비스 보다 훨씬 많아졌다.
규모가 커지다 보니 수 많은 버그들이 발생하게 되었고, 수 많은 양방향의 데이터 흐름 때문에 버그를 수정하기도 힘들었다.
페이스북의 알람 정보가 제대로 업데이트가 되지 않아 알람표시가 계속 나타났던 문제가 대표적이다.
이런 문제점을 개선하기위해 나온것이 바로 MVC 패턴(양방향 데이터 흐름)의 반대인 단방향 데이터 흐름이 적용되었다.
위에 사진의 순서를 정리하면 아래와 같다.
View
는 MVC패턴과 달리 데이터를 변경시키지 않고 Action
을 넘겨준다.Action
은 반드시 Dispatcher
를 지나게 되고 Dispatcher
를 통해 데이터 변경이 일어난다.View
는 변경된 데이터를 Store
를 통해서 전달 받는다.그럼 Flux 애플리케이션의 각 구성요소에 대해 알아보자.(이 부분은 part.2에서 개념들을 더 자세하게 알 수 있다. )
그렇다면 기존의 패턴(MVC)와 무엇이 다른가?
이러한 단방향 데이터 흐름은 기존 패턴에 있던 '상태의 전이'(뷰와 모델 사이의 데이터 변경이 연결된 수많은 곳으로 따라 변경되는 현상)현상을 없애고 '예측 가능 상태'로 만드는 특징이 있다.
페이스북은 Flux 아키텍처를 발표한 후 Flux에 대한 구현체도 공개했는데, 이 구현체에는 dispatch만 구현되어 있어 완전한 Flux 프레임워크라 부르기엔 다소 무리가 있었다.
그리고 2015년 이 시기에 많은 Flux 구현체들이 나타났는데, 널리 사용되는 것 중 하나가 Redux
이다.
리덕스에는 Flux에는 없는 새로운 구성요소가 생겨났는데, 그것이 바로 Reducer
이다.
리듀서는 Flux에는 없는 Redux에서만 찾을 수 있는 용어이다.
액션은 어떤 일이 일어났는지는 알려주지만 애플리케이션의 상태를 어떻게 바꾸어야 할지는 알려주지 않는데, Redux 프레임워크에서는 리듀서가 이 역할을 담당한다.
간단히 말해 Flux 애플리케이션에서 스토어 객체를 업데이트하는 콜백 함수와 하는 역할은 비슷하다.
(이 부분도 나중에 자세히 설명하기로 한다.)
리덕스에는 반드시 지켜야 하는 3가지 원칙이 있다.
진실은 하나의 소스로부터📢 (Single source of truth)
애플리케이션의 모든 상태는 하나의 스토어 안에 하나의 객체 트리 구조로 저장된다.
데이터의 변경은 Reducer를 통해서 일어나며 그 데이터는 스토어에 저장된다.
기본적으로 리액트에서는 부모 컴포넌트가 자식 컴포넌트에서 데이터(상태)를 넘겨줄 수 있지만, 이 데이터의 원천은 항상 스토어가 된다.
모든 변경 사항의 Store에 기록되기 때문에 데이터 흐름의 원천은 항상 ‘Store’이어야 한다.
상태는 읽기 전용이다. 📢
상태를 변화시키는 유일한 방법은 무슨 일이 벌어지는 지를 묘사하는 액션 객체를 전달하는 방법뿐이다.
View에서 일어나는 이벤트는 직접 데이터(상태)를 변경해서는 안 된다. 이벤트는 Action을 Reducer로 전달할 뿐이다. 데이터의 변경은 Reducer만 할 수 있다. Reducer 이외의 공간에서는 데이터(상태)는 읽기모드인 것이다.
변화는 순수 함수로 작성되어야 한다. 📢
액션에 의해 상태 트리가 어떻게 변화하는 지를 지정하기 위해 프로그래머는 순수 리듀서를 작성해야 한다.
이러한 순수 함수의 특징의 순수 Reducer는 3가지 특징을 더 갖는다.