WordPress custom post type permalink structure with custom field value

I am trying to modify the URL structure of my custom post type ‘project’.

I would like the URL structure to be as follows:

Read More

http://localhost/project/%location%/project-name

%location% is a custom field value associated with that post.

So if I had a post called ‘test’ with the custom field value of ‘seattle’, the URL would look like this:

http://localhost/project/seattle/test

I have semi completed this with the following:

function test_query_vars( $query_vars ) {
    $query_vars[] = 'location';
    return $query_vars;
}
add_filter( 'query_vars', 'test_query_vars' );

function test_init() {
    $wp_rewrite->add_rewrite_tag( '%project%', '([^/]+)', 'project=' );
    $wp_rewrite->add_rewrite_tag( '%location%', '([^/]+)', 'location=' );

    $wp_rewrite->add_permastruct( 'project', 'project/%location%/%project%', false );

    // Register post type
    register_post_type( 'project', 
        array(
            'labels' => $labels,
            'public' => true,
            'rewrite' => false,
            'has_archive' => true,
            'menu_position' => NULL,
            'supports' => array ( 'title', 'editor', 'thumbnail', 'page-attributes', 'excerpt', 'comments', 'author' ),
            'yarpp_support' => true,
        )
    );
}
add_action( 'init', 'test_init' );

There are a few problems with this:

  1. The location custom field in the URL can be anything. If I go to http://localhost/project/atlanta/test and the location custom field is actually ‘seattle’, it will still bring up the desired post. It should be a 404 not found since the ‘test’ post has the custom field ‘location’ value set to ‘seattle’.
  2. If I go to http://localhost/project/seattle, it will bring up the Blog, but really it should bring up my projects that have the custom field value set to ‘seattle’.
  3. The archive for this post type is now having a 404, e.g. http://localhost/project/ should be displaying all projects.

I have tried modifying the query using the following but it is still not working:

function test_parse_query( $query ) {
    if ( 'project' == $query->query_vars['post_type'] ) {

        $query->set('meta_query', array(
            array(
                'key' => 'project_location',
                'value' => $query->query_vars['location']
            )
        ));
    }

    return $query;
}
add_filter( 'parse_query', 'test_parse_query' );

Any help would be appreciated 🙂

Related posts