<?php
require_once '../config/cors.php';
require_once '../config/database.php';

$database = new Database();
$db = $database->getConnection();

$method = $_SERVER['REQUEST_METHOD'];

if ($method !== 'POST') {
    http_response_code(405);
    echo json_encode(['success' => false, 'message' => 'Method not allowed']);
    exit;
}

try {
    $data = json_decode(file_get_contents("php://input"), true);

    // Validate required fields
    $userId = $data['userId'] ?? $data['user_id'] ?? null;
    $addressId = $data['addressId'] ?? $data['address_id'] ?? null;
    $paymentMethod = $data['paymentMethod'] ?? $data['payment_method'] ?? 'cash_on_delivery';

    if (!$userId || $userId === 'guest') {
        http_response_code(400);
        echo json_encode(['success' => false, 'message' => 'Valid User ID is required']);
        exit;
    }

    if (!$addressId) {
        http_response_code(400);
        echo json_encode(['success' => false, 'message' => 'Address ID is required']);
        exit;
    }

    // Only allow cash on delivery for now
    if ($paymentMethod !== 'cash_on_delivery') {
        http_response_code(400);
        echo json_encode(['success' => false, 'message' => 'Only Cash on Delivery is available currently. Other payment methods coming soon!']);
        exit;
    }

    // Start transaction
    $db->beginTransaction();

    // Get cart items with variant support
    try {
        $stmt = $db->prepare("SHOW COLUMNS FROM cart_items LIKE 'variant_data'");
        $stmt->execute();
        $hasVariantData = $stmt->rowCount() > 0;
        
        if ($hasVariantData) {
            $stmt = $db->prepare("
                SELECT ci.*, p.name, p.base_price, p.stock
                FROM cart_items ci
                JOIN products p ON ci.product_id = p.id
                WHERE ci.user_id = :user_id AND p.is_active = 1
            ");
        } else {
            $stmt = $db->prepare("
                SELECT ci.*, p.name, p.base_price, p.stock,
                       pv.variant_name, pv.price_diff
                FROM cart_items ci
                JOIN products p ON ci.product_id = p.id
                LEFT JOIN product_variants pv ON ci.variant_id = pv.id
                WHERE ci.user_id = :user_id AND p.is_active = 1
            ");
        }
        
        $stmt->bindParam(':user_id', $userId, PDO::PARAM_STR);
        $stmt->execute();
        
        $cartItems = $stmt->fetchAll(PDO::FETCH_ASSOC);
        
        // Parse variant data for each item
        foreach ($cartItems as &$item) {
            if (isset($item['variant_data']) && $item['variant_data']) {
                $item['variant'] = json_decode($item['variant_data'], true);
            } else if (isset($item['variant_name']) && $item['variant_name']) {
                // Build variant object from joined data
                $item['variant'] = [
                    'id' => $item['variant_id'],
                    'variant_name' => $item['variant_name'],
                    'price_diff' => $item['price_diff']
                ];
            }
        }
    } catch (PDOException $e) {
        // Fallback query
        $stmt = $db->prepare("
            SELECT ci.*, p.name, p.base_price, p.stock
            FROM cart_items ci
            JOIN products p ON ci.product_id = p.id
            WHERE ci.user_id = :user_id AND p.is_active = 1
        ");
        $stmt->bindParam(':user_id', $userId, PDO::PARAM_STR);
        $stmt->execute();
        
        $cartItems = $stmt->fetchAll(PDO::FETCH_ASSOC);
    }

    if (empty($cartItems)) {
        $db->rollBack();
        http_response_code(400);
        echo json_encode(['success' => false, 'message' => 'Cart is empty']);
        exit;
    }

    // Verify address belongs to user
    $stmt = $db->prepare("SELECT id FROM addresses WHERE id = :address_id AND user_id = :user_id");
    $stmt->bindParam(':address_id', $addressId, PDO::PARAM_STR);
    $stmt->bindParam(':user_id', $userId, PDO::PARAM_STR);
    $stmt->execute();
    
    if (!$stmt->fetch()) {
        $db->rollBack();
        http_response_code(400);
        echo json_encode(['success' => false, 'message' => 'Invalid address']);
        exit;
    }

    // Calculate totals
    $subtotal = 0;
    foreach ($cartItems as $item) {
        // Check stock based on variant
        $availableStock = $item['stock']; // Default to product stock
        $stockContext = $item['name'];
        
        // If item has variant, check variant stock
        if (isset($item['variant']) && $item['variant'] && isset($item['variant']['stock'])) {
            $availableStock = $item['variant']['stock'];
            $stockContext = "{$item['name']} (Variant: {$item['variant']['variant_name']})";
        } else if (isset($item['variant_id']) && $item['variant_id']) {
            // Try to get variant stock from database
            try {
                $stmt = $db->prepare("SELECT stock, variant_name FROM product_variants WHERE id = :variant_id");
                $stmt->bindParam(':variant_id', $item['variant_id'], PDO::PARAM_STR);
                $stmt->execute();
                $variantData = $stmt->fetch(PDO::FETCH_ASSOC);
                
                if ($variantData) {
                    $availableStock = $variantData['stock'];
                    $stockContext = "{$item['name']} (Variant: {$variantData['variant_name']})";
                }
            } catch (PDOException $e) {
                // Continue with product stock if variant lookup fails
            }
        }
        
        // Validate stock
        if ($availableStock < $item['quantity']) {
            $db->rollBack();
            http_response_code(400);
            echo json_encode([
                'success' => false, 
                'message' => "Insufficient stock for {$stockContext}. Available: {$availableStock}, Requested: {$item['quantity']}"
            ]);
            exit;
        }
        
        $itemPrice = isset($item['price']) ? $item['price'] : $item['base_price'];
        $subtotal += $itemPrice * $item['quantity'];
    }

    $shippingPrice = 0; // Free shipping for now
    $totalPrice = $subtotal + $shippingPrice;

    // Create order
    $orderId = bin2hex(random_bytes(16));
    $stmt = $db->prepare("
        INSERT INTO orders (
            id, user_id, total_price, subtotal, shipping_price, 
            status, shipping_address_id, payment_status, payment_method
        ) VALUES (
            :id, :user_id, :total_price, :subtotal, :shipping_price,
            'pending', :shipping_address_id, 'pending', :payment_method
        )
    ");
    $stmt->bindParam(':id', $orderId, PDO::PARAM_STR);
    $stmt->bindParam(':user_id', $userId, PDO::PARAM_STR);
    $stmt->bindParam(':total_price', $totalPrice);
    $stmt->bindParam(':subtotal', $subtotal);
    $stmt->bindParam(':shipping_price', $shippingPrice);
    $stmt->bindParam(':shipping_address_id', $addressId, PDO::PARAM_STR);
    $stmt->bindParam(':payment_method', $paymentMethod, PDO::PARAM_STR);
    $stmt->execute();

    // Create order items and update stock
    foreach ($cartItems as $item) {
        $itemPrice = isset($item['price']) ? $item['price'] : $item['base_price'];
        $totalItemPrice = $itemPrice * $item['quantity'];
        
        // Get variant ID from either variant_id column or variant object
        $variantId = null;
        if (isset($item['variant_id']) && $item['variant_id']) {
            $variantId = $item['variant_id'];
        } else if (isset($item['variant']) && $item['variant'] && isset($item['variant']['id'])) {
            $variantId = $item['variant']['id'];
        }
        
        // Insert order item
        $orderItemId = bin2hex(random_bytes(16));
        $stmt = $db->prepare("
            INSERT INTO order_items (
                id, order_id, product_id, variant_id, quantity, unit_price, total_price
            ) VALUES (
                :id, :order_id, :product_id, :variant_id, :quantity, :unit_price, :total_price
            )
        ");
        $stmt->bindParam(':id', $orderItemId, PDO::PARAM_STR);
        $stmt->bindParam(':order_id', $orderId, PDO::PARAM_STR);
        $stmt->bindParam(':product_id', $item['product_id'], PDO::PARAM_STR);
        $stmt->bindParam(':variant_id', $variantId, PDO::PARAM_STR);
        $stmt->bindParam(':quantity', $item['quantity']);
        $stmt->bindParam(':unit_price', $itemPrice);
        $stmt->bindParam(':total_price', $totalItemPrice);
        $stmt->execute();

        // Update product stock (or variant stock if applicable)
        if ($variantId) {
            // Try to update variant stock first
            try {
                $stmt = $db->prepare("UPDATE product_variants SET stock = stock - :quantity WHERE id = :variant_id");
                $stmt->bindParam(':quantity', $item['quantity']);
                $stmt->bindParam(':variant_id', $variantId, PDO::PARAM_STR);
                $stmt->execute();
            } catch (PDOException $e) {
                // Fallback to product stock if variant stock doesn't exist
                $stmt = $db->prepare("UPDATE products SET stock = stock - :quantity WHERE id = :product_id");
                $stmt->bindParam(':quantity', $item['quantity']);
                $stmt->bindParam(':product_id', $item['product_id'], PDO::PARAM_STR);
                $stmt->execute();
            }
        } else {
            // Update product stock
            $stmt = $db->prepare("UPDATE products SET stock = stock - :quantity WHERE id = :product_id");
            $stmt->bindParam(':quantity', $item['quantity']);
            $stmt->bindParam(':product_id', $item['product_id'], PDO::PARAM_STR);
            $stmt->execute();
        }
    }

    // Clear cart
    $stmt = $db->prepare("DELETE FROM cart_items WHERE user_id = :user_id");
    $stmt->bindParam(':user_id', $userId, PDO::PARAM_STR);
    $stmt->execute();

    // Commit transaction
    $db->commit();

    // Get created order with details
    $stmt = $db->prepare("
        SELECT 
            o.*,
            a.label as address_label,
            a.address_line1,
            a.address_line2,
            a.city,
            a.state,
            a.postal_code,
            a.country
        FROM orders o
        LEFT JOIN addresses a ON o.shipping_address_id = a.id
        WHERE o.id = :order_id
    ");
    $stmt->bindParam(':order_id', $orderId, PDO::PARAM_STR);
    $stmt->execute();
    
    $order = $stmt->fetch(PDO::FETCH_ASSOC);

    http_response_code(201);
    echo json_encode([
        'success' => true,
        'message' => 'Order placed successfully!',
        'order' => $order
    ]);

} catch (Exception $e) {
    if ($db->inTransaction()) {
        $db->rollBack();
    }
    
    http_response_code(500);
    echo json_encode([
        'success' => false,
        'message' => 'Internal Server Error: ' . $e->getMessage()
    ]);
}
?>