<?php

namespace WDevs\CustomerOrderExport;


use WDevs\CustomerOrderExport\Channels\ChannelFactory;

class Ajax {

	/**
	 * The ID of this plugin.
	 *
	 * @since    1.0.0
	 * @access   private
	 * @var      string $plugin_name The ID of this plugin.
	 */
	private $plugin_name;

	/**
	 * The version of this plugin.
	 *
	 * @since    1.0.0
	 * @access   private
	 * @var      string $version The current version of this plugin.
	 */
	private $version;


	const AJAX_ACTION_NONCE = 'wdevs-coe-nonce';

	const AJAX_ACTION_TEMPLATE_COLUMNS = 'save_template_columns_changes';

	const AJAX_ACTION_TEMPLATE_DELETE = 'delete_template';

	const POST_ACTION_PREVIEW_FILE = 'preview_file';

	const AJAX_ACTION_FOLDER_MANAGEMENT = 'wdevs_coe_folder_management';

	const AJAX_ACTION_FOLDER_NONCE = 'wdevs_coe_folder_nonce';

	/**
	 * Initialize the class and set its properties.
	 *
	 * @param string $plugin_name The name of this plugin.
	 * @param string $version The version of this plugin.
	 *
	 * @since    1.0.0
	 */
	public function __construct( $plugin_name, $version ) {

		$this->plugin_name = $plugin_name;
		$this->version     = $version;

	}

