Filtering custom post types by post meta in the WordPress admin area

This tutorial shows you how to add filters to a list of posts with a custom post type displayed in the WordPress admin area. We'll look at how you can create filters using custom post meta.

If you've created a custom post type in WordPress, it's possible to view a list of these posts using the default admin interface. In this tutorial we're going to look at how you can add the additional dropdown shown in the screenshot below, where the custom posts can be filtered by custom post meta.

In this this example, the custom post type is 'ticket', and the post meta is 'ticket_assigned_to', which references an administrator user.

To achieve the above, we need to do two things:

  • Add an action to modify the filters available
  • Add a filter to modify the query that searches the posts

Add the custom drop down filter

To start with we'll add the custom drop down filter. We achieve this by using the 'restrict_manage_posts' hook like so:

add_action( 'restrict_manage_posts' , array($this, 'modify_ticket_filters' ) );

public function modify_ticket_filters()
{
    // Only apply the filter to our specific post type
    global $typenow;
    if( $typenow == 'ticket' )
    {
        $admins= get_users( array( 'role' => 'administrator' ) );
        echo "<select name="filter_owner">";
        echo "<option value="">All tickets</option>";
        foreach( $admins as $admin)
        {
            $selected = $admin->ID == $_GET['filter_owner'] ? ' selected ' : '';
            echo "<option value="'"" admin-="">ID . "' " .  $selected . ">" . $admin->user_nicename .  "</option>";
        }
        echo "";
    }
}

Note that there are some other functions WordPress has available for creating dropdowns for categories, pages and users, here's an example:

$args = array(
     'show_option_all' => "Show all tickets",
);

wp_dropdown_users($args);

This code would add a drop down with a full list of users in less lines of code, though it currently isn't possible to filter by admins so not applicable to the current example. See also: wp_dropdown_userswp_dropdown_pages and wp_dropdown_categories.

Filter the results

The next step is to filter the results, we achieve this by adding the filter 'parse_query':

add_filter( 'parse_query', array( $this, 'modify_filter_owner' ) );
public function modify_filter_owner( $query )
{
    global $typenow;
    global $pagenow;

    if( $pagenow == 'edit.php' && $typenow == 'ticket' && $_GET['filter_owner'] )
    {
        $query->query_vars[ 'meta_key' ] = 'ticket_assigned_to';
        $query->query_vars[ 'meta_value' ] = (int)$_GET['filter_owner'];
    }
}

The above code checks if the current page is edit.php, that the post type is our 'ticket' type and that the user is attempting to filter on the new dropdown. If so we append the meta_key and meta_value to the query so that it will restrict the results by the 'ticket_assigned_to' field.

Sign Up

NEXT: How to create a custom WordPress page template

Step-by-step instructions on how to set up a custom WordPress template that can be re-used for multiple pages.

comments powered by Disqus
Sign Up

Popular Tags

350x250

Need a web developer?

If you'd like to work with code synthesis on your next project get in touch via the contact page.