Themes: Avoid autoloading the previous theme's theme mods when switching to another theme.

This reduces unnecessarily autoloaded data from inactive themes, which can contribute to slow database performance as part of excessive autoloading.

Props mukesh27, rajinsharwar, igmoweb, joemcgill, swissspidy, westonruter, flixos90.
Fixes #59537.
See #59975.


git-svn-id: https://develop.svn.wordpress.org/trunk@57153 602fd350-edb4-49c9-b593-d223f7449a82
This commit is contained in:
Felix Arntz 2023-12-04 19:36:27 +00:00
parent b38a6cf976
commit 7ce1281349
2 changed files with 49 additions and 0 deletions

View File

@ -840,6 +840,13 @@ function switch_theme( $stylesheet ) {
$new_theme->delete_pattern_cache();
$old_theme->delete_pattern_cache();
// Set autoload=no for the old theme, autoload=yes for the switched theme.
$theme_mods_options = array(
'theme_mods_' . $stylesheet => 'yes',
'theme_mods_' . $old_theme->get_stylesheet() => 'no',
);
wp_set_option_autoload_values( $theme_mods_options );
/**
* Fires after the theme is switched.
*

View File

@ -0,0 +1,42 @@
<?php
require_once __DIR__ . '/base.php';
/**
* Test autoload for theme mods.
*
* @package WordPress
* @subpackage Theme
*
* @group themes
*/
class Tests_Autoload_Theme_Mods extends WP_Theme_UnitTestCase {
/**
* Tests that theme mods should not autoloaded after switch_theme.
*
* @ticket 39537
*/
public function test_that_on_switch_theme_previous_theme_mods_should_not_be_autoload() {
global $wpdb;
$current_theme_stylesheet = get_stylesheet();
// Set a theme mod for the current theme.
$new_theme_stylesheet = 'block-theme';
set_theme_mod( 'foo-bar-option', 'a-value' );
switch_theme( $new_theme_stylesheet );
$this->assertSame( 'no', $wpdb->get_var( $wpdb->prepare( "SELECT autoload FROM $wpdb->options WHERE option_name = %s", "theme_mods_$current_theme_stylesheet" ) ), 'Theme mods autoload value not set to no in database' );
$this->assertSame( 'yes', $wpdb->get_var( $wpdb->prepare( "SELECT autoload FROM $wpdb->options WHERE option_name = %s", "theme_mods_$new_theme_stylesheet" ) ), 'Theme mods autoload value not set to yes in database' );
switch_theme( $current_theme_stylesheet );
$this->assertSame( 'yes', $wpdb->get_var( $wpdb->prepare( "SELECT autoload FROM $wpdb->options WHERE option_name = %s", "theme_mods_$current_theme_stylesheet" ) ), 'Theme mods autoload value not set to yes in database' );
$this->assertSame( 'no', $wpdb->get_var( $wpdb->prepare( "SELECT autoload FROM $wpdb->options WHERE option_name = %s", "theme_mods_$new_theme_stylesheet" ) ), 'Theme mods autoload value not set to no in database' );
// Basic assertion to make sure that we haven't lost the mods.
$this->assertSame( 'a-value', get_theme_mod( 'foo-bar-option' ) );
}
}