<?php

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

class SimplyIN_System_Check {

	public const TEST_PLUGIN_ACTIVE = 1;

	public const TEST_PLUGIN_INSTALLED = 2;

	public const TEST_PLUGIN_NOT_INSTALLED = 0;


	/**
	 * @var boolean
	 */
	private bool $result = true;

	/**
	 * @var array
	 */
	private array $plugin_config;

	/**
	 * @var string
	 */
	private string $basename;

	/**
	 * @param array $plugin_config
	 */
	public function __construct( array $plugin_config ) {
		$this->plugin_config = $plugin_config;
	}

	public function evaluate_system() {
		$basename       = basename( __DIR__ );
		$this->basename = $basename;

		$this->test_php();
		$this->test_php_extensions_installed();
		$this->test_required_plugins();

		if ( ! $this->result ) {
			return $this->result;
		}

		$wc_min = $this->get_wc_min_version();
		if ( null !== $wc_min ) {
			$this->test_woocommerce_version( $wc_min );
		}

		return $this->result;
	}

	private function test_php(): void {
		if ( PHP_VERSION_ID < $this->get_plugin_min_php_int() ) {
			$this->system_test_failed();
			$this->print_error(
				sprintf(
					'PHP version is older than %s — Simply.IN cannot load. Ask your host to upgrade PHP.',
					$this->get_plugin_min_php()
				)
			);
		}
	}

	private function test_php_extensions_installed(): void {
		if ( $this->get_required_php_extensions() ) {
			$not_installed_extensions = [];
			foreach ( $this->get_required_php_extensions() as $extension ) {
				if ( ! extension_loaded( $extension ) ) {
					$not_installed_extensions[] = $extension;
				}
			}
			if ( ! empty( $not_installed_extensions ) ) {
				$this->system_test_failed();
				$this->print_error(
					sprintf(
						'PHP extensions missing: %s. Install them to use Simply.IN.',
						implode( ', ', $not_installed_extensions )
					)
				);
			}
		}
	}

	public function print_error( $message ): void {
		add_action( 'admin_notices', function () use ( $message ) {
			printf( "<div class='notice notice-error error'><p><strong style='color: red;'>%s: ",
				esc_html( $this->get_plugin_name() ) );
			echo esc_html( $message );
			echo "</strong></p></div>";
		} );
	}

	private function get_plugin__FILE__() {
		return $this->plugin_config['__FILE__'];
	}

	private function get_plugin_slug() {
		return $this->plugin_config['slug'];
	}

	private function get_plugin_lang_dir() {
		return $this->plugin_config['lang_dir'];
	}

	private function get_plugin_text_domain() {
		return $this->plugin_config['text_domain'];
	}

	private function get_plugin_min_php_int() {
		return $this->plugin_config['min_php_int'];
	}

	private function get_plugin_min_php() {
		return $this->plugin_config['min_php'];
	}

	private function get_plugin_name() {
		return $this->plugin_config['name'];
	}

	/**
	 * @return null|array
	 */
	private function get_required_plugins(): ?array {
		return $this->plugin_config['required_plugins'] ?? null;
	}

	/**
	 * @return null|string
	 */
	private function get_wc_min_version(): ?string {
		return $this->plugin_config['wc_min_version'] ?? null;
	}

	/**
	 * @return null|array
	 */
	private function get_required_php_extensions(): ?array {
		return $this->plugin_config['required_php_extensions'] ?? null;
	}

	private function test_plugin( $slug ): int {
		if ( ! function_exists( 'is_plugin_active' ) ) {
			require_once ABSPATH . 'wp-admin/includes/plugin.php';
		}

		if ( is_plugin_active( $slug . '/' . $slug . '.php' ) ) {
			return self::TEST_PLUGIN_ACTIVE;
		} elseif ( is_plugin_inactive( $slug . '/' . $slug . '.php' ) ) {
			return self::TEST_PLUGIN_INSTALLED;
		} else {
			return self::TEST_PLUGIN_NOT_INSTALLED;
		}
	}

