<?php
/**
 * PayPal Webhook Management Class.
 *
 * Handles creation, verification, and management of PayPal webhooks.
 * This class provides methods to:
 * - Create webhooks with PayPal
 * - Verify webhook signatures
 * - Remove/delete webhooks
 *
 * @package sureforms-pro
 * @since 2.4.0
 */

namespace SRFM_Pro\Inc\Business\Payments\PayPal;

// Exit if accessed directly.
defined( 'ABSPATH' ) || exit;

/**
 * PayPal Webhook Management.
 *
 * @since 2.4.0
 */
class Webhook {
	/**
	 * Use PayPal API client trait for HTTP communication.
	 */
	use Client;

	/**
	 * Create PayPal webhook.
	 *
	 * Registers a webhook with PayPal to receive event notifications.
	 * Stores the webhook ID and secret in PayPal settings.
	 *
	 * @param string $mode Payment mode ('test' or 'live').
	 * @since 2.4.0
	 * @return array Response with webhook details or error.
	 */
	public static function create_webhook( $mode ) {
		// Generate webhook URL for this mode.
		// Example: https://sureforms.com/wp-json/sureforms-pro/paypal-test-webhook.

		$hard_coded_mode = 'live' === $mode ? 'live' : 'test';
		$webhook_url     = rest_url( 'sureforms-pro/paypal-' . $hard_coded_mode . '-webhook' );

		// Define events to subscribe to.
		$event_types = [
			// Payment capture events.
			[ 'name' => 'PAYMENT.CAPTURE.COMPLETED' ],    // Payment completed (one-time payments).
			[ 'name' => 'PAYMENT.CAPTURE.REFUNDED' ],     // Payment refunded.
			[ 'name' => 'PAYMENT.CAPTURE.DENIED' ],       // Payment denied.
			[ 'name' => 'PAYMENT.CAPTURE.PENDING' ],      // Payment pending.

			// Subscription payment events.
			[ 'name' => 'PAYMENT.SALE.COMPLETED' ],       // Subscription payment completed (recurring).
			[ 'name' => 'PAYMENT.SALE.REFUNDED' ],        // Subscription payment refunded.

			// Subscription lifecycle events.
			[ 'name' => 'BILLING.SUBSCRIPTION.ACTIVATED' ],   // Subscription activated.
			[ 'name' => 'BILLING.SUBSCRIPTION.CANCELLED' ],   // Subscription cancelled.
			[ 'name' => 'BILLING.SUBSCRIPTION.EXPIRED' ],     // Subscription expired.
			[ 'name' => 'BILLING.SUBSCRIPTION.SUSPENDED' ],   // Subscription suspended.
			[ 'name' => 'BILLING.SUBSCRIPTION.UPDATED' ],     // Subscription updated.

			// Authorization events.
			[ 'name' => 'PAYMENT.AUTHORIZATION.VOIDED' ],     // Authorization voided.
		];

		// Prepare webhook data.
		$webhook_data = [
			'url'         => $webhook_url,
			'event_types' => $event_types,
		];

		// Create webhook via PayPal API.
		$response = self::request( 'v1/notifications/webhooks', $webhook_data, 'POST', $mode );

		// Check if webhook creation was successful.
		if ( empty( $response['success'] ) ) {
			return [
				'success' => false,
				'message' => $response['message'] ?? __( 'Failed to create PayPal webhook.', 'sureforms-pro' ),
			];
		}

		// Extract webhook details.
		$webhook_id  = $response['id'] ?? '';
		$webhook_url = $response['url'] ?? '';

		if ( empty( $webhook_id ) ) {
			return [
				'success' => false,
				'message' => __( 'PayPal webhook created but no ID returned.', 'sureforms-pro' ),
			];
		}

		// Store webhook details in settings.
		$settings = Helper::get_all_paypal_settings();

		if ( 'live' === $mode ) {
			$settings['webhook_live_id']  = $webhook_id;
			$settings['webhook_live_url'] = $webhook_url;
		} else {
			$settings['webhook_test_id']  = $webhook_id;
			$settings['webhook_test_url'] = $webhook_url;
		}

		Helper::update_all_paypal_settings( $settings );

		return [
			'success'     => true,
			'message'     => __( 'PayPal webhook created successfully.', 'sureforms-pro' ),
			'webhook_id'  => $webhook_id,
			'webhook_url' => $webhook_url,
		];
	}

