import json
import logging
from typing import List, Optional

from datetime import datetime, date

from fastapi import APIRouter, Body, Depends, HTTPException, Query
from pydantic import BaseModel
from sqlalchemy.ext.asyncio import AsyncSession

from core.database import get_db
from services.contact_inquiries import Contact_inquiriesService

# Set up logging
logger = logging.getLogger(__name__)

router = APIRouter(prefix="/api/v1/entities/contact_inquiries", tags=["contact_inquiries"])


# ---------- Pydantic Schemas ----------
class Contact_inquiriesData(BaseModel):
    """Entity data schema (for create/update)"""
    name: str
    email: str
    phone: str = None
    subject: str
    message: str


class Contact_inquiriesUpdateData(BaseModel):
    """Update entity data (partial updates allowed)"""
    name: Optional[str] = None
    email: Optional[str] = None
    phone: Optional[str] = None
    subject: Optional[str] = None
    message: Optional[str] = None


class Contact_inquiriesResponse(BaseModel):
    """Entity response schema"""
    id: int
    name: str
    email: str
    phone: Optional[str] = None
    subject: str
    message: str
    created_at: Optional[datetime] = None
    updated_at: Optional[datetime] = None

    class Config:
        from_attributes = True


class Contact_inquiriesListResponse(BaseModel):
    """List response schema"""
    items: List[Contact_inquiriesResponse]
    total: int
    skip: int
    limit: int


class Contact_inquiriesBatchCreateRequest(BaseModel):
    """Batch create request"""
    items: List[Contact_inquiriesData]


class Contact_inquiriesBatchUpdateItem(BaseModel):
    """Batch update item"""
    id: int
    updates: Contact_inquiriesUpdateData


class Contact_inquiriesBatchUpdateRequest(BaseModel):
    """Batch update request"""
    items: List[Contact_inquiriesBatchUpdateItem]


class Contact_inquiriesBatchDeleteRequest(BaseModel):
    """Batch delete request"""
    ids: List[int]


# ---------- Routes ----------
@router.get("", response_model=Contact_inquiriesListResponse)
async def query_contact_inquiriess(
    query: str = Query(None, description="Query conditions (JSON string)"),
    sort: str = Query(None, description="Sort field (prefix with '-' for descending)"),
    skip: int = Query(0, ge=0, description="Number of records to skip"),
    limit: int = Query(20, ge=1, le=2000, description="Max number of records to return"),
    fields: str = Query(None, description="Comma-separated list of fields to return"),
    db: AsyncSession = Depends(get_db),
):
    """Query contact_inquiriess with filtering, sorting, and pagination"""
    logger.debug(f"Querying contact_inquiriess: query={query}, sort={sort}, skip={skip}, limit={limit}, fields={fields}")
    
    service = Contact_inquiriesService(db)
    try:
        # Parse query JSON if provided
        query_dict = None
        if query:
            try:
                query_dict = json.loads(query)
            except json.JSONDecodeError:
                raise HTTPException(status_code=400, detail="Invalid query JSON format")
        
        result = await service.get_list(
            skip=skip, 
            limit=limit,
            query_dict=query_dict,
            sort=sort,
        )
        logger.debug(f"Found {result['total']} contact_inquiriess")
        return result
    except HTTPException:
        raise
    except Exception as e:
        logger.error(f"Error querying contact_inquiriess: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Internal server error: {str(e)}")


@router.get("/all", response_model=Contact_inquiriesListResponse)
async def query_contact_inquiriess_all(
    query: str = Query(None, description="Query conditions (JSON string)"),
    sort: str = Query(None, description="Sort field (prefix with '-' for descending)"),
    skip: int = Query(0, ge=0, description="Number of records to skip"),
    limit: int = Query(20, ge=1, le=2000, description="Max number of records to return"),
    fields: str = Query(None, description="Comma-separated list of fields to return"),
    db: AsyncSession = Depends(get_db),
):
    # Query contact_inquiriess with filtering, sorting, and pagination without user limitation
    logger.debug(f"Querying contact_inquiriess: query={query}, sort={sort}, skip={skip}, limit={limit}, fields={fields}")

    service = Contact_inquiriesService(db)
    try:
        # Parse query JSON if provided
        query_dict = None
        if query:
            try:
                query_dict = json.loads(query)
            except json.JSONDecodeError:
                raise HTTPException(status_code=400, detail="Invalid query JSON format")

        result = await service.get_list(
            skip=skip,
            limit=limit,
            query_dict=query_dict,
            sort=sort
        )
        logger.debug(f"Found {result['total']} contact_inquiriess")
        return result
    except HTTPException:
        raise
    except Exception as e:
        logger.error(f"Error querying contact_inquiriess: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Internal server error: {str(e)}")


@router.get("/{id}", response_model=Contact_inquiriesResponse)
async def get_contact_inquiries(
    id: int,
    fields: str = Query(None, description="Comma-separated list of fields to return"),
    db: AsyncSession = Depends(get_db),
):
    """Get a single contact_inquiries by ID"""
    logger.debug(f"Fetching contact_inquiries with id: {id}, fields={fields}")
    
    service = Contact_inquiriesService(db)
    try:
        result = await service.get_by_id(id)
        if not result:
            logger.warning(f"Contact_inquiries with id {id} not found")
            raise HTTPException(status_code=404, detail="Contact_inquiries not found")
        
        return result
    except HTTPException:
        raise
    except Exception as e:
        logger.error(f"Error fetching contact_inquiries {id}: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Internal server error: {str(e)}")


