Java Finite State Machine (FSM) Manager
JFSM์ ์๋ฐ ๊ธฐ๋ฐ์ ๊ฒฝ๋ ์ํ ๋จธ์ (Finite State Machine) ํ๋ ์์ํฌ์ ๋๋ค. ๊ฐ๊ฒฐํ API๋ก ์ํ ์ฒ์ด(transition)๋ฅผ ์ ์ํ๊ณ , ์ฝ๋ฐฑ๊ณผ ์กฐ๊ฑด(EventCondition), ์ง์ฐ ์คํ ๋ฐ ์ฌ์๋(Retry) ๊ฐ์ ์ค๋ฌด ์นํ ๊ธฐ๋ฅ์ ์ ๊ณตํฉ๋๋ค. ๋ฉํฐ ์ค๋ ๋ ๊ธฐ๋ฐ์ ํ์คํฌ ์คํ๊ธฐ(StateTaskManager)๋ฅผ ํตํด ๋น๋๊ธฐ/์ง์ฐ ์ด๋ฒคํธ ์ฒ๋ฆฌ๋ ์ฝ๊ฒ ๊ตฌ์ฑํ ์ ์์ต๋๋ค.
- ์ต์ ์์กด์ฑ, ์์ ์๋ฐ๋ก ๋์
- ๊ฐ๋จํ DSL ์คํ์ผ์ ์ํ ์ฒ์ด ๋ฑ๋ก API
- ์ฒ์ด ์ฑ๊ณต/์คํจ ์ฝ๋ฐฑ, ๋ค์ ์ด๋ฒคํธ ์ฒด์ด๋(nextEvent)
- ์ง์ฐ(delay) ๋ฐ ์ฌ์๋(nextEventRetryCount) ์ง์
- ์กฐ๊ฑด๋ถ ์คํ(EventCondition) ๋ฐ ์ค์ผ์ค๋ง ์ง์
- ๋ฉํฐ ์ค๋ ๋ ํ์คํฌ ์ฒ๋ฆฌ(StateTaskManager)์ ์์ ํ ๋์์ฑ ์ ์ด
flowchart TB
subgraph JFSM["JFSM Core"]
SM["StateManager<br/>- FSM ์ต์์ ๋งค๋์ <br/>- ์ค๋ ๋ํ/ํ์คํฌ๊ด๋ฆฌ<br/>- Handler ๋ฑ๋ก/์กฐํ/์ญ์ "]
SH["StateHandler<br/>- ๋๋ฉ์ธ ๊ทธ๋ฃน(์ ํ) ๋จ์<br/>- ์ํ/์ด๋ฒคํธ/์ ์ด ๋ฑ๋ก API ์ ๊ณต"]
SEM["StateEventManager<br/>- ์ ์ด ํ
์ด๋ธ(Transition) ๊ด๋ฆฌ<br/>- ์ด๋ฒคํธ ์ฒ๋ฆฌ ์คํ ๋ก์ง"]
SU["StateUnit<br/>- ์ค์ ์ํ๋ฅผ ๊ฐ์ง ์ํฐํฐ<br/>(์ธ์
/์ฃผ๋ฌธ/์ฅ๋น ๋ฑ)"]
ST["StateTaskManager<br/>- ๋ฉํฐ ์ค๋ ๋ ํ์คํฌ ์คํ๊ธฐ<br/>- ๋น๋๊ธฐ/์ง์ฐ ์ด๋ฒคํธ ์ฒ๋ฆฌ"]
EC["EventCondition<br/>- ์ ์ด ์คํ ์ ์กฐ๊ฑด ๊ฒ์ฌ"]
CB["CallBack<br/>- ์ ์ด ์ฑ๊ณต/์คํจ ํ์ฒ๋ฆฌ"]
RM["RetryManager<br/>- ์ฌ์๋ ์ ์ฑ
/์ํ ๊ด๋ฆฌ"]
end
SM --> SH
SH --> SEM
SEM --> SU
SEM --> EC
SEM --> CB
SEM --> RM
SM --> ST
ST --> SEM
flowchart TB
IN["์
๋ ฅ: (StateUnit, Event)"] --> H["StateHandler<br/>๋๋ฉ์ธ ๊ทธ๋ฃน ์ ํ"]
H --> EM["StateEventManager<br/>์ ์ด ํ
์ด๋ธ ์กฐํ"]
EM --> COND{"EventCondition<br/>์กฐ๊ฑด ํต๊ณผ?"}
COND -->|์| TRANS["Transition ์คํ<br/>StateUnit ์ํ ๋ณ๊ฒฝ"]
COND -->|์๋์ค| FAILCB["Fail CallBack<br/>์คํจ ํ์ฒ๋ฆฌ"]
TRANS --> SUCCB["Success CallBack<br/>์ฑ๊ณต ํ์ฒ๋ฆฌ"]
SUCCB --> NEXT{"nextEvent ์กด์ฌ?"}
NEXT -->|์๋์ค| DONE["์ข
๋ฃ"]
NEXT -->|์| DELAY{"delay ์ค์ ?"}
DELAY -->|์์| DISPATCH["์ฆ์ ๋ค์ ์ด๋ฒคํธ ๋์คํจ์น"]
DELAY -->|์์| SCHED["StateTaskManager<br/>์ง์ฐ ์ค์ผ์ค๋ง"]
SCHED --> DISPATCH
DISPATCH --> RETRY{"nextEventRetryCount ์ค์ ?"}
RETRY -->|์์| EM2["StateEventManager<br/>๋ค์ ์ด๋ฒคํธ ์ฒ๋ฆฌ"]
RETRY -->|์์| RM["RetryManager<br/>์ฌ์๋ ์ํ/ํ์ ๊ด๋ฆฌ"]
RM --> EM2
EM2 --> COND
sequenceDiagram
autonumber
participant C as Client Code
participant SM as StateManager
participant SH as StateHandler
participant EM as StateEventManager
participant EC as EventCondition
participant SU as StateUnit
participant CB as CallBack
participant ST as StateTaskManager
participant RM as RetryManager
C->>SM: addStateHandler("ATM")<br/>ํธ๋ค๋ฌ ๋ฑ๋ก
C->>SM: getStateHandler("ATM")<br/>ํธ๋ค๋ฌ ์กฐํ
C->>SH: addState(...)<br/>์ ์ด/์ฝ๋ฐฑ/nextEvent/delay/retry ๋ฑ๋ก
C->>SM: addStateUnit(unit)<br/>์ํ ์ ๋ ๋ฑ๋ก
C->>SM: fireEvent(unit, event)<br/>์ด๋ฒคํธ ์คํ(๊ฐ๋
์ )
SM->>SH: ๋๋ฉ์ธ ํธ๋ค๋ฌ๋ก ๋ผ์ฐํ
SH->>EM: ์ ์ด ํ
์ด๋ธ ์กฐํ/์คํ ์์ฒญ
EM->>EC: ์กฐ๊ฑด ๊ฒ์ฌ
alt ์กฐ๊ฑด ํต๊ณผ
EM->>SU: ์ํ ๋ณ๊ฒฝ(Prev/Cur)
EM->>CB: Success CallBack
alt nextEvent ์กด์ฌ
alt delay ์กด์ฌ
EM->>ST: ์ง์ฐ ์คํ ์ค์ผ์ค๋ง
ST-->>EM: (์๊ฐ ํ) nextEvent ์คํ ํธ๋ฆฌ๊ฑฐ
else delay ์์
EM-->>EM: ์ฆ์ nextEvent ์คํ
end
alt retry ์ค์
EM->>RM: ์ฌ์๋ ์ํ ๊ฐฑ์ /๊ฐ์
end
end
else ์กฐ๊ฑด ์คํจ
EM->>CB: Fail CallBack
end
stateDiagram-v2
[*] --> REGISTERED: StateUnit ๋ฑ๋ก
REGISTERED --> READY: ์ด๊ธฐ ์ํ ์ค์
READY --> RUNNING: Event ๋ฐ์<br/>์ ์ด ํ
์ด๋ธ ๋งค์นญ
RUNNING --> READY: Success CallBack<br/>nextEvent ์์
RUNNING --> WAITING: nextEvent + delay
WAITING --> RUNNING: ์ง์ฐ ์๊ฐ ๋๋ฌ<br/>StateTaskManager ์คํ
RUNNING --> RETRYING: ์คํจ/์กฐ๊ฑด ๋ถ๋ง์กฑ<br/>retry ์ค์
RETRYING --> RUNNING: ์ฌ์๋(ํ์ ๋จ์)
RETRYING --> FAILED: ์ฌ์๋ ์์ง
FAILED --> [*]
JFSM์ ๋ค์๊ณผ ๊ฐ์ ์ํฉ์ ์ ์ฉํฉ๋๋ค.
- ์ฌ์ฉ์/์ ๋ฌด ํ๋ฆ์ ๋ช ํํ ์ํ๋ก ๋ชจ๋ธ๋งํ๊ณ ์ถ์ ๊ฒฝ์ฐ
- ์ด๋ฒคํธ ๊ธฐ๋ฐ์ผ๋ก ๋จ๊ณ๋ณ ์ฒ๋ฆฌ์ ์๋ฌ ๋ณต๊ตฌ/์ฌ์๋๋ฅผ ํ๊ณ ์ถ์ ๊ฒฝ์ฐ
- ๋ฉํฐ ์ค๋ ๋์์ ๋ค์์ ์ํ ๊ฐ์ฒด๋ฅผ ์์ ํ๊ฒ ๊ด๋ฆฌํ๊ณ ์ถ์ ๊ฒฝ์ฐ
๊ตฌ์ฑ ์์๋ ๋ค์๊ณผ ๊ฐ์ต๋๋ค.
StateManager: FSM ์ ์ฒด๋ฅผ ๊ด๋ฆฌํ๋ ์์ ๋งค๋์ . ์ค๋ ๋ ํ ํฌ๊ธฐ, ํธ๋ค๋ฌ/์ ๋ ๋ฑ๋ก/์ญ์ ๋ฑ ์ ๊ณตStateHandler: ํน์ ๋๋ฉ์ธ(์ ํ)์ ์ด๋ฒคํธ์ ์ฒ์ด๋ฅผ ๊ด๋ฆฌStateEventManager: ์ฒ์ด ํ ์ด๋ธ๊ณผ ์คํ ๋ก์ง์ ๋ด๋นStateUnit: ์ค์ ๋ก ์ํ๋ฅผ ๊ฐ๊ณ ์ด๋ฒคํธ๋ฅผ ์ ์ฉ๋ฐ๋ ๊ฐ์ฒด(์ธ์ /์ฃผ๋ฌธ/์ฅ๋น ๋ฑ)EventCondition: ์ฒ์ด ์คํ ์ ์กฐ๊ฑด ๊ฒ์ฌ ์ธํฐํ์ด์คCallBack: ์ฒ์ด ์ฑ๊ณต/์คํจ ์์ ํ์ฒ๋ฆฌ ์ฝ๋ฐฑ ์ธํฐํ์ด์คRetryManager: ์ฌ์๋ ์ ์ฑ ๋ฐ ์ํ ๊ด๋ฆฌ ์ ํธ
UML ๊ฐ์(์์):
- FSM:
JFSM/src/main/resources/uml/fsm_uml.puml - ATM ๋ฐ๋ชจ:
JFSM/src/test/java/atm/uml/atm_state.puml
ํ๋ ์๋น์ค๋ ์ฌ์ฉ์ ํ๋ฆ, ์ฃผ๋ฌธยท๊ฒฐ์ , ๊ธฐ๊ธฐ ์ ์ด(์: ATM) ๋ฑ ๋จ๊ณ์ ๋ก์ง์ด ๋ง์ต๋๋ค. ์ด ํ๋ฆ์ if-else/switch, ํ์ด๋จธ, ์ค๋ ๋, ํ ๋ก์ง์ผ๋ก ์ฆํฅ ๊ตฌํํ๋ฉด ์ฝ๋๊ฐ ๋น ๋ฅด๊ฒ ๋ณต์กํด์ง๊ณ ๊ฒฐํฉ๋๊ฐ ๋์์ง๋๋ค. FSM(Finite State Machine)์ ์์คํ ์ ๊ฐ๋ฅํ ์ํ์ ์ด๋ฒคํธ, ์ ์ด๋ฅผ ๋ช ํํ ์ ์ํด ๋ค์๊ณผ ๊ฐ์ ์ด์ ์ ์ ๊ณตํฉ๋๋ค.
- ๋ณต์ก๋ ๊ด๋ฆฌ์ ๊ฐ๋
์ฑ ํฅ์
- ์ํ์ ์ ์ด(transition)๋ฅผ ํ๋ก ๊ด๋ฆฌํ๋ฏ๋ก ํ๋ฆ์ด ๋ช ํํฉ๋๋ค.
- "์ด๋ค ์ด๋ฒคํธ๊ฐ ์ด๋ค ์ํ์์ ์ ํจํ๊ฐ"๋ฅผ ์ฝ๋ ๋ ๋ฒจ์์ ๊ฐ์ ํ ์ ์์ต๋๋ค.
- ์ ๋ขฐ์ฑ ์๋ ์ค๋ฅ ์ฒ๋ฆฌ์ ํ๋ณต๋ ฅ
- ์ฑ๊ณต/์คํจ ์ฝ๋ฐฑ์ผ๋ก ํ์ฒ๋ฆฌ๋ฅผ ์ผ๊ด๋๊ฒ ์ํํฉ๋๋ค.
nextEvent+delay+nextEventRetryCount๋ก ์คํจ ํ ์ฌ์๋ยท๋ฐฑ์คํยท๋๊ธฐ ๊ฐ์ ํ๋ณต ์ ๋ต์ ์ ์ธ์ ์ผ๋ก ๊ตฌ์ฑํ ์ ์์ต๋๋ค.
- ๋์์ฑ ์ ์ด์ ๋น๋๊ธฐ ์ฒ๋ฆฌ์ ๋จ์ํ
StateTaskManager๊ฐ ์ง์ฐ ์คํ๊ณผ ์ฒด์ด๋์ ์ค๋ ๋ ํ์์ ์์ ํ๊ฒ ์ฒ๋ฆฌํฉ๋๋ค.- ์ด๋ฒคํธ ์กฐ๊ฑด(
EventCondition)์ผ๋ก ๊ฒฝ์ ์กฐ๊ฑด์ด๋ ์ ํจ์ฑ ์ ๊ฒ์ฌ๋ฅผ ์ค์ํํฉ๋๋ค.
- ํ
์คํธ ์ฉ์ด์ฑ๊ณผ ์ถ์ ๊ฐ๋ฅ์ฑ
- ๊ฐ ์ ์ด์ ์ฝ๋ฐฑ์ด ๋ ๋ฆฝ ๋ชจ๋์ด๋ฏ๋ก ๋จ์ ํ ์คํธ๊ฐ ์ฝ์ต๋๋ค.
- ์ํ ์ด๋ ฅ(Prev/Cur)์ผ๋ก ์ผ์ด์ค ์ฌํ๊ณผ ์ฅ์ ๋ถ์์ด ์ฉ์ดํฉ๋๋ค.
- ๋๋ฉ์ธ ์ ํฉ์ฑ๊ณผ ํ์ฅ์ฑ
- ๋๋ฉ์ธ ์ธ์ด(์: READY โ CARD_READ โ PIN_ENTRY)๋ฅผ ๊ทธ๋๋ก ์ฝ๋์ ๋ฐ์ํด ์์ฌ์ํต์ด ์ฌ์์ง๋๋ค.
- ์๋ก์ด ์ํ/์ด๋ฒคํธ ์ถ๊ฐ๊ฐ ๊ธฐ์กด ์ฝ๋์ ์ต์ํ์ ์ํฅ์ผ๋ก ๊ฐ๋ฅํฉ๋๋ค.
JFSM์ด ์ ๊ณตํ๋ ๊ธฐ๋ฅ์ FSM ๋์ ํจ๊ณผ๋ฅผ ์ค๋ฌด์ ๋ง๊ฒ ๊ฐํํฉ๋๋ค.
- ์ ์ธ์ API:
StateHandler.addState(...)๋ก ์ ์ด, ์ฝ๋ฐฑ, ๋ค์ ์ด๋ฒคํธ, ์ง์ฐ, ์ฌ์๋๊น์ง ํ ๋ฒ์ ์ ์ - ์กฐ๊ฑด๋ถ ์คํ:
EventCondition์ผ๋ก ์ฌ์ ๊ฒ์ฆ ๋ก์ง์ ํ๋ฌ๊ทธ์ธ์ฒ๋ผ ์ถ๊ฐ - ๋น๋๊ธฐยท์ค์ผ์ค๋ง: ๋ด๋ถ ์ค์ผ์ค๋ฌ/์ค๋ ๋ํ ๊ธฐ๋ฐ์ผ๋ก ๋ค์ ์ด๋ฒคํธ ์๋ ์ฒ๋ฆฌ
- ์ฌ์๋ ์ ๋ต:
RetryManager๋ฅผ ํตํด ๋จ์ ๋ฐ๋ณต๋ถํฐ ์ ํ ํ์ยท์ง์ฐ ๊ฐ๊ฒฉ๊น์ง ์ ์ฐํ๊ฒ ๊ตฌ์ฑ
์ธ์ FSM์ ์ฐ์ง ์์๋ ๋๋๊ฐ?
- ์ ์ด๊ฐ 1~2๊ฐ ์์ค์ ์์ฃผ ๋จ์ํ ํ๋ก์ฐ
- ์ํ ๊ฐ๋ ์ด ๊ฑฐ์ ์๊ณ ์ ์ฐจํ ์ง์ ๋ก์ง์ผ๋ก ์ถฉ๋ถํ ๊ฒฝ์ฐ ์ด๋ฐ ๊ฒฝ์ฐ์๋ ์คํ๋ ค FSM์ด ๊ณผ์ค๊ณ๊ฐ ๋ ์ ์์ต๋๋ค. ๊ทธ๋ฌ๋ ์ํ/์ด๋ฒคํธ๊ฐ ๋์ด๋๊ณ ๋น๋๊ธฐยท์ง์ฐยท์ฌ์๋๊ฐ ์ฝํ๋ฉด FSM์ด ์ฅ๊ธฐ ์ ์ง๋ณด์ ๊ด์ ์์ ์ ๋ฆฌํฉ๋๋ค.
์๋๋ ์ต์ ๊ตฌ์ฑ ์์์ ๋๋ค.
import com.fsm.StateManager;
import com.fsm.module.StateHandler;
import com.fsm.event.base.CallBack;
// 1) FSM ๋งค๋์ ์์ฑ (ํ์คํฌ ์ค๋ ๋ ์ต๋ ๊ฐ์ ์ง์ )
StateManager fsm = new StateManager(4);
// 2) ํธ๋ค๋ฌ ๋ฑ๋ก (๋๋ฉ์ธ ๊ทธ๋ฃน๋ช
)
fsm.addStateHandler("ATM");
StateHandler handler = fsm.getStateHandler("ATM");
// 3) ์ํ ์ ๋ ๋ฑ๋ก (์ค์ ์ํ๋ฅผ ๊ฐ์ง ๊ฐ์ฒด)
fsm.addStateUnit("acct-001", "ATM", "INIT", new Object());
// 4) ์ฒ์ด ์ ์ (event, from, to, ์ฑ๊ณต์ฝ๋ฐฑ, ์คํจ์ฝ๋ฐฑ, ๋ค์์ด๋ฒคํธ, ์ง์ฐ(ms), ์ฌ์๋)
CallBack ok = (unit, params) -> {
System.out.println("on success: " + unit.getName());
return true;
};
CallBack fail = (unit, params) -> {
System.out.println("on fail: " + unit.getName());
return true;
};
handler.addState(
"INPUT_PIN", // event
"INIT", // from
"PIN_ENTERED", // to
ok, // success callback
fail, // fail callback
"SELECT_MENU", // next event (์ฒด์ด๋)
0, // delay (ms)
0 // retry count
);
// 5) ์ด๋ฒคํธ ์คํ
var unit = fsm.getStateUnit("acct-001");
String nextState = handler.fire("INPUT_PIN", unit);
System.out.println("Next State: " + nextState);
// ์ข
๋ฃ ์
fsm.stop();- StateManager
- FSM ์ ์ฒด ์๋ช ๊ณผ ๋ฆฌ์์ค๋ฅผ ๊ด๋ฆฌํฉ๋๋ค.
- ํธ๋ค๋ฌ(
StateHandler)์ ์ ๋(StateUnit)์ ๋ฑ๋ก/์ญ์ ํฉ๋๋ค. - ๋ด๋ถ์
StateTaskManager๋ฅผ ๋ณด์ ํ๋ฉฐ, ๋น๋๊ธฐ ์์ ์ ์คํํฉ๋๋ค.
- StateHandler
- ์ด๋ฒคํธ ์ฒ์ด ์ ์๋ฅผ ๋ฑ๋กํ๊ณ ,
fire/handle๋ก ์คํํฉ๋๋ค. - ๋์ผ ํธ๋ค๋ฌ ๋ด ์ด๋ฒคํธ ๊ฐ ์ฒด์ด๋(nextEvent)๊ณผ ์ง์ฐ์ ์ฒ๋ฆฌํ ์ ์์ต๋๋ค.
- ์ด๋ฒคํธ ์ฒ์ด ์ ์๋ฅผ ๋ฑ๋กํ๊ณ ,
- StateEventManager
- ์ฒ์ด ํ ์ด๋ธ์ ์ ์ฅํ๊ณ ์คํ ๋ก์ง์ ์ํํฉ๋๋ค.
- ์ฑ๊ณต/์คํจ ์ฝ๋ฐฑ, ์ฌ์๋, ์กฐ๊ฑด ๊ฒ์ฌ ๋ฑ์ ์ค์ผ์คํธ๋ ์ด์ ํฉ๋๋ค.
- StateUnit
- ์ด๋ฆ, ํ์ฌ ์ํ, ๋ถ๊ฐ ๋ฐ์ดํฐ(payload)๋ฅผ ๊ฐ๋ FSM์ ๋์ ๊ฐ์ฒด์ ๋๋ค.
- EventCondition
- ํน์ ์ด๋ฒคํธ ์คํ ์ ์กฐ๊ฑด์ ๊ฒ์ฆํฉ๋๋ค.
- ์คํจ/์ค๋ฅ ์ํฉ ์ ๋ค์ ์ฒ์ด๋ ์ฝ๋ฐฑ ๋์์ ์ํฅ์ ์ค ์ ์์ต๋๋ค.
- CallBack
- ์ฒ์ด ์ฑ๊ณต/์คํจ ์์ ์ ํ์ฒ๋ฆฌ๋ฅผ ๊ตฌํํฉ๋๋ค.
- Retry(์ฌ์๋)
nextEventRetryCount๋ก ๋ค์ ์ด๋ฒคํธ ์ฒด์ด๋ ์ ์ฌ์๋ ํ์๋ฅผ ์ง์ ํฉ๋๋ค.
StateManager fsm = new StateManager(4); // ์ค๋ ๋ ์ต๋ 4๊ฐfsm.addStateHandler("ORDER");
StateHandler handler = fsm.getStateHandler("ORDER");fsm.addStateUnit("order-1001", "ORDER", "NEW", payload);
fsm.getStateUnit("order-1001");
fsm.removeStateUnit("order-1001");์ค๋ฒ๋ก๋ ๋ ๊ฐ์ง๊ฐ ์ ๊ณต๋ฉ๋๋ค.
- ๋จ์ผ from ์ํ์์ to๋ก ์ฒ์ด
- ๋ค์ค from ์ํ ์งํฉ์์ to๋ก ์ฒ์ด
boolean added = handler.addState(
"PAY", // event
"NEW", // fromState
"PAID", // toState
successCb, failCb,
null, // nextEvent ์์ผ๋ฉด null
0, // delay
0, // retry count
new Object[]{/* next params */}
);HashSet<String> from = new HashSet<>(List.of("NEW", "RETRY"));
boolean added = handler.addState(
"PAY", // event
from, // fromStateSet
"PAID", // toState
successCb, failCb,
"SHIP", // nextEvent
1000, // delay 1s ํ nextEvent
3, // ์ต๋ 3ํ ์ฌ์๋
"param1", 123
);String nextState = handler.fire("PAY", stateUnit);addState์nextEvent,delay๋ฅผ ์ง์ ํ๋ฉด ์ฑ๊ณต ์ ๋ค์ ์ด๋ฒคํธ๋ฅผ ์ง์ฐ ํ ์๋ ์คํํฉ๋๋ค.nextEventRetryCount๋ก ์คํจ ์ ์ฌ์๋ ํ์๋ฅผ ์ ์ดํ ์ ์์ต๋๋ค.
EventCondition์ ํธ๋ค๋ฌ์ ๋ฑ๋กํด ์ด๋ฒคํธ ์คํ ์ ๊ฒ์ฆ์ ์ํํ ์ ์์ต๋๋ค.
handler.addEventCondition((event, unit) -> {
// ์คํ ๊ฐ๋ฅ ์ฌ๋ถ ๊ฒ์ฌ (true=ํต๊ณผ)
return unit != null && unit.getIsAlive();
}, 0); // delay(ms) โ ํ์ ์ ์กฐ๊ฑด๋ ์ง์ฐ ํ๊ฐ ๊ฐ๋ฅStateTaskManager์ ๋ด๋ถ ์ค์ผ์ค๋ฌ๊ฐ ์ง์ฐ/์ฒด์ด๋ ์์ ์ ๋ฐฑ๊ทธ๋ผ์ด๋์์ ์คํํฉ๋๋ค.StateManager์์ฑ์์ ํ๋ผ๋ฏธํฐ๋ก ์ค๋ ๋ ์ต๋ ๊ฐ์๋ฅผ ์ค์ ํฉ๋๋ค.
- ์คํจ ์ฝ๋ฐฑ์์ ๋ก๊น /์๋ฆผ/๋ณด์ ๋ก์ง์ ์ํํ ์ ์์ต๋๋ค.
nextEventRetryCount์RetryManager๋ฅผ ํตํด ๋ฐ๋ณต ์คํ ์ ๋ต์ ์ค๊ณํ์ธ์.
ํ ์คํธ ์ฝ๋์ ATM ์ํ ๋จธ์ ์์ ๊ฐ ํฌํจ๋์ด ์์ต๋๋ค.
- ๊ฒฝ๋ก:
JFSM/src/test/java/atm - UML:
JFSM/src/test/java/atm/uml/atm_state.puml
์คํ ํ:
# Maven ํ
์คํธ ์คํ
mvn -f JFSM/pom.xml test -Dtest=atm.BasicAtmStateTest# ์ ์ฒด ํ
์คํธ
mvn -f JFSM/pom.xml test
# ํน์ ํ
์คํธ ํด๋์ค
mvn -f JFSM/pom.xml -Dtest=TestMain testํ๋ก์ ํธ๋ Maven ๊ธฐ๋ฐ์
๋๋ค. ๋ก์ปฌ ๋ชจ๋๋ก ์ฌ์ฉํ ๊ฒฝ์ฐ StateManager ๋ฑ API๋ฅผ ์ง์ import ํ์ฌ ์ฌ์ฉํ์ธ์. (๋ณ๋์ ์ค์ ์ ์ฅ์ ๋ฐฐํฌ ์ ๋ณด๊ฐ ์๋ค๋ฉด ์์ค ์์กด ๋๋ ๋ก์ปฌ ์ค์น๋ฅผ ์ด์ฉํ์ธ์.)
# ๋น๋
mvn -f JFSM/pom.xml clean package
# ๋ก์ปฌ ์ค์น (๋ค๋ฅธ ํ๋ก์ ํธ์์ ์ฌ์ฉ)
mvn -f JFSM/pom.xml clean install์์กด ์์(pom.xml) โ ๋ก์ปฌ ์ค์น ํ ์ฌ์ฉ ์:
<dependency>
<groupId>com.fsm</groupId>
<artifactId>JFSM</artifactId>
<version>1.0.0</version>
</dependency>- Q. ์ํ ์ฒ์ด๋ ์ด๋์ ์ ์ํ๋์?
- A.
StateHandler.addState(...)๋ฅผ ํตํด ์ ์ํฉ๋๋ค.
- A.
- Q. ์ฌ๋ฌ from ์ํ์์ ๊ฐ์ ์ด๋ฒคํธ๋ก ์ฒ์ด ๊ฐ๋ฅํ ๊น์?
- A. ๊ฐ๋ฅํฉ๋๋ค.
HashSet<String>์ผ๋ก from ์ํ ์งํฉ์ ๋๊ธฐ๋ฉด ๋ฉ๋๋ค.
- A. ๊ฐ๋ฅํฉ๋๋ค.
- Q. ๋ค์ ์ด๋ฒคํธ๋ฅผ ์๋ ์คํํ๊ณ ์ถ์ต๋๋ค.
- A.
nextEvent์delay๋ฅผ ์ง์ ํ์ธ์. ์คํจ ์nextEventRetryCount๋ก ์ฌ์๋ ํ์๋ฅผ ์ค์ ํฉ๋๋ค.
- A.
- Q. ์ค๋ ๋ ๊ฐ์๋ ์ด๋ป๊ฒ ์กฐ์ ํ๋์?
- A.
new StateManager(threadMaxCount)๋ก ์์ฑ ์ ์ค์ ํฉ๋๋ค.
- A.
์ด ํ๋ก์ ํธ๋ LICENSE ํ์ผ์ ๋ด์ฉ์ ๋ฐ๋ฆ
๋๋ค.