	/**
	 * Verify webhook signature.
	 *
	 * Verifies that a webhook event came from PayPal by validating
	 * the signature using PayPal's webhook verification API.
	 *
	 * @param array  $verification_data Verification parameters from webhook request.
	 * @param string $mode              Payment mode ('test' or 'live').
	 * @since 2.4.0
	 * @return array Verification response with status.
	 */
	public static function verify_signature( $verification_data, $mode ) {
		// Call PayPal webhook verification endpoint.
		$response = self::request( 'v1/notifications/verify-webhook-signature', $verification_data, 'POST', $mode );

		// Check verification status.
		if ( ! empty( $response['verification_status'] ) && 'SUCCESS' === $response['verification_status'] ) {
			return [
				'success'  => true,
				'verified' => true,
			];
		}

		return [
			'success'  => false,
			'verified' => false,
			'message'  => __( 'Webhook signature verification failed.', 'sureforms-pro' ),
		];
	}

	/**
	 * Delete PayPal webhook.
	 *
	 * Removes a webhook from PayPal and clears the stored webhook details.
	 *
	 * @param string $mode Payment mode ('test' or 'live').
	 * @since 2.4.0
	 * @return array Response with success status.
	 */
	public static function delete_webhook( $mode ) {
		// Get stored webhook ID.
		$settings   = Helper::get_all_paypal_settings();
		$webhook_id = 'live' === $mode
			? ( $settings['webhook_live_id'] ?? '' )
			: ( $settings['webhook_test_id'] ?? '' );

		if ( empty( $webhook_id ) ) {
			return [
				'success' => false,
				'message' => __( 'No webhook found to delete.', 'sureforms-pro' ),
			];
		}

		// Delete webhook via PayPal API.
		$response = self::request( "v1/notifications/webhooks/{$webhook_id}", [], 'DELETE', $mode );

		// PayPal returns 204 No Content on successful deletion.
		if ( ! empty( $response['success'] ) ) {
			// Clear webhook details from settings.
			if ( 'live' === $mode ) {
				$settings['webhook_live_id']  = '';
				$settings['webhook_live_url'] = '';
			} else {
				$settings['webhook_test_id']  = '';
				$settings['webhook_test_url'] = '';
			}

			Helper::update_all_paypal_settings( $settings );

			return [
				'success' => true,
				'message' => __( 'PayPal webhook deleted successfully.', 'sureforms-pro' ),
			];
		}

		return [
			'success' => false,
			'message' => $response['message'] ?? __( 'Failed to delete PayPal webhook.', 'sureforms-pro' ),
		];
	}

	/**
	 * Check if webhook is configured.
	 *
	 * @param string $mode Payment mode ('test' or 'live').
	 * @since 2.4.0
	 * @return bool True if webhook is configured, false otherwise.
	 */
	public static function is_webhook_configured( $mode ) {
		$settings   = Helper::get_all_paypal_settings();
		$webhook_id = 'live' === $mode
			? ( $settings['webhook_live_id'] ?? '' )
			: ( $settings['webhook_test_id'] ?? '' );

		return ! empty( $webhook_id );
	}

	/**
	 * Get webhook details for a mode.
	 *
	 * @param string $mode Payment mode ('test' or 'live').
	 * @since 2.4.0
	 * @return array Webhook details (id, url).
	 */
	public static function get_webhook_details( $mode ) {
		$settings = Helper::get_all_paypal_settings();

		if ( 'live' === $mode ) {
			return [
				'webhook_id'  => $settings['webhook_live_id'] ?? '',
				'webhook_url' => $settings['webhook_live_url'] ?? '',
			];
		}

		return [
			'webhook_id'  => $settings['webhook_test_id'] ?? '',
			'webhook_url' => $settings['webhook_test_url'] ?? '',
		];
	}
}
