checked ) ) { return $transient; } $theme_slug = get_stylesheet(); $current_version = (string) wp_get_theme( $theme_slug )->get( 'Version' ); if ( '' === $current_version ) { return $transient; } // phpcs:ignore WordPress.Security.NonceVerification.Recommended $force_check = ! empty( $_GET['force-check'] ); $remote_version = self::get_remote_version( $force_check ); if ( null === $remote_version || '' === $remote_version ) { return $transient; } $update_data = array( 'theme' => $theme_slug, 'new_version' => $remote_version, 'url' => self::REPO_URL, 'package' => self::PACKAGE_URL, ); if ( ! isset( $transient->response ) || ! is_array( $transient->response ) ) { $transient->response = array(); } if ( ! isset( $transient->no_update ) || ! is_array( $transient->no_update ) ) { $transient->no_update = array(); } if ( version_compare( $remote_version, $current_version, '>' ) ) { $transient->response[ $theme_slug ] = $update_data; unset( $transient->no_update[ $theme_slug ] ); } else { $transient->no_update[ $theme_slug ] = $update_data; unset( $transient->response[ $theme_slug ] ); } return $transient; } /** * Récupère la version distante dans style.css sur la branche main (avec cache Transient). * * @param bool $force_check Ignore le cache si une vérification manuelle est demandée. * @return string|null */ private static function get_remote_version( bool $force_check = false ): ?string { if ( ! $force_check ) { $cached = get_transient( self::VERSION_TRANSIENT ); if ( is_string( $cached ) && '' !== $cached ) { return $cached; } if ( false !== get_transient( self::ERROR_TRANSIENT ) ) { return null; } } $response = wp_remote_get( self::RAW_STYLE_URL, array( 'timeout' => 10, 'sslverify' => true, 'headers' => array( 'Accept' => 'text/plain', ), 'user-agent' => 'WordPress/' . get_bloginfo( 'version' ) . '; ' . home_url( '/' ), ) ); if ( is_wp_error( $response ) || 200 !== (int) wp_remote_retrieve_response_code( $response ) ) { set_transient( self::ERROR_TRANSIENT, 1, 15 * MINUTE_IN_SECONDS ); return null; } $body = (string) wp_remote_retrieve_body( $response ); if ( '' === $body || ! preg_match( '/^\s*\*?\s*Version\s*:\s*([0-9]+\.[0-9]+(?:\.[0-9]+)*(?:-[A-Za-z0-9._-]+)?)/mi', $body, $matches ) ) { set_transient( self::ERROR_TRANSIENT, 1, 15 * MINUTE_IN_SECONDS ); return null; } $remote_version = trim( $matches[1] ); delete_transient( self::ERROR_TRANSIENT ); set_transient( self::VERSION_TRANSIENT, $remote_version, self::CACHE_TTL ); return $remote_version; } /** * Renomme automatiquement le dossier extrait de l'archive Gitea vers get_stylesheet(). * * @param string|WP_Error $source Chemin du dossier extrait. * @param string $remote_source Dossier temporaire parent. * @param WP_Upgrader $upgrader Instance du gestionnaire de mise à jour. * @param array $hook_extra Métadonnées sur l'élément mis à jour. * @return string|WP_Error */ public static function fix_extracted_folder_name( $source, $remote_source, $upgrader, $hook_extra ) { if ( is_wp_error( $source ) || empty( $source ) || empty( $remote_source ) ) { return $source; } $theme_slug = get_stylesheet(); $is_single = isset( $hook_extra['theme'] ) && $hook_extra['theme'] === $theme_slug; $is_bulk = isset( $hook_extra['themes'] ) && is_array( $hook_extra['themes'] ) && in_array( $theme_slug, $hook_extra['themes'], true ); if ( ! $is_single && ! $is_bulk ) { return $source; } // Vérification d'intégrité (indispensable en mise à jour groupée) sur le Text Domain du thème. $style_path = trailingslashit( (string) $source ) . 'style.css'; if ( ! file_exists( $style_path ) ) { return $source; } $header_chunk = file_get_contents( $style_path, false, null, 0, 2048 ); if ( false === $header_chunk || ! preg_match( '/^\s*\*?\s*Text\s+Domain\s*:\s*cgt-fha\b/mi', $header_chunk ) ) { return $source; } $corrected_source = trailingslashit( (string) $remote_source ) . $theme_slug . '/'; if ( untrailingslashit( (string) $source ) === untrailingslashit( $corrected_source ) ) { return $source; } global $wp_filesystem; if ( ! $wp_filesystem ) { require_once ABSPATH . 'wp-admin/includes/file.php'; WP_Filesystem(); } if ( ! $wp_filesystem ) { return $source; } if ( $wp_filesystem->is_dir( $corrected_source ) ) { $wp_filesystem->delete( $corrected_source, true ); } if ( ! $wp_filesystem->move( (string) $source, $corrected_source, true ) ) { return new WP_Error( 'cgt_fha_rename_failed', __( 'Impossible de renommer l\'archive du thème vers le dossier actif.', 'cgt-fha' ) ); } return $corrected_source; } /** * Purge uniquement les transients de version après une mise à jour de thème. * * @param WP_Upgrader $upgrader Instance du gestionnaire de mise à jour. * @param array $hook_extra Métadonnées de la mise à jour terminée. */ public static function purge_version_cache( $upgrader, $hook_extra ): void { if ( 'theme' !== ( $hook_extra['type'] ?? '' ) ) { return; } delete_transient( self::VERSION_TRANSIENT ); delete_transient( self::ERROR_TRANSIENT ); } } CGT_FHA_Gitea_Updater::init();