"""
D.intelligence Quotation Generator
Agent #73 - dintel-quotation-mgr

Generates branded Excel .xlsx quotation files using _dintel-shared utilities.
This is a stub script -- extend with full implementation as needed.

Usage:
    python generate_quotation.py --client "고객사명" --modules A3,T6 --output ./output/

Dependencies:
    - _dintel-shared (../../_dintel-shared/)
    - openpyxl
"""

from __future__ import annotations

import argparse
import sys
from dataclasses import dataclass, field
from datetime import date, timedelta
from pathlib import Path
from typing import Optional

# ---------------------------------------------------------------------------
# Pricing data (mirrors shared/pricing-reference.md)
# ---------------------------------------------------------------------------

MODULE_PRICING: dict[str, dict] = {
    # Analysis (진단)
    "A1": {"name": "비즈니스·브랜드 진단", "duration": "2-3주", "min": 3_000_000, "max": 5_000_000, "phase": "Analysis"},
    "A2": {"name": "고객·소비자 분석", "duration": "3-4주", "min": 4_000_000, "max": 7_000_000, "phase": "Analysis"},
    "A3": {"name": "데이터 분석 (웹·앱)", "duration": "3-5주", "min": 4_000_000, "max": 8_000_000, "phase": "Analysis"},
    "A4": {"name": "디지털 마케팅 진단", "duration": "2-4주", "min": 3_000_000, "max": 6_000_000, "phase": "Analysis"},
    "A5": {"name": "퍼포먼스 마케팅 진단", "duration": "2-3주", "min": 3_000_000, "max": 5_000_000, "phase": "Analysis"},
    "A6": {"name": "운영·관리 진단", "duration": "2-3주", "min": 2_000_000, "max": 4_000_000, "phase": "Analysis"},
    # Treatment (처방)
    "T1": {"name": "브랜드 스토리텔링 & 가이드", "duration": "4-8주", "min": 5_000_000, "max": 12_000_000, "phase": "Treatment"},
    "T2": {"name": "고객 접점 경험 최적화", "duration": "4-6주", "min": 4_000_000, "max": 8_000_000, "phase": "Treatment"},
    "T3": {"name": "디지털 자산 통합관리", "duration": "4-8주", "min": 6_000_000, "max": 15_000_000, "phase": "Treatment"},
    "T4": {"name": "콘텐츠 마케팅", "duration": "4-8주", "min": 4_000_000, "max": 10_000_000, "phase": "Treatment"},
    "T5": {"name": "광고·전환 최적화", "duration": "3-6주", "min": 4_000_000, "max": 8_000_000, "phase": "Treatment"},
    "T6": {"name": "Brand Visibility Treatment", "duration": "4-12주", "min": 5_000_000, "max": 15_000_000, "phase": "Treatment"},
    "T7": {"name": "운영 시스템·자동화", "duration": "4-8주", "min": 4_000_000, "max": 10_000_000, "phase": "Treatment"},
    # Growth (성장)
    "G1": {"name": "퍼포먼스 마케팅", "duration": "월간", "min": 2_000_000, "max": 5_000_000, "phase": "Growth", "monthly": True},
    "G2": {"name": "콘텐츠 마케팅 대행", "duration": "월간", "min": 3_000_000, "max": 6_000_000, "phase": "Growth", "monthly": True},
    "G3": {"name": "모니터링·이슈관리", "duration": "월간", "min": 2_000_000, "max": 4_000_000, "phase": "Growth", "monthly": True},
    "G4": {"name": "연간 계약·운영", "duration": "12개월", "min": 0, "max": 0, "phase": "Growth", "monthly": True},
}

COMPLEXITY_PERCENTILE = {
    "standard": 0.30,
    "complex": 0.60,
    "enterprise": 0.90,
}

DISCOUNT_POLICIES = {
    "multi_3plus": {"label": "3개 모듈 이상 동시 계약", "rate": 0.15},
    "analysis_treatment": {"label": "Analysis → Treatment 연계", "rate": 0.20},
    "full_cycle": {"label": "Full cycle (A→T→G)", "rate": 0.25},
    "g4_annual": {"label": "G4 연간 계약", "rate": 0.20},
    "renewal": {"label": "재계약 (기존 고객)", "rate": 0.10, "stackable": True},
}


