<?php
/**
 * Base settings class for AgenticWP plugin.
 *
 * @package AgenticWP
 */

namespace Agentic_WP;

defined( 'ABSPATH' ) || exit;

use Agentic_WP\Error_Handler;

/**
 * Base class for settings functionality.
 * Provides common utilities and constants used by all settings classes.
 */
abstract class Settings_Base {

	/**
	 * Default session timeout in minutes for background jobs.
	 *
	 * @since 1.0.0
	 * @var int
	 */
	public const BUILD_SESSION_TIMEOUT_MIN = 1440;

	/**
	 * Maximum character length for post creation directions.
	 *
	 * @since 1.0.0
	 * @var int
	 */
	protected const MAX_CREATE_POST_DIRECTIONS = 1500;

	/**
	 * Default JSON schema for structured content output.
	 *
	 * @since 1.0.0
	 * @var array
	 */
	protected const DEFAULT_POST_SCHEMA = array(
		'type'                 => 'object',
		'properties'           => array(
			'title'   => array(
				'type'        => 'string',
				'minLength'   => 1,
				'description' => 'Post title.',
			),
			'excerpt' => array(
				'type'        => 'string',
				'description' => 'Optional post excerpt (plain text).',
			),
			'blocks'  => array(
				'type'        => 'array',
				'description' => 'Ordered list of blocks to render for the post body.',
				'items'       => array(
					'type'                 => 'object',
					'properties'           => array(
						'type'     => array(
							'type'        => 'string',
							'description' => 'Block type: heading, paragraph, list, quote, separator',
						),
						'content'  => array(
							'type'        => 'string',
							'description' => 'Block text content. For list blocks, use items instead.',
						),
						'level'    => array(
							'type'        => 'integer',
							'description' => 'Heading level for heading blocks (2-3 recommended).',
						),
						'ordered'  => array(
							'type'        => 'boolean',
							'description' => 'Whether the list is ordered (numbered).',
						),
						'items'    => array(
							'type'        => 'string',
							'description' => 'List items as a single string with newline-separated entries.',
						),
						'citation' => array(
							'type'        => 'string',
							'description' => 'Optional citation for quote blocks.',
						),
					),
					'additionalProperties' => false,
				),
			),
		),
		'required'             => array( 'title', 'blocks' ),
		'additionalProperties' => false,
	);

	/**
	 * Sanitize checkbox input.
	 *
	 * @param mixed $input The checkbox input value.
	 * @return int
	 */
	public function sanitize_checkbox( $input ) {
		return ! empty( $input ) ? 1 : 0;
	}

	/**
	 * Verify AJAX nonce and user capabilities.
	 *
	 * @param string $nonce_action The nonce action to verify.
	 * @param string $capability   The required user capability.
	 * @return void
	 * @throws \Exception If verification fails.
	 */
	protected function verify_ajax_request( string $nonce_action, string $capability = 'manage_options' ): void {
		if ( ! wp_verify_nonce(
			sanitize_text_field( wp_unslash( $_POST['_ajax_nonce'] ?? '' ) ),
			$nonce_action
		) ) {
			Error_Handler::log_error(
				'security',
				'Invalid nonce in AJAX request',
				array(
					'action'    => $nonce_action,
					'user_id'   => get_current_user_id(),
					'has_nonce' => ! empty( $_POST['_ajax_nonce'] ?? '' ),
				)
			);
			wp_send_json_error( array( 'message' => __( 'Security check failed.', 'agenticwp' ) ), 403 );
		}

		if ( ! current_user_can( $capability ) ) {
			Error_Handler::log_error(
				'security',
				'Insufficient permissions in AJAX request',
				array(
					'action'     => $nonce_action,
					'capability' => $capability,
					'user_id'    => get_current_user_id(),
				)
			);
			wp_send_json_error( array( 'message' => __( 'Insufficient permissions.', 'agenticwp' ) ), 403 );
		}
	}

	/**
	 * Get the bundled default image URL inside the plugin directory.
	 *
	 * @return string
	 */
	protected static function get_bundled_default_image_url(): string {
		$plugin_file = plugin_dir_path( __DIR__ ) . 'agenticwp.php';
		return plugins_url( 'assets/images/agenticWP-logo.png', $plugin_file );
	}

	/**
	 * Render a field with an optional tooltip wrapper.
	 *
	 * Wraps field HTML with tooltip markup including info icon trigger, ARIA attributes,
	 * and tooltip content. Use this helper to add contextual help to any settings field.
	 *
	 * @since 1.0.0
	 *
	 * @param callable $field_callback Function that outputs the field HTML.
	 * @param string   $tooltip_text   HTML content for the tooltip. Empty string disables tooltip.
	 * @param string   $field_id       Unique ID for this field (used for ARIA relationships).
	 * @param array    $args           Optional. Additional arguments:
	 *                                 - 'label_text' (string) Text to place before the info icon.
	 *                                 - 'label_class' (string) CSS class for the label element.
	 *                                 Default empty array.
	 * @return void
	 */
	protected function render_field_with_tooltip( callable $field_callback, string $tooltip_text, string $field_id, array $args = array() ): void {
		$defaults = array(
			'label_text'  => '',
			'label_class' => 'description',
		);
		$args     = wp_parse_args( $args, $defaults );

		// Open field wrapper.
		printf( '<div class="agenticwp-field-wrapper" data-field-id="%s">', esc_attr( $field_id ) );

		// Render field header with optional label and tooltip trigger.
		if ( ! empty( $tooltip_text ) ) {
			echo '<div class="agenticwp-field-header">';

			if ( ! empty( $args['label_text'] ) ) {
				printf(
					'<p class="%s">%s</p>',
					esc_attr( $args['label_class'] ),
					wp_kses_post( $args['label_text'] )
				);
			}

			printf(
				'<button type="button" class="agenticwp-tooltip-trigger" aria-label="%s" aria-expanded="false" aria-describedby="%s">',
				esc_attr__( 'Help', 'agenticwp' ),
				esc_attr( $field_id . '-tooltip' )
			);
			echo '<span class="dashicons dashicons-info-outline"></span>';
			echo '</button>';
			echo '</div>';
		}

		// Render field content.
		echo '<div class="agenticwp-field-content">';
		call_user_func( $field_callback );
		echo '</div>';

		// Render tooltip if text provided.
		if ( ! empty( $tooltip_text ) ) {
			printf(
				'<div id="%s" class="agenticwp-tooltip" role="tooltip" hidden>%s</div>',
				esc_attr( $field_id . '-tooltip' ),
				wp_kses_post( $tooltip_text )
			);
		}

		// Close field wrapper.
		echo '</div>';
	}
}