	/**
	 * Handles template deletion via AJAX request from admin/js/wdevs-customer-order-export-template-columns.js Backbone model.
	 *
	 * Validates nonce and user permissions before deleting a template.
	 * Returns JSON response indicating success/failure.
	 *
	 * @return void Outputs JSON response and terminates
	 * @since 1.0.0
	 */
	public function delete_template_action() {
		if ( ! isset( $_POST['nonce'], $_POST['id'] ) ) {
			wp_send_json_error( 'missing_fields' );
			wp_die();
		}

		if ( ! wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['nonce'] ) ), self::AJAX_ACTION_NONCE ) ) {
			wp_send_json_error( 'bad_nonce' );
			wp_die();
		}

		if ( ! current_user_can( 'manage_woocommerce' ) ) {
			wp_send_json_error( 'missing_capabilities' );
			wp_die();
		}

		$id       = isset( $_POST['id'] ) ? absint( $_POST['id'] ) : 0;
		$template = new Template( $id );

		if ( ! $template->delete() ) {
			wp_send_json_error( 'missing_fields' );
			wp_die();
		}

		global $current_tab;
		$current_tab = 'templates';

		/**
		 * Completes the saving process for options.
		 */
		do_action( 'woocommerce_update_options' );

		wp_send_json_success(
			array(
				'id' => $id,
			)
		);
	}

	/**
	 * Handles template column updates via AJAX request from admin/js/wdevs-customer-order-export-template-columns.js Backbone model.
	 *
	 * Processes changes to template name and columns, saves the template,
	 * and returns updated template data as JSON response.
	 *
	 * @return void Outputs JSON response and terminates
	 * @since 1.0.0
	 */
	public function save_template_columns_changes_action() {
		if ( ! isset( $_POST['nonce'], $_POST['id'], $_POST['changes'] ) ) {
			wp_send_json_error( 'missing_fields' );
			wp_die();
		}

		if ( ! wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['nonce'] ) ), self::AJAX_ACTION_NONCE ) ) {
			wp_send_json_error( 'bad_nonce' );
			wp_die();
		}

		if ( ! current_user_can( 'manage_woocommerce' ) ) {
			wp_send_json_error( 'missing_capabilities' );
			wp_die();
		}

		$id       = isset( $_POST['id'] ) ? absint( $_POST['id'] ) : 0;
		$template = new Template( $id );

		$changes = $this->sanitize_template_changes( wp_unslash( $_POST['changes'] ) );

		if ( isset( $changes['name'] ) ) {
			$template->set_name( $changes['name'] );
		}

		if ( isset( $changes['columns'] ) ) {
			$template->set_columns( $changes['columns'] );
		}

		$template->save();

		global $current_tab;
		$current_tab = 'templates';

		/**
		 * Completes the saving process for options.
		 */
		do_action( 'woocommerce_update_options' );

		wp_send_json_success(
			array(
				'id'                => $template->get_id(),
				'name'              => $template->get_name(),
				'selectableColumns' => $template->get_selectable_columns( 'json' ),
				'columnsFlattened'  => $template->get_selected_columns_flattened(),
			)
		);
	}


	/**
	 * Handles file preview generation via AJAX request from admin/js/wdevs-customer-order-export-preview.js
	 *
	 * Generates a preview export file for a specific order and channel,
	 * then forces download of the generated file.
	 *
	 * @return void Outputs file download and terminates
	 * @since 1.0.0
	 */
	public function preview_file_action() {
		if ( ! isset( $_POST['nonce'], $_POST['section_id'], $_POST['order_id'] ) ) {
			wp_die( esc_html__( 'Missing fields.', 'orderbridge-for-woocommerce' ) );
		}

		if ( ! wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['nonce'] ) ), self::AJAX_ACTION_NONCE ) ) {
			wp_die( esc_html__( 'Invalid nonce.', 'orderbridge-for-woocommerce' ) );
		}

		if ( ! current_user_can( 'manage_woocommerce' ) ) {
			wp_die( esc_html__( 'Insufficient permissions.', 'orderbridge-for-woocommerce' ) );
		}

		$channel_id = ! empty( $_POST['section_id'] ) ? sanitize_text_field( wp_unslash( $_POST['section_id'] ) ) : '';
		$order_id   = ! empty( $_POST['order_id'] ) ? absint( $_POST['order_id'] ) : 0;

		$channel = ChannelFactory::create( $channel_id );

		if ( ! $channel->can_generate() ) {
			wp_die( esc_html__( 'Export couldn\'t be generated. Please review the selected channel settings and try again.', 'orderbridge-for-woocommerce' ) );
		}

		$file_path = $channel->generate( $order_id );

		if ( ! file_exists( $file_path ) || ! is_readable( $file_path ) ) {
			wp_die( esc_html__( 'File not found.', 'orderbridge-for-woocommerce' ) );
		}

		$file_name = basename( $file_path );

		header( 'Content-Type: application/octet-stream' );
		header( 'Content-Disposition: attachment; filename="' . esc_attr( $file_name ) . '"' );

		// phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_operations_readfile
		readfile( $file_path );
		exit;

	}

	/**
	 * Handle AJAX requests for folder management operations
	 * 
	 * Unified endpoint for create, rename, and delete folder operations
	 *
	 * @since 1.0.0
	 */
	public function wdevs_coe_folder_management_action() {
		// Verify user is logged in
		if ( ! is_user_logged_in() ) {
			wp_die( 'Unauthorized', 401 );
		}

		// Verify nonce
		if ( ! isset( $_POST['nonce'] ) || ! wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['nonce'] ) ), self::AJAX_ACTION_FOLDER_NONCE ) ) {
			wp_die( 'Security check failed', 403 );
		}

		// Validate required parameters
		$operation = isset( $_POST['operation'] ) ? sanitize_text_field( wp_unslash( $_POST['operation'] ) ) : '';
		$channel_slug = isset( $_POST['channel_slug'] ) ? sanitize_text_field( wp_unslash( $_POST['channel_slug'] ) ) : '';

		if ( empty( $operation ) || empty( $channel_slug ) ) {
			wp_send_json_error( [
				'message' => __( 'Missing required parameters', 'orderbridge-for-woocommerce' )
			] );
		}

		// Validate operation
		$allowed_operations = [ 'create', 'rename', 'delete', 'select' ];
		if ( ! in_array( $operation, $allowed_operations, true ) ) {
			wp_send_json_error( [
				'message' => __( 'Invalid operation', 'orderbridge-for-woocommerce' )
			] );
		}

		// Get channel instance
		$channel = ChannelFactory::get_channel_by_slug( $channel_slug );
		if ( ! $channel ) {
			wp_send_json_error( [
				'message' => __( 'Invalid channel', 'orderbridge-for-woocommerce' )
			] );
		}

		$user_id = get_current_user_id();
		$result = [];

		// Handle different operations
		switch ( $operation ) {
			case 'create':
				$parent_id = isset( $_POST['parent_id'] ) ? sanitize_text_field( wp_unslash( $_POST['parent_id'] ) ) : '';
				$folder_name = isset( $_POST['folder_name'] ) ? sanitize_text_field( wp_unslash( $_POST['folder_name'] ) ) : '';

				if ( empty( $parent_id ) || empty( $folder_name ) ) {
					wp_send_json_error( [
						'message' => __( 'Missing folder name or parent ID', 'orderbridge-for-woocommerce' )
					] );
				}

				$result = $channel->create_folder( $user_id, $parent_id, $folder_name );
				break;

			case 'rename':
				$folder_id = isset( $_POST['folder_id'] ) ? sanitize_text_field( wp_unslash( $_POST['folder_id'] ) ) : '';
				$new_name = isset( $_POST['new_name'] ) ? sanitize_text_field( wp_unslash( $_POST['new_name'] ) ) : '';

				if ( empty( $folder_id ) || empty( $new_name ) ) {
					wp_send_json_error( [
						'message' => __( 'Missing folder ID or new name', 'orderbridge-for-woocommerce' )
					] );
				}

				$result = $channel->rename_folder( $user_id, $folder_id, $new_name );
				break;

			case 'delete':
				$folder_id = isset( $_POST['folder_id'] ) ? sanitize_text_field( wp_unslash( $_POST['folder_id'] ) ) : '';

				if ( empty( $folder_id ) ) {
					wp_send_json_error( [
						'message' => __( 'Missing folder ID', 'orderbridge-for-woocommerce' )
					] );
				}

				$result = $channel->delete_folder( $user_id, $folder_id );
				break;

			case 'select':
				$folder_id = isset( $_POST['folder_id'] ) ? sanitize_text_field( wp_unslash( $_POST['folder_id'] ) ) : '';
				$folder_name = isset( $_POST['folder_name'] ) ? sanitize_text_field( wp_unslash( $_POST['folder_name'] ) ) : '';

				if ( empty( $folder_id ) ) {
					wp_send_json_error( [
						'message' => __( 'Missing folder ID', 'orderbridge-for-woocommerce' )
					] );
				}

				$result = $channel->select_folder( $user_id, $folder_id, $folder_name );
				break;
		}

		// Send response
		if ( isset( $result['success'] ) && $result['success'] ) {
			wp_send_json_success( $result );
		} else {
			wp_send_json_error( $result );
		}
	}

	/**
	 * Sanitize template changes data from AJAX request
	 *
	 * @param mixed $changes Raw changes data from $_POST
	 * @return array Sanitized changes array
	 * @since 1.0.0
	 */
	private function sanitize_template_changes( $changes ) {
		if ( ! is_array( $changes ) ) {
			return array();
		}

		$sanitized = array();

		// Sanitize template name
		if ( isset( $changes['name'] ) ) {
			$sanitized['name'] = sanitize_text_field( $changes['name'] );
		}

		// Sanitize columns array
		if ( isset( $changes['columns'] ) && is_array( $changes['columns'] ) ) {
			$sanitized['columns'] = $this->sanitize_template_columns( $changes['columns'] );
		}

		return $sanitized;
	}

	/**
	 * Sanitize template columns data
	 *
	 * @param array $columns Raw columns data
	 * @return array Sanitized columns array
	 * @since 1.0.0
	 */
	private function sanitize_template_columns( $columns ) {
		if ( ! is_array( $columns ) ) {
			return array();
		}

		$sanitized_columns = array();

		foreach ( $columns as $column_id => $column_data ) {
			// Validate column ID
			$clean_column_id = sanitize_text_field( $column_id );
			if ( empty( $clean_column_id ) || ! is_array( $column_data ) ) {
				continue;
			}

			// Sanitize column data
			$clean_column = array();

			if ( isset( $column_data['category_id'] ) ) {
				$clean_column['category_id'] = sanitize_text_field( $column_data['category_id'] );
			}

			if ( isset( $column_data['field_id'] ) ) {
				$clean_column['field_id'] = sanitize_text_field( $column_data['field_id'] );
			}

			if ( isset( $column_data['name'] ) ) {
				$clean_column['name'] = sanitize_text_field( $column_data['name'] );
			}

			// Only add if required fields are present
			if ( ! empty( $clean_column['category_id'] ) && ! empty( $clean_column['field_id'] ) && ! empty( $clean_column['name'] ) ) {
				$sanitized_columns[ $clean_column_id ] = $clean_column;
			}
		}

		return $sanitized_columns;
	}
}