posts_

A History of WordPress Search

(and Why Default Search Falls Short)

Don MacKinnon

On-site search has always been one of those features that WordPress ships out of the box — quietly functional, rarely celebrated, and easily overlooked until it becomes a problem.

For years, most WordPress sites could get away with default search because external discovery did the heavy lifting. Google sent traffic, users landed on the right page, and internal search was an afterthought. That dynamic is shifting.

Google's own rollout of AI Overviews in 2024 introduced AI-generated summaries directly into search results, a move Google describes as helping users find information faster. Independent research paints a more complex picture for publishers. A 2025 Pew Research Center study found that Google users are less likely to click through to websites when AI summaries appear. SparkToro's 2024 zero-click study reported that for every 1,000 U.S. Google searches, only 374 clicks go to the open web.

None of this means external SEO is dead. It does mean that when visitors do arrive on your site, their ability to find more of your content — through internal navigation and on-site search — matters more than it used to. For publishers, membership sites, documentation hubs, and content-heavy WordPress installations, on-site content discovery has become a retention and engagement tool, not just a utility.

That raises a practical question: how does WordPress search actually work, and is it up to the job?

This post answers that in detail. We will walk through the mechanics of WordPress core search, trace its evolution across major releases, identify where its design tradeoffs create real-world limitations, and outline practical options for improving or replacing it — whether you are a developer maintaining a single site or an agency managing dozens.

What "WordPress Search" Means in Core

When someone types a query into a WordPress search form and submits it, what actually happens? The answer lives almost entirely inside WP_Query, the class that powers the vast majority of content queries in WordPress.

The Search Pipeline

Here is how a default search request flows through WordPress core:

User query ("s=onion")
       │
       ▼
┌─────────────────────┐
│   WP_Query          │
│   parse_search()    │──► Generates WHERE clause
│                     │    (SQL LIKE on post_title,
│                     │     post_excerpt, post_content)
└─────────┬───────────┘
          │
          ▼
┌─────────────────────┐
│   parse_search_     │
│   order()           │──► Generates ORDER BY clause
│                     │    (CASE-based heuristic ranking)
└─────────┬───────────┘
          │
          ▼
┌─────────────────────┐
│   MySQL             │
│   wp_posts table    │──► Executes query against
│                     │    the posts table
└─────────┬───────────┘
          │
          ▼
┌─────────────────────┐
│   Results           │──► Post objects returned
│   (post_type,       │    to the template layer
│    post_status      │
│    filtered)        │
└─────────────────────┘

The entire search operation happens within a single SQL query against the wp_posts table. There is no separate search index, no scoring engine, and no preprocessing of content. It is a direct database query.

