"""Decision model — every authorization decision is a structured, auditable artifact."""

from datetime import UTC, datetime

from pydantic import BaseModel, Field

from pyauthz.models.action import Effect
from pyauthz.models.context import AccessRequest


class Decision(BaseModel):
    """The result of an authorization evaluation.

    Every call to authorize() produces a Decision, whether access is allowed or denied.
    The Decision carries the full context needed for audit logging and debugging.

    Example:
        decision = rp.authorize(user, "documents:write", doc)
        print(decision.allowed)           # True
        print(decision.matched_policies)  # ["admin-full-access"]
        print(decision.explain())         # "ALLOWED: alice -> documents:write on documents/doc-1 (...)"
    """

    allowed: bool
    effect: Effect
    request: AccessRequest
    matched_policies: list[str] = []
    reasoning: list[str] = []
    evaluated_at: datetime = Field(default_factory=lambda: datetime.now(UTC))
    duration_us: int = 0

    def explain(self) -> str:
        """Human-readable explanation for debugging and audit.

        Returns:
            A single-line summary like 'ALLOWED: alice -> documents:write on documents/doc-1 (reason)'.
        """
        status = "ALLOWED" if self.allowed else "DENIED"
        reasons = "; ".join(self.reasoning) or "no matching policy"
        subj = self.request.subject.id
        act = self.request.action
        res_type = self.request.resource.type
        res_id = self.request.resource.id
        return f"{status}: {subj} -> {act} on {res_type}/{res_id} ({reasons})"
