<?php

namespace Elementor_Pay_Addons\API;

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

use Elementor_Pay_Addons\Stripe\Stripe_API;
use Elementor_Pay_Addons\Shared\Security_Utils;
use Elementor_Pay_Addons\Shared\Logger;

/**
 * REST endpoint for live tax preview (pre-payment order summary).
 *
 * POST epa/v1/tax/preview
 * Body (JSON): { amount, currency, address, tax_behavior, tax_code }
 * Returns: { subtotal, tax_amount, total, currency, tax_breakdown[] }
 */
class Rest_API_Tax_Preview_Controller extends \WP_REST_Controller
{
    public function __construct()
    {
        $this->namespace = trim(EPA_ADDONS_REST_API, '/');
        $this->rest_base = 'tax/preview';
    }

    public function register_routes()
    {
        register_rest_route($this->namespace, $this->rest_base, [
            [
                'methods'             => \WP_REST_Server::CREATABLE,
                'callback'            => [$this, 'preview'],
                'permission_callback' => [$this, 'verify_access'],
            ],
        ]);
    }

    public function verify_access(\WP_REST_Request $request)
    {
        return Security_Utils::client_access_check($request);
    }

    public function preview(\WP_REST_Request $request)
    {
        $body = $request->get_json_params();

        $amount      = isset($body['amount'])       ? absint($body['amount'])                             : 0;
        $currency    = isset($body['currency'])     ? sanitize_text_field(strtolower($body['currency']))  : 'usd';
        $tax_behavior = isset($body['tax_behavior']) ? sanitize_text_field($body['tax_behavior'])         : 'exclusive';
        $tax_code    = isset($body['tax_code'])     ? sanitize_text_field($body['tax_code'])               : '';
        $address_raw = isset($body['address'])      ? $body['address']                                    : [];

        if ($amount <= 0) {
            return new \WP_Error('invalid_amount', __('Amount must be greater than zero.', 'pay-addons-for-elementor'), ['status' => 400]);
        }

        $allowed_fields = ['line1', 'line2', 'city', 'state', 'postal_code', 'country'];
        $address = [];
        foreach ($allowed_fields as $field) {
            if (!empty($address_raw[$field]) && is_string($address_raw[$field])) {
                $address[$field] = sanitize_text_field($address_raw[$field]);
            }
        }

        if (empty($address['country'])) {
            return new \WP_Error('missing_address', __('A billing address with country is required for tax calculation.', 'pay-addons-for-elementor'), ['status' => 400]);
        }

        try {
            $line_item = [
                'amount'       => $amount,
                'reference'    => 'product',
                'tax_behavior' => $tax_behavior,
            ];
            if (!empty($tax_code)) {
                $line_item['tax_code'] = $tax_code;
            }

            $calculation = Stripe_API::create_tax_calculation([
                'currency'         => $currency,
                'line_items'       => [$line_item],
                'customer_details' => [
                    'address'        => $address,
                    'address_source' => 'billing',
                ],
            ]);

            $tax_breakdown = [];
            if (isset($calculation->tax_breakdown)) {
                foreach ($calculation->tax_breakdown as $item) {
                    $tax_breakdown[] = [
                        'display_name' => $item->tax_rate_details->display_name ?? '',
                        'percentage'   => $item->tax_rate_details->percentage_decimal ?? 0,
                        'amount'       => $item->amount ?? 0,
                        'inclusive'    => $item->inclusive ?? false,
                    ];
                }
            }

            return new \WP_REST_Response([
                'subtotal'      => $amount,
                'tax_amount'    => $calculation->tax_amount_exclusive + $calculation->tax_amount_inclusive,
                'total'         => $calculation->amount_total,
                'currency'      => $currency,
                'tax_breakdown' => $tax_breakdown,
            ]);
        } catch (\Exception $ex) {
            Logger::error('tax_preview: ' . $ex->getMessage());
            return new \WP_Error('stripe_tax_error', $ex->getMessage(), ['status' => 400]);
        }
    }
}
