블로그

[테크 콘서트] TECH CONCERT: FRONT END 2019 - 데이터 상태 관리. 그것을 알려주마를 보고 본문

아티클

[테크 콘서트] TECH CONCERT: FRONT END 2019 - 데이터 상태 관리. 그것을 알려주마를 보고

wooluck 2021. 3. 21. 09:26

jQuery 상태 관리

각각의 요소에 dataset으로 상태를 추가해서 관리한다.
이게 왜 문제일까?
요소 A, B, C 가 있다고 하자.
B를 클릭하면 A와 C의 상태를 가져오고 데이터를 조합해서 API를 호출한 뒤 값을 갱신한다고 했을 때,
API의 비동기 적인 결과를 받기 위해 대기하는 중에 A나 C의 상태가 변경이 된다면?
각각의 뷰에서 실시간, 비동기로 변화를 하게 되므로 제어하기가 힘든 상황이 올 수 있고, 결과적으로는 원하지 않는 결과가 나올 가능성이 생기게 된다.

jQuery로 개발하는 경우는 결국 DOM에 상태를 저장하고, 각 요소가 상태를 가지고 있기 때문에 서로 다른 요소의 상태변화 추적이 어려운 문제가 생기게 된다.


AngularJS

AngularJS는 변경이 필요한 대상이 되는 요소가 아닌 출력한 데이터에 초점을 맞추어서 작업을 수행한다.
그러므로 데이터의 값이 변경되면 그에 맞는 출력 작업도 수행이 된다.
AngularJS는 변수의 값만 바꿔줘도 저절로 렌더링이 된다. 도대체 어떤 이유일까?

Angular에서는 서비스, 컨트롤러, 뷰의 3개 영역으로 상태를 관리한다.
그리고 그 형태는 다음과 같다.

SERVICE   |  CONTROLLER   |   VIEW

                LOGIC
LOGIC    --->  -------   --->  VIEW
         |      STATE
----------
         |      LOGIC
STATE    --->  -------   --->  VIEW
                STATE

컨트롤러는 각각 로직과 스테이트를 가지고 있으며, 그리고 그 스테이트의 변화를 기반으로 뷰를 그려주게 된다.
그리고 컨트롤러에서 공통적으로 사용하는 로직을 서비스로 통합하게 된다.

그런데 AngularJS도 jQuery에서 발생했던 상태관리 이슈가 비슷하게 발생하게 된다.
하지만 AngularJS에서는 컨트롤러에서 공통적으로 사용하는 로직을 서비스에 작성하기에 기에 각 요소에 상태를 저장하는 jQuery보다 에러를 추적하는 과정에서 시간 소요가 줄어든다는 장점이 있기 때문이다.


Redux

상태 관리를 할 때, jQuery와 AngularJS 모두 결과적으로 상태변화의 추적에 있어 불편함이 있음.
그래서 이러한 문제들을 개선하기 위해 등장한게 리덕스이며, 그 전에 FLUX와 CQRS를 짚고 넘어가야 한다.

FLUX

리덕스 이전에 FLUX 라는 아키텍처가 있다.
형태는 다음과 같다.

                |---------- ACTION ------
                ▼                       |   
Action ---> Dispatcher ---> Store ---> View

FLUX는 액션에서 뷰로 단방향 흐름의 구조를 가진다.
뷰에서 스토어에 있는 상태를 보여주는 역할을 가지며, 스토어에 상태를 바꾸고 싶다면 뷰에서 디스패처로 액션을 전달하여 스토어의 상태를 업데이트 한다.
기존에는 뷰에서 스토어에 있는 상태를 접근 및 수정했다.
기존의 jQuery와 AngularJS 모두 직접적인 수정을 하게 됐지만 FLUX 아키텍처에서는 그러한 수정을 지양한다.

CQRS (Command and Query Responsibility Segregation)

상태를 읽어오는 것과 상태를 바꾸는 요청을 분리시켜 두는 개념이다.
FLUX에서 뷰는 스토어를 읽어오고 상태를 바꾸는 요청은 Dispatcher에 요청하듯 CQRS도 비슷한 느낌이라고 할 수 있다.
CQRS와 함께 쓰이는 방식으로 이벤트소싱(EventSourcing) 이라는 개념이 있는데 이벤트소싱은 데이터 저장 방법에 관한 개념이며,
이전까지의 환경과는 다르게 이벤트소싱은 발생하는 모든 이벤트를 저장한다.

그리고 위의 FLUX와 CQRS의 개념을 조합해서 만든게 리덕스라고 한다.
형태는 다음과 같다.

                  API
                   ▲
                   |   
    Action ---> Middleware ---> Reducer ---> Store
     ▲                                         |
     |---------------- View --------------------

크게 바뀐 점은 없다. 디스패처가 리듀서로 변경되고, 미들웨어가 추가됐다.
미들웨어는 리듀서가 스토어의 상태를 변경하기 전에 API의 호출이 필요하다면 호출해주는 역할을 한다.
리덕스에서 스토어는 하나의 자바스크립트 오브젝트로 관리가 되며, 이 스토어에 우리가 직접적인 접근을 하지않아도 되게 읽기 전용이고 변경을 해서는 안된다는 규칙을 가진다.
그렇다면 리듀서는 어떻게 수정하는 걸까?
리듀서에서는 스토어의 업데이트가 필요할 때, 새로운 오브젝트를 생성하여 기존의 오브젝트를 교체하는 방식이 된다.
이 때, 기존 오브젝트의 값을 저장하므로 상태변화의 추적이 용이해지며 디버깅이 쉬워지게 된다.

물론 리덕스도 단점은 있다.

 

1. 보일러 플레이트가 많다

간단하게 데이터 하나를 바꾸려고 해도 액션을 만들고, 리듀서를 구현하고, 스토어를 구현하고, API에 요청이 필요하다면 미들웨어도 만들어야 한다.

 

2. 과한 기술

상태관리가 복잡하지 않은 구조의 애플리케이션에서 굳이 구현할 필요가 있을까? 간단한 상태관리만 필요한 경우, 예를 들어 간단한 메모장 같은 것들을 개발할 때는 굳이 쓸 필요가 없다.


참고

앵귤러js : https://docs.angularjs.org/guide/introduction

리덕스 : https://ko.redux.js.org/faq/general#when-should-i-use-redux

플럭스 : https://facebook.github.io/flux/docs/in-depth-overview/

Comments