WordPress at a glance

register_post_type() WP 1.0

Registers a post type.

Note: Post type registrations should not be hooked before the 'init' action. Also, any taxonomy connections should be registered via the $taxonomies argument to ensure consistency when hooks such as 'parse_query' or 'pre_get_posts' are used.

Post types can support any number of built-in core features such as meta boxes, custom fields, post thumbnails, post statuses, comments, and more. See the $supports argument for a complete list of supported features.

Works based on: WP_Post_Type()
Hooks from the function

WP_Post_Type/WP_Error. The registered post type object on success, WP_Error object on failure.


register_post_type( $post_type, $args );
$post_type(string) (required)
Post type key. Must not exceed 20 characters and may only contain lowercase alphanumeric characters, dashes, and underscores. See sanitize_key().

Array or string of arguments for registering a post type.

  • label(string)
    Name of the post type shown in the menu. Usually plural.
    Default: value of $labels['name']

  • labels(array)
    An array of labels for this post type. If not set, post labels are inherited for non-hierarchical types and page labels for hierarchical ones. See get_post_type_labels() for a full list of supported labels.

  • description(string)
    A short descriptive summary of what the post type is.
    Default: ''

  • public(true/false)
    Whether a post type is intended for use publicly either via the admin interface or by front-end users. While the default settings of $exclude_from_search, $publicly_queryable, $show_ui, and $show_in_nav_menus are inherited from public, each does not rely on this relationship and controls a very specific intention.
    Default: false

  • hierarchical(true/false)
    Whether the post type is hierarchical (e.g. page).
    Default: false

  • exclude_from_search(true/false)
    Whether to exclude posts with this post type from front end search results.
    Default: opposite value of $public

  • publicly_queryable(true/false)
    Whether queries can be performed on the front end for the post type as part of parse_request(). Endpoints would include:

    • ?post_type={post_type_key}
    • ?{post_type_key}={single_post_slug}
    • ?{post_type_query_var}={single_post_slug} If not set, the default is inherited from $public.
  • show_ui(true/false)
    Whether to generate and allow a UI for managing this post type in the admin.
    Default: value of $public

  • show_in_menu(true/false/string)
    Where to show the post type in the admin menu. To work, $show_ui must be true. If true, the post type is shown in its own top level menu. If false, no menu is shown. If a string of an existing top level menu (eg. 'tools.php' or 'edit.php?post_type=page'), the post type will be placed as a sub-menu of that.
    Default: value of $show_ui

  • show_in_nav_menus(true/false)
    Makes this post type available for selection in navigation menus.
    Default: value of $public

  • show_in_admin_bar(true/false)
    Makes this post type available via the admin bar.
    Default: value of $show_in_menu

  • show_in_rest(true/false)
    Whether to include the post type in the REST API. Set this to true for the post type to be available in the block editor.

  • rest_base(string)
    To change the base url of REST API route.
    Default: $post_type

  • rest_controller_class(string)
    REST API Controller class name.
    Default: 'WP_REST_Posts_Controller'

  • menu_position(int)
    The position in the menu order the post type should appear. To work, $show_in_menu must be true.
    Default: null (at the bottom)

  • menu_icon(string)
    The url to the icon to be used for this menu. Pass a base64-encoded SVG using a data URI, which will be colored to match the color scheme
    -- this should begin with 'data:image/svg+xml;base64,'. Pass the name of a Dashicons helper class to use a font icon, e.g. 'dashicons-chart-pie'. Pass 'none' to leave div.wp-menu-image empty so an icon can be added via CSS.
    Default: use the posts icon

  • capability_type(string)
    The string to use to build the read, edit, and delete capabilities. May be passed as an array to allow for alternative plurals when using this argument as a base to construct the capabilities, e.g. array('story', 'stories').
    Default: 'post'

  • capabilities(array)
    Array of capabilities for this post type. $capability_type is used as a base to construct capabilities by default. See get_post_type_capabilities().

  • map_meta_cap(true/false)
    Whether to use the internal default meta capability handling.
    Default: false

  • supports(array)
    Core feature(s) the post type supports. Serves as an alias for calling add_post_type_support() directly. Core features include 'title', 'editor', 'comments', 'revisions', 'trackbacks', 'author', 'excerpt', 'page-attributes', 'thumbnail', 'custom-fields', and 'post-formats'. Additionally, the 'revisions' feature dictates whether the post type will store revisions, and the 'comments' feature dictates whether the comments count will show on the edit screen. A feature can also be specified as an array of arguments to provide additional information about supporting that feature. Example: array('my_feature', array('field'=>'value') ).
    Default: an array containing 'title' and 'editor'

  • register_meta_box_cb(callable)
    Provide a callback function that sets up the meta boxes for the edit form. Do remove_meta_box() and add_meta_box() calls in the callback.
    Default: null

  • taxonomies(array)
    An array of taxonomy identifiers that will be registered for the post type. Taxonomies can be registered later with register_taxonomy() or register_taxonomy_for_object_type().
    Default: empty array

  • has_archive(true/false/string)
    Whether there should be post type archives, or if a string, the archive slug to use. Will generate the proper rewrite rules if $rewrite is enabled.
    Default: false

  • rewrite(true/false/array)
    Triggers the handling of rewrites for this post type. To prevent rewrite, set to false. To specify rewrite rules, an array can be passed with any of these keys:

    • slug(string)
      Customize the permastruct slug.
      Default: $post_type key

    • with_front(true/false)
      Whether the permastruct should be prepended with WP_Rewrite::$front.
      Default: true

    • feeds(true/false)
      Whether the feed permastruct should be built for this post type.
      Default: value of $has_archive

    • pages(true/false)
      Whether the permastruct should provide for pagination.
      Default: true

    • ep_mask(const)
      Endpoint mask to assign. If not specified and permalink_epmask is set, inherits from $permalink_epmask. If not specified and permalink_epmask is not set.
      Default: EP_PERMALINK

    Default: true, using $post_type as slug

  • query_var(string/true/false)
    Sets the query_var key for this post type. If false, a post type cannot be loaded at ?{query_var}={post_slug}. If specified as a string, the query ?{query_var_string}={post_slug} will be valid.
    Default: $post_type key

  • can_export(true/false)
    Whether to allow this post type to be exported.
    Default: true

  • delete_with_user(true/false)
    Whether to delete posts of this type when deleting a user. If true, posts of this type belonging to the user will be moved to Trash when then user is deleted. If false, posts of this type belonging to the user will not be trashed or deleted. If not set (the default), posts are trashed if post_type_supports('author'). Otherwise posts are not trashed or deleted.
    Default: null

  • _builtin(true/false)
    FOR INTERNAL USE ONLY! True if this post type is a native or "built-in" post_type.
    Default: false

  • _edit_link(string)
    FOR INTERNAL USE ONLY! URL segment to use for edit link of this post type.
    Default: 'post.php?post=%d'

