AI 판단은 주문 직전에 새로 호출되는 요청이 아니다. 스케줄러가 분석을 만들어 판단 로그로 저장해두면 주문 실행 단계가 그 로그를 다시 읽어 안전장치를 통과한 경우에만 처리한다. 둘을 분리한 이유는 하나다. LLM 응답을 주문 명령으로 쓰면 실패했을 때 무엇이 잘못됐는지 나눌 수 없으니까.

diagram-contract.png


하루 운영 루틴

작업 주기 운영 의미
뉴스/RAG 수집 설정값 기반, 코드 기본값 12시간 수집, 번역, 청크 분할, 임베딩, OpenSearch 저장
시장 심리 갱신 5분 Alternative.me 기반 시장 심리 상태 갱신
AI 판단 생성 60분 관심 종목별 BUY / SELL / HOLD 분석 생성
정확도 검증 30분 과거 판단과 이후 가격 흐름을 비교해 실패 피드백 후보 생성
포트폴리오 스냅샷 1시간 보유 자산, 손익, 상태를 시계열로 저장
실주문 대사 15초 미종결 실주문을 거래소 상태와 대조해 체결을 exactly-once 반영
AI 브리핑 08:30 포트폴리오와 시장 상태 기반 일일 브리핑

판단에 넣는 것

포트폴리오와 기술 지표, RAG 뉴스, 시장 심리에 최근 실패한 판단 피드백까지 넣는다. 기술 지표는 15m나 60m 캔들을 기반으로 계산한 SMA·EMA·Bollinger·RSI와 현재가의 상대 위치다.

조회 오류도 값으로 함께 넘긴다. 데이터가 없는 것과 조회에 실패한 것을 프롬프트 단계에서부터 구분해야 AI가 빈 값을 자기 방식대로 해석하지 않는다.


System Prompt

페르소나는 설정 화면에서 사용자가 바꿀 수 있지만 안전 규칙보다 우선할 수 없다고 프롬프트에 명시했다. 공격적인 페르소나를 넣어도 BUY 조건 자체는 완화되지 않아야 했기 때문이다.


출력 계약과 실행 분리

출력은 decision과 confidence, recommended_weight, reasoning 네 필드로 제한된다. 이 응답은 주문 요청이 아니라 판단 로그고 executor가 별도로 아래 조건을 다시 검사한다.

차단 조건 처리
분석 로그 없음 또는 만료 주문 실행 스킵
decision = HOLD 주문 실행 없음
confidence 부족 (기본 85 미만) 확신도 미달로 스킵
recommended_weight ≤ 0 포지션 비중 제안 없음으로 스킵
포트폴리오 조회 오류 현재 잔고를 신뢰할 수 없어 스킵
entry gate 실패 (기본 70 미만) score, calibrated confidence, 제외 조건에 따라 BUY 차단
shadow mode 주문 후보만 기록하고 실제 주문 없음
live BUY lock 실전 신규 매수는 명시적으로 잠금 해제한 경우만 허용

판단 로그 감사 계보

1차 분석과 BUY 직전 2차 검증이 같은 형태로 저장돼서 정확도 통계에 둘이 섞였다. 성과가 좋게 나와도 무엇 덕분인지 설명할 수 없어서 stage와 계보를 나눴다.