Binance Auto Trader
사용자 매뉴얼
처음 설치한 사용자도 API 연결부터 백테스트, 실거래 시작까지 순서대로 따라 할 수 있도록 구성했습니다. 필요한 내용은 모두 이 HTML 파일 안에 있으며 인터넷 연결 없이도 열립니다.
처음이라면 이 순서만 따라 하세요
Binance Auto Trader는 바이낸스 USDⓈ-M 선물 시장에서 시장 상태를 분류하고, Trend Following과 Mean Reversion 전략을 자동으로 실행합니다. 프로그램을 켠 직후 실거래부터 시작하지 말고 아래 순서를 지키는 것이 중요합니다.
이 매뉴얼을 읽는 가장 빠른 방법
- 처음 사용자: 가입 · API 설정 → 첫 실행 순서 → 백테스트 3단계 → 실거래 체크
- 운영 중인 사용자: Trading 설정 → 화면 패널 → Trade History → 문제 해결
- 전략을 조정하는 사용자: Regime → TF/MR → 포지션 사이징 → 백테스트 엔진
바이낸스 가입 및 API 설정
1. 바이낸스 계정 준비
프로그램 상단의 바이낸스 가입 버튼을 누르면 가입 페이지를 열 수 있습니다. 계정 생성, 본인 인증, USDⓈ-M Futures 활성화를 순서대로 완료하세요. 이미 계정이 있다면 이 단계는 건너뜁니다.
2. Binance에서 API Key 생성
- 1API Management 열기
바이낸스 계정의 API 관리 화면으로 이동합니다. - 2새 API 생성
알아보기 쉬운 이름을 지정하고 보안 인증을 완료합니다. - 3Key와 Secret 보관
Secret은 생성 직후 한 번만 표시될 수 있으므로 안전한 곳에 보관합니다. - 4권한 설정
읽기와 Futures 거래 권한만 활성화하고 출금 권한은 활성화하지 않습니다.
API 권한 체크
| 권한 | 필요 여부 | 비고 |
|---|---|---|
| Enable Futures | 필수 | Binance API 관리 페이지에서 체크 |
| Enable Reading | 필수 | 잔고·포지션 조회 |
| Enable Spot & Margin Trading | 불필요 | 선물 전용이므로 비활성화 권장 |
| Enable Withdrawals | 금지 | 자동매매에 필요 없음 |
| IP 제한 | 강력 권장 | 24시간 운용 PC의 고정 IP가 있을 때 허용 목록 등록 |
3. 프로그램에 API 입력
- 1프로그램 상단에서 API 설정 버튼을 누릅니다.
- 2API Key와 Secret Key를 붙여넣습니다. Secret은 화면에서 마스킹됩니다.
- 3처음 연습할 때는 Testnet을 선택하고 테스트넷 전용 Key를 입력합니다. 실거래 Key와 테스트넷 Key는 서로 다릅니다.
- 4저장 후 연결 상태와 Account Dashboard의 잔고 표시를 확인합니다.
.env 파일을 직접 만들거나 편집할 필요가 없습니다. API 정보와 Testnet 선택은 API 설정 창에서 저장합니다.첫 실행 순서
- 1프로그램 실행
배포 실행 파일 또는 최신 Python 파일을 실행합니다. 창 제목이 현재 배포 버전인지 확인하세요. - 2API 연결 확인
API 설정에서 Key를 저장하고 Account Dashboard에 잔고가 표시되는지 확인합니다. - 3Market과 제외 종목 설정
CRYPTO / TRADFI / ALL 중 대상을 고르고, 거래 제한 또는 원하지 않는 종목을 Excluded Symbols에 한 줄씩 입력합니다. - 4Cache Manager 확인
최초 캔들 다운로드는 백그라운드에서 계속됩니다. 최근 데이터가 준비되면 Trading은 시작할 수 있지만 장기 백테스트는 필요한 기간의 캐시가 준비된 뒤 실행하는 편이 좋습니다. - 5백테스트 3단계 실행
Sweep으로 후보를 찾고 Validation과 Walk-forward로 과최적화 여부를 확인합니다. - 6추천 설정 적용 후 다시 확인
Apply Best Settings를 누른 뒤 Market, Top N, Timeframe, 레짐별 파라미터가 Trading 탭에 의도대로 반영됐는지 직접 확인합니다. - 7Testnet 또는 소액으로 시작
Start Auto Trade를 누르고 Log, Current Top N, Open Positions, Trade History를 함께 확인합니다.
권장 시작값 (보수적)
| 파라미터 | 권장값 | 이유 |
|---|---|---|
| Decision TF | 15m | 방향/추세 판단용. EMA, ADX, Volume, Regime, RSI Exhaustion을 판단 |
| Execute TF | 5m | 실제 진입 타이밍용. Decision 방향과 같은 Donchian 돌파가 나올 때만 주문 |
| Trailing TF | 5m | Decision/Execute TF보다 짧거나 같게 설정하면 트레일링이 빠르게 반응 |
| Leverage | 3 ~ 5 | 5배 초과 시 변동성에 의한 강제청산 위험 급증 |
| Risk % | 0.25 ~ 0.5 | 잔고의 0.25~0.5%만 한 포지션 손절로 소진. 처음엔 0.25 권장 |
| Max Position % | 10 ~ 15 | 포지션 1개 노셔널 상한. 너무 크면 잔고 편중 위험 |
| ATR Mult | 1.5 ~ 2.0 | 낮으면 손절이 너무 좁아 잦은 손절 발생 |
| EMA Gap % | EMA20과 EMA60의 이격률(%). LONG은 EMA Gap 이상, SHORT는 -EMA Gap 이하일 때만 Trend Following 진입 허용. 0은 필터 비활성화. | Mean Reversion에서는 사용하지 않음. |
| Trigger R | 1.0 ~ 1.5 | 1R 수익 달성 후 트레일링 활성화 — 수익권 진입 전 손절 최소화 |
| Regime 활성 | NORMAL + TREND | 초기 운용 기준. 최종값은 사용자가 수행한 백테스트 결과로 결정 |
Cache Manager
프로그램은 Parquet 기반 캔들 캐시를 사용합니다. 최초 실행 시 필요한 캔들을 백그라운드에서 구축하며, 이후에는 새로 마감된 캔들만 증분 업데이트합니다.
동작 방식
- 1manifest 확인
프로그램 시작 시 manifest.json을 읽어 심볼별 캐시 상태를 즉시 확인합니다. manifest는 각 심볼의 첫 캔들·마지막 캔들 시각만 저장하는 경량 인덱스(65KB 수준)입니다. - 2Trading 우선
최근 데이터 확보 후 자동매매는 즉시 시작할 수 있으며, 나머지 히스토리는 백그라운드에서 계속 구축됩니다. - 3주기적 증분 업데이트
선택된 Decision / Execute / Trailing TF와 Dynamic TopN 볼륨 랭킹용 4h 캔들을 주기적으로 추가합니다. 업데이트가 끝난 뒤 다음 마감봉 시간까지 대기하므로, 긴 다운로드 중에 다음 업데이트가 중복 큐잉되지 않습니다. - 4백테스트 API Skip
백테스트 실행 시 manifest를 메모리에 로드하여 심볼별로 O(1) 신선도 체크를 수행합니다. 캐시가 신선하면 API 호출 없이 parquet 파일만 읽어 반환합니다. 캐시 구축 완료 후 반복 백테스트에서 API 호출이 0회로 줄어듭니다. - 5안전 저장
Atomic Write(.tmp→rename)를 사용하여 종료 중에도 기존 캐시를 보호합니다. manifest는 백테스트 Pass 종료 시 최대 2회 일괄 저장합니다.
| 항목 | 설명 |
|---|---|
| Status | Initial Build: 캐시 없음, 365일치 최초 다운로드 중 Updating: 기존 캐시 있음, 새 캔들 증분 추가 중 Ready: 구축 완료 Error: 네트워크 오류 등 |
| Progress | 처리된 (심볼 × 인터벌) 수 / 전체. 예: 490 / 1058 (46%) |
| Cache Hit | manifest가 커버하여 API 호출 없이 로컬 파일에서 직접 읽은 수 |
| API Download | manifest 미커버로 실제 API를 호출하여 다운로드한 수 |
| Errors | 다운로드 실패 심볼 수. 오류 발생 시에만 표시. 해당 심볼은 건너뛰고 계속 진행 |
| Mode | 365-day initial download: 최초 구축 background append: 주기적 증분 업데이트 4h volume cache: Dynamic TopN 볼륨 랭킹용 4시간봉 사전 업데이트 |
| Next Update | 다음 자동 증분 업데이트 예정 시각. 업데이트가 끝난 뒤 각 인터벌의 다음 마감봉 시간까지 대기합니다. |
| Cache Size | 로컬 캐시 디렉터리 전체 크기 |
| Last Sync | 마지막 증분 업데이트 완료 시각 |
/fapi/v1/klines)를 사용합니다. API 키가 설정되지 않아도 인터넷 연결만 있으면 캐시가 정상적으로 구축됩니다.
4h 캔들도 백그라운드에서 미리 구축·증분 업데이트합니다. Sweep 실행 시 Pass 1은 대부분 API 다운로드가 아니라 로컬 parquet/manifest 읽기로 처리되며, 부족한 구간만 보충 다운로드합니다.
- Top N 패널 추가(현재 Top N 심볼 표시)
- 현재 보유 중인 Top N 종목은 파란색 굵은 글씨로 강조
- Excluded Symbols 패널 추가(한 줄에 한 종목 입력)
- Excluded Symbols는 실거래, 백테스트, Validation, Walk-forward에 동일 적용
- Log / Top N / Cache Manager 레이아웃 개선
- Trade History의 OPEN 상태는 날짜와 시간을 모두 표시
Trading 탭
라이브 자동매매의 모든 설정이 이 탭에 집중됩니다. 자동매매 실행 중에는 설정 필드가 비활성화됩니다.
기본 설정
| 파라미터 | 기본값 | 범위 | 설명 |
|---|---|---|---|
| Top N Symbols | 30 | 10~50 | 24h 거래대금 상위 N개 종목을 스캔 대상으로 선정. 클수록 진입 기회 증가·API 부하 증가. 심볼 유니버스는 4시간마다 자동 갱신. |
| Market Universe | CRYPTO | CRYPTO / TRADFI / ALL | CRYPTO: 코인 선물 Top N TRADFI: 금·주식·ETF 등 TRADFI 선물 Top N ALL: 두 시장을 합친 거래대금 Top N |
| Decision TF | 15m | 1m~4h | 진입 신호 판단용 캔들 타임프레임. 짧을수록 신호 빈도 높고 노이즈 많음. 완성된 봉(closed candle)만 신호 판단에 사용. |
| Trailing TF | 5m | 1m~15m | 트레일링 스탑 ATR 계산용 타임프레임. Decision TF보다 짧게 설정해야 트레일링이 더 빠르게 반응. |
| Leverage | 5 | 1~20 | 선물 레버리지 배수. 진입 시 거래소에 자동 설정. 수익·손실 모두 배수로 증폭. 5배 이하 강력 권장. |
| Risk % | 1.0 | 0.1~5.0 | 포지션 1개에서 손절 발동 시 잃는 최대 금액 = 총잔고 × Risk%. 레짐별 Risk%를 지정하지 않으면 이 값이 기본 폴백으로 사용됨. |
| Max Long Pos. | 5 | 1~20 | 동시 보유 LONG 포지션 최대 수. 한도 도달 시 신규 LONG 진입 건너뜀. |
| Max Short Pos. | 5 | 1~20 | 동시 보유 SHORT 포지션 최대 수. LONG과 독립 관리. |
| Max Position % | 20 | 5~100 | 포지션 1개 노셔널 상한 = 총잔고 × Max Position% × 레버리지. Risk 기준 수량과 이 상한 중 더 작은 값 사용. |
3-TF Entry Engine
Trend Following 전략은 판단과 실행을 분리한 3단계 타임프레임 구조를 사용합니다. Decision TF는 방향을 허가하고, Execute TF는 실제 진입 타이밍을 확인하며, Trailing TF는 진입 이후 청산을 관리합니다.
| 구분 | 역할 | 사용 지표 | 예시 |
|---|---|---|---|
| Decision TF | 거래 방향과 진입 허가 판단 | EMA, ADX, Volume, Regime, RSI Exhaustion | 15m에서 LONG/SHORT 방향 결정 |
| Execute TF | 실제 주문 타이밍 확인 | Donchian High/Low 돌파 | 5m에서 같은 방향 돌파가 나오면 진입 |
| Trailing TF | 진입 후 청산·트레일링 관리 | ATR Trailing, Exit Mode | 5m ATR 기준으로 Stop 갱신 |
Regime Settings
각 레짐(QUIET · NORMAL · TREND · PANIC)마다 전략과 파라미터를 독립적으로 설정합니다. 체크박스 OFF 시 해당 레짐에서 신규 진입 없음.
| 파라미터 | Trend Following | Mean Reversion |
|---|---|---|
| Strategy | trend_following (돌파 추세추종) | mean_reversion (평균복귀) |
| ADX ADX Min / ADX Max |
ADX Min: 진입 허용 최소 추세강도. ADX < 이 값이면 진입 무시. 낮으면 신호 증가·오신호↑ | ADX Max: 진입 허용 최대 추세강도. ADX > 이 값이면 진입 무시 (추세장 진입 차단) |
| ATR Mult | 공통. 손절폭 = Entry ATR × ATR Mult. 낮으면 잦은 손절 / 높으면 한 번 손절 시 손실 증가 | |
| Vol Mult / RSI Entry |
Vol Mult: 거래량 > Volume MA × Vol Mult. 낮으면 진입 빈도 증가 | RSI Entry: LONG: RSI ≤ 이 값 / SHORT: RSI ≥ (100 − 이 값). 낮으면 극단 과매도만 포착 |
| Trigger R / BB Sigma |
Trigger R: 트레일링 활성화 거리 = 손절폭 × Trigger R. 낮으면 수익 초기에 트레일링 시작 | BB Sigma: Bollinger Band 밴드폭 배수(σ). 기본 2.0. 낮으면 진입 빈도 증가 |
| Risk % | 레짐별 포지션 사이즈 조정. 미입력 시 기본 설정의 Risk% 사용 | |
| Exit Mode | trailing / partial_tp / fast_exit 선택 (아래 비교 참조) | BB Mid / trailing / partial_tp / fast_exit 선택 가능. BB Mid는 진입 시점의 BB Middle을 목표가로 사용하며, 나머지 모드는 Trend Following과 동일한 청산 방식을 사용합니다. |
Exit Mode 비교
| Exit Mode | 동작 | 특성 | 추천 레짐 |
|---|---|---|---|
| trailing | 손절 또는 트레일링 스탑으로만 청산. 별도 TP 없음 | 강한 추세를 길게 추적 가능. 횡보 전환 시 수익 반납 위험 | NORMAL, TREND |
| partial_tp | 1R 목표 도달 시 50% 선청산 → 나머지 50% 트레일링 계속. RSI 과매수/과매도 시에도 50% 선청산 | 수익 일부 확정 + 추세 지속 시 추가 수익. 균형적 | NORMAL |
| fast_exit | 1R 목표 도달 즉시 전량 청산. 트레일링 없음 | 급변동 구간에서 수익 빠른 확정. 큰 추세 놓칠 수 있음 | PANIC |
| BB Mid | Mean Reversion 전용. BB 중간밴드(SMA20) 도달 시 전량 익절 | 평균복귀 목표 달성 청산. 진입 시점 BB Mid로 타겟 고정 | QUIET (권장) |
CI Filter (선택)
Choppiness Index(CI)를 이용해 횡보 구간에서 Trend Following 진입을 차단합니다. Mean Reversion 전략에는 적용되지 않습니다.
| 설정 | 설명 |
|---|---|
| CI Filter ON | CI < 61.8 조건 추가. CI ≥ 61.8 (횡보 구간)에서는 TF 진입 차단 |
| Period | CI 계산 룩백 기간(봉 수). 기본값 14. 짧을수록 빠른 반응·노이즈 증가. 길수록 안정적·추세 초입 진입 지연 |
서버 Stop (Server-side STOP_MARKET)
포지션 진입 시 Binance 서버에 STOP_MARKET 주문을 자동으로 등록합니다. 봇 프로세스가 다운되거나 네트워크가 끊어진 상황에서도 거래소가 손절을 대신 실행합니다.
| 동작 | 설명 |
|---|---|
| 진입 시 등록 | 포지션 개설 직후 Binance에 STOP_MARKET 주문 자동 등록. workingType=MARK_PRICE 사용 — Last Price 스파이크로 불합리한 청산 방지 |
| trailing 이동 시 갱신 | 트레일링 스탑이 이동할 때마다 기존 주문을 취소하고 새 가격으로 재등록. 서버 stop 가격이 항상 최신 trailing stop과 동기화 |
| 로컬 청산 시 취소 | 봇이 포지션을 청산할 때(STOP, TRAILING_TAKE, TIME_EXIT 등) 서버 stop 주문을 함께 취소. 청산 후 고아 주문이 남지 않음 |
| Emergency Close 시 취소 | [Emergency Close All] 버튼 클릭 시 각 포지션의 서버 stop을 먼저 취소한 뒤 시장가 청산 실행 |
| 외부 청산 감지 시 취소 | 봇이 모르는 사이 포지션이 사라진 경우(수동 청산 등) 다음 monitor 사이클에서 서버 stop을 자동 취소 |
| 재시작 후 복원 | 재시작 시 저장된 server_stop_order_id가 없으면 서버 stop을 자동 재등록 (repair path) |
reduceOnly=true로 등록됩니다. partial close 이후 서버 stop 수량이 실제 잔량보다 크더라도 Binance가 잔량만 청산하므로 초과 포지션이 열리지 않습니다.
[SERVER STOP ERROR] 로그가 찍히고 로컬 stop monitor는 계속 동작합니다. 단, 봇이 오프라인 상태에서는 서버 stop이 없으면 손절이 실행되지 않습니다.
정지 / 비상 청산
| 버튼 | 동작 | 주의 |
|---|---|---|
| Stop | 신규 진입 중단. 기존 포지션은 자동 관리 계속 | 포지션을 유지한 채 안전하게 종료 가능 |
| Emergency Close All | 각 포지션의 서버 STOP_MARKET 주문을 먼저 취소한 뒤, 거래소의 모든 포지션을 시장가 reduce-only로 즉시 청산 | 변동성 구간에서 슬리피지 발생 가능 |
Trading 화면 패널
실거래 중에는 설정값보다 상태 패널을 더 자주 확인하게 됩니다. 아래 네 영역만 익혀도 현재 프로그램 상태를 빠르게 판단할 수 있습니다.
| 패널 | 무엇을 보여 주나 | 확인 포인트 |
|---|---|---|
| Account Dashboard | 잔고, 손익, 포지션 수, 연결 상태 | API 연결 직후 잔고가 맞는지 먼저 확인 |
| Open Positions | 현재 보유 중인 방향, 진입가, 현재가, Stop, PnL | 거래소의 실제 포지션과 수량·방향 대조 |
| Current Top N | 현재 24시간 거래대금 기준 스캔 종목과 마지막 갱신 시각 | 보유 중인 종목은 파란색 굵은 글씨로 강조. 목록은 4시간마다 갱신 |
| Log | 유니버스 갱신, 신호, 주문, Stop, 청산, 오류 | ERROR만 보지 말고 직전 SIGNAL/OPEN 흐름도 함께 확인 |
| API Monitor | REST 호출, WebSocket, User Data Stream 상태 | 호출 급증, WS SILENT, 재연결 반복 여부 확인 |
Excluded Symbols
자동매매에서 제외할 심볼을 한 줄에 하나씩 입력합니다. 예: BTCUSDT. 저장된 목록은 실거래뿐 아니라 Sweep, Validation, Walk-forward에도 동일하게 적용됩니다.
Start · Stop · Emergency Close
| 버튼 | 동작 | 사용 시점 |
|---|---|---|
| Start Auto Trade | 설정값으로 신규 신호 탐색과 포지션 관리를 시작 | 설정·API·잔고를 모두 확인한 뒤 |
| Stop | 신규 진입을 중단하고 기존 포지션 관리는 계속 | 프로그램을 안전하게 멈추거나 신규 진입만 막을 때 |
| Emergency Close All | 서버 Stop을 취소한 뒤 모든 포지션을 시장가로 청산 | 정상 Stop이 어려운 긴급 상황에서만 |
Trade History
프로그램이 관리한 거래와 Binance 체결 내역을 바탕으로 진입·청산·실현손익을 보여 줍니다. 프로그램을 다시 실행하면 최근 3일의 Binance 거래 내역을 불러와 기록을 보완합니다.
| 항목 | 설명 | 확인 방법 |
|---|---|---|
| OPEN | 현재 열려 있는 거래. Open Time은 날짜와 시간을 함께 표시 | Open Positions와 심볼·방향 대조 |
| CLOSED | 청산이 확인된 거래 | Exit Reason과 Fill Price 확인 |
| Realized PnL | Binance 체결 기준 실현손익 | 수수료·여러 번의 부분 체결 때문에 단순 가격차 계산과 다를 수 있음 |
| SERVER STOP | Binance 서버의 STOP_MARKET 주문으로 청산 | 프로그램이 꺼져 있던 동안 체결된 경우도 재시작 후 동기화 |
| Exit Reason | STOP, TRAILING_TAKE, TIME_EXIT, FAST_EXIT 등 | 전략 결과 분석 시 이유별 성과를 분리해 확인 |
Backtest Sweep 탭
여러 파라미터 조합을 일괄 테스트해 레짐별 최적 파라미터를 탐색합니다. Sweep은 각 Regime을 독립적으로 테스트하여 후보 세팅을 찾는 단계이며, 실제 시간축 Adaptive 성과 검증은 Validation 탭에서 수행합니다.
Sweep 방식
예시: QUIET(3조합) + NORMAL(12조합) + TREND(6조합) = 총 21회 실행 (21 = 3 + 12 + 6)
파라미터 리스트 입력
각 파라미터 필드에 콤마(,)로 여러 값을 입력하면 해당 레짐의 Cartesian Product로 테스트됩니다.
# 예시: NORMAL 레짐 ADX Min: 20, 25, 30 ATR Mult: 1.5, 2.0 Vol Mult: 1.2 Trigger R:1.0, 1.5 Risk %: 0.5 # NORMAL 조합 수: 3 × 2 × 1 × 2 × 1 = 12
Sweep 설정 파라미터
| 파라미터 | 설명 |
|---|---|
| Days / Date Range | 백테스트 기간. Recent Days(최근 N일) 또는 날짜 범위 직접 지정 가능 |
| Top N | 백테스트에 사용할 종목 수. 많을수록 통계 신뢰도 증가·시간 증가 |
| Decision TF / Execute TF / Trailing TF | 백테스트에 사용할 3단계 타임프레임. 실거래와 동일하게 Decision은 방향 판단, Execute는 진입 타이밍, Trailing은 청산 관리에 사용 |
| Leverage / Wallet | 백테스트 레버리지·가상 초기 잔고(USDT) |
| Market Universe | CRYPTO / TRADFI / ALL. 백테스트 스캔 대상 결정 |
| Regime 체크박스 | 해당 레짐을 sweep에 포함할지 여부 |
Sweep Combos 카드
Settings 박스 우측에 표시되는 카드입니다. 현재 입력값 기준으로 레짐별 조합 수와 총합, 예상 소요 시간을 실시간으로 계산합니다.
Adaptive Combined Result와 Daily PnL Charts를 표시하지 않습니다.
Sweep의 목적은 성과 검증이 아니라 레짐별 후보 세팅 탐색이므로, 실제 Adaptive 성과와 일별 손익 차트는 Validation에서 확인합니다.
결과 해석
| 지표 | 의미 | 기준 |
|---|---|---|
| PF (Profit Factor) | 총 수익 / 총 손실 | 1.3 이상 우수, 1.0 미만 손실권 |
| Net PnL | 순 수익 (수수료 포함) | 양수여야 유효 |
| Win Rate | 수익 거래 비율 (%) | 전략마다 기준 다름. PF와 함께 해석 |
| MDD | Maximum Drawdown — 최대 낙폭. USDT 절대값과 고점 대비 %를 함께 표시. 예: -234.50 (12.34%) | 낮을수록 좋음. % 기준 20% 초과 주의 |
| Trades | 총 거래 횟수 | 10회 미만은 통계 신뢰도 낮음(INSUFFICIENT) |
| Score | PF×0.45 + Net PnL×0.30 + Trades×0.25 정규화 종합점수 | 레짐 내 Top 10 랭킹 기준 |
Apply Regime Best
Sweep 완료 후 [Apply Regime Best #1] 버튼을 클릭하면 레짐별 최적 파라미터가 Trading 탭의 Regime Settings에 자동 적용됩니다.
Backtest Validation 탭
Sweep으로 선정한 레짐별 Best Setting을 실제 시간축에서 Adaptive 방식으로 검증합니다. Top N 적용, Regime 전환, 포지션 제한, 손익 곡선을 함께 반영하여 실 운용에 가까운 결과를 확인합니다.
Sweep vs Validation 비교
| 항목 | Sweep | Validation |
|---|---|---|
| 목적 | 레짐별 최적 파라미터 탐색 | 선정 세팅의 실제 Adaptive 성과 검증 |
| 계산 방식 | 각 Regime을 독립적으로 분리하여 테스트 | Top N과 시간축 Regime 전환을 반영하여 통합 실행 |
| 입력 | 파라미터 리스트 (콤마 구분) | 단일 파라미터 값 또는 Sweep Best 적용값 |
| 결과 | Adaptive Regime Best Settings + Regime Best Top 10 Ranking | Adaptive Regime Best Settings + Adaptive Combined Result + Daily PnL Charts |
| 용도 | 초기 탐색 | 최종 확인 및 과적합 검증 |
1. Sweep에서 최적 파라미터 선정
2. Validation으로 다른 기간(Out-of-Sample)에서 재검증
3. 두 기간 모두 PF ≥ 1.2 이상이면 실 운용 고려
Regime Best Top 10 Ranking을 표시하지 않습니다.
Validation은 후보 탐색이 아니라 검증 단계이므로, 실제 Adaptive Combined Result와 Daily PnL Charts를 중심으로 확인합니다.
Walk-forward 탭
Validation 탭에 입력된 단일 설정값을 여러 시간 구간에 반복 적용하여, In-sample(IS) 성과가 Out-of-sample(OOS)에서도 얼마나 비슷하게 유지되는지 확인합니다. Walk-forward는 수익성이 좋은 설정을 찾는 기능이 아니라, 이미 선택한 설정의 시간축 일반화 안정성을 검사하는 기능입니다.
Sweep · Validation · Walk-forward 비교
| 기능 | 목적 | 설정 출처 |
|---|---|---|
| Sweep | 여러 조합에서 후보 설정 탐색 | Sweep 탭의 파라미터 목록 |
| Validation | 선택한 단일 설정의 절대 성과 검증 | Validation 탭의 현재 설정 |
| Walk-forward | 동일 설정의 IS/OOS 성과 유사성·안정성 검증 | 실행 시점 Validation 설정 스냅샷 |
동작 원리
전체 기간을 지정한 Window 수로 나누고, 각 Window의 앞부분을 IS, 뒷부분을 OOS로 사용합니다. 동일한 Validation 설정으로 IS와 OOS를 각각 계산한 뒤 두 결과의 유사성을 비교합니다.
# 실행 시 한 번 고정 Validation Settings Snapshot → 모든 Window 공통 적용 W1 → IS 계산 + OOS 계산 → PF Similarity 평가 W2 → IS 계산 + OOS 계산 → PF Similarity 평가 W3 → IS 계산 + OOS 계산 → PF Similarity 평가
세팅 방법
① Validation 탭 — 검증할 단일 설정 준비
검증하려는 설정을 Validation 탭에 입력합니다. Sweep 결과를 적용해도 되고, 사용자가 직접 입력한 설정을 사용해도 됩니다.
② Walk-forward 탭 — 기간·Window 설정
| 항목 | 설명 | 권장값 |
|---|---|---|
| 시작일 / 종료일 | 전체 분석 기간 | 시장 국면이 여러 번 포함되도록 충분히 길게 설정 |
| Window 수 | 전체 기간을 몇 개의 슬라이딩 구간으로 나눌지 결정 | 4~6개 |
| IS 비율 (%) | 각 Window에서 IS가 차지하는 비율. 나머지는 OOS | 70% 전후 |
결과 테이블 컬럼
| 컬럼 | 의미 | 해석 |
|---|---|---|
| IS 거래 / OOS 거래 | 각 구간의 거래 횟수 | 거래 수가 너무 적으면 PF·WR 비교 신뢰도가 낮음 |
| IS PF / OOS PF | 각 구간의 Profit Factor | 절대 수익성은 Validation 결과와 함께 해석 |
| OOS MDD | OOS 최대 낙폭의 USDT·% 표시 | OOS에서 발생한 하락 위험 확인 |
| IS WR / OOS WR | 각 구간 승률 | PF와 함께 사용 |
| WR Δ | OOS WR − IS WR | 0에 가까울수록 승률 유지가 안정적 |
| Trade Ratio | OOS 거래 수 ÷ IS 거래 수 | 기간 길이가 다르므로 단독 평가보다 신호 밀도 변화 참고용 |
| PF Similarity | min(OOS PF ÷ IS PF, IS PF ÷ OOS PF) × 100 | 100%에 가까울수록 IS와 OOS PF가 유사함. OOS가 더 좋아져도 100%를 초과하지 않음 |
| 일반화 평가 | PF Similarity 기반 자동 등급 | 절대 수익성이 아닌 IS/OOS 유사성 평가 |
| Validation Settings | 이번 실행에 고정된 설정 스냅샷 | 어떤 조건으로 결과가 산출됐는지 재현할 때 사용 |
일반화 평가 기준
| 등급 | PF Similarity | 의미 |
|---|---|---|
| Excellent | 90% 이상 | IS와 OOS 성과가 매우 유사 |
| Good | 75% 이상 | 일반화 안정성이 양호 |
| Fair | 60% 이상 | 차이가 있으므로 추가 확인 필요 |
| Weak | 40% 이상 | IS/OOS 성과 편차가 큼 |
| Poor | 40% 미만 | 시간 구간에 따른 성과 불안정성이 매우 큼 |
마지막 요약 창
| 항목 | 설명 |
|---|---|
| 평균 PF Similarity | 전체 Window의 평균 유사성 |
| 최저 PF Similarity | 가장 불안정했던 Window의 유사성 |
| OOS PF ≥ 1.0 Window | OOS가 수익권이었던 Window 수. 일반화 점수와 별도 참고 |
| Generalization Risk | 전체 Window의 유사성과 최저 구간을 종합한 위험도. 낮음 / 중간 / 높음으로 색상 표시 |
권장 사용 절차
- 1Sweep
필요한 경우 여러 조합에서 후보 설정을 탐색합니다. - 2Validation
선택한 단일 설정의 PF, Net PnL, MDD, 거래 수 등 절대 성과를 확인합니다. - 3Walk-forward
같은 Validation 설정으로 여러 Window의 PF Similarity와 Generalization Risk를 확인합니다. - 4최종 판단
Validation 수익성이 충분하고 Walk-forward Risk가 낮거나 허용 가능한 수준일 때 실전 후보로 검토합니다.
실행 시간
실거래 시작 전 최종 체크
아래 항목 중 하나라도 확인되지 않았다면 실거래 시작을 미루세요.
- API 설정에서 Testnet이 아닌 실거래 모드와 실거래 API Key를 선택했다.
- API에 Reading/Futures 권한만 있고 Withdraw 권한은 없다.
- Account Dashboard 잔고와 Binance Futures 잔고가 일치한다.
- Sweep 후보를 다른 기간의 Validation과 Walk-forward로 검증했다.
- 수수료와 슬리피지를 포함한 결과에서도 PF, MDD, 거래 수가 허용 범위다.
- Apply Best Settings 후 Market, Top N, TF, 레짐별 값을 Trading 탭에서 다시 확인했다.
- 거래 제한 종목과 원치 않는 종목을 Excluded Symbols에 입력했다.
- Leverage 3~5배, Risk 0.25~0.5%, Max Position 10~15% 등 보수적 값에서 시작한다.
- Start 후 Binance 앱에서 실제 주문·서버 Stop·포지션 수량을 직접 대조한다.
- 인터넷 장애나 프로그램 종료 시에도 대응할 수 있도록 Binance 앱에 로그인할 수 있다.
시장 Regime 분류
봉 마감 시점마다 ATR%(= ATR ÷ 현재가 × 100)를 계산해 4가지 레짐으로 분류합니다. 레짐에 따라 전략·파라미터가 자동 전환됩니다.
레짐별 파라미터 튜닝 가이드
| 레짐 | ATR Mult | 권장 이유 |
|---|---|---|
| QUIET | 1.0 ~ 1.5 | 저변동 구간이므로 좁은 손절로 MR 리스크 제한 |
| NORMAL | 1.5 ~ 2.0 | 균형 설정. partial_tp와 함께 사용 시 적합 |
| TREND | 2.0 ~ 2.5 | 강한 추세에서 손절 폭 넓혀 조기 손절 방지 |
| PANIC | 2.0 ~ 3.0 | 극단 변동성. 단, fast_exit이므로 실제 손절까지 안 가는 경우 많음 |
Trend Following 전략
NORMAL · TREND · PANIC 레짐에서 사용합니다. EMA 크로스 + Donchian 돌파 + 거래량 급증 + ADX 필터 4가지 조건이 모두 충족될 때 진입합니다.
사용 지표
| 지표 | 계산 방식 | 역할 |
|---|---|---|
| EMA 20 / 60 | 지수이동평균, 기간 20·60 | 추세 방향 판단. EMA20 > EMA60 = 상승추세 |
| ATR | SMA 방식, 기간 14 (Wilder RMA 아님) | 손절폭·트레일링 거리·Regime ATR% 계산 |
| ADX | SMA 방식, 기간 14 | 추세 강도 필터. ADX ≥ ADX Min이어야 진입 |
| Donchian Channel | 최근 20봉 최고가/최저가 | 돌파 신호. 종가 > 이전 봉 Donchian High → LONG |
| Volume MA | 20봉 단순이동평균 | 거래량 급증 필터. 거래량 > MA × Vol Mult |
| RSI | Wilder RSI, 기간 14 | partial_tp 모드 보조 청산 신호 (과매수/과매도) |
| CI | Choppiness Index, 기간 14 (기본) | 선택적. CI < 61.8 조건 추가 시 횡보 진입 차단 |
진입 조건 (4+1)
| 조건 | LONG 진입 | SHORT 진입 |
|---|---|---|
| ① 추세 방향 | EMA20 > EMA60 | EMA20 < EMA60 |
| ② 추세 강도 | ADX ≥ ADX Min | ADX ≥ ADX Min |
| ③ 거래량 급증 | 거래량 > Volume MA × Vol Mult | 거래량 > Volume MA × Vol Mult |
| ④ 가격 돌파 | 완성봉 종가 > 이전봉 Donchian High | 완성봉 종가 < 이전봉 Donchian Low |
| ⑤ CI 필터 (선택) | CI Filter ON 시 추가: CI < 61.8 | |
트레일링 스탑 메커니즘
Trailing TF 봉 기준 ATR이 변경되면 트레일링 거리도 동적으로 갱신됩니다.
Time Exit
포지션 개설 후 72시간이 경과하면 강제 청산합니다. 평균복귀가 장기간 실패하는 케이스를 방어하는 안전망입니다.
Mean Reversion 전략
QUIET 레짐(ATR% < 2, 저변동 횡보)에서 사용합니다. Bollinger Band 이탈 + RSI 과매도/과매수 + ADX Max 필터 3가지 조건이 모두 충족될 때 진입하고, BB 중간밴드(SMA20) 복귀 시 익절합니다.
사용 지표
| 지표 | 계산 방식 | 역할 |
|---|---|---|
| Bollinger Bands | 20봉 SMA ± BB Sigma × σ | 진입 경계: 하단밴드 이탈(LONG) / 상단밴드 이탈(SHORT). 중간밴드(SMA20)가 익절 목표 |
| RSI | Wilder RSI, 기간 14 | 과매도/과매수 확인. RSI ≤ RSI Entry → LONG / RSI ≥ (100 − RSI Entry) → SHORT |
| ATR | SMA 방식, 기간 14 | 손절폭. 손절가 = 진입가 ± ATR × ATR Mult |
| ADX | SMA 방식, 기간 14 | 횡보 확인용 상한 필터. ADX ≤ ADX Max이어야 진입 |
진입 조건 (3가지 모두)
| 조건 | LONG (과매도 반등) | SHORT (과매수 반락) |
|---|---|---|
| ① ADX 횡보 확인 | ADX ≤ ADX Max | ADX ≤ ADX Max |
| ② RSI 과매도/과매수 | RSI ≤ RSI Entry | RSI ≥ (100 − RSI Entry) |
| ③ BB 밴드 이탈 | 종가 < BB Lower (= SMA20 − BB Sigma × σ) | 종가 > BB Upper (= SMA20 + BB Sigma × σ) |
청산 로직
청산 우선순위
포지션 모니터링 루프에서 다음 순서로 청산 조건을 확인합니다.
| 우선순위 | 청산 조건 | 해당 전략 |
|---|---|---|
| 1 | fast_exit: 1R 목표 도달 시 전량 청산 | TF PANIC |
| 2 | partial_tp: 1R 도달 또는 RSI 과매수/과매도 시 50% 선청산 | TF NORMAL |
| 3 | BB Mid 도달 시 전량 익절 | MR QUIET |
| 4 | Time Exit: 보유 72시간 초과 | 전략 공통 |
| 5 | Stop/Trailing Stop: 가격이 손절가 도달 (로컬 monitor) | 전략 공통 |
| 보조 | 서버 STOP_MARKET: 봇 오프라인 시 Binance 서버가 직접 실행. 로컬 청산과 중복되지 않도록 로컬 청산 시 자동 취소 | 전략 공통 |
포지션 사이징
두 가지 기준으로 수량을 계산한 뒤 더 작은 값을 최종 수량으로 사용합니다.
• 최종 수량이 거래소 minQty 미만인 경우
• 필요 증거금이 가용잔고의 95%를 초과하는 경우
• 같은 종목이 이미 로컬 포지션 또는 거래소에 존재하는 경우
계산 예시
# 설정: 잔고=1000 USDT, Risk%=0.5, ATR=50, ATR Mult=2.0 # 레버리지=5, Max Position%=15, 현재가=2000 USDT 손절폭 = 50 × 2.0 = 100 USDT Risk 기준 수량 = (1000 × 0.5%) ÷ 100 = 0.05 개 Cap 기준 수량 = (1000 × 15% × 5) ÷ 2000 = 0.375 개 최종 수량 = min(0.05, 0.375) = 0.05 개 # → 노셔널 0.05 × 2000 = 100 USDT / 증거금 = 100 ÷ 5 = 20 USDT
WebSocket & API 구조
PriceWebSocketManager
현재 보유 포지션 종목만 구독하는 mark-price WebSocket입니다. 포지션 변경 시 자동으로 구독 종목을 재동기화합니다.
| 항목 | 내용 |
|---|---|
| 백엔드 우선순위 | websockets (async) → websocket-client (fallback) |
| 구독 방식 | Active-position only: 보유 종목만 bookTicker/markPrice 구독 |
| SSL | cert_reqs=NONE (일부 환경의 인증서 문제 대응) |
| 재연결 | 구독 종목 변경 시 기존 연결 종료 → 신규 URL로 자동 재연결 |
| 가격 max_age | 10초 이상 경과한 WS 가격은 무효 처리 → REST fallback |
UserDataWebSocketManager (UDS)
Binance User Data Stream으로 계정 이벤트(포지션 변경, 주문 체결)를 실시간 수신합니다.
| 항목 | 내용 |
|---|---|
| 목적 | REST 폴링 없이 포지션 변경 실시간 감지 |
| Listen Key | 자동 발급 + 30분마다 keepalive 갱신 |
| max_age | 300초 이상 UDS 이벤트 없으면 REST safety sync 수행 |
REST Fallback
WS가 연결되었으나 5초 이상 페이로드가 없으면 DashboardThread가 REST로 전체 가격 스냅샷을 가져와 GLOBAL_PRICE_CACHE를 보충합니다.
pip install websockets를 확인하세요.
API 모니터
Trading 탭 상단의 API Monitor 패널에서 API 호출 현황을 실시간으로 확인할 수 있습니다.
| 지표 | 표시값 예시 | 설명 및 정상 기준 |
|---|---|---|
| Health | 🟢 Healthy 🟡 Warning 🔴 Critical |
전체 데이터 수신 상태 종합. Healthy = WS LIVE + 가격 캐시 90% 이상 + fallback 5회 이하. Warning = 부분 정상. Critical = 가격 수신 불가 |
| Data Source | LIVE / MIXED / REST / OFFLINE |
가격·계정 데이터 공급원. LIVE = WS+UDS 모두 정상. MIXED = 일부 REST 혼용. REST = WS 없이 REST만. OFFLINE = 데이터 수신 없음 |
| Price WS | 🟢 LIVE 🟡 Connected(No Data) 🔴 Disconnected |
가격 WebSocket 상태. LIVE = 5초 내 페이로드 수신 + 캐시 80% 이상. Connected(No Data) = 연결됐으나 페이로드 미수신 → REST fallback 작동 중 |
| UDS | 🟢 LIVE ● Connected ● Reconnecting |
User Data Stream 상태. LIVE = 연결 + 300초 내 이벤트 수신. Connected = 연결됐으나 이벤트 없음(거래 없을 때 정상). Reconnecting = 재연결 중 |
| Price Cache | 28 / 30 (93%) | 현재 가격이 캐시된 종목 수 / 전체 스캔 종목 수 (비율). 90% 이상이면 정상. 낮으면 WS 구독 누락 또는 REST fallback 불충분 |
| Last Price | 1.2 sec waiting |
가격 캐시 마지막 갱신 후 경과 시간(WS 또는 REST fallback 포함). 10초 이내 정상. waiting = 아직 가격 수신 없음 |
| Last UDS | 42.3 sec no event yet waiting |
UDS(User Data Stream) 마지막 계정 이벤트 수신 후 경과 시간. 거래가 없으면 오래될 수 있음 — 300초 이내면 LIVE 판정. no event yet = 연결됐으나 아직 이벤트 없음(정상). waiting = UDS 미연결 |
| REST/min | 45 (1.9%) | 지난 1분간 REST API 호출 수 (바이낸스 분당 한도 2,400 대비 비율). 10% 초과 시 과도한 호출 주의 |
| WS Msg/min | 120 | 지난 1분간 가격 WS 페이로드 수신 수. 0이면 WS 연결만 됐고 데이터 미수신 → REST fallback 작동 중. 보유 종목 수에 비례해 증가 |
| REST Fallback/min | 0 / 3 | 최근 1분 동안 WS 대신 REST 가격을 사용한 횟수. WS LIVE 시 보통 0이며, WS가 일시적으로 지연되면 증가합니다. 값은 최근 1분 기준으로 자동 갱신됩니다. Health는 이 값뿐 아니라 Price WS, Cache Fill, Price Age를 함께 종합 판단합니다. |
| Reconnects | 2 | 누적 WS 재연결 횟수. 소량은 정상(네트워크 일시 끊김). 빠른 속도로 계속 증가하면 엔드포인트·방화벽 확인 |
| Last REST Sync | 38 sec - |
마지막 REST safety sync(포지션 전체 대조) 후 경과 시간. UDS 이벤트 공백이 길어지면 자동 수행. - = 아직 sync 없음 |
| WS Version | 1.8.0 | 설치된 websocket-client 버전. 권장 버전은 1.8.0. 불일치 시 시작 로그에 VERSION WARNING 출력 |
트러블슈팅
진입 신호가 전혀 없을 때
| 원인 | 확인·해결 |
|---|---|
| 레짐 체크박스 OFF | 해당 레짐(NORMAL/TREND 등) 체크박스가 ON인지 확인 |
| ADX Min이 너무 높음 | ADX 30 이상이면 신호 드물 수 있음. Sweep으로 최적값 탐색 |
| Vol Mult가 너무 높음 | 거래량 폭발 조건이 너무 엄격함. 1.2~1.5 범위 권장 |
| CI Filter 과도 차단 | CI Filter OFF 후 신호 발생 확인. 횡보 시장에서는 CI가 항상 높을 수 있음 |
| Max Positions 도달 | 기존 포지션이 Max Long/Short 한도에 도달해 있으면 신규 진입 건너뜀 |
| Top N 너무 적음 | 스캔 대상 종목이 너무 적으면 조건 충족 가능성 낮음. Top N 늘리거나 TRADFI 전환 |
WS 연결 문제
| 증상 | 해결 |
|---|---|
| Price WS: SILENT | pip install websockets 후 재시작. websockets 패키지 없으면 websocket-client fallback이 일부 환경에서 페이로드 미수신 |
| 자주 재연결 발생 | 네트워크 안정성을 확인하고 API 설정 창의 Testnet/실거래 선택이 Key와 일치하는지 확인 |
| UDS 연결 안 됨 | API 설정 창에서 Key 저장 여부와 Enable Futures 권한, IP 제한을 확인 |
포지션 관련
| 증상 | 해결 |
|---|---|
| [POSITION UNMANAGED] 로그 | 포지션 상태 파일(state/open_positions.json)에 stop 정보 없음. 해당 포지션은 수동 청산 또는 재시작으로 복원 필요 |
| 재시작 후 포지션 사라짐 | state/ 폴더에 open_positions.json이 있는지 확인. 파일 손상 시 거래소 현황과 수동 대조 |
| 수량 계산 오류로 주문 생략 | 잔고 부족 또는 가격 대비 minQty 미달. 잔고를 늘리거나 레버리지/Risk%를 조정 |
| 같은 종목 중복 진입 시도 | 정상 동작. 이미 보유 중인 종목은 자동으로 건너뜀 |
| [SERVER STOP ERROR] 반복 출력 | Binance API 오류로 STOP_MARKET 등록 실패. 로컬 stop monitor는 계속 작동. API Key에 Enable Futures 권한이 있는지 확인. 네트워크 문제일 경우 다음 사이클에 자동 재시도 |
| SERVER_STOP_FILLED로 청산 기록됨 | 봇이 오프라인인 동안 Binance 서버 stop이 체결된 정상 동작. 재시작 후 다음 monitor 사이클에서 자동 감지·기록 |
| Binance에 오래된 STOP 주문이 남아 있음 | 이전에 생성되었거나 비정상 종료로 남은 고아 주문일 수 있음. Binance 앱/웹에서 수동 취소 후 봇 재시작 권장 |
백테스트 속도 느림
Apply Regime Best 버튼 비활성화
Sweep 완료 후에도 버튼이 비활성화이면 backtest_results/parameter_sweep_summary.csv 파일이 없는 것입니다. Sweep이 정상 완료됐는지 로그를 확인하세요.
로그 해석
Log 창에 출력되는 메시지의 형식과 의미를 시간 순서별로 정리합니다. 메시지에서 {} 부분은 실제 값으로 치환됩니다.
① 시작 시 (Startup)
| 로그 메시지 | 의미 / 조치 |
|---|---|
| Strategy : universe=ALL, top_n=30, entry=15m, trailing=5m, ... | 시작 시 설정 요약 출력. 파라미터가 의도대로 적용됐는지 확인 |
| BASE_URL=https://fapi.binance.com | 메인넷 접속 확인. testnet이면 testnet.binancefuture.com 표시 |
| Server time synced. offset={n} ms | 바이낸스 서버와 시간 동기화 완료. offset이 1,000ms 이상이면 서버 시간 불일치 주의 |
| API KEY / SECRET KEY missing in .env | 오류. 저장된 API 정보가 없음. 프로그램 상단의 API 설정 버튼에서 Key와 Secret을 입력·저장 |
| [WS] Price websocket enabled: active-position bookTicker + REST fallback | 가격 WebSocket 정상 시작. 보유 포지션 종목만 구독하고 REST가 대기 중 |
| [UDS] User data stream enabled (REST safety sync kept) | 계정 이벤트 스트림 시작. 체결·포지션 변경을 실시간 수신 |
| [WS VERSION WARNING] websocket-client 1.9.x may not receive... | 경고. websocket-client 버전이 권장(1.8.0)과 다름. pip install websocket-client==1.8.0 후 재시작 |
| Symbol universe refresh: 4h fixed | 스캔 종목 유니버스를 4시간마다 자동 갱신함을 알리는 안내 |
| Position restore: supervised=3, exchange-only=1 | 재시작 시 포지션 복원 결과. supervised = 자동 관리 복원 수, exchange-only = 상태 파일 없이 거래소에만 있는 포지션 수 |
| WARNING: Some existing exchange positions have no saved SL/TP... | 주의. 상태 파일이 없는 포지션 존재 → 자동 손절 관리 불가. 수동 청산 또는 Emergency Close 필요 |
② 진입 신호 (Signal)
| 로그 메시지 | 의미 / 조치 |
|---|---|
| SIGNAL BTCUSDT LONG / trend_following / REGIME=TREND ATR%=5.21 SET=STRATEGY=trend_following,ADX_MIN25.0,VOL1.5,TRIG1.0,ATR_TRAIL2.0,RISK0.50% | 진입 신호 감지. 종목·방향·전략·레짐·ATR%·파라미터 조합 확인. 이후 포지션 사이징 진행 |
| BTCUSDT sizing: balance=1000.0, available=850.0, risk=5.0000(0.50%), stop_atr_mult=2.00, notional=240.0000, required_margin≈48.0000 | 수량 계산 상세. risk=포지션 최대 손실 금액, notional=포지션 명목금액, required_margin=필요 증거금 |
| BTCUSDT skipped: required_margin=820.0, available=850.0 | 증거금이 가용잔고 95%를 초과해 주문 건너뜀. 잔고 부족 또는 레버리지·Risk% 조정 필요 |
| BTCUSDT already in local positions | 이미 보유 중인 종목. 중복 진입 방지 — 정상 동작 |
| BTCUSDT already exists on exchange | 거래소에 같은 종목 포지션 있음. 중복 진입 방지 — 정상 동작 |
| BTCUSDT adjusted qty below minQty | 계산된 수량이 최소 주문 수량 미달. 잔고를 늘리거나 Risk%·레버리지 조정 필요 |
③ 포지션 개설 (Open)
| 로그 메시지 | 의미 / 조치 |
|---|---|
| OPEN BTCUSDT LONG qty=0.050 entry=42000.000000 SL=41520.000000 TRAIL_TRIGGER=42480.000000 TRAIL_DIST=480.000000 TRAIL_TF=5m TRIGGER_R=1.0 ATR_MULT=2.0 RISK=0.50% STRATEGY=trend_following REGIME=TREND ATR%=5.21 |
주문 체결 완료 로그. SL = 손절가 / TRAIL_TRIGGER = 트레일링 활성화 가격 / TRAIL_DIST = 트레일링 간격 |
| OPEN ETHUSDT SHORT qty=0.200 ... STRATEGY=mean_reversion REGIME=QUIET ATR%=1.43 | MR 전략으로 진입. TRAIL_TRIGGER가 BB Mid 청산 목표가로 설정됨 |
④ 포지션 모니터링 (Monitor)
| 로그 메시지 | 의미 / 조치 |
|---|---|
| TRAILING ON BTCUSDT LONG trigger=42480.000000 | 트레일링 스탑 활성화. 가격이 TRAIL_TRIGGER에 도달. 이후 최고가 추적 시작 |
| TRAIL UPDATE BTCUSDT LONG SL=42200.000000 high=42680.000000 | 트레일링 손절가 상향 갱신. high=현재까지 최고가, SL=갱신된 손절가 |
| TRAIL UPDATE BTCUSDT SHORT SL=41800.000000 low=41600.000000 | SHORT 트레일링. low=최저가, SL=갱신된 손절가(상승 방향) |
| RSI EXIT SIGNAL BTCUSDT LONG RSI=74.2 | RSI 과매수 도달 → partial_tp 모드에서 50% 선청산 트리거. 이후 PARTIAL CLOSE 로그 따라옴 |
| [POSITION UNMANAGED] BTCUSDT: stop/ATR state is missing... | 주의. 해당 포지션의 손절 상태 정보가 없어 자동 관리 불가. 수동 청산하거나 state 파일 복구 후 재시작 |
| [POSITION SYNC] REST safety sync OK (3 open exchange positions); next in 60s | 거래소와 포지션 상태 동기화 성공. UDS 이벤트 공백 시 주기적으로 수행 |
| [SERVER STOP] BTCUSDT LONG stop=41520.000000 orderId=12345678 | Binance에 STOP_MARKET 주문 등록 완료. 봇이 오프라인 상태에서도 해당 가격에서 손절 실행됨 |
| [SERVER STOP CANCEL] BTCUSDT orderId=12345678 TRAILING_TAKE | 서버 stop 주문 취소 완료. 로컬에서 정상 청산했으므로 고아 주문 제거. reason 필드에 청산 원인 표시 |
| [SERVER STOP WARN] BTCUSDT cancel failed: {e} | 경고. 서버 stop 취소 실패 — 이미 체결됐거나 주문 ID가 만료된 경우. 로컬 청산과 중복 청산 가능성이 낮으므로 일반적으로 무시 가능 |
| [SERVER STOP ERROR] BTCUSDT: {e} | 오류. STOP_MARKET 주문 등록 실패. 로컬 stop monitor는 계속 동작하나 봇 오프라인 시 서버 손절이 없음. API 권한·네트워크 확인 |
| MANUAL CLOSE DETECTED BTCUSDT LONG PnL=+32.5000 USDT | 프로그램 외부(앱·웹)에서 포지션이 수동 청산됨. 로컬 상태에서 자동 제거 |
| Universe added: XRPUSDT, SOLUSDT | 4시간 유니버스 갱신 시 새로 추가된 종목 |
| Universe removed: DOGEUSDT | 거래대금 순위 하락으로 스캔 대상에서 제외된 종목 |
⑤ 청산 (Close)
모든 청산 로그는 reason 필드로 원인을 구분합니다.
| 로그 메시지 | 의미 |
|---|---|
| CLOSE BTCUSDT LONG reason=STOP price=41520.000000 PnL=-5.0000 USDT | 손절 청산. 가격이 최초 손절가(SL)에 도달. 트레일링이 활성화되기 전에 손절된 경우 |
| CLOSE BTCUSDT LONG reason=TRAILING_TAKE price=42200.000000 PnL=+35.0000 USDT | 트레일링 스탑 익절. 최고가 대비 trail_distance만큼 하락해 트레일링 손절가 도달. 수익권에서 청산 |
| CLOSE ETHUSDT SHORT reason=MEAN_REVERSION_TAKE price=2050.000000 PnL=+18.0000 USDT | MR 익절. 가격이 진입 시점 BB Mid에 도달. Mean Reversion 목표 달성 |
| CLOSE SOLUSDT LONG reason=TIME_EXIT price=98.500000 PnL=-2.0000 USDT | 72시간 시간 초과 강제 청산. 포지션이 72시간 이상 보유됨. 수익·손실 여부와 무관하게 청산 |
| CLOSE XRPUSDT SHORT reason=fast_exit price=0.620000 PnL=+8.0000 USDT | 빠른 익절. fast_exit 모드에서 1R 목표 도달 즉시 전량 청산 |
| SERVER_STOP_FILLED BTCUSDT LONG PnL=-5.2000 USDT | 서버 stop 체결. 봇이 오프라인인 동안 Binance의 STOP_MARKET 주문이 체결되어 포지션 청산. 봇 재시작 후 다음 monitor 사이클에서 감지·기록됨 |
| PARTIAL CLOSE BTCUSDT LONG reason=RSI_EXIT qty=0.025 price=43100.000000 PnL=+27.5000 USDT remaining=0.025 | RSI 과매수/과매도 50% 선청산. partial_tp 모드에서 RSI 신호로 절반 청산. remaining=남은 수량 |
| PARTIAL CLOSE BTCUSDT LONG reason=partial_tp qty=0.025 price=42480.000000 PnL=+12.0000 USDT remaining=0.025 | 1R 목표 도달 50% 선청산. partial_tp 모드에서 1R(손절폭) 달성 시 절반 청산 |
| {symbol} close skipped: invalid qty | 청산 수량 계산 실패 → 청산 건너뜀. 거래소 minQty 이하이거나 포지션 수량 오류 |
⑥ 경고 및 오류 (Warning & Error)
| 로그 메시지 | 의미 / 조치 |
|---|---|
| [WS WARN] active price symbol sync failed: {e} | WS 구독 종목 업데이트 실패. 다음 주기에 자동 재시도. 반복 시 네트워크 확인 |
| [DASHBOARD] REST fallback standby activated for stale WS price cache | WS 가격이 오래됨 → REST로 전환. WS가 SILENT 상태일 때 자동 발생. 정상 동작이나 WS 확인 권장 |
| [TRAIL INDICATOR ERROR] BTCUSDT: {e} | 트레일링 ATR 계산 중 오류. 캔들 데이터 수신 실패 가능. 해당 봉은 이전 ATR 유지 |
| [PARTIAL CLOSE ERROR] BTCUSDT: {e} | 50% 선청산 주문 실패. 포지션 전량은 유지됨. 네트워크 오류 또는 거래소 오류 |
| [POSITION SYNC ERROR] {e} | REST safety sync 실패. 다음 주기에 재시도. 반복 시 API Key 권한 또는 네트워크 확인 |
| [SCAN ERROR] BTCUSDT: {e} | 해당 종목 스캔 중 오류. 종목 건너뜀, 다음 루프에서 재시도. 반복 시 상세 오류 내용 확인 |
| [UNIVERSE REFRESH ERROR] keep previous symbols: {e} | 유니버스 갱신 실패 → 이전 종목 유지. 네트워크 또는 API 오류 |
| [FATAL] {e} | 자동매매 스레드 치명적 오류. 루프 강제 종료. 로그 내용으로 원인 파악 후 재시작 필요 |
| Auto trader stopped | Stop 버튼으로 정상 종료됨. 기존 포지션은 유지 (자동 관리 중단) |
⑦ 백테스트 로그 (Backtest)
| 로그 메시지 | 의미 |
|---|---|
| Backtest started. Downloading public Binance Futures kline data... | 백테스트 시작. 캔들 데이터 다운로드 중 |
| [DATA 5/30] BTCUSDT | 데이터 다운로드 진행 상황. 30개 종목 중 5번째 다운로드 중 |
| [BACKTEST DATA ERROR] XYZUSDT: {e} | 해당 종목 데이터 다운로드 실패. 해당 종목 건너뜀. 상장폐지·심볼 변경 등 |
| [TREND SWEEP 3/12] ADX25.0_VOL1.5_TRIG1.0_ATR2.0_RISK0.50 | TREND 레짐 Sweep 진행 상황. 12개 조합 중 3번째 실행 중. 파라미터 조합 표시 |
| Stop Backtest requested. | 사용자가 백테스트 중단 요청. 현재 조합 완료 후 종료 |
정상 진입~청산 로그 흐름 예시
# ① 신호 감지 SIGNAL BTCUSDT LONG / trend_following / REGIME=TREND ATR%=5.21 SET=... # ② 수량 계산 BTCUSDT sizing: balance=1000.0, available=850.0, risk=5.0000(0.50%), ... # ③ 진입 체결 OPEN BTCUSDT LONG qty=0.050 entry=42000.000000 SL=41520.000000 TRAIL_TRIGGER=42480.000000 ... # ④ 서버 stop 등록 [SERVER STOP] BTCUSDT LONG stop=41520.000000 orderId=12345678 # ⑤ WS 구독 갱신 [WS] Active price stream symbols=3 reason=position_open # ⑥ 트레일링 활성화 TRAILING ON BTCUSDT LONG trigger=42480.000000 # ⑦ 손절가 갱신 + 서버 stop 갱신 (반복) TRAIL UPDATE BTCUSDT LONG SL=42200.000000 high=42680.000000 [SERVER STOP] BTCUSDT LONG stop=42200.000000 orderId=12345679 TRAIL UPDATE BTCUSDT LONG SL=42400.000000 high=42880.000000 [SERVER STOP] BTCUSDT LONG stop=42400.000000 orderId=12345680 # ⑧ 청산 + 서버 stop 취소 CLOSE BTCUSDT LONG reason=TRAILING_TAKE price=42400.000000 PnL=+20.0000 USDT [SERVER STOP CANCEL] BTCUSDT orderId=12345680 TRAILING_TAKE
용어 사전
프로그램 UI 및 로그에 등장하는 모든 용어를 알파벳·가나다 순으로 정리합니다.
기술 지표 (Indicators)
| 용어 | 설명 및 예시 |
|---|---|
| ATR Average True Range |
평균 진폭 — 변동성의 기준 단위. 14봉의 High-Low 범위를 단순평균(SMA)한 값. 손절폭·포지션 사이즈·Regime 판단에 모두 사용. 예: 15분봉 BTCUSDT ATR = 120 USDT → 한 봉에서 평균 120 USDT 움직임 |
| ATR% ATR Percent |
ATR을 현재가로 나눈 비율. Regime 분류 기준. ATR% = ATR ÷ 현재가 × 100 예: ATR = 120, 가격 = 60,000 → ATR% = 0.2% (QUIET), ATR = 2,400 → ATR% = 4% (TREND) |
| ADX Average Directional Index |
추세 강도 지표 (0~100). 방향 없이 추세 자체의 세기만 측정. 25 이상이면 추세 있음으로 일반적으로 판단. 이 프로그램은 Wilder RMA 대신 SMA 방식 사용. 예: ADX = 15 → 추세 약함(횡보), ADX = 35 → 강한 추세 진행 중 |
| EMA Exponential Moving Average |
지수이동평균 — 최근 봉에 더 높은 가중치. EMA20(단기)이 EMA60(장기) 위면 상승추세, 아래면 하락추세로 판단. 예: EMA20 = 42,500 / EMA60 = 41,800 → EMA20 > EMA60 → LONG 방향 허용 |
| RSI Relative Strength Index |
과매수/과매도 지표 (0~100). Wilder RSI 14봉. 30 이하 = 과매도, 70 이상 = 과매수. MR 진입 필터와 partial_tp 보조 청산에 사용. 예: RSI = 22, RSI Entry = 30 → RSI ≤ 30 충족 → MR LONG 진입 조건 하나 통과 |
| BB Bollinger Bands |
이동평균 ± 표준편차 밴드. SMA20 ± BB Sigma × σ(표준편차). 상단/하단 이탈 시 MR 진입 신호. 중간밴드(SMA20)가 MR 익절 목표. 예: SMA20 = 41,000 / σ = 800 / Sigma = 2.0 → Upper = 42,600, Lower = 39,400, Mid = 41,000 |
| Donchian Channel |
최근 N봉의 최고가/최저가 채널. 20봉 기준. 종가가 채널 상단 돌파 → LONG, 하단 돌파 → SHORT. TF 전략 진입 조건. 예: 최근 20봉 최고가 = 43,100, 현재봉 종가 = 43,250 → Donchian 상단 돌파 → 조건 충족 |
| CI Choppiness Index |
횡보/추세 판별 지표 (1~100). 값이 높을수록 횡보(choppiness), 낮을수록 추세. 61.8 이상이면 횡보로 판단해 TF 진입 차단. CI Filter ON 시에만 적용. 예: CI = 68 → 횡보 구간 → CI Filter ON이면 TF 진입 건너뜀 |
| Volume MA |
거래량 이동평균 (20봉 SMA). TF 진입 조건 중 거래량 급증 필터. 현재 봉 거래량 > Volume MA × Vol Mult 이어야 진입. 예: Volume MA = 500 BTC / Vol Mult = 1.5 → 750 BTC 이상 거래량이어야 조건 충족 |
설정 파라미터 (Parameters)
| 용어 | 설명 및 예시 |
|---|---|
| Decision TF |
진입 신호 판단용 캔들 타임프레임. 완성된 봉(Closed Candle)만 신호에 사용. 짧을수록 신호 빈도↑ 노이즈↑. 예: 15m → 15분마다 완성 봉으로 신호 확인 |
| Trailing TF |
트레일링 스탑 ATR 계산용 타임프레임. Decision TF보다 짧게 설정해야 트레일링이 빠르게 반응. 예: Decision TF = 15m / Execute TF = 5m / Trailing TF = 5m → 5분봉 ATR로 손절폭 갱신 |
| ATR Mult |
ATR 배수 — 손절폭을 결정. 손절폭 = 진입 ATR × ATR Mult. 낮으면 좁은 손절(잦은 손절), 높으면 넓은 손절(한 번에 큰 손실). 예: ATR = 120, ATR Mult = 2.0 → 손절폭 = 240 USDT (진입가 ± 240) |
| Trigger R |
(TF) 트레일링 활성화 거리 배수. Trigger R × 손절폭만큼 가격이 유리하게 이동해야 트레일링 시작. 낮으면 빠른 트레일링 활성. 예: 손절폭 = 240, Trigger R = 1.5 → 360 USDT 이상 수익 시 트레일링 시작 |
| BB Sigma |
(MR) Bollinger Band 표준편차 배수. 높을수록 밴드 폭이 넓어져 진입 빈도 감소. 기본값 2.0. 예: Sigma = 2.0 → SMA20 ± 2σ / Sigma = 1.5 → 더 좁은 밴드, 진입 기회 증가 |
| Vol Mult / RSI Entry |
전략에 따라 의미가 다른 이중 파라미터. • TF: Vol Mult — 거래량 급증 배수 (거래량 > MA × Vol Mult) • MR: RSI Entry — 과매도/과매수 기준선 (LONG: RSI ≤ 이 값) 예: TF Vol Mult = 1.5 / MR RSI Entry = 30 |
| ADX Min / ADX Max |
전략에 따라 의미가 다른 이중 파라미터. • TF ADX Min: 추세 강도 하한. ADX < 이 값이면 진입 안 함 • MR ADX Max: 추세 강도 상한. ADX > 이 값이면 진입 안 함 (추세장 차단) 예: TF ADX Min = 25 / MR ADX Max = 20 |
| Risk % |
포지션 1개 최대 손실 허용 비율. 한 포지션이 손절될 때 잔고의 Risk%만 잃도록 수량 계산. 예: 잔고 1,000 USDT / Risk% = 0.5% → 한 포지션 최대 손실 5 USDT |
| Max Position % |
포지션 1개 노셔널 상한 비율. 잔고 × Max Position% × 레버리지가 최대 주문 가능 노셔널. Risk 기준 수량과 비교해 더 작은 값 사용. 예: 잔고 1,000 / Max Position% = 15% / 레버리지 5 → 노셔널 상한 = 750 USDT |
| Leverage |
선물 레버리지 배수. 증거금 대비 포지션 크기 배수. 수익과 손실이 모두 배수로 증폭. 진입 시 거래소에 자동 설정. 예: 레버리지 5배 / 증거금 100 USDT → 노셔널 500 USDT 포지션 가능 |
| Top N |
24시간 거래대금 상위 N개 종목을 스캔 대상으로 선정. 4시간마다 자동 갱신. 많을수록 기회 증가·API 부하 증가. 예: Top N = 30 → 거래대금 1~30위 USDT 선물 종목만 진입 신호 스캔 |
전략 및 레짐 (Strategy & Regime)
| 용어 | 설명 및 예시 |
|---|---|
| Regime |
시장 상태 분류. ATR%로 QUIET / NORMAL / TREND / PANIC 4단계로 분류. 레짐에 따라 전략·파라미터가 자동 전환. 예: ATR% = 5.2% → TREND 레짐 → TF 전략 적용 |
| Trend Following (TF) |
추세추종 전략. 상승/하락 추세가 시작되는 돌파 시점에 진입해 추세를 따라가는 전략. NORMAL·TREND·PANIC 레짐에서 사용. 핵심: 돌파 진입 → 트레일링 스탑으로 추세 끝까지 추적 |
| Mean Reversion (MR) |
평균복귀 전략. 가격이 평균(BB 중간밴드)에서 크게 벗어났을 때 진입해 평균으로 돌아오는 것을 기대하는 전략. QUIET 레짐에서 사용. 핵심: BB 하단 이탈 + 과매도(RSI) → LONG 진입 → BB Mid 복귀 시 익절 |
| Closed Candle |
완성된 봉 — 아직 진행 중인 봉은 제외. 라이브 거래에서 신호 판단 시 현재 진행 중인 봉(미완성)은 제외하고 직전 완성 봉까지만 사용. 이유: 진행 중인 봉의 가격은 계속 변해 신호가 수시로 바뀜 → 허위 신호 방지 |
청산 및 리스크 (Exit & Risk)
| 용어 | 설명 및 예시 |
|---|---|
| Stop Loss |
손절가. 진입 시 계산. 진입가 ± ATR × ATR Mult. 가격이 이 지점 도달 시 자동 청산. 예: LONG 진입가 42,000 / 손절폭 240 → 손절가 = 41,760 |
| Trailing Stop |
이동 손절 — 수익 구간에서 손절가를 따라 올림. Trigger R 도달 후 활성화. 최고가(LONG) − 손절폭으로 손절가 갱신. 수익을 보호하면서 추세를 더 따라감. 예: 최고가 43,200 / 손절폭 240 → 트레일링 스탑 = 42,960 (손절가 갱신됨) |
| partial_tp |
부분 익절 모드. 1R(손절폭만큼의 수익) 달성 시 포지션의 50%를 먼저 청산하고 나머지 50%는 트레일링 계속. 예: 손절폭 240 → 수익 240 USDT 달성 시 절반 청산, 나머지는 트레일링 |
| fast_exit |
빠른 전량 익절 모드. 1R 목표 달성 즉시 전량 청산. 추세를 더 타지 않고 수익 확정. 주로 PANIC(급변동) 레짐에서 사용 — 큰 추세보다 빠른 수익 확정 우선 |
| BB Mid (Exit) |
MR 전용 익절 모드. 진입 시점의 BB 중간밴드(SMA20)를 목표가로 설정. 가격이 해당 수준 도달 시 전량 익절. 보유 중 실제 BB Mid가 이동해도 목표가는 고정. 예: 진입 시 BB Mid = 41,000 → 가격이 41,000 도달하면 LONG 전량 청산 |
| Time Exit |
시간 초과 강제 청산. 포지션 개설 후 72시간이 경과하면 전략·수익 여부에 관계없이 시장가 청산. 목적: MR이 장기간 실패해 자본이 묶이는 상황 방지 |
| Emergency Close |
긴급 전량 청산 버튼. 거래소에 있는 모든 선물 포지션을 시장가(Reduce-only)로 즉시 청산. 급락·급등 상황에서 수동 개입용. 주의: 슬리피지 발생 가능. 이미 손익이 발생한 상태에서 추가 손실 가능 |
| Reduce-only |
청산 전용 주문 플래그. 해당 플래그가 설정된 주문은 포지션을 늘리지 않고 줄이는 방향으로만 체결. 실수로 반대 포지션이 열리는 것을 방지. Emergency Close·익절 주문·서버 STOP_MARKET에 자동 적용 |
| STOP_MARKET Server Stop |
Binance 서버에 등록된 손절 주문. 지정 가격 도달 시 거래소가 시장가로 자동 청산. workingType=MARK_PRICE를 사용해 Last Price 스파이크에 의한 불합리한 체결을 방지. reduceOnly=true이므로 포지션 잔량만 청산.봇이 오프라인 상태에서도 손절이 실행되는 이중 안전망. 로컬 청산 시 자동 취소됨 |
| Notional |
포지션 명목 금액. 수량 × 현재가. 증거금이 아닌 실제 포지션 크기. 예: 0.05 BTC × 42,000 USDT = 2,100 USDT 노셔널 (증거금은 레버리지로 나눈 420 USDT) |
| Mark Price |
청산 기준 가격. 바이낸스가 제공하는 공정 가격. 일반 거래가(Last Price)와 다를 수 있음. 이 프로그램은 Mark Price 기준으로 손절 판단. 이유: Last Price는 일시적 스파이크가 있어 Mark Price로 불합리한 청산 방지 |
| Liquidation |
강제 청산 (롤).) 증거금이 유지증거금 이하로 떨어지면 거래소가 강제로 포지션 청산. 이 프로그램의 손절(Stop Loss)은 강제청산이 오기 전 선제적으로 청산. 예방: 레버리지를 낮추고 Max Position%를 제한하면 강제청산 위험 감소 |
백테스트 성과 지표 (Performance Metrics)
| 용어 | 설명 및 예시 |
|---|---|
| PF Profit Factor |
수익성 비율 = 총수익 ÷ 총손실. 1.0 = 본전, 1.0 미만 = 손실, 1.3 이상이면 우수한 편. 예: 총수익 1,300 USDT / 총손실 1,000 USDT → PF = 1.3 |
| MDD Max Drawdown |
최대 낙폭 — USDT 절대값과 고점 대비 %를 함께 표시. 낮을수록 좋음. % 기준 20% 초과 시 주의. 예: 고점 잔고 1,200 USDT → 저점 900 USDT → MDD = -300.00 (25.00%) % 계산 기준: 전체 고점이 아닌 MDD 발생 시점의 직전 고점(running peak) 대비. 예를 들어 MDD 이후 더 높은 고점이 형성됐어도 % 계산에는 영향 없음 — "당시 실제 낙폭률"이 의미 있기 때문. |
| Win Rate |
수익 거래 비율. 총 거래 중 이익으로 끝난 비율(%). PF와 함께 봐야 의미 있음. Win Rate 낮아도 PF 높으면 큰 수익·작은 손실 구조. 예: Win Rate 40% + PF 2.0 → 질로 이기는 구조 (추세추종 전형) |
| Net PnL |
순 손익 — 수수료 포함한 최종 손익. 양수여야 유효한 전략. 예: 총거래 수익 +800 USDT / 총손실 -600 USDT / 수수료 -50 USDT → Net PnL = +150 USDT |
| Score |
Sweep 랭킹 종합 점수. PF × 0.45 + Net PnL × 0.30 + Trades × 0.25를 정규화. 레짐 내 Top 10 선정 기준. 거래 횟수가 너무 적으면 PF가 높아도 Score가 낮게 나올 수 있음 |
| INSUFFICIENT |
거래 횟수 부족. 백테스트 결과 거래 횟수가 10회 미만이면 통계 신뢰도가 낮아 이 표시로 경고. 해결: 기간을 늘리거나 Top N을 늘리거나 파라미터를 완화 |
| Cartesian Product |
모든 조합의 곱. 파라미터 A에 3가지, B에 2가지 값을 입력하면 3 × 2 = 6개 조합을 모두 테스트. 예: ADX [20,25,30] × ATR Mult [1.5,2.0] = 6개 조합 sweep |
| Out-of-Sample |
최적화에 사용하지 않은 검증 기간. Sweep에서 찾은 파라미터를 다른 기간(OOS)에서 Validation으로 재검증해 과적합 여부 확인. 예: Sweep 기간 2025.01~03 → Validation 기간 2025.04~06으로 OOS 검증 |
인프라 및 API (Infrastructure)
| 용어 | 설명 및 예시 |
|---|---|
| WebSocket (WS) |
실시간 양방향 연결 프로토콜. REST처럼 매번 요청하지 않고 서버가 데이터를 밀어주는(push) 방식. 가격 실시간 수신에 사용. 이점: REST 대비 API 호출 횟수 대폭 감소, 지연(latency) 감소 |
| REST API |
요청-응답 방식 HTTP API. 클라이언트가 요청할 때만 데이터를 받음. 주문 실행, 잔고 조회, 캔들 데이터 다운로드에 사용. WS가 끊어지면 REST가 자동으로 가격 폴백 역할을 수행 |
| UDS User Data Stream |
계정 이벤트 전용 WebSocket. 체결·포지션변경·잔고변경 등 계정 관련 이벤트를 실시간 수신. Listen Key가 필요하며 30분마다 자동 갱신(keepalive). 이점: REST 폴링 없이 체결 즉시 포지션 상태 갱신 가능 |
| Listen Key |
UDS 인증 토큰. User Data Stream 구독 시 필요한 일회용 키. 60분 유효, 30분마다 keepalive 요청으로 갱신. 만료되면 UDS 연결이 끊어지므로 프로그램이 자동으로 keepalive 유지 |
| bookTicker |
실시간 최우선 호가 스트림. 최우선 매수/매도 호가가 바뀔 때마다 즉시 전송. 가격 WebSocket의 구독 채널. 이 프로그램은 보유 포지션 종목의 bookTicker만 구독 (active-position only) |
| REST Fallback/min |
WS 대신 REST로 가격 조회하는 보조 수단. WS가 연결됐으나 데이터가 오지 않을 때 자동으로 전환. API 모니터의 REST Fallback 카운터로 확인 가능. WS 정상 시 0, WS SILENT 상태에서 증가 |
| Testnet |
바이낸스 테스트 환경. 실제 자금이 오가지 않는 모의 거래 환경. API 설정 창에서 선택하며 테스트넷 API Key는 실거래와 별도 발급 필요. 반드시 Testnet에서 먼저 검증 후 실거래 전환 권장 |
| USDT-M Futures |
USDT 기반 무기한 선물. 바이낸스 USDⓈ-M 무기한 선물 시장. 증거금과 손익이 모두 USDT로 정산. 이 프로그램의 거래 대상. 코인-M(COIN-M) 선물과는 다름 — 이 프로그램은 COIN-M 미지원 |
| state/ 폴더 |
포지션 상태 영속성 저장소. atomic write로 저장되며 재시작 시 자동 복원. • open_positions.json — 진입가·손절가·전략 등 포지션 정보. server_stop_order_id·server_stop_price·server_stop_status 필드도 함께 저장되어 재시작 후 서버 stop 상태 복원• reentry_cooldowns.json — 청산 후 재진입 차단 쿨다운 상태. 재시작해도 쿨다운이 유지되어 청산 직후 동일 종목 즉시 재진입을 막음. 복원 시 [REENTRY] 쿨다운 복원: ['BTCUSDT'] (만료까지 최대 N초) 로그 출력파일이 손상되면 포지션·쿨다운 복원 불가 — 정기적으로 백업 권장 |
전체 아키텍처
프로그램은 GUI, 데이터 수집, 캐시, 백테스트 엔진, 실거래 엔진, 주문 실행 계층으로 나누어 동작합니다. 핵심 목표는 실거래와 백테스트의 종목 선정·지표 계산·진입/청산 로직을 최대한 동일하게 유지하면서, 반복 실행 속도를 캐시로 개선하는 것입니다.
아키텍처 다이어그램
PySide6 GUI
│
├─ Trading Tab
│ ├─ AutoTradeThread
│ ├─ Price WebSocket
│ ├─ User Data Stream
│ └─ Order / Position Manager
│
├─ Backtest Sweep
│ └─ BacktestThread
│
├─ Backtest Validation
│ └─ BacktestThread
│
└─ Walk-forward
└─ WalkForwardThread
Binance REST / WebSocket
│
├─ Public Market Data
│ └─ Candle Cache
│ └─ Historical Build
│ └─ Indicator Cache
│ └─ market_data Memory Cache
│ └─ Backtest / Validation / Walk-forward
│
└─ Private Account Data
├─ UserDataStream
├─ Position State Store
└─ Order Engine
주요 구성 요소
| 구성 요소 | 역할 | 비고 |
|---|---|---|
| GUI | Trading, Sweep, Validation, Walk-forward 설정과 결과 표시 | PySide6 기반 |
| AutoTradeThread | 실시간 진입 스캔, 포지션 관리, 청산 처리 | 실거래 엔진 |
| BacktestThread | Sweep 및 Validation 백테스트 실행 | 실거래 로직과 동일한 전략 조건 사용 |
| WalkForwardThread | IS 최적화와 OOS 검증을 반복 실행 | 과최적화 검증용 |
| Candle Cache | 캔들 데이터를 로컬에 저장하고 재사용 | 최초 구축 후 증분 업데이트 |
| Historical Build | 캐시 캔들을 읽어 내부 market_data 구조 생성 | OHLCV DataFrame 생성 단계 |
| Indicator Cache | EMA, ATR, ADX, RSI, CI 등 계산 결과 재사용 | 반복 백테스트 속도 개선 |
| Memory Cache | 동일 데이터 조건의 market_data를 메모리에 보관 | 전략 파라미터 변경 시에도 재사용 |
데이터 흐름
데이터는 REST와 WebSocket에서 들어와 캐시와 메모리 구조를 거친 뒤 전략 엔진에 전달됩니다. 실거래와 백테스트는 실행 시점만 다를 뿐, 가능한 한 같은 지표와 조건을 사용하도록 설계되어 있습니다.
실거래 데이터 흐름
Price WebSocket
│
▼
Global Price Cache
│
▼
Position Monitor / Trailing Stop
│
▼
Order Engine
│
▼
Binance Futures
User Data Stream
│
▼
Balance / Position / Order Event
│
▼
Dashboard / Position State Store
백테스트 데이터 흐름
Binance REST 또는 Local Candle Cache
│
▼
OHLCV DataFrame
│
▼
Historical Build
│
▼
Indicator Cache
│
▼
market_data
│
▼
Dynamic Top N Universe
│
▼
Strategy Signal
│
▼
Virtual Position / Exit Simulation
│
▼
PnL / MDD / PF / Trade Log
데이터별 사용 위치
| 데이터 | 사용 위치 | 설명 |
|---|---|---|
| OHLCV | Backtest / Validation / Walk-forward | 캔들 기반 지표 계산과 진입/청산 시뮬레이션에 사용 |
| quote_volume | Dynamic Top N | 4시간마다 과거 24시간 거래량 순위 계산 |
| WebSocket Price | Trading | 실시간 트레일링 스탑, 현재가 표시, 포지션 모니터링 |
| User Data Event | Trading / Dashboard | 체결, 포지션 변경, 잔고 변화를 실시간 반영 |
| Trade CSV | 분석 / 검증 | 실거래 결과 분석 및 향후 AI 분석 데이터로 활용 |
캐시 구조
캐시는 디스크 파일(재시작 후에도 유지)과 실행 중 메모리(백테스트 1회 동안 유지)로 구성됩니다. 각 계층이 역할을 분담하여 API 호출과 디스크 I/O를 최소화합니다.
캐시 계층 구조
── 디스크 (재시작 후에도 유지) ──────────────────────────────
1. manifest.json candle_cache/manifest.json
심볼별 first/last open_time 인덱스 (65KB 수준)
API 호출 없이 캐시 신선도를 즉시 판단하는 데 사용
2. Candle Cache (parquet) candle_cache/{SYMBOL}/{interval}.parquet
실제 OHLCV 캔들 데이터 (심볼당 100~200KB)
CacheUpdateThread가 5분마다 새 캔들만 증분 추가
── 메모리 (백테스트 1회 실행 중 유지) ──────────────────────────
3. manifest_cache 백테스트 시작 시 manifest.json 전체 로드
심볼별 O(1) 신선도 체크 → API skip 여부 결정
다운로드 중 메모리만 갱신, Pass 종료 시 디스크에 1회 저장
4. market_data {symbol: {entry/execute/trailing: DataFrame}}
parquet 읽기 결과를 메모리에 보관
같은 실행 내 파라미터 조합 변경 시 재사용 (TF·기간 동일할 때)
5. Indicator Cache {symbol: DataFrame with EMA/ADX/ATR/RSI/CI}
_precompute_indicators() 결과
같은 실행 내 모든 파라미터 조합이 공유
market_data 재사용 조건
같은 백테스트 실행 내에서 파라미터 조합을 바꿀 때, OHLCV 데이터(market_data)는 아래 조건에 따라 재사용 여부가 결정됩니다.
| 변경 항목 | market_data 재사용 | 설명 |
|---|---|---|
| ADX | 재사용 | 전략 조건만 바뀌며 OHLCV 데이터는 동일 |
| ATR Mult | 재사용 | 손절폭 계산값만 바뀜 |
| Volume Mult | 재사용 | 진입 필터 임계값만 바뀜 |
| Trigger R | 재사용 | 트레일링 활성화 기준만 바뀜 |
| Risk % | 재사용 | 포지션 수량 계산만 바뀜 |
| Exit Mode | 재사용 | 청산 로직만 바뀜 |
| Regime ON/OFF | 재사용 | 신호 사용 여부만 바뀜 |
| Top N | 재사용 | Dynamic Top N 목록은 다시 계산하지만 OHLCV는 동일 |
| Market Universe | 재빌드 | CRYPTO/TRADFI/ALL Universe가 달라짐 |
| Decision TF | 재빌드 | 진입 판단 캔들 자체가 달라짐 |
| Execute TF | 재빌드 | 실제 진입 타이밍 캔들이 달라짐 |
| Trailing TF | 재빌드 | ATR Trailing 계산 캔들이 달라짐 |
| 기간 | 재빌드 | 필요한 캔들 범위가 달라짐 |
| 새 백테스트 실행 | 재빌드 | 메모리 캐시는 실행 간 공유하지 않음. 단, 캔들 파일(parquet)은 재사용 |
Dynamic Top N 알고리즘
Dynamic Top N은 실거래와 백테스트의 종목 선정 차이를 줄이기 위한 기능입니다. 고정된 Top N 목록을 전체 기간에 사용하지 않고, 4시간마다 과거 24시간 거래량 기준으로 Top N을 다시 선정합니다.
기본 개념
매 4시간마다: 1. 각 종목의 직전 24시간 quote_volume 합산 2. 거래량 기준 내림차순 정렬 3. 상위 N개를 해당 4시간 구간의 활성 Universe로 지정 4. 기존 보유 포지션은 계속 관리 5. 신규 진입만 해당 시점의 Top N에 포함된 종목으로 제한
왜 전체 Universe 데이터를 준비하는가?
장기 백테스트에서는 어떤 종목이 특정 시점에 거래량 급증으로 Top N에 들어올지 사전에 알 수 없습니다. 따라서 Dynamic Top N의 정확도를 유지하려면 전체 Universe의 거래량 데이터를 기준으로 각 4시간 버킷의 Top N을 계산해야 합니다.
2-pass 다운로드와 ever-active
거래량 순위 계산에는 4h 캔들만 사용하고, 전략 TF(15m/5m 등)는 한 번이라도 Top N에 들어간 심볼(ever-active)에 대해서만 다운로드합니다. 4h 캔들은 Cache Manager가 백그라운드에서 미리 구축하므로, Sweep 실행 시 Pass 1은 대부분 캐시 읽기만 수행합니다. 이를 통해 전략 TF 다운로드 범위를 전체 Universe(~500개)에서 ever-active(~100개)로 대폭 줄입니다.
Pass 1: 전체 Universe(~500개) × 4h 캔들
→ 4h 캐시는 시작 시 백그라운드에서 사전 구축
→ Sweep 실행 시 manifest 신선 구간은 API 없이 parquet만 읽음
→ 4h vol_data 기반 Dynamic Top N 계산
→ ever_active = 어느 한 버킷에서라도 Top N에 포함된 심볼 집합
Pass 2: ever_active(~100개) × Decision / Execute / Trailing TF
→ 실제 전략 시뮬레이션에 사용할 market_data 구성
※ ever_active가 비어있으면(Pass 1 실패 등) "[WARN] Dynamic TopN empty; fallback to static TopN"
로그와 함께 Static Top N으로 자동 전환됩니다.
| 방식 | 장점 | 단점 | 정확도 |
|---|---|---|---|
| Static Top N | 빠름 | 기간 내 거래량 변화 반영 부족 | 실거래와 차이 가능 |
| Dynamic Top N | 실거래 종목 갱신 방식과 유사 | 장기 기간에서 데이터 준비량 증가 | 높음 |
Top N 변경 시 동작
Top N 값을 50에서 100으로 바꾸면 OHLCV 데이터는 재사용하고, 4시간 버킷별 활성 종목 목록만 다시 계산합니다. 따라서 Market, 기간, Timeframe이 같다면 Historical Build는 재사용할 수 있습니다.
백테스트 엔진 동작 방식
백테스트 엔진은 데이터 준비, 지표 계산, Dynamic Top N 생성, 신호 탐색, 가상 체결, 포지션 관리, 결과 집계 순서로 동작합니다.
실행 순서
- 1기간 설정
Recent Days 또는 Date Range 기준으로 테스트 기간을 결정합니다. 지표 안정화를 위해 앞쪽 warm-up 구간을 추가로 확보합니다. - 2manifest 사전 로드
manifest.json을 메모리에 로드합니다. 이후 심볼별 신선도 체크가 O(1)로 동작하여 API 호출 생략 여부를 즉시 결정합니다. - 3Pass 1 — 4h 볼륨 캐시 로드
전체 Universe(~500개) × 4h 캔들을 읽습니다. 4h 캔들은 시작 시 백그라운드에서 미리 업데이트되며, manifest가 신선하면 API 호출 없이 parquet만 읽습니다. 부족한 구간만 보충 다운로드하고 결과를 vol_data로 수집합니다. - 4Dynamic Top N 생성 / ever-active 계산
vol_data 기반으로 4h 버킷별 Top N 목록을 빌드하고, ever-active(전체 기간 중 한 번이라도 Top N에 포함된 심볼 집합)를 도출합니다. - 5Pass 2 — 전략 TF 다운로드
ever-active 심볼(~100개)만 Decision / Execute / Trailing TF 캔들을 읽습니다. 역시 manifest 신선 시 API 0회. 결과를 market_data로 수집합니다. - 6Indicator 계산
EMA, ADX, ATR, RSI, CI 등을 심볼당 1회 계산합니다. Sweep은 프로세스 경계를 OHLCV만 통과시키고, 각 worker 프로세스 초기화 시 독립 계산합니다 (pickle 전송량 감소). Walk-forward는 부모 프로세스에서 1회 계산 후 전체 윈도우가 재사용합니다. - 7신호 탐색
Regime, Strategy, ADX, Volume/RSI, Donchian/BB 조건을 확인해 진입 후보를 만듭니다. - 8가상 체결 및 포지션 관리
Risk %, Max Position %, Max Long/Short, Leverage, 수수료, 슬리피지를 반영해 포지션을 시뮬레이션합니다. - 9결과 집계
Net PnL, PF, Win Rate, MDD, Trades, Daily PnL, 레짐별 성과를 계산합니다.
Sweep / Validation / Walk-forward 차이
| 모드 | 목적 | 데이터 다운로드 | 파라미터 실행 |
|---|---|---|---|
| Sweep | 레짐별 최적 파라미터 탐색 | 2-pass (4h all + 3TF ever-active) | 전체 조합 grid search, 결과 표로 비교 |
| Validation | 단일 파라미터 조합 상세 검증 | 동일 2-pass | 1회 실행, 레짐별 상세 결과 출력 |
| Walk-forward | 단일 Validation 설정의 IS/OOS 유사성 검증 × N윈도우 | 동일 2-pass (전체 기간 1회) | 실행 시 Validation 설정을 고정하고 각 Window의 IS·OOS에 동일 적용. 데이터는 모든 Window가 재사용 |
체결 모델
백테스트는 실제 주문을 내지 않고 가상 포지션을 생성합니다. 수수료와 슬리피지를 반영하여 실거래에 가까운 결과를 계산합니다.
| 항목 | 반영 방식 |
|---|---|
| 수수료 | 진입과 청산에 각각 fee rate 적용 |
| 슬리피지 | 진입/청산 가격에 bps 단위로 보수적 반영 |
| 레버리지 | 노셔널 계산과 Max Position 제한에 반영 |
| Risk % | 손절폭 기준 포지션 수량 계산 |
| 동시 포지션 제한 | Max Long / Max Short 개수 제한 적용 |
| 같은 봉 내 SL/TP 동시 터치 | 같은 캔들에서 고가가 TP, 저가가 SL을 동시에 터치했을 때 SL 우선 처리. OHLC만으로 봉 내 체결 순서를 알 수 없으므로 보수적 가정을 적용. 실거래 대비 결과가 소폭 낮게 나올 수 있음 |
성능 최적화
백테스트 속도는 API 다운로드 → SSD 읽기(parquet) → Indicator 계산 → 전략 조합 실행 순으로 나뉩니다. 각 단계를 캐시와 skip 로직으로 최소화하는 구조입니다.
실행 상황별 속도
| 상황 | 주요 작업 | 속도 특성 |
|---|---|---|
| 최초 실행 (캐시 없음) | 전체 Universe 캔들 API 다운로드 + parquet 저장 | 가장 오래 걸림 (수분) |
| 캐시 구축 후 백테스트 | manifest 체크 → API 0회 → parquet 읽기 → Indicator 계산 | SSD 읽기만 (~10초) |
| 같은 실행 내 파라미터 변경 | market_data + Indicator Cache 재사용, 전략 조건만 재평가 | 가장 빠름 (초 단위) |
| TF·기간·Market 변경 | parquet 재읽기 + market_data 재구성 | SSD 읽기 (~10초) |
| 프로그램 재시작 후 백테스트 | manifest 체크 → API 0회 → parquet 읽기 (캐시 있으면) | SSD 읽기만 |
최적화 기법 목록
| 기법 | 효과 |
|---|---|
| CacheUpdateThread 5분 주기 | 백테스트 실행 전 캐시가 항상 신선하게 유지됨 |
| manifest 사전 로드 | 백테스트 시작 시 manifest 1회 로드 → 심볼별 O(1) 신선도 체크 |
| Manifest-based API skip | 캐시 신선 시 API 호출 0회, parquet만 읽음 (Pass 1 × 500회 절약) |
| 2-pass 다운로드 | 전체 Universe는 4h 1회, 전략 TF는 ever-active(~100개)만 |
| manifest 일괄 저장 | 심볼별 저장 → Pass 종료 시 최대 2회 일괄 저장 |
| 임시 파일 정리 1회화 | 백테스트 시작 시 1회만 .tmp 파일 정리 (반복 호출 방지) |
| Indicator Cache | EMA/ATR/ADX/RSI/CI를 심볼당 1회 계산, 모든 파라미터 조합이 공유 |
| Sweep worker-side 지표 계산 | OHLCV만 프로세스 경계 전송 → 각 worker가 초기화 시 독립 계산. 지표 컬럼이 포함된 큰 DataFrame을 N회 복사하지 않아 pickle 전송량 감소 |
| Dynamic Top N 재계산 분리 | Top N 변경 시 OHLCV는 재사용, 활성 Universe만 재계산 |
주요 로그 해석
[Pass 1/2] 볼륨 랭킹용 4h 캔들 다운로드: N개 심볼
→ 전체 Universe × 4h 캔들 읽기 시작
→ manifest 신선하면 API 0회, parquet만 읽음
[Pass 2/2] ever-active N개 심볼 전략 TF 다운로드
→ 적어도 한 번 TopN에 든 심볼만 전략 TF 읽기
VOL N/M {sym} → Pass 1 진행 현황
STRAT N/M {sym} → Pass 2 진행 현황
[WF-VOL N/M] / [WF-STRAT N/M]
→ Walk-forward 2-pass 진행 현황