The Default Fields WordPress Searches (and What It Doesn't)

By default, WP_Query::parse_search() searches three columns in the wp_posts table:

  • post_title
  • post_excerpt
  • post_content

That is the full scope. WordPress default search does not look at:

  • Custom fields (post meta), including ACF fields
  • Taxonomy terms (categories, tags, custom taxonomies)
  • Author names
  • Comments
  • Rendered block content (it searches the raw post_content column, which contains block markup)
  • Attached media filenames or alt text

This design is intentional. WordPress core search is built for simplicity and broad compatibility. It works against the standard post table with no assumptions about what plugins, themes, or custom fields exist on any given installation.

As WordPress VIP's documentation notes, the resulting SQL for a search like /?s=onion looks roughly like this:

SELECT wp_posts.ID
FROM wp_posts
WHERE 1=1
  AND (
    (wp_posts.post_title LIKE '%onion%')
    OR (wp_posts.post_excerpt LIKE '%onion%')
    OR (wp_posts.post_content LIKE '%onion%')
  )
  AND wp_posts.post_type IN ('post', 'page')
  AND (wp_posts.post_status = 'publish')
ORDER BY wp_posts.post_title LIKE '%onion%' DESC,
         wp_posts.post_date DESC
LIMIT 10

Matching Strategy: SQL LIKE and Wildcards

WordPress uses SQL LIKE with leading and trailing wildcards (%term%) for matching. This means it performs substring matching — a search for "press" will match "WordPress," "express," and "pressure."

When the exact query argument is set, WordPress drops the wildcards and performs a full-value match instead. By default, exact is not set, so all searches are substring-based.

For multi-word queries, WordPress splits the search string into individual terms (respecting quoted phrases) and requires all terms to match across the searched columns. Each term must appear in at least one of the three columns. Terms prefixed with - are treated as exclusions (since WordPress 4.7).

The LIKE '%term%' pattern has a well-documented performance implication: because the wildcard appears at the start of the pattern, MySQL cannot use standard B-tree indexes for this query. As the MySQL 8.0 documentation on range optimization explains, a LIKE condition is only usable as a range condition when the pattern does not start with a wildcard character. This means every search query requires MySQL to perform a full scan of the matched columns, which can become costly as the wp_posts table grows.

A default WordPress installation does not create FULLTEXT indexes on these columns. For small databases, this is rarely a visible problem. For sites with tens of thousands of posts or more, search query times can increase noticeably.

Ordering Strategy: Heuristic "Relevance"

WordPress does not use a scoring algorithm like TF-IDF or BM25. Instead, WP_Query::parse_search_order() builds a CASE-based ordering heuristic that assigns priority tiers:

  1. Tier 1 — Full search phrase found in post_title
  2. Tier 2 — All individual search terms found in post_title
  3. Tier 3 — Any individual search term found in post_title
  4. Tier 4 — Full search phrase found in post_excerpt
  5. Tier 5 — Full search phrase found in post_content
  6. Tier 6 — Everything else

Within each tier, posts are sorted by post_date (newest first). For single-term searches, the ordering is simpler: it sorts by whether the title matches, then by date.

This heuristic works reasonably well for basic use cases: if you search for something that appears in a post title, that post will tend to float to the top. But the system has no concept of term frequency, field weighting, or distance between matched terms. A post where the search term appears once in a 10,000-word article ranks the same as a post where it appears in every paragraph — as long as both fall into the same tier.

So what?

  • WordPress search queries three columns using substring matching with no index support by default.
  • The "relevance" ordering is a simple tiered heuristic, not a scoring algorithm.
  • Custom fields, taxonomies, and metadata are entirely outside the scope of default search.

A Short History of WordPress Search: Milestones That Matter

WordPress search has evolved incrementally. The changes have been meaningful but infrequent, and the core architecture — a LIKE-based query against wp_posts — has remained fundamentally the same since the feature's inception. Here are the milestones that matter most for developers.

WordPress 3.7.0 (October 2013) — parse_search() and parse_search_order() Introduced

WordPress 3.7 formalized the search SQL generation into two dedicated methods inside WP_Query: parse_search() (responsible for generating the WHERE clause) and parse_search_order() (responsible for the ORDER BY clause). Before 3.7, this logic was inlined within WP_Query::get_posts(). Extracting it into named methods made the search behavior more transparent and easier for developers to trace and understand, though it did not change what was searched or how results were ranked.

WordPress 4.7.0 (December 2016) — Exclusion Prefix Filter

WordPress 4.7 introduced the wp_query_search_exclusion_prefix filter, which enabled the - prefix for excluding terms from search results. Searching for recipes -vegan now excludes posts containing "vegan." The filter also allows developers to change or disable the exclusion prefix entirely.

WordPress 6.2.0 (March 2023) — search_columns Argument and post_search_columns Filter

WordPress 6.2 was the most significant recent change to the search system. It introduced the search_columns argument for WP_Query, allowing developers to specify which of the three default columns (post_title, post_excerpt, post_content) to include in a search query. Alongside it, the post_search_columns filter was added, enabling programmatic control over search columns on a per-query basis.

This was a practical improvement. Before 6.2, narrowing the searched columns required hooking into the raw SQL via the posts_search filter — a powerful but fragile approach. The search_columns argument provides a supported, forward-compatible way to control search scope without touching SQL.

Post-6.2: Incremental Improvements

Subsequent WordPress releases have not introduced major structural changes to the search system. Minor improvements to query parsing and edge-case handling have appeared, but the fundamental architecture — LIKE-based matching against post_title, post_excerpt, and post_content with heuristic ordering — remains unchanged as of WordPress 6.7.

So what?

  • WordPress search has had exactly three notable milestones in over a decade: structured methods (3.7), exclusion support (4.7), and column control (6.2).
  • The core search architecture has not fundamentally changed. The improvements have been about developer ergonomics, not search capability.

The Core Limitations (and Why They Matter on Real Sites)

Understanding the mechanics makes it easier to see where WordPress default search creates practical problems. These are not bugs — they are design tradeoffs that become limitations as sites grow in complexity and content volume.

Limited Content Coverage

As discussed above, WordPress only searches post_title, post_excerpt, and post_content. For sites that store significant content in custom fields — product specifications, event dates, location data, ACF-managed structured content — this means a large portion of the site's searchable information is invisible to the search system.

Taxonomy terms are similarly excluded. A post tagged with "JavaScript" will not appear in a search for "JavaScript" unless that word also appears in the title, excerpt, or body. For sites that rely heavily on taxonomies for content organization, this is a meaningful gap.

Relevance Is Heuristic and Hard to Tune

The tier-based ordering system provides a rough approximation of relevance. But it offers no way to weight fields differently (for instance, giving post_title matches more importance than post_content matches), no term-frequency awareness, and no way to incorporate external signals like popularity, recency weighting, or editorial boosting.

For a blog with a few hundred posts, the heuristic often produces reasonable results. For a documentation site, a knowledge base, or a publication with thousands of articles across many topics, the lack of tunable relevance means search results often feel "close but not quite right."

Performance and Scaling Constraints

The %term% wildcard pattern means that every search query is, at the database level, effectively a full table scan of the searched columns. WordPress does not create FULLTEXT indexes by default, and even adding them would not help with LIKE-based queries (they serve different query types).

On sites with a few thousand posts, this is often not noticeable. On sites with tens or hundreds of thousands of posts, or on shared hosting environments where database resources are constrained, search queries can become measurably slow. Complex queries — multi-term searches, or searches combined with taxonomy or meta filtering — compound the issue because they add additional JOIN and WHERE conditions to an already-expensive query.

UX Limitations

WordPress default search provides no built-in support for features that users increasingly expect from search interfaces:

  • No autocomplete or "search-as-you-type" suggestions
  • No faceted filtering (by category, date range, post type, etc.)
  • No "did you mean?" or typo tolerance
  • No "no results" recovery (suggested content, related posts)
  • No result highlighting or snippet previews

These are frontend concerns, and it is entirely possible to build some of them on top of default search with custom code. But the backend does not provide the signals (like relevance scores or facet counts) that make these features performant and useful.

No First-Class Analytics Loop

WordPress does not track what users search for, what they click, or what searches return zero results. Without this data, there is no feedback loop to identify content gaps, improve relevance, or understand how visitors are trying to navigate the site.

Analytics can be added via plugins or custom logging, but it is not part of core search, which means most WordPress sites have no visibility into their search performance at all.

So what?

  • Custom fields and taxonomies — often containing the most structured, specific content on a site — are invisible to default search.
  • The relevance system cannot be tuned, weighted, or extended without modifying SQL directly.
  • Performance degrades predictably as content volume grows.
  • Modern search UX patterns (autocomplete, facets, typo tolerance) have no backend support in core.

Why Default WordPress Search Is Inadequate for Modern Content Discovery

The limitations above are not abstract. They connect directly to outcomes that WordPress developers and agencies deal with regularly.

When search does not cover custom fields, users searching for a product specification, a staff member's name, or a location will get no results — even though the content exists. Zero-result searches are one of the highest-friction moments in a user's experience and a common driver of site abandonment.

When relevance is poor, users see results that are technically correct but practically unhelpful. A search for "pricing" that surfaces a three-year-old blog post mentioning the word once, instead of the current pricing page, erodes confidence in the site's ability to help.

When search is slow, users notice. Even a one- or two-second delay on a search results page creates a perception of poor quality. On sites where search is a primary navigation tool — documentation sites, support portals, directories — this directly impacts whether users find what they need.

And without analytics, teams have no way to know whether any of these problems are happening, how often, or for which queries.

For a personal blog or a brochure site with a handful of pages, default search is fine. For content-rich WordPress installations where on-site discovery matters — publishers, membership sites, knowledge bases, directories, multi-author publications, support portals — the tradeoffs that make default search simple and compatible are the same tradeoffs that make it inadequate.

What You Can Do Instead

There is no single right answer for every site. The right approach depends on your content volume, the complexity of your data model, your performance requirements, and how much maintenance overhead you can absorb. Here is how to think about the options, from lightest to most involved.

Option 1: Improve Core Search Using WordPress Hooks and Arguments

WordPress provides several hooks and arguments that let you adjust search behavior without replacing the search system entirely. For sites with small-to-medium content volumes and straightforward data models, these can meaningfully improve results.

Using search_columns (WordPress 6.2+)

The search_columns argument lets you narrow which columns WP_Query searches. For example, if you want search to only match against post titles (useful for directory-style lookups):

$query = new WP_Query( array(
    's'              => 'pricing',
    'search_columns' => array( 'post_title' ),
) );

You can also use the post_search_columns filter to apply this globally or conditionally:

add_filter( 'post_search_columns', function( $columns, $search, $query ) {
    if ( ! is_admin() && $query->is_main_query() && $query->is_search() ) {
        // Only search titles and excerpts on the frontend
        return array( 'post_title', 'post_excerpt' );
    }
    return $columns;
}, 10, 3 );

Tradeoffs: This is clean, supported, and forward-compatible. But it only lets you restrict the default columns — you cannot add new columns (like post meta) this way, and it does not change how results are ordered.

Using the posts_search Filter

The posts_search filter gives you access to the raw SQL WHERE clause that WordPress generates for search. This is the most powerful customization point, but also the most fragile.

add_filter( 'posts_search', function( $search, $query ) {
    if ( ! is_admin() && $query->is_main_query() && $query->is_search() ) {
        global $wpdb;
        $term = $wpdb->esc_like( $query->get( 's' ) );
        // Add taxonomy term name matching (example only — test thoroughly)
        $search .= $wpdb->prepare(
            " OR ({$wpdb->posts}.ID IN (
                SELECT tr.object_id FROM {$wpdb->term_relationships} tr
                INNER JOIN {$wpdb->term_taxonomy} tt ON tr.term_taxonomy_id = tt.term_taxonomy_id
                INNER JOIN {$wpdb->terms} t ON tt.term_id = t.term_id
                WHERE t.name LIKE %s
            ))",
            '%' . $term . '%'
        );
    }
    return $search;
}, 10, 2 );

