WP Super Cache has a setting which allows the cache to be cleared when a post is saved. I needed to clear the cache when a widget is saved. It turned out to be surprisingly easy.
Simply add the following code to functions.php or your custom WordPress plugin:
[sourcecode language=”php”]
add_filter( ‘widget_update_callback’, ‘sjc_widget_save’, 10, 3 );
function sjc_widget_save( $instance, $new_instance, $old_instance, $this ) {
// if WP Super Cache is being used, clear the cache
global $file_prefix;
if ( function_exists( ‘wp_cache_clean_cache’ ) ) wp_cache_clean_cache( $file_prefix );
// don’t forget to return the widget content
return $instance;
}
[/sourcecode]
The code above will clear the entire cache any time a widget is saved. If you only want to clear the cache when a particular widget is saved, you will need to add a conditional that searches for something identifying the widget in the widget content ($instance), for example:
[sourcecode language=”php”]
add_filter( ‘widget_update_callback’, ‘sjc_widget_save’, 10, 3 );
function sjc_widget_save( $instance, $new_instance, $old_instance, $this ) {
if ( stristr( $instance, ‘my identifying string’ ) ) {
// if WP Super Cache is being used, clear the cache
global $file_prefix;
if ( function_exists( ‘wp_cache_clean_cache’ ) ) wp_cache_clean_cache( $file_prefix );
}
// don’t forget to return the widget content
return $instance;
}
[/sourcecode]
This method utilises the widget_update_callback filter, which is largely undocumented. We’re not actually filtering the widget content, we’re just returning it unchanged. In effect, we’re using the hook as an action rather than a filter, but it achieves our goal.
This filter will work for all of the built-in widgets, but may not work for widgets created by plugins depending on how they were created.
This will only work for the WP Super Cache plugin, which is what the client I am working for uses. I actually use W3 Total Cache on this site, but haven’t looked into how to do this with W3TC. If I ever get around to that, I’ll update this post.
I also need to point out that this code works by using a function that is part of WP Super Cache. As such, although it works with the current version of WP Super Cache, there is no guarantee that future versions will not include changes that break this.
Hi Stephen.
This looks great!
I do not really understand why this feature is not included as an option in WP super cache since there is an option to clear the cache when a post is updated.
Is it possible to include this code in any way so this will work for all themes and all sites in the multi site setup?
Maybe it is possible to write a WP super cache plugin?
I do not have the knowledge yet to write a plugin of my own but maybe you do?
I am pretty sure that a plugin to WP super cache that adds this feature would be highly appreciated by many user of WP super cache plugin.
Thanks for the tip. I’m using W3 Total Cache and was wondering why my widget updates weren’t taking. By the way, the way to do this for WTC is:
if (function_exists(‘w3tc_pgcache_flush’)) { w3tc_pgcache_flush(); }
Do you know what action/filter gets called when widgets are deleted? Your solution only works for when a widget is updated.
Thank you, I was going crazy trying to figure out why my widgets weren’t showing the updated information. Best to you in 2014.
I am currently using this code for clearing WP Super Cache when widget is updated.
add_action( ‘sidebar_admin_setup’, ‘wp_clear_cache_custom’ );
function wp_clear_cache_custom() {
global $wpdb;
wp_cache_clear_cache( $wpdb->blogid );
}
Be careful. I added the first example of code to my functions today, using the My Custom Functions plugin and it crashed my site (white screen, whether I wanted admin screen or to view pages). I’m on WordPress 4.8.1. I had to use ftp to get into the plugin and sort it.
Hi Paul,
Sorry to hear that. I just gave it a whirl in WP 4.8.1 with WP Super Cache 1.5.3 and My Custom Functions 4.6 and it didn’t crash for me.
I wouldn’t have been super surprised if it had, given this post is almost 6 years old now, but it still works for me. I assume you copied and pasted it directly from above? If so, there must be something else going on – maybe a conflict with another plugin.
Anyway, to anyone else reading this, please proceed with caution. Thanks.