[STK2-06] 시그널 조합 + 서비스
작업 내용 (설계 의도)
변경 사항
signal.py: combine()(0.6×감성 + 0.4×모멘텀, [-1,1] 클램핑)·classify()(5단계 라벨).
signal_service.py: build_signal() 파이프라인 오케스트레이션, Signal/Stock dataclass.
- STK2-02·04·05를 결합하는 통합 티켓.
의존
- 선행: STK2-02, STK2-04, STK2-05
- 후행: STK2-07, STK2-08
다이어그램
처리 흐름
sequenceDiagram
participant API as main.py
participant SVC as signal_service.py
participant TC as toss_client
participant NW as news / headlines
participant SE as sentiment
participant MO as momentum
participant SG as signal.py
API->>SVC: build_signal(symbol)
SVC->>TC: get_stock(symbol)
SVC->>TC: get_closes(symbol)
SVC->>NW: fetch + dedup(headlines)
SVC->>SE: score(headlines)
SVC->>MO: score(closes)
SE-->>SVC: sentiment_score
MO-->>SVC: momentum_score
SVC->>SG: combine(sentiment_score, momentum_score)
SG->>SG: clamp(0.6×s + 0.4×m, -1, 1)
SG->>SG: classify(composite)
SG-->>SVC: Signal dataclass
SVC-->>API: Signal
클래스 의존
flowchart LR
subgraph Application["Application"]
signal_service["signal_service.py (build_signal)"]
signal["signal.py (combine, classify)"]
end
subgraph Infra["Infrastructure"]
toss_client["toss_client.py"]
end
subgraph Domain["Domain"]
sentiment["sentiment.py"]
momentum["momentum.py"]
news["news.py / headlines.py"]
end
signal_service --> signal
signal_service --> toss_client
signal_service --> sentiment
signal_service --> momentum
signal_service --> news
테스트 케이스
- 종합 점수가
0.6×감성 + 0.4×모멘텀 공식으로 계산된다.
- 감성 0.8, 모멘텀 0.5일 때 composite는 0.68이고 라벨은 “강한 긍정”이다.
- composite ≥ 0.5이면 “강한 긍정”, 0.15≤x<0.5이면 “긍정”으로 분류된다.
- composite가 -1.5가 되도록 입력해도 clamp 후 -1.0이 반환된다.
- 감성·모멘텀 모두 0이면 composite 0.0, 라벨 “중립”이다.
build_signal 은 Signal dataclass의 모든 필드가 채워진 객체를 반환한다.