Im using the pre_get_posts hook to customize my query for a custom post type archive.
Some of the posts for this custom post type have a meta key mp_micropub_accredited with the meta value of 1 and others don’t have this meta key set.
I use the following code,
function micropubs_filter_posts( $query ) { if ( !is_admin() && $query->is_post_type_archive( 'micropubs' ) && $query->is_main_query() ) { $query->set( 'posts_per_page', 5 ); $accredited = filter_input( INPUT_GET, 'orderby', FILTER_SANITIZE_STRING ); if ( empty( $accredited ) ) return; if ( $accredited === 'accredited' ) { $query->set( 'meta_key', 'mp_micropub_accredited' ); $query->set( 'orderby', 'meta_value_num' ); } } } add_action( 'pre_get_posts', 'micropubs_filter_posts' );
So when i locate to this address in my browser it displays only the posts with the meta key set and no other posts.
http://localhost/site/post-type-archive/?orderby=accredited
How is it possible to include all the other posts that don’t have the mp_micropub_accredited meta key set but are displayed after the ones that are?
Your help much appreciated. 🙂
1 Answer
I would suggest you when you are updating meta values with 1 update rest with 0.
I mean set the key in all posts with 1 or 0 to avoid the complex query.
You can still do it with a simple script. It will check if key doesn’t exist then update it with 0. So your current code will work like charm.
OR
You can use compare
with NOT EXISTS
$meta_query = array(
'relation' => 'OR',
array(
'key' => 'mp_micropub_accredited',
'value' => 1
),
array(
'key' => 'mp_micropub_accredited',
'compare' => 'NOT EXISTS'
)
);
$query->set( 'meta_query', $meta_query );
$query->set( 'orderby', 'meta_value_num' );
Note: This solution will only work with WP >= 3.9 as NOT EXISTS
only works with 3.5 and greater and there was a bug with NOT EXISTS
which has been fixed in 3.9!