spring statemachine

46
Spring Statemachine 적용사례 by 구강원

Upload: domaindriven-domaindriven

Post on 15-Jan-2017

1.048 views

Category:

Software


2 download

TRANSCRIPT

Page 1: Spring statemachine

Spring Statemachine 적용사례by 구강원

Page 2: Spring statemachine

State (상태)

Page 3: Spring statemachine

State

“임의의주어진시간에의갖게되는하나의상태를칭한다”

Page 4: Spring statemachine

문을 만들어보아요!

Page 5: Spring statemachine

오늘의 주인공 방문입니다.

Page 6: Spring statemachine

방문 클래스 정의

방문 방문 클래스

Door

+ doOpen() :void

+ doClose() :void

+ doLock() :void

+ doUnlock() :void

+ isWayEmpty() :boolean

Page 7: Spring statemachine

Door

- state :DoorState = Opend

+ doOpen() :void

+ doClose() :void

+ doLock() :void

+ doUnlock() :void

«enumeratio...

DoorState

Opend

Closed

Locked

방문 클래스 + 방문 상태

방문 상태 정의

Page 8: Spring statemachine

방문 상태도

방문 클래스

방문 상태도

Locked

Opened Closed

Initial

doClose [doorWay->IsWayEmpty]

doLockdoUnlock

doOpen

create

Door

- state :DoorState = Opend

+ doOpen() :void

+ doClose() :void

+ doLock() :void

+ doUnlock() :void

«enumeratio...

DoorState

Opend

Closed

Locked

Page 9: Spring statemachine

방문 상태표(State Chart)

방문 상태도

Locked

Opened Closed

Initial

doClose [doorWay->IsWayEmpty]

doLockdoUnlock

doOpen

create

State

Next State

S0

Locked

S1

Opened

S2

Closed

S3

Initial

S0Locked

doUnlock

S1Opened

doCl... do...

S2Closed

doLock doOpen

S3Initial

create

방문 상태표(state chart)

Page 10: Spring statemachine

State MachineDiagram(상태도)

상태도 표기법

Page 11: Spring statemachine

State Machine Diagram

• 사건(Event)에따른상태간전이(Transition) 및 전이조건(Guard) 그리고 상태변경에

따른행위(Action)를정의한다이어그램

• 제어플로우가아닌상태변경과관련된프로세스에적합

• 라이프사이클전체를취급하거나동시동작을기술이필요할때사용

Page 12: Spring statemachine

● entry : 상태진입시실행될액션

● exit : 상태진출시실행될액션

● do : 상태안에서반복실행될처리, 상태이동시중단

State Machine 표기법

Page 13: Spring statemachine

State Machine 표기법

Trigger

● 상태전이가발생(촉발) 하는원인으로보통이벤트라칭한다.

● signal, event, change, passage time 4가지 발생(촉발) 타입

Guard

● 상태이동성립조건, 성립조건이 True일경우만상태전이가가능하다.

Effect

● 상태이동에따른효과, 실행액션Source State Target State

trigger [guard] / effect

Page 14: Spring statemachine

여러가지 State

Pseudo

StateChoice

Page 15: Spring statemachine

상태를 추가 해보세요

Page 16: Spring statemachine

무한 합니다….

말발굽 이중잠금장치 자동잠금장치

Page 17: Spring statemachine

도어락 추가

Locked

+ entry / 도어락 잠김

Opened Closed

+ entry / 도어락 열림

Initial

비밀번호일치 5초후 자동 이벤트 발생

doClose [doorWay->IsWayEmpty]

doLock

doUnlock

doOpen

create

12

도어락추가

Page 18: Spring statemachine

Action 위치

1 2 3

Page 19: Spring statemachine

Action 위치에따른 실행1 2 3

Page 20: Spring statemachine

SpringState Machine

적용사례

Page 21: Spring statemachine

A사 O2O 프로젝트

