<?php
/**
 * WooCommerce Integration
 *
 * @package ReplyIt_Chat_Widget
 */

// Exit if accessed directly
if (!defined('ABSPATH')) {
    exit;
}

class ReplyIt_WooCommerce {

    /**
     * Single instance
     */
    private static $instance = null;

    /**
     * Get instance
     */
    public static function instance() {
        if (is_null(self::$instance)) {
            self::$instance = new self();
        }
        return self::$instance;
    }

    /**
     * Constructor
     */
    private function __construct() {
        // Add WooCommerce-specific hooks here if needed
        add_action('woocommerce_add_to_cart', [$this, 'on_add_to_cart'], 10, 6);
    }

    /**
     * Hook: When product is added to cart
     */
    public function on_add_to_cart($cart_item_key, $product_id, $quantity, $variation_id, $variation, $cart_item_data) {
        // Future: Trigger proactive message "Product added to cart"
    }

    /**
     * Get customer data
     * Note: Order info is NOT included here - use lookup_customer_order tool for order queries
     */
    public static function get_customer_data() {
        if (!is_user_logged_in()) {
            return [
                'is_logged_in' => false
            ];
        }

        $user = wp_get_current_user();
        $customer = new WC_Customer($user->ID);

        // Only basic customer info - order data retrieved via tool calling
        return [
            'is_logged_in' => true,
            'email' => $user->user_email,
            'first_name' => $customer->get_first_name(),
            'last_name' => $customer->get_last_name(),
        ];
    }

    /**
     * Get cart data
     */
    public static function get_cart_data() {
        if (!function_exists('WC') || WC()->cart->is_empty()) {
            return null;
        }

        $cart = WC()->cart;
        $items = [];

        foreach ($cart->get_cart() as $cart_item) {
            $product = $cart_item['data'];

            $items[] = [
                'product_id' => $cart_item['product_id'],
                'name' => $product->get_name(),
                'quantity' => $cart_item['quantity'],
                'price' => (float) $product->get_price(),
                'subtotal' => (float) $cart_item['line_subtotal'],
                'sku' => $product->get_sku(),
            ];
        }

        return [
            'items_count' => $cart->get_cart_contents_count(),
            'total' => (float) $cart->get_cart_contents_total(),
            'currency' => get_woocommerce_currency(),
            'items' => $items,
        ];
    }

    /**
     * Get current product data (if on product page)
     */
    public static function get_current_product() {
        if (!is_product()) {
            return null;
        }

        global $product;

        if (!$product) {
            return null;
        }

        // Get categories
        $categories = [];
        $terms = get_the_terms($product->get_id(), 'product_cat');
        if ($terms && !is_wp_error($terms)) {
            foreach ($terms as $term) {
                $categories[] = $term->name;
            }
        }

        return [
            'id' => $product->get_id(),
            'name' => $product->get_name(),
            'price' => (float) $product->get_price(),
            'regular_price' => (float) $product->get_regular_price(),
            'sale_price' => (float) $product->get_sale_price(),
            'stock_status' => $product->get_stock_status(),
            'stock_quantity' => $product->get_stock_quantity(),
            'sku' => $product->get_sku(),
            'categories' => $categories,
            'short_description' => $product->get_short_description(),
        ];
    }

    /**
     * Get order by ID with secure order_key verification
     *
     * SECURITY: This function uses WooCommerce's order_key for authentication.
     * order_key is a unique token generated for each order and sent to customers
     * in their order confirmation email. This is the same mechanism used by
     * WooCommerce's built-in order tracking page (/order-received/{order_id}/?key={order_key})
     *
     * @param int|string $order_id The order ID
     * @param string $order_key The unique order key from confirmation email
     * @param string|null $email Optional additional email verification
     * @return array|null Order data or null if not found/unauthorized
     */
    public static function get_order_data_secure($order_id, $order_key, $email = null) {
        if (empty($order_id) || empty($order_key)) {
            return null;
        }

        // Get the order
        $order = wc_get_order($order_id);

        if (!$order) {
            return null;
        }

        // SECURITY: Verify order_key matches (case-sensitive comparison)
        // This is the same verification WooCommerce uses for order tracking
        if (!hash_equals($order->get_order_key(), $order_key)) {
            // Invalid order key - return null without revealing the order exists
            return null;
        }

        // Optional: Additional email verification if provided
        if (!empty($email) && strtolower($order->get_billing_email()) !== strtolower($email)) {
            return null;
        }

        return self::format_order_data($order);
    }

