"""FastAPI dependency injection helpers for PyAuthz.

These are used with FastAPI's `Depends()` to inject the PyAuthz engine,
the resolved Subject, or the full Decision into route handlers.
"""

from __future__ import annotations

from fastapi import Request

from pyauthz import Decision, PyAuthz, Subject


def get_pyauthz(request: Request) -> PyAuthz:
    """FastAPI dependency that returns the PyAuthz engine from request state.

    Requires PyAuthzMiddleware to be installed.

    Example:
        @app.get("/check")
        async def check(rp: PyAuthz = Depends(get_pyauthz)):
            ...
    """
    return request.state.pyauthz


def get_subject(request: Request) -> Subject:
    """FastAPI dependency that returns the resolved Subject from request state.

    Requires PyAuthzMiddleware to be installed.

    Example:
        @app.get("/me")
        async def me(subject: Subject = Depends(get_subject)):
            return {"id": subject.id, "roles": subject.roles}
    """
    return request.state.subject


def get_decision(request: Request) -> Decision | None:
    """FastAPI dependency that returns the most recent Decision from request state.

    Only available after a `@requires()` decorator has run on the current request.
    Returns None if no authorization check has been performed yet.

    Example:
        @app.get("/documents/{doc_id}")
        @requires("documents:read")
        async def get_doc(doc_id: str, decision: Decision = Depends(get_decision)):
            print(decision.explain())
    """
    return getattr(request.state, "pyauthz_decision", None)
