<?php

declare( strict_types=1 );

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

/**
 * REST routes for payment operations.
 * POST /payments/stripe/intent   — create a Stripe Payment Intent for a pending booking
 * POST /payments/stripe/webhook  — Stripe webhook receiver (no auth)
 */
class Playard_API_Payments {

	private Playard_Payment $payment;

	public function __construct( Playard_Payment $payment ) {
		$this->payment = $payment;
	}

	public function register_routes(): void {
		$namespace = 'playard/v1';

		register_rest_route( $namespace, '/payments/stripe/intent', [
			'methods'             => 'POST',
			'callback'            => [ $this, 'create_intent' ],
			'permission_callback' => '__return_true',
			'args'                => [
				'booking_ref' => [ 'required' => true, 'type' => 'string' ],
			],
		] );

		register_rest_route( $namespace, '/payments/stripe/webhook', [
			'methods'             => 'POST',
			'callback'            => [ $this, 'stripe_webhook' ],
			'permission_callback' => '__return_true',
		] );

		// Pro can register additional payment routes here (PayPal, bKash, Razorpay, etc.)
		do_action( 'playard_register_payment_routes', $namespace );
	}

	public function create_intent( WP_REST_Request $request ): WP_REST_Response {
		$booking_ref = sanitize_text_field( (string) $request->get_param( 'booking_ref' ) );
		$coupon_code = strtoupper( sanitize_text_field( (string) ( $request->get_param( 'coupon_code' ) ?? '' ) ) );
		$result      = $this->payment->create_stripe_intent( $booking_ref, $coupon_code );

		if ( is_wp_error( $result ) ) {
			return new WP_REST_Response(
				playard_rest_error( $result->get_error_code(), $result->get_error_message() ),
				422
			);
		}

		return new WP_REST_Response( playard_rest_success( $result ), 200 );
	}

	public function stripe_webhook( WP_REST_Request $request ): WP_REST_Response {
		$payload = $request->get_body();
		$sig     = (string) ( $request->get_header( 'stripe-signature' ) ?? '' );
		$result  = $this->payment->handle_webhook( $payload, $sig );

		if ( is_wp_error( $result ) ) {
			// Log the error but always return 200 to prevent Stripe from retrying.
			error_log( '[Playard] Stripe webhook error: ' . $result->get_error_message() ); // phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_error_log
			return new WP_REST_Response( [ 'received' => true, 'error' => $result->get_error_code() ], 200 );
		}

		return new WP_REST_Response( [ 'received' => true ], 200 );
	}
}