    /**
     * Get order by ID or email (internal use only - for logged-in customers)
     *
     * @deprecated Use get_order_data_secure() for public API access
     * @internal This method should only be used for authenticated/internal requests
     */
    public static function get_order_data($order_id = null, $email = null) {
        if (empty($order_id) && empty($email)) {
            return null;
        }

        $order = null;

        // If order_id is provided, try to get it directly
        if (!empty($order_id)) {
            $order = wc_get_order($order_id);

            // If email is also provided, verify ownership
            if ($order && !empty($email) && strtolower($order->get_billing_email()) !== strtolower($email)) {
                return null;
            }
        }

        // If not found by ID and email provided, find by email (for logged-in users)
        if (!$order && !empty($email)) {
            // Only allow this for logged-in users whose email matches
            if (!is_user_logged_in()) {
                return null;
            }

            $current_user = wp_get_current_user();
            if (strtolower($current_user->user_email) !== strtolower($email)) {
                return null;
            }

            $orders = wc_get_orders([
                'billing_email' => $email,
                'limit' => 1,
                'orderby' => 'date',
                'order' => 'DESC',
            ]);

            if (!empty($orders)) {
                $order = $orders[0];
            }
        }

        if (!$order) {
            return null;
        }

        return self::format_order_data($order);
    }

    /**
     * Format order data for API response
     *
     * @param WC_Order $order
     * @return array
     */
    private static function format_order_data($order) {
        // Get order items
        $items = [];
        foreach ($order->get_items() as $item) {
            $product = $item->get_product();
            $items[] = [
                'name' => $item->get_name(),
                'quantity' => $item->get_quantity(),
                'total' => (float) $item->get_total(),
                'sku' => $product ? $product->get_sku() : '',
            ];
        }

        // Get tracking info if available
        $tracking_number = $order->get_meta('_tracking_number', true);
        $tracking_url = $order->get_meta('_tracking_url', true);

        // Format order data
        // NOTE: order_key is intentionally NOT included in the response
        // to prevent exposure of the authentication token
        return [
            'order_id' => $order->get_id(),
            'order_number' => $order->get_order_number(),
            'status' => $order->get_status(),
            'status_label' => wc_get_order_status_name($order->get_status()),
            'total' => (float) $order->get_total(),
            'currency' => $order->get_currency(),
            'date_created' => $order->get_date_created()->format('Y-m-d H:i:s'),
            'customer_email' => $order->get_billing_email(),
            'customer_name' => $order->get_billing_first_name() . ' ' . $order->get_billing_last_name(),
            'items' => $items,
            'items_count' => $order->get_item_count(),
            'tracking_number' => $tracking_number ?: null,
            'tracking_url' => $tracking_url ?: null,
            'payment_method' => $order->get_payment_method_title(),
            'shipping_method' => $order->get_shipping_method(),
            'shipping_address' => [
                'address_1' => $order->get_shipping_address_1(),
                'address_2' => $order->get_shipping_address_2(),
                'city' => $order->get_shipping_city(),
                'state' => $order->get_shipping_state(),
                'postcode' => $order->get_shipping_postcode(),
                'country' => $order->get_shipping_country(),
            ],
        ];
    }

    /**
     * Send order data to ReplyIt backend
     */
    public static function send_order_to_backend($order_data, $session_id = null) {
        if (empty($order_data)) {
            return false;
        }

        $config = ReplyIt_Core::get_config();
        if (empty($config['widget_id']) || empty($config['api_secret'])) {
            return false;
        }

        $api_url = $config['api_url'] . '/api/widgets/' . $config['widget_id'] . '/tools/order-status';

        $payload = [
            'action' => 'store',
            'order_data' => $order_data,
        ];

        // Add session ID if provided
        if (!empty($session_id)) {
            $payload['session_id'] = $session_id;
            error_log('ReplyIt: Sending order with session_id: ' . $session_id);
        } else {
            error_log('ReplyIt: WARNING - No session_id provided for order');
        }

        error_log('ReplyIt: Sending order data: ' . wp_json_encode([
            'order_id' => $order_data['order_id'] ?? $order_data['order_number'] ?? 'unknown',
            'has_session_id' => !empty($session_id),
            'api_url' => $api_url,
        ]));

        $response = wp_remote_post($api_url, [
            'headers' => [
                'Content-Type' => 'application/json',
                'X-Widget-Secret' => $config['api_secret'],
            ],
            'body' => wp_json_encode($payload),
            'timeout' => 15,
        ]);

        if (is_wp_error($response)) {
            error_log('ReplyIt: Failed to send order data - ' . $response->get_error_message());
            return false;
        }

        $response_code = wp_remote_retrieve_response_code($response);
        return $response_code >= 200 && $response_code < 300;
    }

