Opened 8 years ago
Last modified 2 months ago
#37178 new enhancement
Add $cache_only parameter to get_option
Reported by: | joostdevalk | Owned by: | |
---|---|---|---|
Milestone: | Awaiting Review | Priority: | normal |
Severity: | normal | Version: | |
Component: | Options, Meta APIs | Keywords: | has-patch dev-feedback needs-unit-tests |
Focuses: | performance | Cc: |
Description
When you do get_option()
and the option doesn't exist in the option cache, WordPress does a query to check whether that option exists and loads it. This is great as default behavior, but when you know that an option would have been autoloaded, you might not want that to happen.
I propose adding a parameter $cache_only
, which defaults to false, which, when set to true, returns false when there is no option set in the cache. The "workaround" currently would be to set an empty option, but that means adding unnecessary data to the database.
Attachments (2)
Change History (10)
@
8 years ago
Rewrote a bit :) Don't know in which scenario it could be handy. That one select isn't so perf expensive. If somebody is using get_option he/she needs to know if it exists, that's default consideration for me from the function name.
#1
in reply to:
↑ description
@
8 years ago
Replying to joostdevalk:
The "workaround" currently would be to set an empty option, but that means adding unnecessary data to the database.
Another workaround would be adding a pre_option_*
filter for that option that returns an empty string or null
to short-circuit the function and avoid the SQL query:
function wp37178_get_autoloaded_option( $option, $default = false ) { // prevent non-existent options from triggering multiple queries $notoptions = wp_cache_get( 'notoptions', 'options' ); if ( isset( $notoptions[ $option ] ) ) { return $default; } $alloptions = wp_load_alloptions(); if ( isset( $alloptions[$option] ) ) { $value = $alloptions[$option]; } else { $value = wp_cache_get( $option, 'options' ); } if ( ! $value ) { $value = null; } return maybe_unserialize( $value ); } add_filter( 'pre_option_myoption', 'wp37178_get_autoloaded_option' );
#5
@
3 years ago
- Milestone set to Awaiting Review
Readding a milestone. Seems like it was lost at some point.
Also, copying over some of my findings from exploring this in ticket:54459#comment:2:
I took a look and reacquainted with how
get_option()
works because I feel like this has come up somewhere for me in the past.
It seems there are a few ways to accomplish this already. Because this change would be an opt-in change, I'm wondering if these are better options because they don't require additional arguments to be added.
- Using the
pre_cache_alloptions
filter, someone could check! isset( $alloptions['myoption'] )
and add the default value for that option.wp_load_alloptions()
fetches all options withautoload = 'yes'
(unless there are no options set toautoload
).- At some point during the bootstrap process after
wp_load_alloptions()
has been called (or after calling it early on), a dev could run code that checks the keys present in thealloptions
cache, and add their own knownautoload
options with default values before updating that cache.- The same as previous, a dev could add their keys to the
notoptions
cache, and the function would fall back to returning the passed default value without a query.Personally, I like option 3 because it allows a different default to be passed in different locations where
get_option()
is called if desired. A filter could be probably be added to allow someone to adjust thenotoptions
cache before it's updated to make this easier.
Another way to protect these extra queries is to have a list of registered options. But this is really the same thing as the
alloption
list, except it would include the ones that don't currently exist.
Patch, first go.