<?php
/**
 * Vérification checksums wordpress.org après switch.
 *
 * @package CVS
 * @license GPL-2.0-or-later
 */

defined( 'ABSPATH' ) || exit;

class CVS_Checksums {

	const RESULT_OPTION = 'cvs_last_checksum_result';

	/**
	 * @param string|null $version
	 * @param string|null $locale
	 * @return array{ok:bool,checked:int,missing:array<int,string>,version:string}
	 */
	public static function verify_install( $version = null, $locale = null ) {
		$version = CVS_Settings::sanitize_version( $version ?: get_bloginfo( 'version' ) );
		$locale  = $locale ?: get_locale();

		$result = array(
			'ok'      => false,
			'checked' => 0,
			'missing' => array(),
			'version' => $version,
			'locale'  => $locale,
			'time'    => current_time( 'mysql' ),
		);

		if ( ! $version ) {
			update_option( self::RESULT_OPTION, $result, false );
			return $result;
		}

		$url = add_query_arg(
			array(
				'version' => $version,
				'locale'  => $locale,
			),
			'https://api.wordpress.org/core/checksums/1.0/'
		);

		$response = wp_remote_get(
			$url,
			array(
				'timeout'   => 30,
				'sslverify' => true,
			)
		);

		if ( is_wp_error( $response ) ) {
			$result['error'] = $response->get_error_message();
			update_option( self::RESULT_OPTION, $result, false );
			return $result;
		}

		$body = json_decode( wp_remote_retrieve_body( $response ), true );
		if ( empty( $body['checksums'] ) || ! is_array( $body['checksums'] ) ) {
			$result['error'] = __( 'Checksum data unavailable for this version or locale.', 'core-version-switcher-by-volade' );
			update_option( self::RESULT_OPTION, $result, false );
			return $result;
		}

		$missing = array();
		$checked = 0;
		$sample  = array(
			'wp-includes/version.php',
			'wp-admin/admin.php',
			'wp-login.php',
		);

		foreach ( $sample as $relative ) {
			if ( empty( $body['checksums'][ $relative ] ) ) {
				continue;
			}
			$path = ABSPATH . $relative;
			if ( ! is_readable( $path ) ) {
				$missing[] = $relative;
				continue;
			}
			++$checked;
			$hash = md5_file( $path );
			if ( ! hash_equals( strtolower( (string) $body['checksums'][ $relative ] ), strtolower( (string) $hash ) ) ) {
				$missing[] = $relative;
			}
		}

		$result['checked'] = $checked;
		$result['missing'] = $missing;
		$result['ok']      = $checked > 0 && empty( $missing );

		update_option( self::RESULT_OPTION, $result, false );
		return $result;
	}

	public static function get_last_result() {
		$result = get_option( self::RESULT_OPTION, array() );
		return is_array( $result ) ? $result : array();
	}
}
