<?php

namespace Pixeldev\SquareWooSync\Orders;

use Pixeldev\SquareWooSync\Square\SquareHelper;

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

class WooOrder
{
    public static function init_hooks()
    {
        add_action('woocommerce_order_status_completed', [__CLASS__, 'schedule_square_order_completion'], 10, 1);

        // We'll accept 2 parameters in our scheduled action: $order_id and $square_order_id.
        add_action('squarewoosync-pro_update_square_order_status', [__CLASS__, 'handle_scheduled_square_order_completion'], 10, 2);
    }

    /**
     * Schedules a background job to update the Square order to COMPLETED.
     */
    public static function schedule_square_order_completion($order_id)
    {
        $order = wc_get_order($order_id);
        if (!$order) {
            return;
        }

        $settings = get_option('square-woo-sync_settings', []);

        // Ensure statusSyncWooToSquare is enabled.
        if (
            empty($settings['orders']['statusSyncWooToSquare'])
            || $settings['orders']['statusSyncWooToSquare'] !== true
        ) {
            return;
        }

        // Retrieve the Square order ID from a custom meta key.
        $square_order_id = $order->get_meta('square_order_id');
        if (empty($square_order_id)) {
            return;
        }

        // Optional: add a note so the admin knows we're scheduling an update.
        $order->add_order_note(
            sprintf(
                'A background job has been scheduled to update Square order %s to COMPLETED (including fulfillments).',
                $square_order_id
            )
        );

        // Schedule the action if Action Scheduler is available, otherwise do it immediately.
        if (function_exists('as_schedule_single_action')) {
            as_schedule_single_action(
                time(),
                'squarewoosync-pro_update_square_order_status',
                [$order_id, $square_order_id],
                'pixeldev-square-woo-sync'
            );
        } else {
            // Immediate fallback
            self::handle_scheduled_square_order_completion($order_id, $square_order_id);
        }
    }

    /**
     * The scheduled action callback.
     * 1) Fetch the latest Square order (to get current version + fulfillments).
     * 2) Mark any incomplete fulfillments -> COMPLETED.
     * 3) Mark the order state -> COMPLETED.
     * 4) PUT to Square using the updated 'order' object.
     */
    public static function handle_scheduled_square_order_completion($order_id, $square_order_id)
    {
        $settings = get_option('square-woo-sync_settings', []);

        if (
            empty($settings['orders']['statusSyncWooToSquare'])
            || $settings['orders']['statusSyncWooToSquare'] !== true
        ) {
            return;
        }

        $wc_order = wc_get_order($order_id);
        if (!$wc_order) {
            return;
        }

        // 1) Fetch the latest Square order to get version + fulfillments
        $square_helper = new SquareHelper();
        $get_response = $square_helper->square_api_request("/orders/{$square_order_id}", 'GET');

        // If we failed to get the Square order details or no version found, add a note and stop.
        if (
            !$get_response['success']
            || empty($get_response['data']['order']['version'])
        ) {
            $error_msg = !empty($get_response['error']) ? $get_response['error'] : 'No version found in the Square order.';
            $wc_order->add_order_note(
                sprintf(
                    'Could not update Square order %s to COMPLETED. Error: %s',
                    $square_order_id,
                    $error_msg
                )
            );
            return;
        }

        // Pull out the version and fulfillments from the response
        $square_order_version = $get_response['data']['order']['version'];
        $fulfillments         = $get_response['data']['order']['fulfillments'] ?? [];

        // 2) Mark any incomplete fulfillments as COMPLETED
        // If no fulfillments exist, $fulfillments might be an empty array, which is fine.
        foreach ($fulfillments as &$fulfillment) {
            if (!isset($fulfillment['state']) || $fulfillment['state'] !== 'COMPLETED') {
                $fulfillment['state'] = 'COMPLETED';
            }
        }
        unset($fulfillment);

        // 3) Prepare the PUT body: set order state -> COMPLETED, include updated fulfillments, version, location, etc.
        $put_body = [
            'order' => [
                'state'         => 'COMPLETED',
                'version'       => $square_order_version,
                'location_id'   => $settings['location'] ?? '',
                'fulfillments'  => $fulfillments,
            ],
            'idempotency_key' => uniqid('sq_order_', true),
        ];

        // 4) Send the PUT request to update the Square order
        $put_response = $square_helper->square_api_request("/orders/{$square_order_id}", 'PUT', $put_body);

        if (!empty($put_response['success']) && $put_response['success'] === true) {
            $wc_order->add_order_note(
                sprintf(
                    'Square order %s has been updated to COMPLETED (fulfillments also marked COMPLETED).',
                    $square_order_id
                )
            );
        } else {
            $error_msg = !empty($put_response['error']) ? $put_response['error'] : 'Unknown error.';
            $wc_order->add_order_note(
                sprintf(
                    'Failed to fully update Square order %s. Error: %s',
                    $square_order_id,
                    $error_msg
                )
            );
        }
    }
}