O2O

이미지출처

Page 22: Spring statemachine

훌륭한 DA 한분이 상태를 잘 정의

O2O주문모델링 - 주문상태

접수구분 - 배정상태 - 수락결과 - 출고유형

1 개월 설계 및 기술 검토

Page 23: Spring statemachine

일반 주문 상태 약 19개

O2O주문모델링 - 주문상태

접수구분 - 배정상태 - 수락결과 - 출고유형

내가 생각 했던 사용 기대용어배정접수,

배정확정,

수락요청수락, 거절,

출고지시,

출고완료….

Page 24: Spring statemachine

공식 용어가 아닌 코드 값으로 대화

10-10

10-20

20-10

30-10

30-20

20-99

....

배정접수,

배정확정,

수락요청수락, 거절,

출고지시,

출고완료….

사용 기대 용어 실제 사용 용어

X

O2O주문모델링 - 주문상태

접수구분 - 배정상태 - 수락결과 - 출고유형

Page 25: Spring statemachine

혼란

Page 26: Spring statemachine

이런느낌?

Page 27: Spring statemachine

생존을 위한 몸부림

A군담당 B군담당(나) C군담당

B군담당(나) B군담당(나)

Page 28: Spring statemachine

상태 코드의 비밀

A군담당 B군담당(나) C군담당

10

20 30 41 50 9030

31

40

상태전이 = 현재 상태 +1 or + 10

Page 29: Spring statemachine

상태도를 그리기 전까지...

-상태전이는다음과같았다.상태전이 = 현재상태 +1 or + 10

-다음 4가지값의조합으로주문상태를식별한다.접수구분 - 배정상태 - 수락결과 - 출고유형

-각상태변경시 entry action, guard 등이다양하게존재

-각개인이이해하는수준이틀리고일치하지않음

A군 B군C군

Page 30: Spring statemachine

갱신! 갱신! 갱신! 상태도 최종 완성

-교환에대한상태도추가

-반품에대한상태도추가

-취소에대한상태도추가

Page 31: Spring statemachine

Implementation(구현)

어떻게?

Page 32: Spring statemachine

껌기계를 만들어 보아요

매진(껌없음)

대기(동전없음) 동전있음

껌배출

Choice

동전입력 [동전없음]

크랭크 돌림/껌내보냄

[남은껌있음]

[남은껌 없음]

껌 꺼냄

껌채움

껌뽑기 기계

Page 33: Spring statemachine

코드가직관적? 이고빠르게결과를낼수있다… 단변화에취약

1안 : 닥 개발

if if if if if... huk huk huk

public void insertQuarter() {

if (state == HAS_QUARTER) {

System.out.println("You can't insert another quarter");

} else if (state == NO_QUARTER) {

state = HAS_QUARTER;

System.out.println("You inserted a quarter");

} else if (state == SOLD_OUT) {

System.out.println("You can't insert a quarter, the machine is sold out");

} else if (state == SOLD) {

System.out.println("Please wait, we're already giving you a gumball");

}

}

