<?php
/**
 * Indexing Credits Endpoint (Week 27, updated Week 30)
 *
 * Proxies backend BoostCoin to the WP admin UI without exposing backend_site_api_key to the browser.
 *
 * Week 30: Credits are now unified BoostCoin with token-based metering.
 * PayPal purchase routes are deprecated - all purchases go through the Usage page.
 *
 * @package BoostBot
 */

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

class BoostBot_Indexing_Credits_Endpoint extends BoostBot_Base_Endpoint {

    protected $rest_base = 'indexing-credits';

    public function register() {
        // GET /wp-json/boostbot/v1/indexing-credits/status
        $this->register_route(
            '/status',
            'GET',
            array( $this, 'get_status' ),
            array( $this, 'admin_access' )
        );

        // POST /wp-json/boostbot/v1/indexing-credits/consume
        $this->register_route(
            '/consume',
            'POST',
            array( $this, 'consume' ),
            array( $this, 'admin_access' )
        );

        // Week 30: PayPal routes deprecated but kept for graceful error handling
        // POST /wp-json/boostbot/v1/indexing-credits/purchases/paypal/create-order
        $this->register_route(
            '/purchases/paypal/create-order',
            'POST',
            array( $this, 'create_paypal_order' ),
            array( $this, 'admin_access' )
        );

        // POST /wp-json/boostbot/v1/indexing-credits/purchases/paypal/capture-order
        $this->register_route(
            '/purchases/paypal/capture-order',
            'POST',
            array( $this, 'capture_paypal_order' ),
            array( $this, 'admin_access' )
        );
    }

    private function require_backend_client() {
        $backend_base_url = trim( (string) BoostBot_Settings::get( 'backend_base_url', '' ) );
        if ( empty( $backend_base_url ) ) {
            return new WP_Error( 'boostbot_backend_not_configured', __( 'Backend is not configured.', 'boostbot' ) );
        }
        if ( ! class_exists( 'BoostBot_Indexing_Credits_Backend_Client' ) ) {
            return new WP_Error( 'boostbot_backend_client_missing', __( 'Indexing credits backend client is not available.', 'boostbot' ) );
        }
        return new BoostBot_Indexing_Credits_Backend_Client();
    }

    public function get_status( $request ) {
        $client = $this->require_backend_client();
        if ( is_wp_error( $client ) ) {
            return $this->error( $client->get_error_message(), 400 );
        }

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

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

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

    /**
     * Consume BoostCoin for indexing operations (token-based metering).
     *
     * Week 30: Updated to accept token-based parameters.
     *
     * @param WP_REST_Request $request
     * @return WP_REST_Response
     */
    public function consume( $request ) {
        $client = $this->require_backend_client();
        if ( is_wp_error( $client ) ) {
            return $this->error( $client->get_error_message(), 400 );
        }

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

        $job_id       = sanitize_text_field( (string) $request->get_param( 'job_id' ) );
        $input_tokens = absint( $request->get_param( 'input_tokens' ) );
        $output_tokens = absint( $request->get_param( 'output_tokens' ) );
        $provider     = sanitize_text_field( (string) $request->get_param( 'provider' ) );
        $model        = sanitize_text_field( (string) $request->get_param( 'model' ) );
        $idem         = sanitize_text_field( (string) $request->get_param( 'idempotency_key' ) );

        // Legacy support: accept delta_chunks for backward compatibility
        $delta_chunks = absint( $request->get_param( 'delta_chunks' ) );

        if ( empty( $job_id ) || empty( $idem ) ) {
            return $this->error( __( 'Invalid consume request: missing job_id or idempotency_key.', 'boostbot' ), 400 );
        }

        // Week 30: Token-based metering
        if ( $input_tokens > 0 || $output_tokens > 0 ) {
            if ( empty( $provider ) || empty( $model ) ) {
                return $this->error( __( 'Invalid consume request: missing provider or model for token-based metering.', 'boostbot' ), 400 );
            }

            $res = $client->consume( (string) $site_id, array(
                'job_id'          => $job_id,
                'input_tokens'    => $input_tokens,
                'output_tokens'   => $output_tokens,
                'provider'        => $provider,
                'model'           => $model,
                'idempotency_key' => $idem,
            ) );
        } elseif ( $delta_chunks > 0 ) {
            // Legacy: chunk-based (backend will estimate tokens)
            $res = $client->consume( (string) $site_id, array(
                'job_id'          => $job_id,
                'input_tokens'    => 0,
                'output_tokens'   => 0,
                'provider'        => $provider ?: 'openai',
                'model'           => $model ?: 'text-embedding-3-small',
                'delta_chunks'    => $delta_chunks,
                'idempotency_key' => $idem,
            ) );
        } else {
            return $this->error( __( 'Invalid consume request: missing token counts or delta_chunks.', 'boostbot' ), 400 );
        }

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

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

    /**
     * Create PayPal order for indexing credits.
     *
     * @deprecated Week 30 - Returns deprecation error. Use unified purchase flow.
     *
     * @param WP_REST_Request $request
     * @return WP_REST_Response
     */
    public function create_paypal_order( $request ) {
        return $this->error(
            __( 'Indexing credits are no longer sold separately. Please purchase BoostCoin from the Usage page (שימוש ועלויות).', 'boostbot' ),
            410
        );
    }

    /**
     * Capture PayPal order for indexing credits.
     *
     * @deprecated Week 30 - Returns deprecation error. Use unified purchase flow.
     *
     * @param WP_REST_Request $request
     * @return WP_REST_Response
     */
    public function capture_paypal_order( $request ) {
        return $this->error(
            __( 'Indexing credits are no longer sold separately. Please purchase BoostCoin from the Usage page (שימוש ועלויות).', 'boostbot' ),
            410
        );
    }
}

