<?php
/**
 * AJAX Donation Handler
 *
 * @package SureDonation
 */

namespace SureDonation\Inc\Ajax;

use SureDonation\Inc\Database\Tables\Donations;
use SureDonation\Inc\Database\Tables\Donors;
use SureDonation\Inc\Emails\Email_Handler;
use SureDonation\Inc\Helper;
use SureDonation\Inc\Payments\Payment_Helper;
use SureDonation\Inc\Traits\Get_Instance;

// Exit if accessed directly.
if ( ! defined( 'ABSPATH' ) ) {
	exit;
}

/**
 * Donation_Handler class.
 *
 * @since 0.0.1
 */
class Donation_Handler {
	use Get_Instance;

	/**
	 * Constructor.
	 *
	 * @since 0.0.1
	 */
	public function __construct() {
		add_action( 'wp_ajax_suredonation_submit_donation', [ $this, 'handle_donation_submission' ] );
		add_action( 'wp_ajax_nopriv_suredonation_submit_donation', [ $this, 'handle_donation_submission' ] );
	}

	/**
	 * Handle donation form submission.
	 *
	 * @return void
	 * @since 0.0.1
	 */
	public function handle_donation_submission() {
		// First check if nonce exists before accessing any other POST data.
		if ( ! isset( $_POST['suredonation_nonce'] ) ) {
			wp_send_json_error( __( 'Security check failed', 'suredonation' ) );
		}

		// Sanitize nonce value.
		$nonce = sanitize_text_field( wp_unslash( $_POST['suredonation_nonce'] ) );

		// Now get values needed to determine nonce action.
		$is_standalone = isset( $_POST['is_standalone'] ) && '1' === $_POST['is_standalone'];
		$campaign_id   = isset( $_POST['campaign_id'] ) ? intval( $_POST['campaign_id'] ) : 0;

		// Verify nonce - different nonce for standalone vs campaign-linked forms.
		$nonce_action = $is_standalone ? 'suredonation_donation_standalone' : 'suredonation_donation_' . $campaign_id;

		if ( ! wp_verify_nonce( $nonce, $nonce_action ) ) {
			wp_send_json_error( __( 'Security check failed', 'suredonation' ) );
		}

		// Validate campaign only if not standalone.
		$campaign = null;
		if ( ! $is_standalone ) {
			if ( ! $campaign_id ) {
				wp_send_json_error( __( 'Invalid campaign', 'suredonation' ) );
			}

			$campaign = get_post( $campaign_id );
			if ( ! $campaign || SUREDONATION_POST_TYPE !== $campaign->post_type ) {
				wp_send_json_error( __( 'Invalid campaign', 'suredonation' ) );
			}
		}

		// Get form data.
		$amount        = isset( $_POST['amount'] ) ? floatval( $_POST['amount'] ) : 0;
		$cover_fees    = isset( $_POST['cover_fees'] ) ? true : false;
		$is_anonymous  = isset( $_POST['is_anonymous'] ) ? true : false;
		$donor_name    = $is_anonymous ? __( 'Anonymous', 'suredonation' ) : sanitize_text_field( wp_unslash( $_POST['donor_name'] ?? '' ) );
		$donor_email   = sanitize_email( wp_unslash( $_POST['donor_email'] ?? '' ) );
		$donor_phone   = sanitize_text_field( wp_unslash( $_POST['donor_phone'] ?? '' ) );
		$donor_comment = sanitize_textarea_field( wp_unslash( $_POST['donor_comment'] ?? '' ) );

		// Validate required fields.
		if ( $amount <= 0 ) {
			wp_send_json_error( __( 'Invalid donation amount', 'suredonation' ) );
		}

		if ( ! $is_anonymous ) {
			if ( empty( $donor_name ) ) {
				wp_send_json_error( __( 'Donor name is required', 'suredonation' ) );
			}
			if ( empty( $donor_email ) || ! is_email( $donor_email ) ) {
				wp_send_json_error( __( 'Valid email address is required', 'suredonation' ) );
			}
		}

		// Calculate fee and amounts.
		$fee_percentage = 0.029; // 2.9%
		$fee_fixed      = 0.30;
		$base_amount    = $amount;
		$fees_covered   = 0;

		if ( $cover_fees ) {
			// Calculate the base amount from total (reverse calculation).
			$base_amount  = ( $amount - $fee_fixed ) / ( 1 + $fee_percentage );
			$fees_covered = $amount - $base_amount;
		}

		// Get or create donor.
		$donor_id = 0;
		if ( ! empty( $donor_email ) ) {
			$donor_id = Donors::get_or_create( $donor_email, $donor_name, $donor_phone );
		}

		// Get payment mode.
		$payment_mode = 'live';
		if ( class_exists( 'SureDonation\Inc\Payments\Payment_Helper' ) ) {
			$payment_mode = Payment_Helper::get_payment_mode();
		}

		// Create donation in database.
		$donation_id = Donations::add(
			[
				'campaign_id'    => $campaign_id,
				'donor_id'       => $donor_id ? $donor_id : 0,
				'amount'         => number_format( $base_amount, 2, '.', '' ),
				'fees_covered'   => number_format( $fees_covered, 2, '.', '' ),
				'currency'       => Payment_Helper::get_currency(),
				'gateway'        => 'manual',
				'payment_status' => 'pending',
				'payment_mode'   => $payment_mode,
				'donor_name'     => $donor_name,
				'donor_email'    => $donor_email,
				'donor_phone'    => $donor_phone,
				'is_anonymous'   => $is_anonymous ? 1 : 0,
				'donation_type'  => 'one-time',
				'donor_comment'  => $donor_comment,
				'ip_address'     => Helper::get_client_ip(),
				'user_agent'     => isset( $_SERVER['HTTP_USER_AGENT'] ) ? sanitize_text_field( wp_unslash( $_SERVER['HTTP_USER_AGENT'] ) ) : '',
				'referer_url'    => isset( $_SERVER['HTTP_REFERER'] ) ? esc_url_raw( wp_unslash( $_SERVER['HTTP_REFERER'] ) ) : '',
			]
		);

		if ( ! $donation_id ) {
			wp_send_json_error( __( 'Failed to create donation', 'suredonation' ) );
		}

		// Note: Donation status will be updated by payment gateway webhooks or manual confirmation.

		// Send donation confirmation email.
		$donation_data = [
			'id'           => $donation_id,
			'donor_name'   => $donor_name,
			'donor_email'  => $donor_email,
			'amount'       => $base_amount,
			'fees_covered' => $fees_covered,
			'currency'     => Payment_Helper::get_currency(),
		];

		Email_Handler::send_donation_confirmation( $donation_id, $campaign_id, $donation_data );

		// Get thank you message.
		$thank_you_message = '';
		if ( ! $is_standalone && $campaign_id ) {
			$thank_you_message = Helper::get_campaign_meta_value( $campaign_id, 'thank_you_message', '' );
		}
		if ( empty( $thank_you_message ) ) {
			$thank_you_message = esc_html__( 'Your generous contribution will make a real difference. A confirmation email has been sent to you.', 'suredonation' );
		}

		// Send success response.
		wp_send_json_success(
			[
				'donation_id' => $donation_id,
				'message'     => wp_kses_post( Helper::get_string_value( $thank_you_message ) ),
			]
		);
	}
}
