Including categories in search results

I am trying to include categories in search results. I’ve been searching for hours now with no solution.

By “including categories” I don’t mean search in a certain category, I mean let’s say I have a bicycle store and have many companies included in the site; a user searched for BMX mountain cross for example. It will return the category BMX first (by clicking you’ll be sent to the category page) and the posts related to the search term like WordPress normally does.

Read More

Does anyone have any clues or could point me to the right direction?

Related posts

Leave a Reply

7 comments

  1. I’m using this code in my search.php above the main loop:

    $search_term = explode( ' ', get_search_query( false ) );   
    global $wpdb;
    $select = "
    SELECT DISTINCT t.*, tt.* 
    FROM wp_terms AS t 
    INNER JOIN wp_term_taxonomy AS tt 
    ON t.term_id = tt.term_id 
    WHERE tt.taxonomy IN ('category')";      
    $first = true;
    foreach ( $search_term as $s ){
        if ( $first ){
            $select .= " AND (t.name LIKE '%s')";
            $string_replace[] = '%'.$wpdb->esc_like( $s ).'%';
            $first = false;
        }else{
            $select .= " OR (t.name LIKE '%s')";
            $string_replace[] = '%'. $wpdb->esc_like( $s ).'%';
        }
    }
    $select .= " ORDER BY t.name ASC";
    $terms = $wpdb->get_results( $wpdb->prepare( $select, $string_replace ) );
    if ( count($terms) > 0 ){
        echo '<ul>';
        foreach ( $terms as $term ) {
            echo '<li><a href="'.esc_url( get_term_link( $term ) ).'" title="'.esc_attr( $term->name ).'">' . esc_html( $term->name ) . '</a></li>';
        }
        echo '</ul>';
    }
    

    This code does an extra DB query, but search for categories not only associated to returned posts, but does an extra seach for each word in a search term and brings all found categories – even empty.

  2. Use get_terms(), then you don’t need to use a custom query to the database.

    $terms = get_terms( 'category', array(
        'name__like' => $s,
        'hide_empty' => true // Optional 
    ) );
    if ( count($terms) > 0 ){
        echo '<ul>';
        foreach ( $terms as $term ) {
            echo '<li><a href="' . esc_url( get_term_link( $term ) ) . '" title="' . esc_attr( $term->name ) . '">' . esc_html( $term->name ) . '</a></li>';
        }
        echo '</ul>';
    }
    

    Based on birgire‘s answer on a similar question: https://wordpress.stackexchange.com/a/239680/50432

  3. I’ve created a custom search results page that matches the keyword (s) with categories, posts, cpt’s…

    Here’s sthe code for the categories (it also shows a category ACF field for images:

    <?php
        // post categories in results
        $terms = get_terms( 'post', array(
            'name__like' => $s,
            'hide_empty' => false // Optional 
        ) );
    ?>
    <?php
    // list post categories in results
    if ( count($terms) > 0 ) {
        echo '<div class="sr-categories">';
        echo '<h3 class="search-title">Category results</h3>';
    ?>
    <div class="posts-wrap posts-layout-default  row">
        <?php
            foreach ( $terms as $term ) { ?>
    
            <?php
                echo '<article class="sub-cat-row col-md-4 col-sm-6 col-xs-6 col-xxs-12">';
                echo '<a href="' . esc_url( get_term_link( $term ) ) . '" title="' . esc_attr( $term->name ) . '">';
    
                $taximg_id = get_field('image', $term);
                $taxsize = "grid-image"; // (thumbnail, medium, large, full or custom size)
                $taximage = wp_get_attachment_image_src( $taximg_id, $taxsize );
    
                if($taximg_id) { ?>
                    <img src="<?php echo $taximage[0]; ?>" alt="" class="img-responsive" />
                <?php } else { ?>
                    <img src="<?php echo get_stylesheet_directory_uri(); ?>/assets/images/default-image-600x400.png" alt="" title="" />
                <?php }
    
                echo '<div class="sc-title text-center">' . esc_html( $term->name ) . '</div></a>';
                echo '</article>';
    
                //get_template_part('template-parts/loop/content','listevents');
                wp_reset_postdata();
            }
    
         ?>
    </div>
    <?php echo '</div>'; // eof sr-events
    } else {
        echo 'No Event categories found';
    }
    ?>
    
  4. Obviously possible, if it works like this, I’m using TwentyTwelve, you have to edit search.php. You will find the loop there:

    <?php while ( have_posts() ) : the_post(); ?>
    <?php get_template_part( 'content', get_post_format() ); ?>
    <?php endwhile; ?>
    

    So, the loop is taking the post_format(). So you have to edit content.php. Here you will find these:

    <?php if ( is_search() ) : // Only display Excerpts for Search ?>
    <div class="entry-summary">
    <?php the_excerpt(); ?>
    </div><!-- .entry-summary -->
    

    Just change that to:

    <?php if ( is_search() ) : // Only display Excerpts for Search ?>
    <div class="entry-summary">
    <?php the_category(); ?><br/>
    <?php the_excerpt(); ?>
    </div><!-- .entry-summary -->
    

    If everything goes right, than it will echo the Category associated the search result. But if everything goes right like we want. 🙂

  5. Based on the @PhilOwen answer, I added the following to the top of my theme’s search.php page:

    // post categories in results
    $terms = get_terms( 'taxonomy-goes-here', array(
      'name__like' => $s,
      'hide_empty' => false // Optional
    ) );
    
    if ( count($terms) > 0 ) {
      foreach ( $terms as $term ) {
        echo '<h2><a href="' . esc_url( get_term_link( $term ) ) . '" title="' . esc_attr( $term->name ) . '">';
        echo esc_html( $term->name );
        echo '</a></h2>';
      }
    }
    

    I think it will often make sense to display the taxonomy term matches–if they exist–above the specific items, as they would be higher up in the hierarchy of data.

  6. I found a better way and wanted to share
    no need that use $wpdb
    this code work for me:

    $val = get_search_query();
    $categories = get_terms( ['taxonomy' => 'product_cat'] );
        foreach($categories as $cat){
        if (stristr($cat->name , $val)){
            echo '<tr><td><a href="'.get_term_link( $cat ).'" >' .$cat->name.'</a></td></tr>';
            break;
    }
    

    this code search in product category and It does not need to be exactly the same

  7. PROBLEM: As of march 2022, wordpress doesn’t search for category or tag.

    SOLUTION/WORKAROUND: Use a plugin to allow searching for category or tag. I’ve tested it with the free version of the Relevanssi-Plugin. https://www.relevanssi.com/features/. Other Plugins may work, too.

    DISCLAIMER: I am not affiliated with relevanssi or any other wp search plugin vendor.