from fastapi import APIRouter, Request
from fastapi.responses import JSONResponse
from ..utils import MONGODB_DATABASE, mongodb_connect, check_access, get_user_sub, send_push_notification

mongodb_client = mongodb_connect()
router = APIRouter(
    prefix="/notifications",
    tags=["notifications"],
    responses={404: {"description": "Not found"}},
)

@router.get("")
async def get_notifications(request: Request):
    auth_token = request.headers["authorization"].replace("Bearer ", "")
    check_access(auth_token, ["*"])
    user_sub = get_user_sub(auth_token)
    try:
        notifications = list(mongodb_client[MONGODB_DATABASE]["notifications"].find(
            {"user_sub": user_sub},
            {"_id": 0}
        ).sort("sent_at", -1))
        responseObject = {
            "status": "success",
            "content": notifications,
            "endpoint": "GetNotifications",
        }
        return JSONResponse(content=responseObject, status_code=200)
    except Exception as e:
        responseObject = {
            "status": "error",
            "endpoint": "GetNotifications",
            "message": str(e),
        }
        return JSONResponse(content=responseObject, status_code=500)
    
@router.put("")
async def read_all_notifications(request: Request):
    auth_token = request.headers["authorization"].replace("Bearer ", "")
    check_access(auth_token, ["*"])
    my_user_sub = get_user_sub(auth_token)
    
    try:
        result = mongodb_client[MONGODB_DATABASE]["notifications"].update_many(
            {"user_sub": my_user_sub, "status": "sent"},
            {"$set": {"status": "read"}}
        )

        if result.modified_count == 0:
            responseObject = {
                "status": "error",
                "endpoint": "ReadAllNotifications",
                "message": "Aucune notification à lire",
            }
            return JSONResponse(content=responseObject, status_code=404)
        
        responseObject = {
            "status": "success",
            "endpoint": "ReadAllNotifications",
            "message": "Toutes les notifications ont été marquées comme lues",
        }
        return JSONResponse(content=responseObject, status_code=200)
    except Exception as e:
        responseObject = {
            "status": "error",
            "endpoint": "ReadAllNotifications",
            "message": str(e),
        }
        return JSONResponse(content=responseObject, status_code=500)

@router.post("/token/update")
async def update_push_token(request: Request, token_data: dict):
    auth_token = request.headers["authorization"].replace("Bearer ", "")
    user_sub = get_user_sub(auth_token)
    
    if not user_sub:
        responseObject = {
            "status": "error",
            "endpoint": "UpdatePushToken",
            "message": "Invalid user",
        }
        return JSONResponse(content=responseObject, status_code=401)
    
    token = token_data.get("token")
    if not token:
        responseObject = {
            "status": "error",
            "endpoint": "UpdatePushToken",
            "message": "Token is required",
        }
        return JSONResponse(content=responseObject, status_code=400)
    
    mongodb_client[MONGODB_DATABASE]["push_tokens"].update_one(
        {"token": token},
        {"$set": {"user_sub": user_sub}},
        upsert=True
    )
    
    responseObject = {
        "status": "success",
        "endpoint": "UpdatePushToken",
        "message": "Push token updated successfully",
    }
    return JSONResponse(content=responseObject, status_code=200)

@router.get("/send/test")
async def send_test_notification(request: Request):
    """Send a push notification to users with 'see' role."""
    auth_token = request.headers["authorization"].replace("Bearer ", "")
    check_access(auth_token, ["*"])
    
    users = list(mongodb_client[MONGODB_DATABASE]["users"].find(
        {"roles": "see", "active": True},
        {"_id": 0, "sub": 1}
    ))
    
    send_push_notification(users, "Alert", "This is a test notification, sent by the API to users with the 'see' role")

    responseObject = {
        "status": "success",
        "endpoint": "SendTestNotification",
        "message": "Push notifications sent",
    }
    return JSONResponse(content=responseObject, status_code=200)

@router.put("/{sub}")
async def read_notifications(request: Request, sub: str):
    auth_token = request.headers["authorization"].replace("Bearer ", "")
    check_access(auth_token, ["*"])

    try:
        notification_cursor = mongodb_client[MONGODB_DATABASE]["notifications"].find_one(
            {"sub": sub},
            {"_id": 0, "sub": 1, "status": 1}
        )

        if not notification_cursor:
            responseObject = {
                "status": "error",
                "endpoint": "ReadNotifications",
                "message": f"Notification '{sub}' n'existe pas",
            }
            return JSONResponse(content=responseObject, status_code=404)
        
        result = mongodb_client[MONGODB_DATABASE]["notifications"].update_one(
            {"sub": sub},
            {"$set": {"status": "read"}}
        )

        if result.matched_count == 0:
            responseObject = {
                "status": "error",
                "endpoint": "ReadNotifications",
                "message": f"Erreur lors de la mise à jour de la notification",
            }
            return JSONResponse(content=responseObject, status_code=500)
        
        responseObject = {
            "status": "success",
            "endpoint": "ReadNotifications",
            "message": f"Notification '{sub}' lu",
        }
        return JSONResponse(content=responseObject, status_code=200)
    except Exception as e:
        responseObject = {
            "status": "error",
            "endpoint": "ReadNotifications",
            "message": str(e),
        }
        return JSONResponse(content=responseObject, status_code=500)