Blog / WordPress/ Complete Guide: Make WordPress Search Only Post Titles (Updated)

Complete Guide: Make WordPress Search Only Post Titles (Updated)

WordPress 实现只搜索文章标题的完整方法(更新)

The Limitations of WordPress Default Search

WordPress's default search function simultaneously retrieves content from post titles, content, tags, and other fields. While this provides broad coverage, it can sometimes lead to imprecise search results, surfacing many articles with low relevance to the keywords, which negatively impacts user experience.

Solution: Modifying the Search Logic

By adding custom code to your theme's functions.php file, you can modify the WordPress search query to match only post titles. This is the most direct and effective method.

Core Code Implementation

Add the following code to the end of your current theme's functions.php file:

/**
 * Modify WordPress search to search only post titles.
 *
 * @param string   $search   The search WHERE clause in the SQL query.
 * @param WP_Query $wp_query The WP_Query object.
 * @return string  Modified WHERE clause.
 */
function wp_search_by_title_only($search, $wp_query) {
    global $wpdb;

    // Skip if search term is empty.
    if (empty($search)) {
        return $search;
    }

    $query_vars = $wp_query->query_vars;
    // Determine if exact match is requested to decide on wildcard usage.
    $wildcard_prefix = empty($query_vars['exact']) ? '%' : '';
    $search_terms = $query_vars['search_terms'];

    $title_search = '';
    $search_and = '';

    // Loop through search terms to build LIKE queries for titles.
    foreach ((array) $search_terms as $term) {
        // Use $wpdb method for safe string handling to prevent SQL injection.
        $escaped_term = $wpdb->esc_like($term);
        $title_search .= $search_and . "($wpdb->posts.post_title LIKE '" . $wildcard_prefix . $escaped_term . $wildcard_prefix . "')";
        $search_and = ' AND ';
    }

    if (!empty($title_search)) {
        // Replace the original search condition with the title-specific one.
        $search = " AND (" . $title_search . ") ";

        // Optional: Filter out password-protected posts for non-logged-in users.
        if (!is_user_logged_in()) {
            $search .= " AND ($wpdb->posts.post_password = '')";
        }
    }

    return $search;
}
// Add filter with priority 500 to run after other plugins.
add_filter('posts_search', 'wp_search_by_title_only', 500, 2);

Code Explanation & Notes

  • Function Name: Changed from __search_by_title_only to wp_search_by_title_only to avoid using a double underscore prefix (typically reserved for PHP magic methods).
  • Security: Uses $wpdb->esc_like() instead of the deprecated like_escape() function to ensure query safety.
  • Clarity: Optimized variable naming and code structure with detailed comments.
  • Activation: Takes effect immediately after saving. All front-end searches on your site will match only post titles.
  • Scope: This modification affects all search forms on the site (including widgets and forms generated by get_search_form()).

Alternative: Using a Search Plugin

If you are uncomfortable editing code or desire more flexible configuration options (e.g., searching titles and specific custom fields simultaneously), consider using a professional search plugin such as:

  • Relevanssi
  • SearchWP
  • WP Extended Search

These plugins typically provide a backend interface for easily configuring search weight and scope, offering more powerful features.

Summary

Using the code modification above, you can quickly refine WordPress search to target only post titles, thereby improving result relevance and user experience. Before implementation, it is recommended to back up your functions.php file or use a child theme for safety.

Post a Comment

Your email will not be published. Required fields are marked with *.