Default: array()


  • Global. Array. $wp_post_types List of post types.


Since 2.9.0 Introduced.
Since 3.0.0 The show_ui argument is now enforced on the new post screen.
Since 4.4.0 The show_ui argument is now enforced on the post type listing screen and post editing screen.
Since 4.6.0 Post type object returned is now an instance of WP_Post_Type.
Since 4.7.0 Introduced show_in_rest, rest_base and rest_controller_class arguments to register the post type in REST API.
Since 5.3.0 The supports argument will now accept an array of arguments for a feature. .

Code of register_post_type() WP 5.5.1

function register_post_type( $post_type, $args = array() ) {
	global $wp_post_types;

	if ( ! is_array( $wp_post_types ) ) {
		$wp_post_types = array();

	// Sanitize post type name.
	$post_type = sanitize_key( $post_type );

	if ( empty( $post_type ) || strlen( $post_type ) > 20 ) {
		_doing_it_wrong( __FUNCTION__, __( 'Post type names must be between 1 and 20 characters in length.' ), '4.2.0' );
		return new WP_Error( 'post_type_length_invalid', __( 'Post type names must be between 1 and 20 characters in length.' ) );

	$post_type_object = new WP_Post_Type( $post_type, $args );

	$wp_post_types[ $post_type ] = $post_type_object;


	 * Fires after a post type is registered.
	 * @since 3.3.0
	 * @since 4.6.0 Converted the `$post_type` parameter to accept a `WP_Post_Type` object.
	 * @param string       $post_type        Post type.
	 * @param WP_Post_Type $post_type_object Arguments used to register the post type.
	do_action( 'registered_post_type', $post_type, $post_type_object );

	return $post_type_object;

From tag: WP extension (enhancement)

More from tag: Custom post type (post_type)

More from category: Custom Types

vladlu 100vlad.lu
Editors: kama 100
No comments
    Log In . Register