# /opt/docker/dev/service_finder/backend/app/api/v1/endpoints/search.py
from fastapi import APIRouter, Depends
from sqlalchemy.ext.asyncio import AsyncSession
from sqlalchemy import select, func, or_
from sqlalchemy.orm import selectinload
from app.db.session import get_db
from app.api.deps import get_current_user
from app.models.marketplace.organization import Organization, Branch
from geoalchemy2 import WKTElement
from typing import Optional

router = APIRouter()

@router.get("/match")
async def match_service(
    lat: Optional[float] = None,
    lng: Optional[float] = None,
    radius_km: float = 20.0,
    sort_by: str = "distance",
    db: AsyncSession = Depends(get_db),
    current_user = Depends(get_current_user)
):
    """
    Geofencing keresőmotor PostGIS segítségével.
    Ha nincs megadva lat/lng, akkor nem alkalmazunk távolságszűrést.
    """
    # Alap lekérdezés: aktív szervezetek és telephelyek
    query = select(
        Organization.id,
        Organization.name,
        Branch.city,
        Branch.branch_rating,
        Branch.location
    ).join(
        Branch, Organization.id == Branch.organization_id
    ).where(
        Organization.is_active == True,
        Branch.is_deleted == False
    )
    
    # Távolság számítás és szűrés, ha van koordináta
    if lat is not None and lng is not None:
        # WKT pont létrehozása a felhasználó helyéhez
        user_location = WKTElement(f'POINT({lng} {lat})', srid=4326)
        
        # Távolság kiszámítása méterben (ST_DistanceSphere)
        distance_col = func.ST_DistanceSphere(Branch.location, user_location).label("distance_meters")
        query = query.add_columns(distance_col)
        
        # Szűrés a sugárra (ST_DWithin) - a távolság méterben, radius_km * 1000
        query = query.where(
            func.ST_DWithin(Branch.location, user_location, radius_km * 1000)
        )
    else:
        # Ha nincs koordináta, ne legyen distance oszlop
        distance_col = None
    
    # Rendezés a sort_by paraméter alapján
    if sort_by == "distance" and lat is not None and lng is not None:
        query = query.order_by(distance_col.asc())
    elif sort_by == "rating":
        query = query.order_by(Branch.branch_rating.desc())
    elif sort_by == "price":
        # Jelenleg nincs ár információ, ezért rendezés alapértelmezettként (pl. név)
        query = query.order_by(Organization.name.asc())
    else:
        # Alapértelmezett rendezés: távolság, ha van, különben név
        if distance_col is not None:
            query = query.order_by(distance_col.asc())
        else:
            query = query.order_by(Organization.name.asc())
    
    # Lekérdezés végrehajtása
    result = await db.execute(query)
    rows = result.fetchall()
    
    # Eredmények formázása
    results = []
    for row in rows:
        row_dict = {
            "id": row.id,
            "name": row.name,
            "city": row.city,
            "rating": row.branch_rating,
        }
        if lat is not None and lng is not None:
            row_dict["distance_km"] = round(row.distance_meters / 1000, 2) if row.distance_meters else None
        results.append(row_dict)
    
    return {"results": results}