# "Did You Mean" Suggestions for Empty Searches

> When a search finds nothing, suggests a corrected spelling based on the words in your post titles, such as "Did you mean chocolate brownies?", with a link to search again.

- Type: PHP
- Runs: Run everywhere
- Category: [Search](https://wpide.com/library/category/search/)
- Tags: search, spelling, suggestions
- Author: WPIDE Team
- Installs: 0
- Updated: 2026-10-28
- Page: https://wpide.com/library/did-you-mean-search-suggestions/

## Code

```php
// Text before the suggestion.
$wpide_dym_label = 'Did you mean';

$wpide_dym_vocabulary = function () {
    $words = get_transient( 'wpide_dym_words' );

    if ( is_array( $words ) ) {
        return $words;
    }

    global $wpdb;

    $types  = array_values( get_post_types( array( 'exclude_from_search' => false ) ) );
    $holder = implode( ',', array_fill( 0, count( $types ), '%s' ) );
    $titles = $wpdb->get_col( $wpdb->prepare( "SELECT post_title FROM {$wpdb->posts} WHERE post_status = 'publish' AND post_type IN ($holder) ORDER BY post_date DESC LIMIT 3000", $types ) ); // phpcs:ignore WordPress.DB

    $words = array();

    foreach ( $titles as $title ) {
        foreach ( preg_split( '/[^\p{L}\p{N}]+/u', strtolower( $title ), -1, PREG_SPLIT_NO_EMPTY ) as $word ) {
            if ( strlen( $word ) > 2 ) {
                $words[ $word ] = true;
            }
        }
    }

    $words = array_keys( $words );
    set_transient( 'wpide_dym_words', $words, DAY_IN_SECONDS );

    return $words;
};

add_action( 'save_post', function ( $post_id, $post ) {
    if ( 'publish' === $post->post_status ) {
        delete_transient( 'wpide_dym_words' );
    }
}, 10, 2 );

$wpide_dym_html = function () use ( $wpide_dym_vocabulary, $wpide_dym_label ) {
    static $html = null;

    if ( null !== $html ) {
        return $html;
    }

    $html  = '';
    $terms = (array) get_query_var( 'search_terms' );
    $vocab = $wpide_dym_vocabulary();

    if ( ! $terms || ! $vocab || count( $terms ) > 6 ) {
        return $html;
    }

    $lookup  = array_flip( $vocab );
    $changed = false;
    $fixed   = array();

    foreach ( $terms as $term ) {
        $term = strtolower( $term );
        $best = $term;

        if ( strlen( $term ) > 3 && ! isset( $lookup[ $term ] ) ) {
            // Allow 1 typo in short words and 2 in longer ones.
            $limit = strlen( $term ) >= 7 ? 2 : 1;
            $score = $limit + 1;

            foreach ( $vocab as $word ) {
                if ( abs( strlen( $word ) - strlen( $term ) ) > $limit ) {
                    continue;
                }

                $distance = levenshtein( $term, $word );

                if ( $distance < $score ) {
                    $score = $distance;
                    $best  = $word;
                }
            }
        }

        $changed = $changed || $best !== $term;
        $fixed[] = $best;
    }

    if ( $changed ) {
        $suggestion = implode( ' ', $fixed );
        $html       = '<p class="wpide-did-you-mean">' . esc_html( $wpide_dym_label ) . ' <a href="' . esc_url( get_search_link( $suggestion ) ) . '"><strong>' . esc_html( $suggestion ) . '</strong></a>?</p>';
    }

    return $html;
};

// Classic themes: printed where the "nothing found" message starts.
add_action( 'loop_no_results', function ( $query ) use ( $wpide_dym_html ) {
    static $printed = false;

    if ( $printed || wp_is_block_theme() || ! $query->is_main_query() || ! $query->is_search() ) {
        return;
    }

    $printed = true;
    echo $wpide_dym_html(); // phpcs:ignore WordPress.Security.EscapeOutput -- escaped when built.
} );

// Block themes: added to the Query block's "No results" area.
add_filter( 'render_block_core/query-no-results', function ( $content ) use ( $wpide_dym_html ) {
    return is_search() && '' !== trim( $content ) ? $wpide_dym_html() . $content : $content;
} );
```

## Notes

Works best for Latin-alphabet words; the word list is cached for a day and refreshed when you publish.

## How to use it

Install the free WPIDE plugin (https://wordpress.org/plugins/wpide/), find ""Did You Mean" Suggestions for Empty Searches" in its snippet library and add it in one click; or create a new PHP snippet in WPIDE (or any code snippets plugin) and paste the code above. More snippets: https://wpide.com/library/
