Since WordPress 3.0 you can use Custom Post Types and you can define your own types of content – it’s more like pages than posts! Thereby you can use automatically the Permalink structure of your WordPress installation. That means, if you create a new post type, you can use Permalinks.
But the Permalinks only work if you recreate the Rewrite Rules of WordPress – that’s why many users initially have problems with it. If you create a new post type you probably get a 404 if you open this page because WordPress doesn’t know the URL-structure in your Permalinks since you didn’t create the Rewrite Rules again.
The easiest way is to safe the Permalink structure in your settings again. Alternatively you can include in your Plugin or Theme the function flush_rewrite_rules()
. This enables to create the Rewrite Rules again. Important: Flush rules only on activation or deactivation. Don’t do it on any other hook.
Comments
21 responses to “Custom Post Type and Permalink”
Thanks for the info Frank. I’m going to have to try the custom post types one of these days.
“The easiest way is to safe the Permalink structure in your settings again”
Only visiting the Permalink page in the Admin Settings is enough, it flushes the rewrite rules.
“Alternatively you can include in your Plugin or Theme the function flush_rewrite_rules().”
Not a good idea because 1. It is too heavy to flush the rules each time a page is visited and 2. This may break other plug-ins’ permalink structure.
Please flush only after include the new custom post type!
To clarify: Flush rules *only* on activation (and deactivation). Don’t do it on any other hook.
Does this apply to custom taxonomies, too? Because I am having trouble with the permalinks of custom category-type taxonomies.
Well, to answer myself here, yes, it does!
I was already giving up. Thank you so much for this timely info.
So to clarify if I wanted to flush after a theme is activated would that be the appropriate place to make the function call?
Thanks!
Can you give us real example custom post type?
Can you someone explain how to flush rules suitably from functions.php?
Its a confusing issue to new theme developers as you can see here: http://wordpress.stackexchange.com/questions/3122/wordpress-custom-post-types-breaks-permalink-on-theme-reinstall
I think I’ve fixed the problem. You just need to add the following line after your register_post_type call:
flush_rewrite_rules( false );
I just tried this out, and it worked beautifully to fix my permalink issues. In my blog theme, I have the custom post type initialized in my functions.php file. I added the flush_rewrite_rules(); function to the file, within the create_my_post_types() function that initializes my custom post type (self-named, not a wordpress function) , but after the register_post_type() function that defines the parameters of the custom post type. confused? Well here’s my code, hopefully this will display properly:
add_action( 'init', 'create_my_post_types' );
function create_my_post_types() {
register_post_type( 'genera',
array(
'labels' => array(
'name' => __( 'GENERA' ),
'singular_name' => __( 'GENERA Entry' ),
'add_new' => __( 'Add New' ),
'add_new_item' => __( 'Add New GENERA Entry' ),
'edit' => __( 'Edit' ),
'edit_item' => __( 'Edit GENERA Entry' ),
'new_item' => __( 'New GENERA Entry' ),
'view' => __( 'View GENERA' ),
'view_item' => __( 'View GENERA Entry' ),
'search_items' => __( 'Search GENERA' ),
'not_found' => __( 'No GENERA Entries found' ),
'not_found_in_trash' => __( 'No GENERA Entries found in Trash' ),
'parent' => __( 'Parent GENERA Entry' ),
),
'public' => true,
'show_ui' => true,
'publicly_queryable' => true,
'rewrite' => true,
'exclude_from_search' => false,
'menu_position' => 20,
/* Global control over capabilities. */
'capability_type' => 'post',
'supports' => array( 'title', 'editor', 'comments', 'trackbacks', 'revisions', 'author', 'excerpt', 'custom-fields', 'thumbnail', 'page-attributes' ),
)
);
flush_rewrite_rules();
}
in order to see the new permalink structure, you will of course have to have ‘rewrite’ set to => true
Ah, good idea to throw everything into init.
[…] you may need to “flush” them). The plugin does flush the rewrite rules on activation as recommended, however some websites seem to require a manual flush. To do so, go to your admin menu settings […]
Thanx for the post.
And special thanx to Karl for the example – that’s exactly what I was looking for!
holy crap….i’ve been looking for a solution to this for almost 2 hours and all i had to do was resave my permalink structure….lame-0 but at least I got it fixed! Thanks!
Hi there,
I’m trying to use this method with custom date meta for my permalink rewrite. I can’t figure out for the life of me why I can’t get around the 404 issue. Ive even added in your flush_rewrite_rules into my code and nothing.
Settings > Permalink Structure: /%category%/%postname%/
Here is my function below- it’s working fine for creating the actual permalink but i cannot access the post without getting the 404.
add_filter('post_type_link','calendar_link_filter',1,3);
function calendar_link_filter( $post_link, $id = 0, $leavename = FALSE ) {
$post = get_post($id);
if($post->post_type != 'super_duper') {
return $post_link;
}
$date = get_post_meta($post->ID,'event_start_date',true);
$date = strtotime($date);
$str = $post_link;
$str = str_replace('%cal_year%',date("Y",$date),$str);
$str = str_replace('%cal_month%',date("m",$date),$str);
$str = str_replace('%cal_day%',date("d",$date),$str);
return $str;
}
add_action( 'init', 'create_my_post_types' );
function create_my_post_types() {
register_post_type( 'super_duper',
array(
'labels' => array(
'name' => __( 'Super Dupers' ),
'singular_name' => __( 'Super Duper' )
),
'hierarchical' => false,
'show_ui' => true, // UI in admin panel
'publicly_queryable' => true,
'rewrite' => true,
'public' => true,
'rewrite' => array('slug' => 'events8/%cal_year%/%cal_month%/%cal_day%'),
)
);
flush_rewrite_rules();
}
I’m looking for help with a similar problem here:
http://wordpress.org/support/topic/need-help-diagnosing-permalink-problem-reports?replies=1
My plugin code works fine on my site and those of some other users who are happy with it, but I’m also getting isolated reports of 404 errors when people try to use the permalinks.
[…] Deaktivierung tun. Mehr Infos zu Custom Posts Types und Permalinks findest du auch im Artikel »Custom Post Types and Permalinks« auf […]
Do you know why you shouldn’t put it in, say, a function called by an init hook? I’ve been testing it and it seems to work fine . . .
Don’t call flush after the register function. (Many examples above do this.)
Instead, add two functions, one attached to the “register_activation_hook( __FILE__, ‘activate_cb’ );” which in turn adds an action to ‘init’ (priority 11 just to be sure) and that function in turn flushes the rewrite. Otherwise, you are flushing on every single page load (not good).