	/**
	 * Ensure declared dependencies (e.g. WooCommerce) are installed and active.
	 *
	 * @return void
	 */
	private function test_required_plugins(): void {
		$required = $this->get_required_plugins();
		if ( ! $required ) {
			return;
		}

		foreach ( $required as $slug ) {
			if ( self::TEST_PLUGIN_ACTIVE !== $this->test_plugin( $slug ) ) {
				$this->system_test_failed();
				$this->print_error(
					sprintf(
						'Simply.IN requires plugin "%s" to be installed and active.',
						$slug
					)
				);
			}
		}
	}


	public function system_test_failed(): void {
		$this->result = false;
	}

	private function test_woocommerce_version( $wc_min_version ): bool {
		// Prefer the Plugin header / active plugin path — DB option can stay high after partial downgrades or before WC loads (load order vs "Simply.IN").
		$wc_version = $this->resolve_active_woocommerce_version_string();

		if ( empty( $wc_version ) ) {
			$this->system_test_failed();
			$this->print_error( 'WooCommerce is required and could not be detected.' );

			return false;
		}

		if ( version_compare( (string) $wc_version, (string) $wc_min_version, '<' ) ) {
			$this->system_test_failed();
			$this->print_error(
				sprintf(
					'Simply.IN requires WooCommerce %s or newer (detected version: %s). Please update WooCommerce.',
					$wc_min_version,
					(string) $wc_version
				)
			);

			return false;
		}

		return true;

	}

	/**
	 * Read WooCommerce version from the active plugin file on disk, then WC_VERSION, then DB option.
	 * The option can stay high after a downgrade; this matches the plugin list and installed files.
	 *
	 * @return string Non-empty semver string when detectable.
	 */
	private function resolve_active_woocommerce_version_string(): string {
		if ( defined( 'WP_PLUGIN_DIR' ) ) {
			$active_slugs   = (array) get_option( 'active_plugins', [] );
			$network_active = [];

			if ( function_exists( 'is_multisite' ) && is_multisite() ) {
				$network_active = array_keys( (array) get_site_option( 'active_sitewide_plugins', [] ) );
			}

			$active_slugs = array_merge( $active_slugs, $network_active );

			foreach ( array_unique( array_filter( array_map( 'strval', $active_slugs ) ) ) as $relative ) {
				if ( ! is_string( $relative ) || '' === $relative ) {
					continue;
				}

				if ( ! preg_match( '#/woocommerce\\.php$#', $relative ) ) {
					continue;
				}

				$full_path = WP_PLUGIN_DIR . '/' . $relative;

				if ( ! is_readable( $full_path ) ) {
					continue;
				}

				$file_headers = get_file_data(
					$full_path,
					array(
						'Name'    => 'Plugin Name',
						'Version' => 'Version',
					),
					'plugin'
				);

				$name_raw = isset( $file_headers['Name'] ) ? wp_strip_all_tags( (string) $file_headers['Name'] ) : '';
				$is_standard_path = ( 0 === strpos( $relative, 'woocommerce/' ) );
				$name_looks_like_wc = ( '' !== $name_raw && false !== stripos( $name_raw, 'WooCommerce' ) );

				if ( ! $is_standard_path && ! $name_looks_like_wc ) {
					continue;
				}

				$from_header = isset( $file_headers['Version'] ) ? trim( (string) $file_headers['Version'] ) : '';

				if ( '' !== $from_header ) {
					return $from_header;
				}
			}
		}

		if ( defined( 'WC_VERSION' ) && is_string( WC_VERSION ) && WC_VERSION !== '' ) {
			return WC_VERSION;
		}

		$db_ver = get_option( 'woocommerce_version' );

		return is_string( $db_ver ) && '' !== trim( $db_ver ) ? trim( $db_ver ) : '';

	}
}