Tradeoffs: This works, but you are now responsible for SQL correctness, escaping, and performance. Subqueries against the terms tables add overhead. This approach can be useful for targeted improvements but becomes difficult to maintain as complexity grows. Test thoroughly in staging before deploying.

Option 2: Use a WordPress Search Plugin

Several plugins add an indexing layer on top of or alongside the WordPress database, improving both coverage and relevance without requiring custom code. Options in this category include Relevanssi, SearchWP, and Jetpack Search, among others.

These plugins generally work by building a secondary index that includes custom fields, taxonomies, and other content types. They replace the default WP_Query search behavior with their own query logic, providing features like field weighting, fuzzy matching, and result highlighting.

The tradeoff is that they add database overhead (for locally-indexed plugins) or introduce a dependency on an external service (for cloud-indexed plugins). They also vary significantly in performance characteristics, feature depth, and maintenance requirements.

For agencies managing multiple client sites, the key consideration is often operational consistency: how easy is a plugin to configure across many installations, and how much ongoing tuning does it require?

Option 3: Use a Dedicated Search Engine

For sites where search is a core part of the user experience — high-traffic publications, large directories, documentation platforms, e-commerce catalogs — teams sometimes choose to offload search from the WordPress database entirely.

Dedicated search engines (whether self-hosted options like Elasticsearch, Meilisearch, or Typesense, or hosted services) maintain their own indexes, provide purpose-built relevance algorithms, and are designed to handle the query patterns and volumes that general-purpose databases are not optimized for.