public void turnCrank() {

if (state == SOLD) {

System.out.println("Turning twice doesn't get you another gumball!");

} else if (state == NO_QUARTER) {

System.out.println("You turned but there's no quarter");

} else if (state == SOLD_OUT) {

System.out.println("You turned, but there are no gumballs");

} else if (state == HAS_QUARTER) {

System.out.println("You turned...");

state = SOLD;

Page 34: Spring statemachine

코드가깔끔해지고 “If hell” 에서벗어날수있음

하지만각상태별로의존성제약이생김

2안 : State Pattern 적용

public void insertQuarter() {

state.insertQuarter();

}

public void turnCrank() {

state.turnCrank();

state.dispense();

}

깔금 깔금

class HasQuarterState implements State {...

}

class HasQuarterState implements State {...

}

상태로직을담은상태 클래스

Page 35: Spring statemachine

State Pattern

Context

+ request() :void

«interface»

State

+ handle() :void

껌배출

껌매진

동전없음

동전있음

상태를기반으로하는행동을캡슐화하고현재상태에위임한다.

• 객체내부상태가바뀜에따라객체의행동을바꿀수있다.

• OCP(Open Close Principal) 따른다.

(상태를무한증가시킬수있음…)

• 바뀌는부분인상태를캡슐화

• 전략패턴과비슷

Page 36: Spring statemachine

Gumball Class Diagram O2O 주문배정 Class Diagram

O2O State Pattern 적용시...

Page 37: Spring statemachine

3안 SpringState Machine

복잡한 상태를 부탁해

Page 38: Spring statemachine

S2M Feature

Easy to use flat one level state machine for simple use cases.

Hierarchical state machine structure to ease complex state configuration.

State machine regions to provide even more complex state configurations.

Usage of triggers, transitions, guards and actions.

Type safe configuration adapter.

Builder pattern for easy instantiation for use outside of Spring Application context

Recipes for usual use cases

Distributed state machine based on a Zookeeper

State machine event listeners.

Spring IOC integration to associate beans with a state machine.

Page 39: Spring statemachine

S2M Example

Locked

Opened Closed

Initial

doClose [doorWay->IsWayEmpty]

doLockdoUnlock

doOpen

create

Page 40: Spring statemachine

상태머신 요소(상태,이벤트, 가드) 식별

static enum States {

Opend, Closed, Locked

}

static enum Events {

Open, Close, Lock, Unlock

}

@Bean

static Guard<States, Events> isEmptyDoorWay() {

return new Guard<States, Events>() {

@Override

public boolean evaluate(StateContext<States, Events> context) {

return new Random().nextBoolean();

}

};

}

➜ Enum Type 상태 정의

➜ Enum Type 이벤트정의

➜ Guard 즉 상태 전이가능 여부평가

Page 41: Spring statemachine

상태머신 Configuration@Configuration

@EnableStateMachine

public static class Config1 extends EnumStateMachineConfigurerAdapter<States, Events> {

@Override

public void configure(StateMachineStateConfigurer<States, Events> states) throws Exception {

states

.withStates()

.initial(States.Closed)

.states(EnumSet.allOf(States.class));

}

@Override

public void configure(StateMachineTransitionConfigurer<States, Events> transitions) throws Exception {

transitions

.withExternal()

.source(States.Opend).target(States.Closed).event(Events.Close)

.guard(isEmptyDoorWay())

.and()

.withExternal()

.source(States.Closed).target(States.Opend).event(Events.Open);

}

}

➜상태 등록 Config

➜상태 동작(이벤트, 가드) config

Page 42: Spring statemachine

S2M에서 제공하는 상태

States

Hierarchical States

Distributed States

Regions

Transitions

Guards

Actions

Pseudo States

Initial State

Terminate State

History State

Choice State

Fork State

Join State

Page 43: Spring statemachine

도입결과

1.현격히줄어즌코드량(IF문제거)

2.주문상태전이가명확해지고좀비상태가줄어듬정의하지않은상태전이가일어나는현상

3.컴포넌트간역할이명확해짐모든상태변경처리는 S2M이처리… but 일부분은적용하지못하고프로젝트종료

프로젝를겸한 2개월안정화기간동안문제가발생한곳이주로 S2M을적용하지못한곳

Page 44: Spring statemachine

마치며

1.상태머신을적용하기위해선상태도를반드시그립니다.

2. S2M GitHub의 Example을꼭활용하세요

3. S2M 사용시 1.0.2 이상사용하세요@Scope 적용가능

(Spring 4.2이에에서@Scope을사용하기위해약간의수정필요)

Page 45: Spring statemachine

4년전 이맘때쯤... Redmine 일감 상태도

Before After

반복반복반복…

Page 46: Spring statemachine

감사합니다