Removing a post type name (prefix) from a URL
Option 1.
Suppose we have a new post type team
, which has an URL of the form: example.com/team/dream-team
. We want to remove the prefix team
and make links of this post type look like this: example.com/dream-team
.
add_filter( 'post_type_link', 'remove_post_type_slug', 10, 2 ); add_action( 'pre_get_posts', 'add_post_type_to_get_posts_request' ); // Remove the prefix with the post type name from the URL function remove_post_type_slug( $post_link, $post ){ if( $post->post_type === 'team' ){ return str_replace( "/$post->post_type/", '/', $post_link ); } return $post_link; } // Adding a post type to the query function add_post_type_to_get_posts_request( $query ){ if( is_admin() || ! $query->is_main_query() ){ return; // not a primary request } // not a query with a name parameter (like a static page) if( ! isset( $query->query['page'] ) || empty( $query->query['name'] ) || count( $query->query ) != 2 ){ return; } $query->set( 'post_type', [ 'post', 'page', 'team' ] ); // 'team' added }
Here we should keep in mind that our new URL of the form ``example.com/dream-team``` is exactly the same structure as the URL of static pages. And if the name of the static page and the post of the new type will coincide, then we'll get a conflict, and probably the wrong post will be shown. But since this situation is very unlikely, we simply keep this possible bug in mind and don't handle it in any way.
Option 2
In this variant post type is called pool_services
and here we use the funciton add_permastruct() instead of the post_type_link hook - it allows us to remove post type name from URL not only at frontend but also in the admin area.
As a result, we'll get a URL of the form /postname
instead of /pool-services/postname
.
add_action( 'init', 'pw24_post_type_rewrite' ); add_action( 'pre_get_posts', 'pw24_add_post_type_to_get_posts_request' ); function pw24_post_type_rewrite() { global $wp_rewrite; // in this case the post type is `pool_services` $wp_rewrite->add_rewrite_tag( "%pool_services%", '([^/]+)', "pool_services=" ); $wp_rewrite->add_permastruct( 'pool_services', '%pool_services%' ); } function pw24_add_post_type_to_get_posts_request( $query ){ if( is_admin() || ! $query->is_main_query() ){ return; // not a primary request } // not a query with a name parameter (like a static page) if( ! isset( $query->query['page'] ) || empty( $query->query['name'] ) || count( $query->query ) != 2 ){ return; } // add 'pool_services' $query->set( 'post_type', [ 'post', 'page', 'pool_services' ] ); }
Now in the links (on the site and in the admin area), there is no 'pool-services' post type name and all pages work as they should.
—