# ---------------------------------------------------------------------------
# Data classes
# ---------------------------------------------------------------------------

@dataclass
class LineItem:
    code: str
    name: str
    phase: str
    complexity: str = "standard"
    base_price: int = 0
    months: int = 1  # for Growth modules
    subtotal: int = 0


@dataclass
class QuotationDraft:
    ref: str = ""
    client_name: str = ""
    industry: str = ""
    date_created: date = field(default_factory=date.today)
    validity_days: int = 30
    line_items: list[LineItem] = field(default_factory=list)
    subtotal: int = 0
    discount_label: str = ""
    discount_rate: float = 0.0
    discount_amount: int = 0
    total_before_vat: int = 0
    is_renewal: bool = False


# ---------------------------------------------------------------------------
# Pricing logic
# ---------------------------------------------------------------------------

def calculate_price(code: str, complexity: str = "standard") -> int:
    """Calculate module price based on complexity percentile within range."""
    module = MODULE_PRICING.get(code)
    if not module:
        raise ValueError(f"Unknown module code: {code}")
    pct = COMPLEXITY_PERCENTILE.get(complexity, 0.30)
    price_range = module["max"] - module["min"]
    return int(module["min"] + price_range * pct)


def determine_discount(line_items: list[LineItem], is_renewal: bool = False) -> tuple[str, float]:
    """Determine the highest applicable base discount, plus renewal if applicable."""
    phases = {item.phase for item in line_items}
    num_modules = len(line_items)
    has_g4 = any(item.code == "G4" for item in line_items)

    # Determine base discount (highest wins)
    base_label = ""
    base_rate = 0.0

    if phases >= {"Analysis", "Treatment", "Growth"}:
        base_label = DISCOUNT_POLICIES["full_cycle"]["label"]
        base_rate = DISCOUNT_POLICIES["full_cycle"]["rate"]
    elif "Analysis" in phases and "Treatment" in phases:
        base_label = DISCOUNT_POLICIES["analysis_treatment"]["label"]
        base_rate = DISCOUNT_POLICIES["analysis_treatment"]["rate"]
    elif has_g4:
        base_label = DISCOUNT_POLICIES["g4_annual"]["label"]
        base_rate = DISCOUNT_POLICIES["g4_annual"]["rate"]
    elif num_modules >= 3:
        base_label = DISCOUNT_POLICIES["multi_3plus"]["label"]
        base_rate = DISCOUNT_POLICIES["multi_3plus"]["rate"]

    # Stack renewal discount
    if is_renewal and base_rate > 0:
        base_label += " + 재계약"
        base_rate = min(base_rate + 0.10, 0.35)
    elif is_renewal:
        base_label = DISCOUNT_POLICIES["renewal"]["label"]
        base_rate = 0.10

    return base_label, base_rate


def build_quotation(
    client_name: str,
    modules: list[tuple[str, str]],  # [(code, complexity), ...]
    industry: str = "",
    is_renewal: bool = False,
    growth_months: int = 3,
) -> QuotationDraft:
    """Build a complete quotation draft."""
    today = date.today()
    ref = f"DI-Q-{today.strftime('%Y%m%d')}-001"

    draft = QuotationDraft(
        ref=ref,
        client_name=client_name,
        industry=industry,
        date_created=today,
        is_renewal=is_renewal,
    )

    for code, complexity in modules:
        module = MODULE_PRICING[code]
        price = calculate_price(code, complexity)
        months = growth_months if module.get("monthly") else 1
        item = LineItem(
            code=code,
            name=module["name"],
            phase=module["phase"],
            complexity=complexity,
            base_price=price,
            months=months,
            subtotal=price * months,
        )
        draft.line_items.append(item)

    draft.subtotal = sum(item.subtotal for item in draft.line_items)
    draft.discount_label, draft.discount_rate = determine_discount(draft.line_items, is_renewal)
    draft.discount_amount = int(draft.subtotal * draft.discount_rate)
    draft.total_before_vat = draft.subtotal - draft.discount_amount

    return draft


