Make WordPress Core


Ignore:
Timestamp:
02/07/2023 08:53:01 AM (4 years ago)
Author:
audrasjb
Message:

Query: Add a search_columns argument to control which fields are searched in a search query.

Previously, the s argument of the WP_Query::parse_query() method searched the post_title, post_excerpt, and post_content fields, with no way of controlling this apart from using the posts_search filter and adjusting the SQL manually. This changeset adds the ability to specify which fields are searched when performing a query, using the search_columns argument.

Props johnbillion, birgire, petitphp, audrasjb, costdev, mukesh27.
Fixes #43867.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/wp-includes/class-wp-query.php

    r55035 r55248  
    611611                        'author__in',
    612612                        'author__not_in',
     613                        'search_columns',
    613614                );
    614615
    … …  
    638639         * @since 5.3.0 Introduced the `$meta_type_key` parameter.
    639640         * @since 6.1.0 Introduced the `$update_menu_item_cache` parameter.
     641         * @since 6.2.0 Introduced the `$search_columns` parameter.
    640642         *
    641643         * @param string|array $query {
    … …  
    751753         *                                                    character used for exclusion can be modified using the
    752754         *                                                    the 'wp_query_search_exclusion_prefix' filter.
     755         *     @type array           $search_columns          Array of column names to be searched. Accepts 'post_title',
     756         *                                                    'post_excerpt' and 'post_content'. Default empty array.
    753757         *     @type int             $second                  Second of the minute. Default empty. Accepts numbers 0-59.
    754758         *     @type bool            $sentence                Whether to search by phrase. Default false.
    … …  
    14111415                $q['search_orderby_title'] = array();
    14121416
     1417                $default_search_columns = array( 'post_title', 'post_excerpt', 'post_content' );
     1418                $search_columns         = ! empty( $q['search_columns'] ) ? $q['search_columns'] : $default_search_columns;
     1419                if ( ! is_array( $search_columns ) ) {
     1420                        $search_columns = array( $search_columns );
     1421                }
     1422
     1423                /**
     1424                 * Filters the columns to search in a WP_Query search.
     1425                 *
     1426                 * The supported columns are `post_title`, `post_excerpt` and `post_content`.
     1427                 * They are all included by default.
     1428                 *
     1429                 * @since 6.2.0
     1430                 *
     1431                 * @param string[] $search_columns Array of column names to be searched.
     1432                 * @param string   $search         Text being searched.
     1433                 * @param WP_Query $query          The current WP_Query instance.
     1434                 */
     1435                $search_columns = (array) apply_filters( 'post_search_columns', $search_columns, $q['s'], $this );
     1436
     1437                // Use only supported search columns.
     1438                $search_columns = array_intersect( $search_columns, $default_search_columns );
     1439                if ( empty( $search_columns ) ) {
     1440                        $search_columns = $default_search_columns;
     1441                }
     1442
    14131443                /**
    14141444                 * Filters the prefix that indicates that a search term should be excluded from results.
    … …  
    14401470                        $like = $n . $wpdb->esc_like( $term ) . $n;
    14411471
     1472                        $search_columns_parts = array();
     1473                        foreach ( $search_columns as $search_column ) {
     1474                                $search_columns_parts[ $search_column ] = $wpdb->prepare( "({$wpdb->posts}.$search_column $like_op %s)", $like );
     1475                        }
     1476
    14421477                        if ( ! empty( $this->allow_query_attachment_by_filename ) ) {
    1443                                 $search .= $wpdb->prepare( "{$searchand}(({$wpdb->posts}.post_title $like_op %s) $andor_op ({$wpdb->posts}.post_excerpt $like_op %s) $andor_op ({$wpdb->posts}.post_content $like_op %s) $andor_op (sq1.meta_value $like_op %s))", $like, $like, $like, $like );
    1444                         } else {
    1445                                 $search .= $wpdb->prepare( "{$searchand}(({$wpdb->posts}.post_title $like_op %s) $andor_op ({$wpdb->posts}.post_excerpt $like_op %s) $andor_op ({$wpdb->posts}.post_content $like_op %s))", $like, $like, $like );
    1446                         }
     1478                                $search_columns_parts['attachment'] = $wpdb->prepare( "(sq1.meta_value $like_op %s)", $like );
     1479                        }
     1480
     1481                        $search .= "$searchand(" . implode( " $andor_op ", $search_columns_parts ) . ')';
     1482
    14471483                        $searchand = ' AND ';
    14481484                }
Note: See TracChangeset for help on using the changeset viewer.