<?php
/**
 * Checkout Handler — REST API proxy to Supabase checkout-session function
 *
 * @package PackshotPhotoAI
 */

namespace PackshotPhotoAI\API;

use PackshotPhotoAI\Core\CreditManager;
use PackshotPhotoAI\Core\Encryption;
use PackshotPhotoAI\Core\Logger;
use WP_REST_Request;
use WP_REST_Response;

defined('ABSPATH') || exit;

/**
 * Handles checkout session creation and status polling
 */
class CheckoutHandler {

    private const NAMESPACE    = 'packshotphoto/v1';
    private const SUPABASE_URL = 'https://duubkqjowabuevqudtbk.supabase.co/functions/v1';

    /**
     * Register REST API routes
     */
    public function register_routes(): void {
        // Create checkout session
        register_rest_route(self::NAMESPACE, '/checkout', [
            'methods'             => 'POST',
            'callback'            => [$this, 'create_checkout'],
            'permission_callback' => function () {
                return current_user_can('manage_options');
            },
        ]);

        // Poll for checkout completion
        register_rest_route(self::NAMESPACE, '/checkout/poll', [
            'methods'             => 'GET',
            'callback'            => [$this, 'poll_checkout'],
            'permission_callback' => function () {
                return current_user_can('manage_options');
            },
        ]);

        // Get current credits status (balance + history)
        register_rest_route(self::NAMESPACE, '/credits/status', [
            'methods'             => 'GET',
            'callback'            => [$this, 'get_credits_status'],
            'permission_callback' => function () {
                return current_user_can('manage_options');
            },
        ]);

        // Manually trigger sync
        register_rest_route(self::NAMESPACE, '/credits/sync', [
            'methods'             => 'POST',
            'callback'            => [$this, 'sync_credits'],
            'permission_callback' => function () {
                return current_user_can('manage_options');
            },
        ]);
    }

    /**
     * Manually sync credits
     */
    public function sync_credits(WP_REST_Request $request): WP_REST_Response {
        $result = CreditManager::force_sync();
        return new WP_REST_Response($result, $result['success'] ? 200 : 404);
    }

    /**
     * Create Stripe Checkout Session via Supabase
     */
    public function create_checkout(WP_REST_Request $request): WP_REST_Response {
        $package_id = sanitize_text_field($request->get_param('package_id') ?? '');
        $currency   = sanitize_text_field($request->get_param('currency') ?? 'pln');
        $email      = sanitize_email($request->get_param('email') ?? wp_get_current_user()->user_email);
        $site_url   = sanitize_text_field($request->get_param('current_url'));

        $result = $this->get_checkout_session_url($package_id, $currency, $email, $site_url);

        if (is_wp_error($result)) {
            return new WP_REST_Response(['success' => false, 'message' => $result->get_error_message()], 500);
        }

        return new WP_REST_Response([
            'success'       => true,
            'checkout_url'  => $result,
            'site_url_hash' => CreditManager::generate_site_hash(),
        ]);
    }

    /**
     * Core logic to get checkout URL from Supabase
     */
    public function get_checkout_session_url(string $package_id, string $currency = 'usd', string $email = '', string $current_url = ''): string|\WP_Error {
        $allowed_packages = ['starter', 'pro', 'business', 'test'];
        if (!in_array($package_id, $allowed_packages, true)) {
            return new \WP_Error('invalid_package', 'Invalid package');
        }

        if (empty($email)) {
            $email = wp_get_current_user()->user_email;
        }

        if (empty($current_url)) {
            $current_url = admin_url('tools.php?page=packshotphoto-ai');
        }

        $site_url_hash = CreditManager::generate_site_hash();
        $is_promo_active = CreditManager::is_welcome_promo_active();

        $response = wp_remote_post(self::SUPABASE_URL . '/checkout-session', [
            'timeout'   => 15,
            'headers'   => ['Content-Type' => 'application/json'],
            'sslverify' => false,
            'body'      => wp_json_encode([
                'package_id'    => $package_id,
                'currency'      => $currency,
                'site_url'      => $current_url,
                'site_url_hash' => $site_url_hash,
                'email'         => $email,
                'discount_pct'  => $is_promo_active ? 50 : 0,
                'promo_code'    => $is_promo_active ? 'WELCOME50' : '',
            ]),
        ]);

        if (is_wp_error($response)) {
            return $response;
        }

        $body = json_decode(wp_remote_retrieve_body($response), true);

        if (!empty($body['url'])) {
            return $body['url'];
        }

        return new \WP_Error('stripe_error', $body['error'] ?? 'Unknown error');
    }

    /**
     * Handles standard GET redirects for purchasing credits (bypassing JS if needed)
     */
    public function handle_php_checkout_redirect(): void {
        if (!isset($_GET['packshotphoto_buy']) || !current_user_can('manage_options')) {
            return;
        }

        $nonce = isset($_GET['_wpnonce']) ? sanitize_text_field(wp_unslash($_GET['_wpnonce'])) : '';
        if (!wp_verify_nonce($nonce, 'packshotphoto_buy_package')) {
            wp_die(esc_html__('Security check failed. Please try again.', 'packshotphoto-ai'), esc_html__('Error', 'packshotphoto-ai'), ['response' => 403]);
        }

        $package = sanitize_text_field(wp_unslash($_GET['packshotphoto_buy']));
        $url = $this->get_checkout_session_url($package, 'usd');

        if (!is_wp_error($url)) {
            // phpcs:ignore WordPress.Security.SafeRedirect.wp_redirect_wp_redirect
            wp_redirect($url);
            exit;
        } else {
            wp_die('Checkout error: ' . esc_html($url->get_error_message()));
        }
    }

    /**
     * Poll Supabase for checkout completion
     */
    public function poll_checkout(WP_REST_Request $request): WP_REST_Response {
        $site_url_hash = sanitize_text_field($request->get_param('hash') ?? '');

        if (empty($site_url_hash)) {
            return new WP_REST_Response(['status' => 'error'], 400);
        }

        $result = CreditManager::poll_checkout_status($site_url_hash);

        if (!$result) {
            return new WP_REST_Response(['status' => 'error'], 500);
        }

        if (($result['status'] ?? '') === 'completed' && !empty($result['api_key'])) {
            $encrypted = Encryption::encrypt($result['api_key']);
            update_option('packshotphoto_api_key', $encrypted);
            Logger::info('CheckoutHandler: API key auto-saved after purchase', ['hash' => $site_url_hash]);
        } else {
            if (($result['status'] ?? '') !== 'completed') {
                Logger::info('CheckoutHandler: Poll in progress...', ['hash' => $site_url_hash, 'status' => $result['status'] ?? 'pending']);
            }
        }

        return new WP_REST_Response($result);
    }

    /**
     * Get full credits status (balance + history).
     * With ?refresh=1 it busts the transient cache and fetches live from Supabase.
     * force_sync() is intentionally NOT called here — only from POST /credits/sync.
     */
    public function get_credits_status(WP_REST_Request $request): WP_REST_Response {
        $force = (bool) $request->get_param('refresh');
        if ($force) {
            // Only clear the transient — let fetch_status_from_api() re-populate it
            delete_transient('packshotphoto_credits_cache');
        }

        $status = CreditManager::get_full_status();
        $response = new WP_REST_Response($status);

        // Prevent browser/server-side caching of real-time balance
        $response->header('Cache-Control', 'no-cache, must-revalidate, max-age=0');
        $response->header('Pragma', 'no-cache');
        $response->header('Expires', 'Wed, 11 Jan 1984 05:00:00 GMT');

        return $response;
    }
}