# ---------------------------------------------------------------------------
# Excel generation (stub -- requires openpyxl and _dintel-shared)
# ---------------------------------------------------------------------------

def generate_xlsx(draft: QuotationDraft, output_dir: Path) -> Path:
    """Generate branded .xlsx quotation file.

    TODO: Implement full branded workbook using _dintel-shared/src/dintel/excel.py.
    This stub creates a basic workbook structure.
    """
    try:
        from openpyxl import Workbook
        from openpyxl.styles import Alignment, Font, PatternFill
    except ImportError:
        print("ERROR: openpyxl is required. Install with: pip install openpyxl", file=sys.stderr)
        sys.exit(1)

    wb = Workbook()

    # -- Sheet 1: Cover --
    ws_cover = wb.active
    ws_cover.title = "표지"
    ws_cover["B2"] = "D.intelligence :: SMART Marketing Clinic ::"
    ws_cover["B2"].font = Font(name="Pretendard", size=16, bold=True)
    ws_cover["B4"] = "견적서 (Quotation)"
    ws_cover["B4"].font = Font(name="Pretendard", size=24, bold=True)
    ws_cover["B6"] = f"고객사: {draft.client_name}"
    ws_cover["B7"] = f"업종: {draft.industry}"
    ws_cover["B8"] = f"견적번호: {draft.ref}"
    ws_cover["B9"] = f"작성일: {draft.date_created.isoformat()}"
    ws_cover["B10"] = f"유효기간: {(draft.date_created + timedelta(days=draft.validity_days)).isoformat()}"
    ws_cover["B12"] = "DRAFT -- 검토 대기"
    ws_cover["B12"].font = Font(color="FF0000", bold=True, size=14)

    # -- Sheet 2: Scope --
    ws_scope = wb.create_sheet("서비스 범위")
    headers = ["모듈 코드", "모듈명", "Phase", "복잡도", "비고"]
    for col, header in enumerate(headers, 1):
        cell = ws_scope.cell(row=1, column=col, value=header)
        cell.font = Font(bold=True)
    for row, item in enumerate(draft.line_items, 2):
        ws_scope.cell(row=row, column=1, value=item.code)
        ws_scope.cell(row=row, column=2, value=item.name)
        ws_scope.cell(row=row, column=3, value=item.phase)
        ws_scope.cell(row=row, column=4, value=item.complexity)

    # -- Sheet 3: Timeline (placeholder) --
    ws_timeline = wb.create_sheet("일정")
    ws_timeline["A1"] = "Phase"
    ws_timeline["B1"] = "Module"
    ws_timeline["C1"] = "Duration"
    ws_timeline["A1"].font = Font(bold=True)
    ws_timeline["B1"].font = Font(bold=True)
    ws_timeline["C1"].font = Font(bold=True)
    for row, item in enumerate(draft.line_items, 2):
        ws_timeline.cell(row=row, column=1, value=item.phase)
        ws_timeline.cell(row=row, column=2, value=f"{item.code} {item.name}")
        module = MODULE_PRICING[item.code]
        ws_timeline.cell(row=row, column=3, value=module["duration"])

    # -- Sheet 4: Pricing --
    ws_pricing = wb.create_sheet("견적 내역")
    draft_fill = PatternFill(start_color="FFFF00", end_color="FFFF00", fill_type="solid")
    price_headers = ["모듈 코드", "모듈명", "단가 (원)", "수량/개월", "소계 (원)"]
    for col, header in enumerate(price_headers, 1):
        cell = ws_pricing.cell(row=1, column=col, value=header)
        cell.font = Font(bold=True)
    for row, item in enumerate(draft.line_items, 2):
        ws_pricing.cell(row=row, column=1, value=item.code)
        ws_pricing.cell(row=row, column=2, value=item.name)
        price_cell = ws_pricing.cell(row=row, column=3, value=item.base_price)
        price_cell.fill = draft_fill
        price_cell.number_format = "#,##0"
        ws_pricing.cell(row=row, column=4, value=item.months)
        subtotal_cell = ws_pricing.cell(row=row, column=5, value=item.subtotal)
        subtotal_cell.fill = draft_fill
        subtotal_cell.number_format = "#,##0"

    summary_row = len(draft.line_items) + 3
    ws_pricing.cell(row=summary_row, column=4, value="소계").font = Font(bold=True)
    ws_pricing.cell(row=summary_row, column=5, value=draft.subtotal).number_format = "#,##0"

    if draft.discount_rate > 0:
        summary_row += 1
        ws_pricing.cell(row=summary_row, column=3, value=draft.discount_label)
        ws_pricing.cell(row=summary_row, column=4, value=f"-{int(draft.discount_rate * 100)}%")
        disc_cell = ws_pricing.cell(row=summary_row, column=5, value=-draft.discount_amount)
        disc_cell.number_format = "#,##0"
        disc_cell.font = Font(color="FF0000")

    summary_row += 1
    ws_pricing.cell(row=summary_row, column=4, value="합계 (VAT 별도)").font = Font(bold=True, size=12)
    total_cell = ws_pricing.cell(row=summary_row, column=5, value=draft.total_before_vat)
    total_cell.font = Font(bold=True, size=12)
    total_cell.number_format = "#,##0"
    total_cell.fill = draft_fill

    summary_row += 1
    ws_pricing.cell(row=summary_row, column=5, value="Andrew 검토 필요").font = Font(color="FF0000", italic=True)

    # -- Sheet 5: Terms --
    ws_terms = wb.create_sheet("계약 조건")
    terms = [
        ("결제 조건", "착수금 50% / 완료 후 50%"),
        ("견적 유효기간", "발행일로부터 30일"),
        ("부가세", "별도 (10%)"),
        ("범위 변경", "서면 합의 후 별도 견적"),
        ("계약 해지", "착수 전 전액 환불 / 착수 후 진행분 정산"),
        ("", ""),
        ("D.intelligence", "SMART Marketing Clinic"),
        ("Website", "dintelligence.co.kr"),
        ("담당자", "Andrew Yim"),
    ]
    for row, (label, value) in enumerate(terms, 1):
        ws_terms.cell(row=row, column=1, value=label).font = Font(bold=True)
        ws_terms.cell(row=row, column=2, value=value)

    # Save
    output_dir.mkdir(parents=True, exist_ok=True)
    filename = f"{draft.ref}_{draft.client_name.replace(' ', '_')}_DRAFT.xlsx"
    filepath = output_dir / filename
    wb.save(filepath)
    return filepath


