Searching is a vital feature on most WordPress sites. But sometimes those results can get cluttered with irrelevant entries or private pages you‘d rather not surface publicly.
In this guide, I‘ll show you how to take control of search with the powerful pre_get_posts
filter in WordPress. We‘ll look at how to limit results to specific post types, like posts, pages, or custom types.
As a developer with over 15 years experience building on WordPress, I‘ve used pre_get_posts
countless times to improve search and filter content. Read on as I share my best tips and tricks!
Contents
What is pre_get_posts and Why Should You Care?
The pre_get_posts
action first appeared way back in WordPress 2.1. It allows you to modify the main WordPress query before it executes. This opens up so many possibilities!
With pre_get_posts
you can alter the query variables that control:
- Which posts, pages or custom post types are retrieved
- The number of results
- Ordering, like reverse chronological
- And more…
For search queries, we can use pre_get_posts
to restrict results only to certain post types. This is perfect for improving relevance or hiding private content.
Let‘s look at a basic usage example:
function limit_search($query) {
if ($query->is_search && !is_admin() ) {
$query->set(‘post_type‘, array(‘post‘));
}
return $query;
}
add_filter(‘pre_get_posts‘,‘limit_search‘);
Here we check if it‘s a front-end search query, then limit results only to regular blog posts.
How to Filter Search Results by Post Type
The key is using $query->set(‘post_type‘)
and passing an array of allowed post types:
$query->set(‘post_type‘, array(‘post‘, ‘page‘));
This would restrict search to just posts and pages.
You can also use custom post types defined by plugins or your theme:
$query->set(‘post_type‘, array(‘post‘, ‘movies‘));
And exclude post types like this:
$query->set(‘post_type‘, array(‘post‘, ‘page‘, -‘attachment‘));
The minus sign -
in front of attachment
keeps attachments out of search results.
Limiting search results to just blog posts, excluding other post types
Why Would You Want to Limit Search by Post Type?
There are a few good reasons to filter search results this way:
-
Improving relevance by focusing on specific content types.
-
Hiding private or unfinished drafts from search results.
-
Removing media attachments from cluttering up results.
-
Excluding custom post types that you don‘t want to be searchable.
Personally, I‘ve used search filters like this on client sites many times over the years. It‘s an easy way to fine-tune search without complex custom code.
Things to Keep in Mind When Filtering Search
Here are a few tips to make sure your custom search filters work smoothly:
-
Test filters thoroughly – log out and search as a subscriber. Remember admins may still see all post types.
-
Check paginated search results too. Your filters apply to paging navigation as well.
-
Watch for plugin conflicts. Deactivate other plugins to isolate issues.
-
Consider accessibility and SEO when limiting search types.
-
For more advanced filtering, try SearchWP or Relevanssi.
Real-World Examples From 15 Years Working With WordPress
Over my many years building WordPress sites, I‘ve used pre_get_posts
to solve search issues countless times. Here are just a couple examples:
-
On an ecommerce site, we filtered search to only
product
post types – excluding orders, docs, etc. This made finding products much easier. -
For a magazine site, search was cluttered with old attachments and non-public content. Filters cleaned it up.
Don‘t be afraid to experiment with different post type arrays to get search working just right!
Summary
I hope this guide has shown how powerful pre_get_posts
can be for fine-tuning WordPress search. Limiting results by post types helps improve relevance and hide unwanted content.
The key is defining an allowed array like:
$query->set(‘post_type‘, array(‘post‘, ‘page‘));
And optionally excluding types:
$query->set(‘post_type‘, array(‘post‘, ‘page‘, -‘attachment‘));
Be sure to test thoroughly and watch for pagination and plugin issues. Happy searching!