The main advantages are performance consistency at scale, advanced relevance tuning (field weighting, synonyms, typo tolerance, faceted search), and a clean separation of concerns — your WordPress database handles content management, and the search engine handles content discovery.

The tradeoffs are real: added infrastructure complexity, an indexing pipeline to maintain, and a dependency on an additional service. For teams with the resources and the need, this separation often pays for itself in search quality and operational predictability.

Decision Checklist: When to Move Beyond Default Search

Not every site needs a search overhaul. Here is a practical checklist to help you assess whether your current search setup is limiting your site.

You should consider improving or replacing default search if:

  • Your site has more than a few hundred posts and search performance has noticeably declined.
  • Important content lives in custom fields (ACF, meta boxes, custom post type fields) that default search cannot reach.
  • Users frequently report that search "does not work" or returns irrelevant results.
  • You rely on taxonomies for content organization, but taxonomy terms do not influence search results.
  • Your site serves as a knowledge base, documentation hub, or support portal where search is a primary navigation tool.
  • You have no visibility into what users are searching for or how often searches return zero results.
  • You need features like autocomplete, faceted filtering, or typo tolerance that default search does not support.
  • You manage multiple client sites and need a repeatable, low-maintenance search solution.

Default search is likely fine if:

  • Your site has a small number of pages or posts (under a few hundred).
  • Content is primarily in post titles and body text (not custom fields or taxonomies).
  • Search is a secondary navigation tool, not a primary one.
  • You are on a tight budget and have minimal search-related user complaints.

