From 93c3290b631ede1b242d1a872d6c7b06b30b635d Mon Sep 17 00:00:00 2001 From: Marcus Quinn Date: Mon, 24 Mar 2025 16:07:11 +0000 Subject: [PATCH] refactor: move Theme tab functionality to WP_Allstars_Theme_Manager class --- admin/includes/class-theme-manager.php | 332 ++++++++++++++++++++++++ admin/settings.php | 340 +------------------------ 2 files changed, 337 insertions(+), 335 deletions(-) create mode 100644 admin/includes/class-theme-manager.php diff --git a/admin/includes/class-theme-manager.php b/admin/includes/class-theme-manager.php new file mode 100644 index 0000000..33f8677 --- /dev/null +++ b/admin/includes/class-theme-manager.php @@ -0,0 +1,332 @@ +"); + + // Show loading overlay + $container.css("position", "relative").append($loadingOverlay); + + // AJAX request to get themes + $.ajax({ + url: ajaxurl, + type: "POST", + data: { + action: "wp_allstars_get_themes", + _wpnonce: wpAllstars.nonce + }, + success: function(response) { + $loadingOverlay.remove(); + if (response.success) { + $container.html(response.data); + // Initialize theme action buttons + if (typeof initThemeHandlers === "function") { + initThemeHandlers(); + } + } else { + $container.html("

" + response.data + "

"); + } + }, + error: function(xhr, status, error) { + $loadingOverlay.remove(); + $container.html("

Failed to load themes. Please try again. Error: " + error + "

"); + console.error("AJAX Error:", xhr.responseText); + } + }); + } + + // Initialize theme handlers + window.initThemeHandlers = function() { + // Activate theme + $(".activate-now").click(function(e) { + e.preventDefault(); + + var $button = $(this); + var slug = $button.data("slug"); + var name = $button.data("name"); + var nonce = $button.data("nonce"); + + $button.text("Activating...").addClass("updating-message").attr("disabled", true); + + $.ajax({ + url: ajaxurl, + type: "POST", + data: { + action: "wp_allstars_activate_theme", + theme: slug, + _wpnonce: nonce + }, + success: function(response) { + if (response.success) { + $button.removeClass("updating-message").addClass("updated-message").text("Activated"); + setTimeout(function() { + window.location.reload(); + }, 1000); + } else { + $button.removeClass("updating-message").text("Error"); + alert("Error: " + response.data); + } + }, + error: function(xhr, status, error) { + $button.removeClass("updating-message").text("Error"); + alert("Error: " + error); + } + }); + }); + }; + }); + '; + } + + /** + * Display the theme tab content + */ + public static function display_tab_content() { + ?> +
+ +
+ +

Loading theme data...

