Creating a custom post type (CPT) in WordPress programmatically is a powerful way to extend the functionality of your website. Custom post types allow you to create content types that go beyond the default posts and pages, such as portfolios, testimonials, or products. In this guide, we’ll walk through the steps to create a custom post type programmatically.
Before diving into the code, it’s important to understand what a custom post type is. In WordPress, a post type is a way of grouping content. The default post types include:
Custom post types allow you to create your own group of content, which can have different custom fields, taxonomies, and display options.
To keep your changes organized and update-safe, it’s best to add custom post types in a child theme’s functions.php
file or in a custom plugin. Here’s how you can do it:
wp-content/themes/your-child-theme/
.functions.php
file.wp-content/plugins/
.custom-post-types
.custom-post-types.php
.Here’s the code snippet you need to add to your functions.php
or custom-post-types.php
file:
function create_custom_post_type() {
$labels = array(
'name' => _x( 'Books', 'Post type general name', 'textdomain' ),
'singular_name' => _x( 'Book', 'Post type singular name', 'textdomain' ),
'menu_name' => _x( 'Books', 'Admin Menu text', 'textdomain' ),
'name_admin_bar' => _x( 'Book', 'Add New on Toolbar', 'textdomain' ),
'add_new' => __( 'Add New', 'textdomain' ),
'add_new_item' => __( 'Add New Book', 'textdomain' ),
'new_item' => __( 'New Book', 'textdomain' ),
'edit_item' => __( 'Edit Book', 'textdomain' ),
'view_item' => __( 'View Book', 'textdomain' ),
'all_items' => __( 'All Books', 'textdomain' ),
'search_items' => __( 'Search Books', 'textdomain' ),
'parent_item_colon' => __( 'Parent Books:', 'textdomain' ),
'not_found' => __( 'No books found.', 'textdomain' ),
'not_found_in_trash' => __( 'No books found in Trash.', 'textdomain' ),
'featured_image' => _x( 'Book Cover Image', 'Overrides the “Featured Image” phrase for this post type.', 'textdomain' ),
'set_featured_image' => _x( 'Set cover image', 'Overrides the “Set featured image” phrase for this post type.', 'textdomain' ),
'remove_featured_image' => _x( 'Remove cover image', 'Overrides the “Remove featured image” phrase for this post type.', 'textdomain' ),
'use_featured_image' => _x( 'Use as cover image', 'Overrides the “Use as featured image” phrase for this post type.', 'textdomain' ),
'archives' => _x( 'Book archives', 'The post type archive label used in nav menus.', 'textdomain' ),
'insert_into_item' => _x( 'Insert into book', 'Overrides the “Insert into post”/”Insert into page” phrase.', 'textdomain' ),
'uploaded_to_this_item' => _x( 'Uploaded to this book', 'Overrides the “Uploaded to this post”/”Uploaded to this page” phrase.', 'textdomain' ),
'filter_items_list' => _x( 'Filter books list', 'Screen reader text for the filter links heading.', 'textdomain' ),
'items_list_navigation' => _x( 'Books list navigation', 'Screen reader text for the pagination heading.', 'textdomain' ),
'items_list' => _x( 'Books list', 'Screen reader text for the items list heading.', 'textdomain' ),
);
$args = array(
'labels' => $labels,
'public' => true,
'publicly_queryable' => true,
'show_ui' => true,
'show_in_menu' => true,
'query_var' => true,
'rewrite' => array( 'slug' => 'book' ),
'capability_type' => 'post',
'has_archive' => true,
'hierarchical' => false,
'menu_position' => null,
'supports' => array( 'title', 'editor', 'author', 'thumbnail', 'excerpt', 'comments' ),
'show_in_rest' => true, // Enable Gutenberg editor
);
register_post_type( 'book', $args );
}
add_action( 'init', 'create_custom_post_type' );
In the code above, the custom post type is named “Book.” Here’s how you can customize it:
labels
: Change these to suit the name and purpose of your custom post type.public
: Set to true
to make the post type public.supports
: This array controls what features the post type supports, like title, editor, thumbnails, etc. Add or remove features based on your needs.rewrite
: Customize the URL slug for your custom post type.show_in_rest
: Set to true
if you want to use the Gutenberg editor with your custom post type.After registering your custom post type, it’s essential to flush the permalinks to avoid 404 errors on your new post type. To do this:
Go to your WordPress dashboard, and you should see a new menu item for your custom post type (e.g., “Books”). You can start adding content, and it will behave like any other post type.
Creating a custom post type programmatically in WordPress is a straightforward process that significantly enhances the flexibility of your site. By following these steps, you can tailor your WordPress site to better fit your content needs, whether it’s for a portfolio, testimonials, or any other custom content type.
Ready to take your WordPress site to the next level? Start creating custom post types today and unlock new possibilities for managing and displaying your content!