<?php
/**
 * Purchases Endpoint (Week 26)
 *
 * Initiates backend-first PayPal purchase flow without exposing backend secrets to the browser.
 *
 * @package BoostBot
 */

if ( ! defined( 'ABSPATH' ) ) {
    exit;
}

class BoostBot_Purchases_Endpoint extends BoostBot_Base_Endpoint {

    /**
     * @var string
     */
    protected $rest_base = 'purchases';

    public function register() {
        // GET /wp-json/boostbot/v1/purchases/paypal-config
        $this->register_route(
            '/paypal-config',
            'GET',
            array( $this, 'paypal_config' ),
            array( $this, 'admin_access' )
        );

        // POST /wp-json/boostbot/v1/purchases/create-order
        $this->register_route(
            '/create-order',
            'POST',
            array( $this, 'create_order' ),
            array( $this, 'admin_access' ),
            array(
                'package_id' => array(
                    'required' => true,
                    'type'     => 'string',
                ),
            )
        );

        // POST /wp-json/boostbot/v1/purchases/capture-order
        $this->register_route(
            '/capture-order',
            'POST',
            array( $this, 'capture_order' ),
            array( $this, 'admin_access' ),
            array(
                'order_id' => array(
                    'required' => true,
                    'type'     => 'string',
                ),
            )
        );

        // POST /wp-json/boostbot/v1/purchases/refund-capture
        $this->register_route(
            '/refund-capture',
            'POST',
            array( $this, 'refund_capture' ),
            array( $this, 'admin_access' ),
            array(
                'capture_id' => array(
                    'required' => true,
                    'type'     => 'string',
                ),
            )
        );
    }

    /**
     * Return PayPal client config for admin smart-buttons rendering.
     */
    public function paypal_config( $request ) {
        $backend_base_url = trim( (string) BoostBot_Settings::get( 'backend_base_url', '' ) );
        if ( empty( $backend_base_url ) ) {
            return $this->error( __( 'Credits backend is not configured.', 'boostbot' ), 400 );
        }

        $url = rtrim( $backend_base_url, '/' ) . '/api/v1/sales/config';
        $res = wp_remote_get(
            $url,
            array(
                'timeout' => 10,
                'headers' => array(
                    'Accept' => 'application/json',
                ),
            )
        );

        if ( is_wp_error( $res ) ) {
            return $this->error( $res->get_error_message(), 502 );
        }

        $status = (int) wp_remote_retrieve_response_code( $res );
        $raw    = (string) wp_remote_retrieve_body( $res );
        $json   = json_decode( $raw, true );

        if ( $status >= 400 || ! is_array( $json ) || empty( $json['success'] ) || ! is_array( $json['data'] ?? null ) ) {
            return $this->error( __( 'Failed to fetch PayPal config.', 'boostbot' ), 502 );
        }

        $data      = $json['data'];
        $client_id = sanitize_text_field( (string) ( $data['paypal_client_id'] ?? '' ) );
        $env       = sanitize_text_field( (string) ( $data['paypal_env'] ?? 'sandbox' ) );

        if ( '' === $client_id ) {
            return $this->error( __( 'PayPal is not configured.', 'boostbot' ), 400 );
        }

        return $this->success(
            array(
                'paypal_client_id' => $client_id,
                'paypal_env'       => $env,
            )
        );
    }

    public function create_order( $request ) {
        $backend_base_url = trim( (string) BoostBot_Settings::get( 'backend_base_url', '' ) );
        if ( empty( $backend_base_url ) ) {
            return $this->error( __( 'Credits backend is not configured.', 'boostbot' ), 400 );
        }

        if ( ! class_exists( 'BoostBot_Credits_Backend_Client' ) ) {
            return $this->error( __( 'Credits backend client is not available.', 'boostbot' ), 500 );
        }

        $package_id = sanitize_text_field( (string) $request->get_param( 'package_id' ) );
        if ( empty( $package_id ) ) {
            return $this->error( __( 'package_id is required.', 'boostbot' ), 400 );
        }

        $client = new BoostBot_Credits_Backend_Client();
        $site_id = $client->ensure_site_id();
        if ( is_wp_error( $site_id ) ) {
            return $this->error( $site_id->get_error_message(), 500 );
        }

        // Return/cancel URLs: point back to WP admin.
        // IMPORTANT: Do NOT use hash fragments here. PayPal appends `token` (order_id) and `PayerID`
        // as query params, and hash fragments are not sent to the server (we need them server-side to capture).
        $return_url = admin_url( 'admin.php?page=boostbot&bb_purchase=success' );
        $cancel_url = admin_url( 'admin.php?page=boostbot&bb_purchase=cancel' );

        $resp = $client->create_paypal_order( (string) $site_id, $package_id, $return_url, $cancel_url );
        if ( is_wp_error( $resp ) ) {
            return $this->error( $resp->get_error_message(), 500 );
        }

        return $this->success( $resp );
    }

    public function capture_order( $request ) {
        $backend_base_url = trim( (string) BoostBot_Settings::get( 'backend_base_url', '' ) );
        if ( empty( $backend_base_url ) ) {
            return $this->error( __( 'Credits backend is not configured.', 'boostbot' ), 400 );
        }

        if ( ! class_exists( 'BoostBot_Credits_Backend_Client' ) ) {
            return $this->error( __( 'Credits backend client is not available.', 'boostbot' ), 500 );
        }

        $order_id = sanitize_text_field( (string) $request->get_param( 'order_id' ) );
        if ( empty( $order_id ) ) {
            return $this->error( __( 'order_id is required.', 'boostbot' ), 400 );
        }

        $client = new BoostBot_Credits_Backend_Client();
        $site_id = $client->ensure_site_id();
        if ( is_wp_error( $site_id ) ) {
            return $this->error( $site_id->get_error_message(), 500 );
        }

        $resp = $client->capture_paypal_order( (string) $site_id, $order_id );
        if ( is_wp_error( $resp ) ) {
            return $this->error( $resp->get_error_message(), 500 );
        }

        return $this->success( $resp );
    }

    public function refund_capture( $request ) {
        $backend_base_url = trim( (string) BoostBot_Settings::get( 'backend_base_url', '' ) );
        if ( empty( $backend_base_url ) ) {
            return $this->error( __( 'Credits backend is not configured.', 'boostbot' ), 400 );
        }

        if ( ! class_exists( 'BoostBot_Credits_Backend_Client' ) ) {
            return $this->error( __( 'Credits backend client is not available.', 'boostbot' ), 500 );
        }

        $capture_id = sanitize_text_field( (string) $request->get_param( 'capture_id' ) );
        if ( empty( $capture_id ) ) {
            return $this->error( __( 'capture_id is required.', 'boostbot' ), 400 );
        }

        $client = new BoostBot_Credits_Backend_Client();
        $site_id = $client->ensure_site_id();
        if ( is_wp_error( $site_id ) ) {
            return $this->error( $site_id->get_error_message(), 500 );
        }

        $resp = $client->refund_paypal_capture( (string) $site_id, $capture_id );
        if ( is_wp_error( $resp ) ) {
            return $this->error( $resp->get_error_message(), 500 );
        }

        return $this->success( $resp );
    }
}