    /**
     * Search products by various criteria
     *
     * @param array $args Search arguments (query, sku, product_id, category, limit)
     * @return array Search results
     */
    public static function search_products($args = []) {
        $query = $args['query'] ?? '';
        $sku = $args['sku'] ?? '';
        $product_id = $args['product_id'] ?? '';
        $category = $args['category'] ?? '';
        $limit = min(intval($args['limit'] ?? 10), 20); // Max 20 products

        $products = [];

        // Search by product ID first (exact match)
        if (!empty($product_id)) {
            $product = wc_get_product(intval($product_id));
            if ($product && $product->get_status() === 'publish') {
                return [
                    'products' => [self::format_product_data($product)],
                    'total_found' => 1,
                    'search_type' => 'product_id'
                ];
            }
            return [
                'products' => [],
                'total_found' => 0,
                'search_type' => 'product_id',
                'message' => __('Product not found with this ID.', 'replyit-chat-widget')
            ];
        }

        // Search by SKU (exact match)
        if (!empty($sku)) {
            $product_id_by_sku = wc_get_product_id_by_sku($sku);
            if ($product_id_by_sku) {
                $product = wc_get_product($product_id_by_sku);
                if ($product && $product->get_status() === 'publish') {
                    return [
                        'products' => [self::format_product_data($product)],
                        'total_found' => 1,
                        'search_type' => 'sku'
                    ];
                }
            }
            return [
                'products' => [],
                'total_found' => 0,
                'search_type' => 'sku',
                'message' => __('Product not found with this SKU.', 'replyit-chat-widget')
            ];
        }

        // Build query args for search
        $query_args = [
            'status' => 'publish',
            'limit' => $limit,
            'orderby' => 'relevance',
            'order' => 'DESC',
        ];

        // Text search
        if (!empty($query)) {
            $query_args['s'] = sanitize_text_field($query);
        }

        // Category filter
        if (!empty($category)) {
            // Try to find category by name or slug
            $term = get_term_by('name', $category, 'product_cat');
            if (!$term) {
                $term = get_term_by('slug', sanitize_title($category), 'product_cat');
            }
            if ($term) {
                $query_args['category'] = [$term->slug];
            }
        }

        // Execute query
        $wc_products = wc_get_products($query_args);

        foreach ($wc_products as $product) {
            $products[] = self::format_product_data($product);
        }

        return [
            'products' => $products,
            'total_found' => count($products),
            'search_type' => !empty($query) ? 'keyword' : (!empty($category) ? 'category' : 'all'),
            'query' => $query,
            'category' => $category
        ];
    }

    /**
     * Format product data for API response
     *
     * @param WC_Product $product
     * @return array
     */
    private static function format_product_data($product) {
        // Get categories
        $categories = [];
        $terms = get_the_terms($product->get_id(), 'product_cat');
        if ($terms && !is_wp_error($terms)) {
            foreach ($terms as $term) {
                $categories[] = $term->name;
            }
        }

        // Get image
        $image_id = $product->get_image_id();
        $image_url = $image_id ? wp_get_attachment_image_url($image_id, 'medium') : null;

        // Stock info
        $stock_status = $product->get_stock_status();
        $stock_quantity = $product->get_stock_quantity();
        $stock_text = '';

        switch ($stock_status) {
            case 'instock':
                $stock_text = $stock_quantity !== null
                    ? sprintf(__('%d in stock', 'replyit-chat-widget'), $stock_quantity)
                    : __('In stock', 'replyit-chat-widget');
                break;
            case 'outofstock':
                $stock_text = __('Out of stock', 'replyit-chat-widget');
                break;
            case 'onbackorder':
                $stock_text = __('Available on backorder', 'replyit-chat-widget');
                break;
        }

        // Price info
        $regular_price = $product->get_regular_price();
        $sale_price = $product->get_sale_price();
        $current_price = $product->get_price();
        $on_sale = $product->is_on_sale();

        return [
            'id' => $product->get_id(),
            'name' => $product->get_name(),
            'sku' => $product->get_sku() ?: null,
            'price' => (float) $current_price,
            'regular_price' => $regular_price ? (float) $regular_price : null,
            'sale_price' => $sale_price ? (float) $sale_price : null,
            'on_sale' => $on_sale,
            'currency' => get_woocommerce_currency(),
            'currency_symbol' => get_woocommerce_currency_symbol(),
            'stock_status' => $stock_status,
            'stock_quantity' => $stock_quantity,
            'stock_text' => $stock_text,
            'categories' => $categories,
            'short_description' => wp_strip_all_tags($product->get_short_description()),
            'permalink' => $product->get_permalink(),
            'image_url' => $image_url,
            'type' => $product->get_type(),
            'average_rating' => (float) $product->get_average_rating(),
            'review_count' => (int) $product->get_review_count(),
        ];
    }
}
