"""IO contracts for the rule-based квартирография recommender.

POST /api/v1/analytics/recommend/mix
"""

from typing import Any, Literal

from pydantic import BaseModel, Field

ClassLiteral = Literal["Comfort", "Comfort+", "Business", "Elite"]


class RecommendMixInput(BaseModel):
    district_name: str = Field(..., min_length=2, max_length=80)
    area_total_m2: float | None = Field(default=None, ge=100, le=500_000)
    target_class: ClassLiteral | None = None
    months_window: int = Field(default=12, ge=3, le=24)
    # Velocity / pricing scenario knobs (live-tuned client-side; backend just
    # ships base coefficients so frontend can recompute without round-trips).
    # 0.01..3.0 = -99%..+200% к рынку. min=0.01 (а не 0) чтобы избежать
    # деления на 0 / pf^elasticity = ∞ при «бесплатной» цене.
    price_factor: float = Field(default=1.0, ge=0.01, le=3.0)
    target_months: int | None = Field(default=None, ge=3, le=120)


class RecommendBucket(BaseModel):
    bucket: str
    share_pct: float
    deal_count: int
    area_avg_m2: float
    area_median_m2: float
    price_median_per_m2: float
    price_p25_per_m2: float
    price_p75_per_m2: float
    units_planned: int | None = None
    revenue_planned_rub: float | None = None
    # Velocity baseline (units/month for THIS project allocated to this bucket
    # at price_factor=1.0). Frontend scales by price_factor^elasticity for live
    # what-if recompute.
    velocity_per_month: float | None = None
    months_to_sellout: float | None = None
    # Success-driven mix flag (issue #25): bucket has top success_score in district
    is_top_success: bool = False


class RecommendComparable(BaseModel):
    obj_id: int
    comm_name: str | None = None
    dev_name: str | None = None
    obj_class: str | None = None
    flat_count: int | None = None
    sold_perc: float | None = None
    cad_quarter: str | None = None
    lat: float | None = None
    lon: float | None = None
    buildings_n: int | None = None


class RecommendMixOutput(BaseModel):
    scope: dict[str, Any]
    buckets: list[RecommendBucket]
    summary: dict[str, Any]
    comparables: list[RecommendComparable]
