I am trying to customize the search results for a generic search, but only if it’s using the search.php
template. I have other searches on my site, and I don’t want this filter interfering with them. Everything works on the following code, except for is_page_template('search.php')
.
Once I enter that line of code as a condition, it just reverts to the normal search filtering, because my IF condition is failing. How do I only run my code if we’re on the search.php
page?
//Filter the search for only posts and parts
function SearchFilter($query)
{
if ($query->is_search && is_page_template('search')) {
$query->set('post_type', array('post', 'parts'));
$query->set('meta_key', 'Manufacturer');
$query->set('orderby', 'meta_value');
$query->set('order', 'ASC');
}
return $query;
}
add_filter('pre_get_posts', 'SearchFilter');
Lets break it down step by step:
if ($query->is_search && is_page_template('search')) {
There are 3 problems here
is_page_template
search.php
isn’t a page template, that’s not how the search template is loaded. So this won’t work.
But if it did work, there’s a new problem. Functions such as is_page_template
etc rely on the main query, but we’re in a pre_get_posts
filter, you don’t know if that query has been set yet, or if you’re filtering that query or another.
So we need to:
- remove the
is_page_template
check, it doesn’t do what you think it does
- Add an
$query->is_main_query()
check so the filter doesn’t interfere with widgets and other queries
Methods vs member variables
if ($query->is_search
This doesn’t work, and should be generating PHP warnings for you. The problem is that is_search
is a function/method not a variable, it should be:
if ( $query->is_search() && $query->is_main_query() ) {
But search.php
?
WordPress decides which template is loaded based on the main query. If it’s the main query, and is_search
is true, then search.php
will be loaded.
Because of this, WordPress hasn’t decided which template to use when your filter happens. In fact, you can make WordPress change which template it loads by modifying the query variables. For example, if you unset all the variables, and tell it to load a single post, you won’t get search.php
, or an archive at all, you’re likely to get single.php
instead
What About Search Queries in Page Templates?
is_main_query
will be false, so not an issue