주식 추천 고도화 PRD
배경 (Background)
현재 시스템은 두 가지 문제를 가진다.
기능 공백: ML 서비스로부터 종목 신호·예측·추천을 제공하지만, 사용자가 “내가 얼마에 몇 주 샀는가”를 기록하고 그 기준으로 손익을 계산하거나 최적 매도 시점을 추천받는 기능이 없다. 예측도 5일 단기 고정이어서 중기·장기 방향 판단이 불가능하다.
토큰 낭비: ML 신호 결과가 두 겹의 단기 TTL 캐시(ML in-memory 10분 + Aggregator Redis 10분)로 관리된다. TTL이 만료될 때마다 Claude CLI subprocess가 자동 호출되며, 추천 종목 조회 시에는 CURATED_SYMBOLS 12개 종목에 대해 최대 12회/10분의 LLM 호출이 발생한다. 사용자 의도와 무관하게 토큰이 소비된다.
목표
- 사용자가 주식 종목 · 평균 매수가 · 보유 수량을 수동으로 입력할 수 있다.
- 현재가와 비교한 손익(금액 · 수익률)을 산출한다.
- 입력한 종목(내 포트폴리오)과 추천 종목에 대해 단기 · 중기 · 장기 방향의 예측과 매도 추천을 제공한다.
- LLM 호출을 사용자의 명시적 새로고침 요청으로만 제한한다 — 신호 결과를 MySQL에 영속화하여 TTL 만료에 의한 자동 LLM 호출을 제거한다.
요구사항
| ID | 요구사항 | 우선순위 |
|---|---|---|
| R-01 | 종목 코드(symbol), 평균 매수가, 보유 수량을 입력·수정·삭제할 수 있다 | 높음 |
| R-02 | 한 종목을 여러 건 입력하는 경우는 허용하지 않는다 (종목당 1건) | 높음 |
| R-03 | 현재가는 기존 Toss API로 조회한다 | 높음 |
| R-04 | 손익 = (현재가 − 평균 매수가) × 보유 수량 으로 계산한다 | 높음 |
| R-05 | 수익률(%) = (현재가 − 평균 매수가) / 평균 매수가 × 100 으로 계산한다 | 높음 |
| R-06 | 단기(1~2주) 예측: 주 단위 등락 범위 + 최적 매도일 추천을 제공한다 | 높음 |
| R-07 | 중기(4~8주) 예측: 주 단위 등락 범위 + 최적 매도일 추천을 제공한다 | 높음 |
| R-08 | 장기(12~26주) 예측: 주 단위 등락 범위 + 최적 매도일 추천을 제공한다 | 보통 |
| R-09 | 내 포트폴리오 탭: 매도 시 예상 손익 = (추천 매도가 − 평균 매수가) × 보유 수량 을 표시한다 | 높음 |
| R-10 | 추천 종목 탭: 기준가 = 현재가(lastClose), 현재가 대비 예상 변동률(%) 을 표시한다 | 보통 |
| R-11 | 신호/예측/추천 최초 조회 시 ML을 호출하고 결과를 MySQL에 저장한다 | 높음 |
| R-12 | 이후 동일 조회는 ML을 호출하지 않고 DB에서 반환한다 (TTL 없음, 영구 보존) | 높음 |
| R-13 | 사용자가 새로고침을 요청할 때만 ML을 재호출하고 DB를 갱신한다 | 높음 |
| R-14 | Redis 캐시 레이어와 ML in-memory TtlCache를 제거한다 | 높음 |
사용자 시나리오
시나리오 1 — 포트폴리오 손익 확인 및 매도 추천 조회
- 사용자가 “삼성전자 50,000원 × 100주 매수” 입력
- 현재가 52,000원 조회 → 손익 +200,000원 (+4%) 표시
- 단기 추천: 3주 후 54,000원 예상, 해당 시점 매도 시 +400,000원 (+8%)
- 중기 추천: 6주 후 58,000원 예상, 해당 시점 매도 시 +800,000원 (+16%)
시나리오 2 — 신호 재사용 및 명시적 새로고침
- 추천 종목 탭에서 단기/중기/장기 예측 확인 (기준가 기반)
- 새로고침 버튼을 누르기 전까지 신호는 DB에서 재사용 — 불필요한 LLM 호출 없음
- 사용자가 새로고침 버튼 클릭 → ML 재호출 → 최신 신호로 DB 갱신
범위 외
- 자동 매매(실제 주문) 연동은 포함하지 않는다.
- 토스 API 실제 보유 종목(Holding)과 수동 포트폴리오는 별개로 유지한다.
- 신호 이력(과거 버전 보관)은 포함하지 않는다 — 최신 1건만 보관한다.
- ML 모델 자체의 변경은 없다.