from fastapi import APIRouter, Depends, UploadFile, File, Form, HTTPException
from typing import List, Union, Optional
from sqlalchemy.orm import Session
import json
import logging

from app.api import deps
from app.schemas.product import ProductResponse, ProductDetailResponse, ProductCreate
from app.services.product_service import ProductService
from app.services.media_service import MediaService

router = APIRouter()

@router.get("/", response_model=List[ProductResponse])
def list_products(db: Session = Depends(deps.get_db)):
    """Retrieve the list of products"""
    return ProductService.get_products(db)

@router.get("/{product_id}", response_model=ProductDetailResponse)
def get_product_detail(product_id: int, db: Session = Depends(deps.get_db)):
    """Retrieve product details for the given product ID"""
    return ProductService.get_product_detail(db, product_id)

@router.post("/", response_model=ProductResponse)
async def create_product_endpoint(
    product_in: str = Form(...),
    images: List[UploadFile] = File([]),
    db: Session = Depends(deps.get_db),
    media_service: MediaService = Depends(deps.get_media_service)
):
    """
    Create a new product by providing a JSON string containing the product data via 'product_in'.
    
    Expected form-data:
    - product_in: JSON string with the following keys:
        {
            "name": "Product Name",
            "description": "Product description",
            "category_id": 1,
            "points_required": 100,
            "stock": 50,
            "status": 1,
            "specifications": {"color": "blue", "size": "M"}  // optional
        }
    - images: (Optional) file upload(s) for product images (max 5)
    """
    logger = logging.getLogger('adimsayar')
    logger.info(f"상품 등록 요청 받음: {product_in}")
    logger.info(f"이미지 업로드 수: {len(images)}")
    
    for idx, img in enumerate(images):
        logger.info(f"이미지 {idx+1}: 파일명={img.filename}, 컨텐츠 타입={img.content_type}, 크기={img.size}")
    
    try:
        product_data = json.loads(product_in)
        logger.info(f"변환된 상품 데이터: {product_data}")
    except Exception as e:
        logger.error(f"JSON 변환 오류: {str(e)}")
        raise HTTPException(status_code=400, detail="Invalid JSON provided for product_in")
    
    product_payload = ProductCreate(**product_data)
    logger.info(f"상품 페이로드 생성 완료: {product_payload}")
    
    try:
        product = ProductService.create_product(db, product_payload, images, media_service)
        logger.info(f"상품 생성 완료: {product.id}")
        return ProductResponse.from_orm(product)
    except Exception as e:
        logger.error(f"상품 생성 중 오류: {str(e)}", exc_info=True)
        raise

@router.put("/{product_id}", response_model=ProductResponse)
async def update_product_endpoint(
    product_id: int,
    product_in: str = Form(...),
    images: List[UploadFile] = File([]),
    db: Session = Depends(deps.get_db),
    media_service: MediaService = Depends(deps.get_media_service)
):
    """
    Update an existing product by providing a JSON string containing the product data via 'product_in'.
    
    Expected form-data:
    - product_in: JSON string with the following keys:
        {
            "name": "Updated Product Name",
            "description": "Updated product description",
            "category_id": 1,
            "points_required": 100,
            "stock": 50,
            "status": 1,
            "specifications": {"color": "red", "size": "L"}  // optional
        }
    - images: (Optional) file upload(s) for product images (max 5)
    """
    try:
        product_data = json.loads(product_in)
    except Exception:
        raise HTTPException(status_code=400, detail="Invalid JSON provided for product_in")
    
    product_payload = ProductCreate(**product_data)
    product = ProductService.update_product(db, product_id, product_payload, images, media_service)
    return ProductResponse.from_orm(product)

@router.delete("/{product_id}", response_model=dict)
def delete_product_endpoint(product_id: int, db: Session = Depends(deps.get_db)):
    """Delete a product by its ID"""
    return ProductService.delete_product(db, product_id)
