"""
Payment Request API router.
"""

from typing import Any, Dict
from fastapi import APIRouter, Depends, Request, status, HTTPException
from sqlalchemy.orm import Session

from src.core.database import get_db
from src.apps.auth.utils.auth import get_current_user, get_current_merchant
from src.apps.merchants.schemas.merchant_common import MerchantSchema
from src.apps.users.schemas.user_common import UserSchema
from src.apps.base.schemas.responses import BaseResponse
from src.apps.payment_requests import services
from src.apps.payment_requests.schemas.requests import (
    MerchantPaymentRequestCreateSchema,
    MerchantPaymentRequestUpdateSchema,
)
from src.apps.payment_requests.schemas.responses import PaymentRequestResponseSchema
from src.apps.payment_requests.payment_request_constants import DEFAULT_SCHEDULE_PAYMENTS_LIST

router = APIRouter()


@router.post("", name="Create Payment Request", response_model=PaymentRequestResponseSchema)
async def create_payment_request(
    payload: MerchantPaymentRequestCreateSchema,
    request: Request,
    db: Session = Depends(get_db),
    merchant: MerchantSchema = Depends(get_current_merchant),
    current_user: UserSchema = Depends(get_current_user),
    # is_permitted: bool = Depends(
    #     PermissionGuard(module=MODULES.PAYMENT_REQUEST, operation=OPERATIONS.CREATE)
    # ),
) -> PaymentRequestResponseSchema:
    """
    Call this API to create a payment request as a merchant

    On successful execution the API would return '200 OK' JSON response of the following format
    ```
    {
        "data": {
            "amount": 100.0,
            "payment_frequency": "split",
            "authorization_type": "request_auth",
            "payment_method": "card",
            "status": "full_amount_pending",
            "save_payment_method": false,
            "allow_tip": false,
            "configure_adjustment": false,
            "message": "",
            "id": 8,
            "due_date": "2021-10-25T19:29:17.454292+00:00",
            "billing_date": "2021-10-25T19:29:17.454292+00:00",
            "created_at": "2021-10-25T19:29:17.454292+00:00",
            "line_items": [...],
            "created_by": { ... }
        },
        "status_code": 200,
        "success": true,
        "message": "Request handled successfully"
    }
    ```
    """
    response = await services.create_payment_request(
        db=db,
        merchant=merchant,
        payload=payload,
        current_user=current_user,
        request=request,
    )
    
    return response

@router.get(
    "/{payment_request_id}/schedule",
    name="List of schedule of Payment Request",
    response_model=Dict[str, Any],
)
async def schedule_list(
    # db: Session = Depends(get_db),
    payment_request_id: str,
    # merchant: MerchantSchema = Depends(get_current_merchant),
    current_user: UserSchema = Depends(get_current_user),
    # payment_request_id: str = Path(
    #     ...,
    #     regex=regexp.PAYMENT_REQUEST_UNIQUE_ID,
    #     description="The payment_request_id of the payment request, usually in the form of pr_xxx",
    # ),
    # _from: Optional[str] = Query(
    #     default=None,
    #     regex=regexp.ISO_DATETIME_FORMAT,
    #     description="Start date of listing to be done. Must be of format YYYY-MM-DD",
    # ),
    # _to: Optional[str] = Query(
    #     default=None,
    #     regex=regexp.ISO_DATETIME_FORMAT,
    #     description="End date of listing to be done. Must be of format YYYY-MM-DD",
    # ),
    # page: int = Query(
    #     default=1,
    #     ge=1,
    #     description="Number of page that needs to be fetched from the records",
    # ),
    # per_page: int = Query(
    #     default=12,
    #     ge=1,
    #     le=constants.MAX_PER_PAGE,
    #     description="Number of page that needs to be fetched from the records",
    # ),
) -> Dict[str, Any]:
    """
    Call this API to fetch payment Request's Schedule

    On successfull execution the API would return '200 OK' JSON response of the following format
    ```
    {
        "data": {
            "auth_date": "2024-10-14 15:14:26.123445 ",
            "scheduled_date": "2024-10-17 15:14:16.000000 ",
            "amount": 1311.0,
            "paid_amount": null,
            "paid_date": null,
            "status_text": "overdue",
            "invoice_literal": "100000327",
            "invoice_id": "inv_9h8BYmZbK6eEK7WF",
            "sequence_id": 1,
            "following_invoice_id": "inv_9h8BYmZbK6eEK7WF",
            "transactions_info": {
                "txn_id": "",
                "txn_literal": ""
            }
        },
        "status_code": 200,
        "success": true,
        "message": "Subscription Scheduled fetched successfully."
    }
    ```
    """
    try:
        response = {"data":DEFAULT_SCHEDULE_PAYMENTS_LIST, "success": True, "message": "Subscription Scheduled fetched successfully."}
        return response
    except Exception as e:
        raise HTTPException(
            status_code=status.HTTP_400_BAD_REQUEST,
            detail=str(e)
        )

@router.patch("/{payment_request_id}", name="Update Payment Request", response_model=PaymentRequestResponseSchema)
async def update_payment_request(
    payment_request_id: str,
    payload: MerchantPaymentRequestUpdateSchema,
    request: Request,
    db: Session = Depends(get_db),
    merchant: MerchantSchema = Depends(get_current_merchant),
    current_user: UserSchema = Depends(get_current_user),
    # is_permitted: bool = Depends(
    #     PermissionGuard(module=MODULES.PAYMENT_REQUEST, operation=OPERATIONS.UPDATE)
    # ),
) -> PaymentRequestResponseSchema:
    """
    Call this API to update an existing payment request as a merchant.
    Only fields provided in the request will be updated.

    On successful execution the API would return '200 OK' JSON response with the updated payment request.
    """
    response = await services.update_payment_request(
        db=db,
        merchant=merchant,
        payment_request_id=payment_request_id,
        payload=payload,
        current_user=current_user,
        request=request,
    )
    
    return response
