from __future__ import annotations

import logging
from functools import wraps

from amsdal_models.classes.model import Model
from amsdal_server.apps.common.permissions.enums import Action

logger = logging.getLogger(__name__)


def with_amsdal_context(func):
    """Bridge MCP request_ctx into AMSDAL context.

    Copies Starlette Request (with .user/.auth from parent middleware)
    from MCP's request_ctx ContextVar into AmsdalContextManager.
    """

    @wraps(func)
    async def wrapper(*args, **kwargs):
        try:
            from amsdal.context.manager import AmsdalContextManager
            from mcp.server.lowlevel.server import request_ctx

            mcp_context = request_ctx.get()
            request = getattr(mcp_context, 'request', None)
            if request is not None:
                AmsdalContextManager.add_to_context('request', request)
        except LookupError:
            pass
        return await func(*args, **kwargs)

    return wrapper


async def authorize_class(model_cls: type[Model], action: Action) -> None:
    """Check class-level authorization for the current request.

    Delegates to PermissionsMixin.authorize_class which publishes a
    ClassAuthorizeEvent. Raises AmsdalAuthorizationError if denied.
    """
    from amsdal_server.apps.common.mixins.permissions_mixin import PermissionsMixin
    from amsdal_server.apps.common.permissions.enums import ResourceType

    await PermissionsMixin.authorize_class(ResourceType.MODELS, model_cls.__name__, action)


async def authorize_object(obj: Model, action: Action) -> None:
    """Check object-level authorization for the current request.

    Delegates to PermissionsMixin.authorize_object which publishes an
    ObjectAuthorizeEvent. Raises AmsdalAuthorizationError if denied.
    """
    from amsdal_server.apps.common.mixins.permissions_mixin import PermissionsMixin

    await PermissionsMixin.authorize_object(obj, action)