# ---------------------------------------------------------------------------
# CLI entry point
# ---------------------------------------------------------------------------

def main():
    parser = argparse.ArgumentParser(description="D.intelligence Quotation Generator")
    parser.add_argument("--client", required=True, help="Client name (고객사명)")
    parser.add_argument("--industry", default="", help="Client industry (업종)")
    parser.add_argument("--modules", required=True, help="Comma-separated module codes (e.g., A3,T6,G2)")
    parser.add_argument("--complexity", default="standard", choices=["standard", "complex", "enterprise"],
                        help="Default complexity tier for all modules")
    parser.add_argument("--renewal", action="store_true", help="Existing client (재계약)")
    parser.add_argument("--growth-months", type=int, default=3, help="Number of months for Growth modules")
    parser.add_argument("--output", default="./output", help="Output directory")

    args = parser.parse_args()

    module_list = [(code.strip(), args.complexity) for code in args.modules.split(",")]

    draft = build_quotation(
        client_name=args.client,
        modules=module_list,
        industry=args.industry,
        is_renewal=args.renewal,
        growth_months=args.growth_months,
    )

    filepath = generate_xlsx(draft, Path(args.output))

    print(f"Quotation draft generated: {filepath}")
    print(f"  Reference: {draft.ref}")
    print(f"  Client: {draft.client_name}")
    print(f"  Modules: {', '.join(item.code for item in draft.line_items)}")
    print(f"  Subtotal: {draft.subtotal:,}원")
    if draft.discount_rate > 0:
        print(f"  Discount: {draft.discount_label} (-{int(draft.discount_rate * 100)}%, -{draft.discount_amount:,}원)")
    print(f"  Total (VAT 별도): {draft.total_before_vat:,}원")
    print()
    print("STATUS: DRAFT -- Andrew 검토 대기")


if __name__ == "__main__":
    main()
