Adding Custom Fields to Search

I’m trying to add custom fields to my search so that it can be refined by meta values. Currently I have added some select lists to my normal search:

<form role="search" action="<?php echo site_url('/'); ?>" method="get" id="searchform">
    <input type="hidden" name="s" value="carcpt" /> <!-- // hidden 'products' value -->

    <select name="price">
        <option value="">Nothing</option>
        <option value="500.00">500.00</option>
        <option value="100.00">100.00</option>
        <option value="50.00">50.00</option>
    </select>

    <select name="year">
        <option value="">Nothing</option>
        <option value="2011">2011</option>
        <option value="2007">2007</option>
        <option value="1991">1991</option>
    </select>

    <input type="submit" alt="Search" value="Search" />
</form>

and at the top of my search.php I have this conditional:

Read More
$q = get_search_query();
if($q = 'carcpt'){

    $price = $_GET['price'];
    $year = $_GET['year'];

    $search = new WP_Query(
        array(
            'post_type' => 'carcpt',
            'meta_query' => array(
                array(
                    'key' => '_price',
                    'value' => $price
                ),
                array(
                    'key' => '_year',
                    'value' => $year
                )
            )
        )
    );
}

That’s the scenario – I have 2 questions:

1) This seems like a very ‘hacky’ way to add and refine my search results by custom fields – is there a better / more widely accepted way to do this?

2) The problem with the query above is that if the user does not enter a price or year – it will run the query and return only post with empty price/year meta. In my query is there a way to determine if a meta is empty and modify my query accordingly – not including a switch?

Related posts

1 comment

  1. 1) I think that your solution is perfectly acceptable in terms of the “right way” – post meta is intended for searching. Doesn’t seem hacky to me.

    2) What you should do is build the meta_query separately:

    $meta_query = array();
    
    if( !empty( $_GET['price'] ) ) {
        $meta_query[] = array( 'key' => '_price', 'value' => $_GET['price'] );
    }
    if( !empty( $_GET['year'] ) ) {
        $meta_query[] = array( 'key' => '_year', 'value' => $_GET['year'] );
    }
    
    $search = new WP_Query( array(
        'post_type' => 'carcpt',
        'meta_query' => $meta_query
    ) );
    

    This way you’re only querying on meta keys that have a supplied, non-empty value.

    I would like to point out that modification of query variables is better done in the pre_get_posts action, otherwise, as in this instance two queries will be executed: one for the search of ‘carcpt’, and then the second query for the ‘carcpt’ post type and meta query.

Comments are closed.