from typing import Any, Optional

from fastapi import APIRouter, Depends, HTTPException, Query

from decnet.telemetry import traced as _traced
from decnet.web.dependencies import require_viewer, repo
from decnet.web.db.models import CredentialReuseResponse

router = APIRouter()


@router.get(
    "/credential-reuse",
    response_model=CredentialReuseResponse,
    tags=["Credentials"],
    responses={
        401: {"description": "Could not validate credentials"},
        403: {"description": "Insufficient permissions"},
        422: {"description": "Validation error"},
    },
)
@_traced("api.list_credential_reuse")
async def list_credential_reuse(
    limit: int = Query(50, ge=1, le=1000),
    offset: int = Query(0, ge=0, le=2147483647),
    min_target_count: int = Query(2, ge=2, le=2147483647),
    secret_kind: Optional[str] = None,
    user: dict = Depends(require_viewer),
) -> dict[str, Any]:
    """Paged list of credential-reuse findings ordered by target_count desc.

    Each row collapses every Credential capture sharing the same secret
    + principal across distinct (decky, service) pairs into a single
    finding with the union of attacker UUIDs/IPs and reach.
    """
    def _norm(v: Optional[str]) -> Optional[str]:
        if v in (None, "null", "NULL", "undefined", ""):
            return None
        return v

    kind = _norm(secret_kind)
    total, data = await repo.list_credential_reuses(
        limit=limit,
        offset=offset,
        min_target_count=min_target_count,
        secret_kind=kind,
    )
    return {
        "total": total,
        "limit": limit,
        "offset": offset,
        "data": data,
    }


@router.get(
    "/credential-reuse/{reuse_id}",
    tags=["Credentials"],
    responses={
        401: {"description": "Could not validate credentials"},
        403: {"description": "Insufficient permissions"},
        404: {"description": "CredentialReuse row not found"},
    },
)
@_traced("api.get_credential_reuse")
async def get_credential_reuse(
    reuse_id: str,
    user: dict = Depends(require_viewer),
) -> dict[str, Any]:
    """One credential-reuse finding by UUID, or 404."""
    row = await repo.get_credential_reuse_by_id(reuse_id)
    if row is None:
        raise HTTPException(status_code=404, detail="credential_reuse not found")
    return row
