Make WordPress Core

Opened 14 years ago

Closed 12 years ago

#15548 closed defect (bug) (fixed)

Cache inconsistencies between get_option and get_blog_option

Reported by: mwidmann's profile mwidmann Owned by:
Milestone: 3.5 Priority: normal
Severity: normal Version: 3.0.1
Component: Multisite Keywords: caching memcache has-patch
Focuses: Cc:


When an option is updated for a blog update_option calls wp_cache_set to update the cache for that option.

The problem comes when the option is accessed through get_blog_option from another site. There the cache never gets updated (unless the caching - in our case memcached - is recycled.

Steps to reproduce, I'm updating the admin_email, so be sure to change it back afterwards:

echo "fetching using get_blog_option<br>";
echo get_blog_option( 6, 'admin_email' );

switch_to_blog( 6 );
echo "<br>fetching using get_option before update<br>";
echo get_option( 'admin_email' );
echo "<br>updating...<br>";
update_option( 'admin_email', '' );
echo "<br>fetching using get_option after update<br>";
echo get_option( 'admin_email' );

echo "<br>fetching using get_blog_option after uptdate<br>";
echo get_blog_option( 6, 'admin_email' );

The output will look like something similar to this:

fetching using get_blog_option
fetching using get_option before update

fetching using get_option after update
fetching using get_blog_option after uptdate

If no caching is enabled than - of course - this issue doesn't come up as the value is always fetched form the database.

The best solution most probably would be to modify the either hook into update_option and delete_option actions from ms-blogs.php and then update or delete the value based on the given option.

Change History (9)

#1 @mwidmann
14 years ago

Here's a way around this limitation, I load it from a mu-plugin.

add_action( 'update_option', 'vmh_update_option', 11, 3 );
add_action( 'delete_option', 'vmh_delete_option', 11, 2 );

function vmh_update_option( $option, $oldvalue, $newvalue ) {
	global $blog_id;

	if ( is_multisite() ) {
		$key = $blog_id."-".$option."-blog_option";
		$value = wp_cache_get( $key, "site-options" );
		if ( FALSE !== $value ) {
			wp_cache_set( $key, $newvalue, "site-options" );
function vmh_delete_option( $option, $oldvalue ) {
	global $blog_id;

	if ( is_multisite() ) {
		$key = $blog_id."-".$option."-blog_option";
		wp_cache_delete( $key, "site-options" );

#2 @scribu
14 years ago

Related: #14992

#3 @markjaquith
13 years ago

  • Milestone changed from Awaiting Review to Future Release
  • Type changed from defect (bug) to enhancement

#4 @SergeyBiryukov
12 years ago

  • Keywords changed from caching, memcache to caching memcache

Closed #19822 as a duplicate. Has a patch: ticket:19822:patch.diff.

#5 @mohanjith
12 years ago

  • Cc moha@… added
  • Type changed from enhancement to defect (bug)

#6 @uglyrobot
12 years ago

  • Cc aaron@… added
  • Keywords has-patch added
  • Version changed from 3.0.1 to 3.3.1

#7 @SergeyBiryukov
12 years ago

  • Version changed from 3.3.1 to 3.0.1

Version number indicates when the bug was initially introduced/reported.

#8 @scribu
12 years ago

  • Milestone changed from Future Release to 3.5

This should be fixed as of [21357].

#9 @scribu
12 years ago

  • Resolution set to fixed
  • Status changed from new to closed
Note: See TracTickets for help on using tickets.