Search results for '상태 관리'

Angular State Management (NGXS) Code

2018. 9. 22. 23:04

오늘은 지난 글에서 소개했던 ngxs의 코드를 살펴보겠습니다.


아래와 같은 순서로 만들어 가게 되는데요.


1. Action 추가 (소비 내역 추가)

2. State 추가 (하루 소비 내역)

3. Select 추가 (component에서 하루 소비 내역 조회)


1. Action 추가


action은 데이터를 변경하는 동작을 말합니다.

소비 내역을 추가하는 action을 정의하였습니다.

(저는 가계부를 만드는 개인 프로젝트 진행중입니다.)

import { Consumption } from "../domain/consumption";

export class AddConsumption {
    static readonly type = '[Budget Page] Add Consumption';
    constructor(public consumption: Consumption) {}
}

지난 번 생성한 Consumption 도메인을 활용합니다.


type에는 어떠한 action인지 설명을 적어줍니다.

ngxs 공식 페이지에서는 아래와 같은 규칙을 권장합니다.

- 명령이 수행되는 맥락 (ex: [User API],[Product Page])

- 행위를 설명하는 동사 (ex: Get, Add, Delete)

- 행위의 대상 Entity (ex: User, Product)


constructor는 추가할 consumption을 인자로 받습니다.


즉, 설명과 Action이 수행될 metadata를 정의해주는 것입니다.


2. State 추가


State의 이름과 기본값, action의 실제 동작을 정의합니다.

ngxs 코드의 가장 핵심 부분이라고 볼 수 있습니다.


State는 @State라는 annotation을 사용하여 정의합니다.

import { Action, State, StateContext } from '@ngxs/store';
import { DailyExpense } from '../domain/dailyExpense';
import { AddConsumption } from './budget.actions';

@State({
    name: 'dailyExpense',
    defaults: {
        datetime: new Date(),
        consumptions: [],
    }
})
export class DailyExpenseState {
    @Action(AddConsumption)
    addConsumption(context: StateContext, action:AddConsumption){
        const state = context.getState();
        context.setState({
            ...state,
            consumptions: [
                ...state.consumptions,
                // this is the new consumption instance that we add
                action.consumption,
            ],
        });
    }
}

name은 Store에서 State를 구분하는 역할을 합니다.

따라서 유일(Unique)한 이름을 부여해야만 합니다.


기본값은 날짜와 소비내역 배열로 하였습니다.


State class에는 action과 dependency를 정의합니다.

저는 아직 dependency는 정의하지 않았구요.

action만 정의하였습니다.


Action 추가에서 action의 class를 만들었죠.

실제 수행되는 코드는 State안에 있습니다.

@Action annotation을 사용합니다.

context와 action을 인자로 받는 method를 만듭니다.

context에는 ngxs Store에 저장된 State가 담겨있습니다.

그것을 가져와서 action을 수행합니다.


3. Select 활용


이제 실제로 Component에서 State를 활용해보겠습니다.

먼저 app.module.ts에 import를 해주어야합니다.

...
import { NgxsModule } from '@ngxs/store';
import { DailyExpenseState } from './budget/budget.state';

@NgModule({
  declarations: [
    ...
  ],
  imports: [
    ...
    NgxsModule.forRoot([
      DailyExpenseState
    ])
  ],
  bootstrap: [AppComponent]
})
export class AppModule { }

ngxs 모듈에 정의한 State를 넣어주었습니다.


다음은 State를 사용할 Component의 코드를 보겠습니다.

...
import { Store, Select } from "@ngxs/store";
import { Observable } from 'rxjs';

@Component({
    ...
})
export class BudgetComponent implements OnInit {
    ...
    // ngxs select
    @Select(state => state.dailyExpense) dailyExpense$: Observable<DailyExpense>;

    // ngxs store dependency injection
    constructor(private store: Store) { }

    ngOnInit() {
        this.balance = this.budget;
        this.date = new FormControl(new Date());

        this.dailyExpense$.subscribe((dailyExpense) => {
            // using state data
            ...
        })
    }

    // using ngxs action 
    addConsumption(consumption: Consumption) {
        this.store
            .dispatch(new AddConsumption(consumption));;
    }
}

State를 조회하기 위해 @Select annotation을 사용합니다.

State중 가져올 값을 lambda 형태로 정의해주면 됩니다.

그리고 저장할 변수값을 정하죠. 

보통 $를 붙여서 state임을 표시합니다. 


타입을 보면 아시겠지만 state는 rxjs의 Observable 입니다.

따라서 subscribe하면 값이 화면에 동적으로 반영되죠.


state를 변경할 때는 설명드린바와 같이 action을 사용합니다.