@router.post("", response_model=Contact_inquiriesResponse, status_code=201)
async def create_contact_inquiries(
    data: Contact_inquiriesData,
    db: AsyncSession = Depends(get_db),
):
    """Create a new contact_inquiries"""
    logger.debug(f"Creating new contact_inquiries with data: {data}")
    
    service = Contact_inquiriesService(db)
    try:
        result = await service.create(data.model_dump())
        if not result:
            raise HTTPException(status_code=400, detail="Failed to create contact_inquiries")
        
        logger.info(f"Contact_inquiries created successfully with id: {result.id}")
        return result
    except ValueError as e:
        logger.error(f"Validation error creating contact_inquiries: {str(e)}")
        raise HTTPException(status_code=400, detail=str(e))
    except Exception as e:
        logger.error(f"Error creating contact_inquiries: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Internal server error: {str(e)}")


@router.post("/batch", response_model=List[Contact_inquiriesResponse], status_code=201)
async def create_contact_inquiriess_batch(
    request: Contact_inquiriesBatchCreateRequest,
    db: AsyncSession = Depends(get_db),
):
    """Create multiple contact_inquiriess in a single request"""
    logger.debug(f"Batch creating {len(request.items)} contact_inquiriess")
    
    service = Contact_inquiriesService(db)
    results = []
    
    try:
        for item_data in request.items:
            result = await service.create(item_data.model_dump())
            if result:
                results.append(result)
        
        logger.info(f"Batch created {len(results)} contact_inquiriess successfully")
        return results
    except Exception as e:
        await db.rollback()
        logger.error(f"Error in batch create: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Batch create failed: {str(e)}")


@router.put("/batch", response_model=List[Contact_inquiriesResponse])
async def update_contact_inquiriess_batch(
    request: Contact_inquiriesBatchUpdateRequest,
    db: AsyncSession = Depends(get_db),
):
    """Update multiple contact_inquiriess in a single request"""
    logger.debug(f"Batch updating {len(request.items)} contact_inquiriess")
    
    service = Contact_inquiriesService(db)
    results = []
    
    try:
        for item in request.items:
            # Only include non-None values for partial updates
            update_dict = {k: v for k, v in item.updates.model_dump().items() if v is not None}
            result = await service.update(item.id, update_dict)
            if result:
                results.append(result)
        
        logger.info(f"Batch updated {len(results)} contact_inquiriess successfully")
        return results
    except Exception as e:
        await db.rollback()
        logger.error(f"Error in batch update: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Batch update failed: {str(e)}")


@router.put("/{id}", response_model=Contact_inquiriesResponse)
async def update_contact_inquiries(
    id: int,
    data: Contact_inquiriesUpdateData,
    db: AsyncSession = Depends(get_db),
):
    """Update an existing contact_inquiries"""
    logger.debug(f"Updating contact_inquiries {id} with data: {data}")

    service = Contact_inquiriesService(db)
    try:
        # Only include non-None values for partial updates
        update_dict = {k: v for k, v in data.model_dump().items() if v is not None}
        result = await service.update(id, update_dict)
        if not result:
            logger.warning(f"Contact_inquiries with id {id} not found for update")
            raise HTTPException(status_code=404, detail="Contact_inquiries not found")
        
        logger.info(f"Contact_inquiries {id} updated successfully")
        return result
    except HTTPException:
        raise
    except ValueError as e:
        logger.error(f"Validation error updating contact_inquiries {id}: {str(e)}")
        raise HTTPException(status_code=400, detail=str(e))
    except Exception as e:
        logger.error(f"Error updating contact_inquiries {id}: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Internal server error: {str(e)}")


@router.delete("/batch")
async def delete_contact_inquiriess_batch(
    request: Contact_inquiriesBatchDeleteRequest,
    db: AsyncSession = Depends(get_db),
):
    """Delete multiple contact_inquiriess by their IDs"""
    logger.debug(f"Batch deleting {len(request.ids)} contact_inquiriess")
    
    service = Contact_inquiriesService(db)
    deleted_count = 0
    
    try:
        for item_id in request.ids:
            success = await service.delete(item_id)
            if success:
                deleted_count += 1
        
        logger.info(f"Batch deleted {deleted_count} contact_inquiriess successfully")
        return {"message": f"Successfully deleted {deleted_count} contact_inquiriess", "deleted_count": deleted_count}
    except Exception as e:
        await db.rollback()
        logger.error(f"Error in batch delete: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Batch delete failed: {str(e)}")


@router.delete("/{id}")
async def delete_contact_inquiries(
    id: int,
    db: AsyncSession = Depends(get_db),
):
    """Delete a single contact_inquiries by ID"""
    logger.debug(f"Deleting contact_inquiries with id: {id}")
    
    service = Contact_inquiriesService(db)
    try:
        success = await service.delete(id)
        if not success:
            logger.warning(f"Contact_inquiries with id {id} not found for deletion")
            raise HTTPException(status_code=404, detail="Contact_inquiries not found")
        
        logger.info(f"Contact_inquiries {id} deleted successfully")
        return {"message": "Contact_inquiries deleted successfully", "id": id}
    except HTTPException:
        raise
    except Exception as e:
        logger.error(f"Error deleting contact_inquiries {id}: {str(e)}", exc_info=True)
        raise HTTPException(status_code=500, detail=f"Internal server error: {str(e)}")