#!/usr/bin/env python3
"""2단계: Ground Truth 정합 매매 기법 실행 및 비교."""

from __future__ import annotations

import argparse
import logging
import sys
from pathlib import Path

ROOT = Path(__file__).resolve().parents[1]
SRC = ROOT / "src"
if str(SRC) not in sys.path:
    sys.path.insert(0, str(SRC))

from deepcoin.config import load_settings
from deepcoin.data.intervals import interval_label
from deepcoin.evaluation.report import (
    build_comparison_report,
    render_comparison_html,
    save_comparison_report,
)
from deepcoin.techniques.base import TechniqueParams
from deepcoin.techniques.registry import list_technique_ids
from deepcoin.techniques.runner import (
    load_ground_truth,
    run_all_techniques,
    save_technique_result,
)


def _configure_logging(verbose: bool) -> None:
    """로깅 레벨을 설정한다."""
    level = logging.DEBUG if verbose else logging.INFO
    logging.basicConfig(
        level=level,
        format="%(asctime)s [%(levelname)s] %(message)s",
        datefmt="%Y-%m-%d %H:%M:%S",
    )


def main() -> int:
    """CLI 진입점."""
    parser = argparse.ArgumentParser(description="매매 기법 실행 및 GT 정합 비교 (2단계)")
    parser.add_argument(
        "--techniques",
        type=str,
        default=None,
        help="실행할 기법 ID (쉼표 구분). 기본: 전체",
    )
    parser.add_argument("--tolerance", type=int, default=None, help="GT 정합 허용 봉 수")
    parser.add_argument("--no-report", action="store_true", help="비교 리포트 생략")
    parser.add_argument("-v", "--verbose", action="store_true")
    args = parser.parse_args()

    _configure_logging(args.verbose)
    settings = load_settings()

    if not settings.ground_truth_file.exists():
        logging.error("Ground Truth 파일 없음: %s — 먼저 02_ground_truth.py 실행", settings.ground_truth_file)
        return 1

    gt_result = load_ground_truth(settings.ground_truth_file)
    technique_ids = None
    if args.techniques:
        technique_ids = [t.strip() for t in args.techniques.split(",") if t.strip()]

    params = TechniqueParams(
        interval_min=settings.gt_interval_min,
        lookback_days=settings.gt_lookback_days,
        min_leg_pct=settings.gt_min_leg_pct,
        initial_cash_krw=settings.gt_initial_cash_krw,
        fee_rate=settings.gt_trading_fee_rate,
        extra={"reversal_pct": settings.gt_zigzag_reversal_pct},
    )

    tolerance = args.tolerance or settings.gt_align_tolerance_bars

    logging.info(
        "기법 실행: %s %s, %s일, tolerance=%s봉",
        settings.symbol,
        interval_label(params.interval_min),
        params.lookback_days,
        tolerance,
    )

    results = run_all_techniques(
        db_path=settings.db_path,
        symbol=settings.symbol,
        params=params,
        gt_result=gt_result,
        tolerance_bars=tolerance,
        technique_ids=technique_ids,
    )

    saved_paths: list[Path] = []
    for result in results:
        path = save_technique_result(result, settings.techniques_dir)
        saved_paths.append(path)
        align = result.alignment or {}
        legs = align.get("legs", {})
        print(
            f"  [{result.technique_id}] {result.technique_name}: "
            f"레그 {result.summary.get('leg_count', 0)}개, "
            f"수익 {result.pnl.get('total_return_pct', 0):+.1f}%, "
            f"GT정합 score={align.get('score', 0)*100:.1f} "
            f"(leg recall {legs.get('leg_recall', 0)*100:.0f}%)"
        )

    print(f"\n=== 2단계 기법 실행 완료 ({len(results)}개) ===")
    print(f"저장: {settings.techniques_dir}/")
    for path in saved_paths:
        print(f"  - {path.name}")

    if not args.no_report:
        report = build_comparison_report(results, gt_result, settings.symbol)
        json_path = save_comparison_report(report, settings.analysis_report_json)
        html_path = render_comparison_html(report, settings.analysis_report_html)
        print(f"\n=== GT 정합 순위 (상위 3) ===")
        gt_return = report["gt"]["return_pct"]
        print(f"GT 벤치마크: {gt_return:+.1f}%")
        for idx, row in enumerate(report["ranking"][:3], start=1):
            print(
                f"  {idx}. {row['technique_name']}: "
                f"score {row['score']*100:.1f}, "
                f"수익 {row['tech_return_pct']:+.1f}%, "
                f"leg recall {row['leg_recall']*100:.0f}%"
            )
        print(f"리포트 JSON: {json_path}")
        print(f"리포트 HTML: {html_path}")

    print(f"\n등록 기법: {', '.join(list_technique_ids())}")
    return 0


if __name__ == "__main__":
    raise SystemExit(main())