+
+
+ 'kadence', + 'fields' => array( + 'sections' => false, + 'description' => true, + 'rating' => true, + 'ratings' => false, + 'downloaded' => true, + 'download_link' => true, + 'last_updated' => true, + 'homepage' => true, + 'tags' => false, + 'screenshot_url' => true, + 'version' => true, + 'requires' => true, + 'requires_php' => true, + 'active_installs' => true, + 'author' => true, + 'preview_url' => true, + ) + )); + + // Cache the result if successful + if (!is_wp_error($theme_data)) { + self::set_cached_theme($theme_data); + } + } else { + error_log('WP ALLSTARS: Using cached theme data'); + } + + if (is_wp_error($theme_data)) { + error_log('WP ALLSTARS Theme API Error: ' . $theme_data->get_error_message()); + wp_send_json_error('Theme API Error: ' . $theme_data->get_error_message()); + return; + } + + error_log('WP ALLSTARS: Successfully fetched theme data'); + + // Format author data + $author = ''; + if (is_string($theme_data->author)) { + $author = $theme_data->author; + } elseif (is_array($theme_data->author)) { + $author = isset($theme_data->author['display_name']) ? $theme_data->author['display_name'] : ''; + } + + error_log('WP ALLSTARS: Theme data retrieved, generating HTML'); + + // Generate custom HTML for the theme using our template partial + ob_start(); + include(plugin_dir_path(dirname(__FILE__)) . 'partials/theme-panel.php'); + $html = ob_get_clean(); + + if (empty($html)) { + error_log('WP ALLSTARS: Empty HTML generated'); + wp_send_json_error('Failed to generate theme display'); + return; + } + + error_log('WP ALLSTARS: Successfully generated theme display, HTML length: ' . strlen($html)); + wp_send_json_success($html); + exit; // Ensure we exit after sending the JSON response + + } catch (Exception $e) { + error_log('WP ALLSTARS Theme loading exception: ' . $e->getMessage()); + error_log('WP ALLSTARS Theme loading exception trace: ' . $e->getTraceAsString()); + wp_send_json_error('Theme loading error: ' . $e->getMessage()); + } catch (Error $e) { + error_log('WP ALLSTARS Theme loading error: ' . $e->getMessage()); + error_log('WP ALLSTARS Theme loading error trace: ' . $e->getTraceAsString()); + wp_send_json_error('Theme loading error: ' . $e->getMessage()); + } + } + + /** + * AJAX handler for theme activation + */ + public static function activate_theme() { + // Debug information + error_log('Theme activation AJAX request received: ' . print_r($_POST, true)); + + // Check nonce with the correct action name + if (!check_ajax_referer('wp-allstars-nonce', '_wpnonce', false)) { + error_log('Theme activation failed: Invalid nonce'); + wp_send_json_error('Invalid security token sent.'); + return; + } + + if (!current_user_can('switch_themes')) { + error_log('Theme activation failed: Permission denied'); + wp_send_json_error('Permission denied'); + return; + } + + $theme = isset($_POST['theme']) ? sanitize_text_field($_POST['theme']) : ''; + if (empty($theme)) { + error_log('Theme activation failed: No theme specified'); + wp_send_json_error('No theme specified'); + return; + } + + // Get the theme object + $theme_obj = wp_get_theme($theme); + if (!$theme_obj->exists()) { + error_log('Theme activation failed: Theme does not exist - ' . $theme); + wp_send_json_error('Theme does not exist'); + return; + } + + // Set the new theme + switch_theme($theme); + error_log('Theme activation success - ' . $theme); + wp_send_json_success(); + } +} diff --git a/admin/settings.php b/admin/settings.php index 13e14ed..43e3078 100644 --- a/admin/settings.php +++ b/admin/settings.php @@ -46,214 +46,20 @@ require_once dirname(__FILE__) . '/includes/class-plugin-manager.php'; require_once dirname(__FILE__) . '/includes/class-pro-plugins-manager.php'; require_once dirname(__FILE__) . '/includes/class-settings-manager.php'; require_once dirname(__FILE__) . '/includes/class-tools-manager.php'; +require_once dirname(__FILE__) . '/includes/class-theme-manager.php'; // Initialize the managers WP_Allstars_Plugin_Manager::init(); WP_Allstars_Pro_Plugins_Manager::init(); WP_Allstars_Settings_Manager::init(); WP_Allstars_Tools_Manager::init(); +WP_Allstars_Theme_Manager::init(); // Remove the old plugins API filter since we're handling everything in the AJAX endpoint remove_filter('plugins_api_result', 'wp_allstars_plugins_api_result'); -// Add transient caching for theme data -function wp_allstars_get_cached_theme() { - $cache_key = 'wp_allstars_theme_kadence'; - return get_transient($cache_key); -} - -function wp_allstars_set_cached_theme($data) { - $cache_key = 'wp_allstars_theme_kadence'; - set_transient($cache_key, $data, 12 * HOUR_IN_SECONDS); -} - -// Add AJAX endpoint for theme -function wp_allstars_ajax_get_themes() { - error_log('WP ALLSTARS: Theme AJAX handler started'); - - // Check nonce with the correct action name - if (!isset($_POST['_wpnonce'])) { - error_log('WP ALLSTARS: No nonce provided'); - wp_send_json_error('No security token provided.'); - return; - } - - if (!check_ajax_referer('wp-allstars-nonce', '_wpnonce', false)) { - error_log('WP ALLSTARS: Invalid nonce: ' . sanitize_text_field($_POST['_wpnonce'])); - wp_send_json_error('Invalid security token sent.'); - return; - } - - if (!current_user_can('install_themes')) { - error_log('WP ALLSTARS: User does not have permission to install themes'); - wp_send_json_error('Permission denied'); - return; - } - - error_log('WP ALLSTARS: Starting theme fetch process'); - - try { - error_log('WP ALLSTARS: Fetching theme data for kadence'); - - // Check if we have cached data first - $theme_data = wp_allstars_get_cached_theme(); - - // If no cached data, fetch from API - if (empty($theme_data)) { - error_log('WP ALLSTARS: No cached theme data, fetching from API'); - - // Get theme data with minimal fields - $theme_data = themes_api('theme_information', array( - 'slug' => 'kadence', - 'fields' => array( - 'sections' => false, - 'description' => true, - 'rating' => true, - 'ratings' => false, - 'downloaded' => true, - 'download_link' => true, - 'last_updated' => true, - 'homepage' => true, - 'tags' => false, - 'screenshot_url' => true, - 'version' => true, - 'requires' => true, - 'requires_php' => true, - 'active_installs' => true, - 'author' => true, - 'preview_url' => true, - ) - )); - - // Cache the result if successful - if (!is_wp_error($theme_data)) { - wp_allstars_set_cached_theme($theme_data); - } - } else { - error_log('WP ALLSTARS: Using cached theme data'); - } - - if (is_wp_error($theme_data)) { - error_log('WP ALLSTARS Theme API Error: ' . $theme_data->get_error_message()); - wp_send_json_error('Theme API Error: ' . $theme_data->get_error_message()); - return; - } - - error_log('WP ALLSTARS: Successfully fetched theme data'); - - // Format author data - $author = ''; - if (is_string($theme_data->author)) { - $author = $theme_data->author; - } elseif (is_array($theme_data->author)) { - $author = isset($theme_data->author['display_name']) ? $theme_data->author['display_name'] : ''; - } - - error_log('WP ALLSTARS: Theme data retrieved, generating HTML'); - - // Generate custom HTML for the theme using our template partial - ob_start(); - include(plugin_dir_path(__FILE__) . 'partials/theme-panel.php'); - $html = ob_get_clean(); - - if (empty($html)) { - error_log('WP ALLSTARS: Empty HTML generated'); - wp_send_json_error('Failed to generate theme display'); - return; - } - - error_log('WP ALLSTARS: Successfully generated theme display, HTML length: ' . strlen($html)); - wp_send_json_success($html); - exit; // Ensure we exit after sending the JSON response - - } catch (Exception $e) { - error_log('WP ALLSTARS Theme loading exception: ' . $e->getMessage()); - error_log('WP ALLSTARS Theme loading exception trace: ' . $e->getTraceAsString()); - wp_send_json_error('Theme loading error: ' . $e->getMessage()); - } catch (Error $e) { - error_log('WP ALLSTARS Theme loading error: ' . $e->getMessage()); - error_log('WP ALLSTARS Theme loading error trace: ' . $e->getTraceAsString()); - wp_send_json_error('Theme loading error: ' . $e->getMessage()); - } -} -add_action('wp_ajax_wp_allstars_get_themes', 'wp_allstars_ajax_get_themes'); - -// Clear theme cache when themes are updated -function wp_allstars_clear_theme_cache() { - delete_transient('wp_allstars_theme_kadence'); -} -add_action('upgrader_process_complete', 'wp_allstars_clear_theme_cache', 10, 0); -add_action('switch_theme', 'wp_allstars_clear_theme_cache'); - -// Add AJAX handler for theme activation -function wp_allstars_activate_theme() { - // Debug information - error_log('Theme activation AJAX request received: ' . print_r($_POST, true)); - - // Check nonce with the correct action name - if (!check_ajax_referer('wp-allstars-nonce', '_wpnonce', false)) { - error_log('Theme activation failed: Invalid nonce'); - wp_send_json_error('Invalid security token sent.'); - return; - } - - if (!current_user_can('switch_themes')) { - error_log('Theme activation failed: Permission denied'); - wp_send_json_error('Permission denied'); - return; - } - - $theme = isset($_POST['theme']) ? sanitize_text_field($_POST['theme']) : ''; - if (empty($theme)) { - error_log('Theme activation failed: No theme specified'); - wp_send_json_error('No theme specified'); - return; - } - - // Get the theme object - $theme_obj = wp_get_theme($theme); - if (!$theme_obj->exists()) { - error_log('Theme activation failed: Theme does not exist - ' . $theme); - wp_send_json_error('Theme does not exist'); - return; - } - - if ($theme_obj->errors()) { - error_log('Theme activation failed: Theme has errors - ' . print_r($theme_obj->errors(), true)); - wp_send_json_error('Theme has errors'); - return; - } - - // Check if theme is already active - $current_theme = wp_get_theme(); - if ($current_theme->get_stylesheet() === $theme) { - error_log('Theme is already active: ' . $theme); - wp_send_json_success(array( - 'message' => 'Theme is already active', - 'customize_url' => admin_url('customize.php') - )); - return; - } - - // Switch the theme - error_log('Switching to theme: ' . $theme); - switch_theme($theme); - - // Check if the switch was successful - $active_theme = wp_get_theme(); - if ($active_theme->get_stylesheet() === $theme) { - error_log('Theme activated successfully: ' . $theme); - wp_send_json_success(array( - 'message' => 'Theme activated successfully', - 'customize_url' => admin_url('customize.php') - )); - } else { - error_log('Failed to activate theme: ' . $theme . ', active theme is: ' . $active_theme->get_stylesheet()); - wp_send_json_error('Failed to activate theme'); - } -} -add_action('wp_ajax_wp_allstars_activate_theme', 'wp_allstars_activate_theme'); +// Theme functionality has been moved to WP_Allstars_Theme_Manager class // Register settings page HTML function wp_allstars_settings_page() { @@ -315,54 +121,7 @@ function wp_allstars_settings_page() { } }); '); - } elseif ($active_tab === 'theme') { - wp_allstars_clear_theme_cache(); - require_once ABSPATH . 'wp-admin/includes/theme.php'; - wp_enqueue_script('theme-install'); - wp_enqueue_script('updates'); - add_thickbox(); - wp_enqueue_style('wp-allstars-admin', plugins_url('css/wp-allstars-admin.css', __FILE__)); - wp_enqueue_style('wp-allstars-plugins', plugins_url('css/wp-allstars-plugins.css', __FILE__)); - - // Add inline script to load themes directly - same approach as plugins tab - wp_add_inline_script('wp-allstars-admin', ' - jQuery(document).ready(function($) { - if ($("#wpa-theme-list").length && $("#wpa-theme-list").is(":empty")) { - var $container = $("#wpa-theme-list"); - var $loadingOverlay = $("
"); - - // Show loading overlay - $container.css("position", "relative").append($loadingOverlay); - - // AJAX request to get themes - $.ajax({ - url: ajaxurl, - type: "POST", - data: { - action: "wp_allstars_get_themes", - _wpnonce: wpAllstars.nonce - }, - success: function(response) { - $loadingOverlay.remove(); - if (response.success) { - $container.html(response.data); - // Initialize theme action buttons - if (typeof initThemeHandlers === "function") { - initThemeHandlers(); - } - } else { - $container.html("

" + response.data + "

"); - } - }, - error: function(xhr, status, error) { - $loadingOverlay.remove(); - $container.html("

Failed to load themes. Please try again. Error: " + error + "

"); - console.error("AJAX Error:", xhr.responseText); - } - }); - } - }); - '); + // Theme-specific scripts and styles are now handled in WP_Allstars_Theme_Manager::enqueue_scripts } ?>
@@ -669,96 +428,7 @@ function wp_allstars_settings_page() {
-
- -
- -

Loading theme data...

-
-
- +