Implementation Spotlight: Searchcraft for WordPress

Searchcraft is a search engine designed to replace default WordPress search with a dedicated, externally indexed search layer. It is one option in the category of dedicated search engines discussed above.

What it replaces: The Searchcraft WordPress plugin is positioned as a drop-in replacement for default WordPress search. Once configured, search queries are routed to Searchcraft's index instead of the WordPress database.

How indexing works: Post and page content is sent to the Searchcraft API for indexing on an opt-in basis. Index data is stored remotely — the plugin does not add data or tables to your WordPress database. No user data or site content is shared with third parties.

What it supports:

  • Instant search results with multiple layout options, including pop-over and faceted search
  • Custom post types and custom taxonomies
  • Customizable search fields and weighting
  • Synonyms, stopwords, and search analytics (configured via Searchcraft Cloud)
  • Works with Searchcraft Cloud (hosted) or self-hosted Searchcraft Core (manual configuration required)

What it does not support: WooCommerce is not supported at this time. The plugin is designed for standard WordPress posts, pages, and custom post types.

Where to learn more:

Conclusion: WordPress Search Is a Solid Baseline — Until It Isn't

WordPress default search does exactly what it was designed to do: provide a simple, compatible, zero-configuration search experience that works out of the box on any WordPress installation. For many sites, that is enough.

The design tradeoffs that enable this simplicity — searching only three columns, using substring matching without indexes, applying a basic ordering heuristic — are reasonable defaults. They become limitations when content models grow beyond simple posts, when content volumes reach the thousands, when users expect modern search UX, or when on-site discovery becomes a business-critical function.

The good news is that the path from default search to something better is well-established. WordPress provides hooks for targeted improvements. Search plugins add indexing and relevance. Dedicated search engines provide the performance, features, and analytics that content-heavy sites require.

The first step is measurement: understand what your users are searching for, whether they are finding it, and where the friction lives. From there, the right level of investment becomes clearer.

Frequently Asked Questions

How does WordPress search work by default?
WordPress default search uses WP_Query to run a SQL LIKE query against three columns in the wp_posts table: post_title, post_excerpt, and post_content. Results are ordered using a heuristic that prioritizes title matches, then falls back to date order.

Why is WordPress search slow on large sites?
WordPress uses LIKE '%term%' patterns for search matching. Because the wildcard appears at the start of the pattern, MySQL cannot use standard B-tree indexes, often resulting in a full table scan. This tends to become noticeable as the wp_posts table grows into the tens of thousands of rows or more.

Does WordPress search include custom fields or ACF data?
No. By default, WordPress only searches post_title, post_excerpt, and post_content. Custom fields (including ACF fields), taxonomy terms, and other metadata are not included. You can extend search to include these using the posts_search filter or a search plugin.

What changed in WordPress 6.2 for search?
WordPress 6.2 introduced the search_columns argument for WP_Query and the post_search_columns filter, allowing developers to control which of the three default columns are searched. This was the most significant search improvement in recent WordPress releases.

Can I improve WordPress search without a plugin?
Yes, to a degree. WordPress provides the search_columns argument (6.2+), the post_search_columns filter, and the posts_search filter for customizing search behavior. These are effective for targeted improvements but have limits — particularly around relevance scoring, performance at scale, and modern UX features.

When should I replace WordPress default search?
Consider replacing default search when your site relies on custom fields or taxonomies for important content, when search performance has degraded, when you need features like autocomplete or faceted filtering, or when you have no visibility into search analytics. The decision depends on your content model, traffic, and how central search is to your users' experience.

enterprise pilots_

Your Mission Awaits

The next frontier of discovery is here, ready for you. Your users deserve search experiences that delight, engage, and convert. Your developers deserve tools that accelerate velocity, not create friction. And your bottom line deserves technology that drives revenue, not bloated bills.

Searchcraft is your vessel. Built by developers, for developers, it’s powerful enough for hyperscale infrastructure, simple enough to deploy in minutes, and lean enough to cut your infrastructure spend by 40%.

Strap in, spin up, and prepare for liftoff.

Contact the Crew for Enterprise Plans

Searchcraft only uses your personal information to administer your account and provide the products and services you requested. To stay up to date on the latest product enhancements and features, check the box below:

By clicking submit, you consent to allow Searchcraft to store and process the personal information above.

Thank you.
A Searchcraft crew member will be in touch soon.
Something went wrong. Please try that again.