action을 사용할 때에는 생성자에 주입한 Store를 이용합니다.

Store에 action 객체를 생성하여 dispatch하는 형태입니다.


복잡해보이지만 천천히 살펴보시면 쉽게 이해가 되실 겁니다.

지난 포스팅의 ngxs의 개념이 도움이 되실거에요.

(http://dschci.tistory.com/111)


아래는 ngxs를 기반으로 동작하는 화면입니다.


ngxs를 활용한 화면 예제


다음에는 동작화면의 Material Form에 대해 알아볼게요.

진행하는 작업은 github에서 보실 수 있습니다.


소스주소: https://github.com/jsrho1023/account-book

'IT Tech > Angular' 카테고리의 다른 글

Angular Forms (Validation)  (0) 2018.10.14
Angular Forms (Simple)  (0) 2018.10.07
Angular State Management (NGXS)  (0) 2018.09.15
Npm 거슬리는 pacakge-lock.json?  (2) 2018.09.02
Angular 업데이트(Update from 5 to 6)  (0) 2018.05.19

TechTrip IT Tech/Angular

Angular State Management (NGXS)

2018. 9. 15. 22:57

지난 번에는 Service를 만들어 비즈니스 로직을 분리해봤습니다.


원래 Service에 RxJS를 더해 직접 구현하려다가

(Angular 기본접근법은 그렇습니다) 

조금 변경하여 State Management 라이브러리를 도입하기로 하였습니다.

Application 복잡도는 낮지만 배움과 재미를 위한 개발이라서요.


라이브러리는 많은 선배 개발자들의 고민을 바탕으로 하고 있습니다.

그렇게 만들어진 좋은 구조를 익혀가는 것도 의미가 있다고 생각되었어요.


Angular의 State Management를 생각하면 먼저 떠오르는 것은 ngrx입니다.

하지만 저는 ngxs를 써보려고 합니다.


그 이유는 ngxs가 더 Angular 답기 때문입니다.


ngrx의 출발은 Angular가 아닌 React입니다.

React는 Redux라는 State Management 라이브러리를 가지고 있습니다. 

 ※ React는 Facebook에서 만든 Front-End Library

Redux를 Angular로 가져온 것이 바로 ngrx 입니다.

잘 사용하려면 먼저 Redux를 이해할 필요가 있습니다.

Redux를 이해하려면 React의 라이프사이클에 익숙해야하죠.

즉, Learning Curve가 높을 수 있습니다.


그에 반해 ngxs는 ngrx보다는 새로운 angular 전용 라이브러리입니다.


오늘은 ngxs의 간단한 소개를 할까 합니다.

ngxs는 4가지 중요한 개념이 있습니다.

(다른 State Management 라이브러리도 비슷한 개념을 가집니다.)


먼저 doc site의 설명을 그대로 가져오면 아래와 같습니다.

State: state를 정의하는 class

Action: 수행하는 action과 metadata에 대한 정보가 담긴 class 

Selects: Store에서 state의 일부를 가져오는 function

Store: state의 저장소이자, action, select를 관리하는 전역 객체


네 이해 안되실거에요. 저도 그렇습니다.


제가 작업하면서 개념적으로 이해한 것은 아래와 같습니다.

State: Angular Component가 화면에 보여줘야하는 데이터

Action: 서버와 통신(비동기)하고 데이터를 변경하는 역할

Selects: 데이터를 Angular Component에게 가져오는 역할

Store: State를 저장, action과 select를 관리/참조하는 중심


저는 머리 속에 아래 그림처럼 정리하였습니다.

사실 많은 부분을 생략하여 그린 그림입니다.

이해를 돕는 차원에서 봐주시면 될 것 같아요.


ngxs 중요 개념 (많은 부분 생략)


그래서 ngxs 라이브러리를 사용하면 좋은 점은 무엇일까요?

스스로 개발해야했던 부분이 이미 상당부분 구현되어있습니다.

아마도 제가 스스로 만드는 것보다 훨씬 잘 만들어져있겠죠.


서버와의 통신 부분이 구조화/모듈화될 수 있습니다.

코드 관리가 더 수월해지는 장점이 있습니다.


다음 포스팅에서는 실제 코드로 작성된 부분을 공유해볼게요.


정보출처:

ngxs document site - https://ngxs.gitbook.io/ngxs


'IT Tech > Angular' 카테고리의 다른 글

Angular Forms (Simple)  (0) 2018.10.07
Angular State Management (NGXS) Code  (0) 2018.09.22
Npm 거슬리는 pacakge-lock.json?  (2) 2018.09.02
Angular 업데이트(Update from 5 to 6)  (0) 2018.05.19
Angular Service 만들기  (2) 2018.05.13

TechTrip IT Tech/Angular