부 증식 파이프라인 로드맵 TDD

Background

PRD에서 정의한 5페이즈(데이터 자산화 → 엣지 검증 → 리스크 관리 → 실행 자동화 → 모델 고도화)의 기술 설계를 정의한다. 핵심 원칙은 검증되지 않은 엣지 위에 모델·자동매매를 쌓지 않는다이며, P2(엣지 검증)가 전체 게이트다.

Overview

  • 무엇을: 40캔들 즉석 분석 구조를, 수년치 시계열 자산 + 정직한 백테스트 + 리스크 레이어 + 실행 경로로 확장한다.
  • : 부 증식의 병목은 모델 성능이 아니라 데이터·검증·리스크·실행의 부재다.
  • 어떻게: 데이터 적재·영속화는 기존 컨벤션대로 BE(Kotlin)가, 백테스트·모델 계산은 ml(Python)이 담당한다. 실행은 신규 증권사 Gateway로 분리한다.

Terminology

용어정의
OHLCV시가·고가·저가·종가·거래량 일봉 데이터
Edge(엣지)시장 평균 대비 전략의 초과수익. 본 시스템의 검증 대상
Look-ahead(룩어헤드)시점 t 판단에 t 이후 정보가 새어든 오염. 백테스트 신뢰성의 적
Slippage(슬리피지)의도 가격과 실제 체결 가격의 차이
MDDMaximum Drawdown. 최고점 대비 최대 하락폭
Position Sizing자본 대비 종목별 투입 비중 결정
Paper Trading실자본 없이 실시간 신호로 모의 체결만 기록

Define Problem

AS-IS

  • 가격 데이터는 요청 시마다 토스에서 일봉 20~40개를 즉석 fetch (toss_client.py#get_closes). 영속 저장 없음.
  • 백테스트는 이 40개 캔들로만 워크포워드 (backtest.py#run_backtest). 거래비용·슬리피지 미반영, 표본 크기 통계적 무의미.
  • 4팩터 가중치는 코드 상수 (signal.py _WEIGHTS). 데이터 학습 없음.
  • 리스크·포지션·실행 레이어 자체가 존재하지 않는다.

TO-BE

  • BE가 수년치 OHLCV·수급·재무를 MySQL에 시계열 적재 → ml이 룩어헤드 없이 조회.
  • ml에 거래비용·슬리피지 반영 백테스트 엔진 신설 → 엣지 유의성 리포트 산출.
  • 리스크 레이어(손절·사이징·MDD 한도)를 백테스트와 실행 양쪽에 공통 적용.
  • 증권사 주문 Gateway로 신호→주문→체결 경로 확보(페이퍼트레이딩 선행).

Possible Solutions

벤치마킹 참조

제품/도구카테고리참조 패턴
Zipline / backtrader백테스트 엔진룩어헤드 차단·거래비용 모델·이벤트 드리븐 체결
vectorbt벡터화 백테스트다종목 대규모 표본을 빠르게 검증
QuantConnect LEAN통합 퀀트 플랫폼데이터·백테스트·실행을 한 파이프라인으로
한국투자증권 KIS Developers주문 API국내 개인 자동매매 표준 진입점

방안 비교 — 데이터 적재 주체

방안설명왜 채택 / 미채택
BE(Kotlin)가 적재·영속화, ml은 읽기KRX 수급 연동 ADR 패턴과 일치 (ml stateless)채택 — 기존 컨벤션·인프라 재사용, 영속화 책임 일원화
ml(Python)이 직접 적재·저장백테스트와 같은 언어미채택 — ml stateless 원칙 위반, 영속화 이중화

방안 비교 — 백테스트 엔진

방안설명왜 채택 / 미채택
자체 경량 엔진(현 backtest.py 확장)거래비용·슬리피지·다종목·장기표본을 자체 구현1차 채택 — 의존성 최소, 로직 투명. P5에서 한계 시 라이브러리 전환
backtrader/vectorbt 도입성숙한 OSS 엔진후보 — 종목 수·전략 복잡도 증가 시 전환

Detail Design

클래스/모듈 역할 정의

P1 데이터 자산화 (BE: marketflow 확장 또는 신규 pricehistory 패키지)

클래스레이어역할
DailyPricedomain일봉 OHLCV Rich Domain Entity (룩어헤드 방지 불변식 포함)
PriceHistoryRepositorydomain일봉 영속화 interface
PriceBackfillGatewaydomain외부 소스(토스/증권사)에서 과거 일봉 수집 interface
BackfillPriceHistoryUseCaseapplication종목별 과거 N년 일봉 백필 오케스트레이션
PriceHistoryRepositoryImplinfrastructureJPA 구현 (daily_prices 테이블)

P2 엣지 검증 (ml: backtest 엔진 확장)

모듈역할입력 → 출력
CostModel수수료·세금·슬리피지 반영체결 의도 → 실효 체결가·비용
BacktestEngine룩어헤드 차단 워크포워드OHLCV 시계열 + 전략 → 거래 로그·수익곡선
EdgeReport엣지 유의성 판정수익곡선 → 초과수익·t검정·승률·MDD·샤프

P3 리스크 관리 (ml + BE 공통 규칙)

모듈역할
PositionSizer자본 대비 종목 비중 산출 (고정비율/변동성 기반)
RiskGate손절·일일 손실 한도·MDD 한도 검사

P4 실행 자동화 (BE: 기존 order 재사용 + 신규 제안·승인)

기존 order 도메인을 그대로 재사용한다 (ADR-003). TossOrderGatewayImpl·OrderDomainService#placeOrder·OrderStatus 전이·PlaceOrderUseCase는 이미 토스 주문(매수·매도·정정·취소)을 구현해 동작 중이다. 신규 증권사 Gateway·신규 Order 도메인을 만들지 않는다.

P4 신규 작업은 신호→제안→수동 승인 게이트뿐이다 (ADR-005).

클래스레이어역할
OrderProposaldomain주문 제안 Rich Domain Entity (제안·승인·거부 상태)
OrderProposalRepositorydomain제안 영속화 interface
PaperExecutor, PaperFillRepositorydomain모의 체결·가상 포지션 (paper 모드, 토스 호출 없음)
ProposeOrderUseCaseapplication신호+RiskGate 통과 주문을 제안으로 생성
ApproveOrderProposalUseCaseapplication승인 시 모드 분기 — paper=PaperExecutor, live=기존 PlaceOrderUseCase

컨벤션: live 모드의 토스 주문은 외부 시스템 호출이므로 기존 OrderGateway(TossOrderGatewayImpl) 사용. 기본 모드는 paper(ADR-006). 신호→제안→승인→집행 흐름은 presentation Controller → UseCase → DomainService 준수.

Component Diagram

flowchart LR
    subgraph BE["BE (Kotlin) — 적재·영속화·실행"]
        Backfill[BackfillPriceHistoryUseCase]
        PriceRepo[PriceHistoryRepository]
        Propose[ProposeOrderUseCase]
        Approve[ApproveOrderProposalUseCase]
        PlaceUC[PlaceOrderUseCase 기존]
        TossGw[TossOrderGatewayImpl 기존]
    end
    subgraph ML["ml (Python) — 검증·모델"]
        Engine[BacktestEngine]
        Cost[CostModel]
        Edge[EdgeReport]
        Sizer[PositionSizer]
    end
    subgraph Store["MySQL (3308)"]
        Prices[(daily_prices)]
        Trades[(backtest_runs)]
        Orders[(orders)]
    end
    Backfill --> PriceRepo
    PriceRepo --> Prices
    Engine --> Prices
    Engine --> Cost
    Engine --> Edge
    Edge --> Trades
    Sizer --> Engine
    Propose --> Approve
    Approve --> PlaceUC
    PlaceUC --> TossGw
    PlaceUC --> Orders

Sequence Diagram — P2 엣지 검증 흐름

sequenceDiagram
    participant Runner as 검증 실행기
    participant Engine as BacktestEngine
    participant Prices as daily_prices
    participant Cost as CostModel
    participant Edge as EdgeReport
    Runner->>Engine: run(symbols, 3years, strategy)
    Engine->>Prices: load(symbol, t0..t)
    loop 각 시점 t (룩어헤드 차단)
        Engine->>Engine: signal(closes[..t])
        Engine->>Cost: applyCost(intendedFill)
        Cost-->>Engine: 실효 체결가·비용
    end
    Engine->>Edge: summarize(equityCurve, trades)
    Edge-->>Runner: 초과수익·t값·승률·MDD·샤프

ERD

erDiagram
    daily_prices {
        bigint id PK
        varchar symbol
        date trade_date
        decimal open
        decimal high
        decimal low
        decimal close
        bigint volume
    }
    backtest_runs {
        bigint id PK
        varchar strategy
        date period_start
        date period_end
        decimal excess_return
        decimal sharpe
        decimal mdd
        decimal t_stat
    }
    order_proposals {
        bigint id PK
        varchar symbol
        varchar side
        decimal price
        int quantity
        varchar status
        varchar source_signal
        datetime proposed_at
        datetime decided_at
    }
    paper_fills {
        bigint id PK
        bigint proposal_id
        varchar symbol
        varchar side
        decimal fill_price
        int quantity
        datetime filled_at
    }

daily_prices는 (symbol, trade_date) unique. orders는 기존 테이블 재사용(신규 아님). order_proposals·paper_fills만 신규. DDL 전문·정밀도는 각 티켓에 둔다.

Testing Plan

레이어대상핵심 시나리오
domainDailyPrice, OrderProposal룩어헤드 불변식, 제안 승인/거부 상태 전이
applicationBackfillPriceHistoryUseCase, ProposeOrderUseCase, ApproveOrderProposalUseCase백필 멱등성, 리스크게이트 미통과 시 제안 미생성, 승인 시 기존 집행 호출
infrastructurePriceHistoryRepositoryImpl, OrderProposalRepositoryImplTestContainers MySQL upsert. (토스 주문은 기존 TossOrderGatewayImpl 재사용)
ml 단위CostModel, BacktestEngine, EdgeReport거래비용 반영 정확성, 룩어헤드 누출 0 검증, 표본 0건/단일 종목 엣지 케이스
ml 검증EdgeReport무작위 신호 입력 시 엣지가 유의하지 않게 나오는지(가짜 엣지 차단)
scenarioE2E백필 → 백테스트 → 엣지 리포트 → (페이퍼)주문 전체 플로우

반드시 포함: 룩어헤드 누출 테스트(시점 t에 t+1 종가 주입 시 실패), 무작위 신호로 엣지 0 검증(가짜 엣지 탐지). 이 둘이 백테스트 신뢰성의 핵심 실패 경로다.

Observability

지표의미알람 조건
backfill_rows_total적재된 일봉 행 수백필 실패·0건
backtest_run_duration백테스트 실행 시간임계 초과 시 엔진 전환 신호
edge_t_stat최근 엣지 t값유의성 소멸(엣지 붕괴) 감지
order_reject_total리스크게이트 차단 주문 수급증 시 전략·시장 이상

Release Scenario

  1. P1: daily_prices 마이그레이션 → 백필 배치 1회 실행 → 적재 검증. 롤백: 역방향 DDL로 테이블 drop.
  2. P2: ml 백테스트 엔진 배포 → 다종목 검증 실행 → 엣지 리포트 산출(읽기 전용, 실거래 영향 없음).
  3. P3: 리스크 레이어를 백테스트에 먼저 적용 → MDD 통제 확인 후 실행 경로에 연결.
  4. P4: 신호→제안(order_proposals) 생성 먼저 → 사용자 승인 시 기존 PlaceOrderUseCase로 토스 집행. 완전 자동 아님(수동 승인). 롤백: 제안 생성 비활성화 플래그로 즉시 중단(기존 수동 주문 경로는 영향 없음).
  5. P5: P2에서 엣지 확인된 경우에만 착수.

Project Information

  • 일정: 페이즈별 순차. P1·P2가 게이트로 선행.
  • 의존: P2 → P1, P3 → P2, P4 → P3, P5 → P2(엣지 확인 조건부).

Document History

날짜변경 내용작성자
2026-06-27최초 작성 — 5페이즈 기술 설계biuea