0

I am working with custom posts to create a 'document' custom post type and then trying to assign the category during wp_insert_post, have tried using both post_category and tax_input to no success.

I am registering the custom post as below, keeping in the relevant bits below so it does have $labels defined and a few more $args that I have stripped out.

My research has indicated that permissions need to be created in the custom post type before assigning them to a user role. The user is not logged in, which I understand causes some issues, however in this case I have $user_id passed in which provides the ID in the title and to set the author without a problem so I don't think this is where the problem lies.

Any thoughts on where I am going wrong?

Registering the custom post type:

function document_custom_post_type() {
 
register_taxonomy('document-category', 'Documents',array(
    "hierarchical" => true,
    "label" => "Categories",
    "singular_label" => "document",
    'query_var' => true,
    'rewrite' => array( 'documents' => 'slug name of new registered taxonomy',
    'with_front' => false ),
    'public' => true)
    );
          
    $args = array(
        'labels'              => $labels,
        'supports'            => array( 'title', 'author', 'comments' , 'custom-fields', ),
        'taxonomies'          => array( 'document-category', ),
        'hierarchical'        => true,
        'public'              => true,
        'capabilities'        => array(
            'manage_terms'    => 'manage_document',
            'edit_terms'      => 'manage_document',
            'delete_terms'    => 'manage_document',
            'assign_terms'    => 'edit_posts'
        ),
        'capability_type'     => 'post',
        'map_meta_cap'    => true,
    );
     
    // Registering Document Custom Post Type
    register_post_type( 'document', $args );
 
}
add_action( 'init', 'document_custom_post_type', 0 );

The user role in particular has several caps already, but in this case edit_posts and manage_document are both set to true:

    $client_role = add_role('Client', __('Client'), array(
    'read'                       => true,
    'edit_posts'                 => true,

    'edit_documents'             => true,
    'edit_others_documents'      => false,
    'publish_documents'          => true,
    'read_private_documents'     => false,
    'manage_document'            => true,
    'delete_document'           => true,
    'delete_private_documents'   => true,
    'delete_published_documents' => true,
    'delete_others_documents'    => false,
    'edit_private_documents'     => false,
    'edit_published_documents'   => true,
    
    )); 

When the user verifies their email, I create two custom post types with some pre-defined settings so the example below is for category ID 6 and category ID 4. All fields except the category works, I've included both versions I've tried in the commented out rows:

In functions.php:

            $user_post = array(
                'post_title'     => 'Security Questionnaire '.$user_id.'',
                'post_status'    => 'publish',
                'post_author'    => $user_id,
                'post_type'      => 'document',
                'page_template'  => 'page-templates/document.php',
                //'post_category'  => array( 4 ),
                'tax_input' => array( 'document-category' => array(4) ), //ID = 4 is the tag ID for the Security Questionnaires category
            );
            $post_id = wp_insert_post( $user_post );

And then:

            $user_post = array(
                'post_title'     => 'Contract '.$user_id.'',
                'post_status'    => 'publish',
                'post_author'    => $user_id,
                'post_type'      => 'document',
                'page_template'  => 'page-templates/document.php',
                //'post_category'  => array( 6 )
                'tax_input' => array( 'document-category' => array(6) ), //ID = 6 is the tag ID for the Contract category
            );
            $post_id = wp_insert_post( $user_post );

            $verified_user = new WP_User( $user_id );
            $verified_user->set_role( 'client' );

Can anyone see where I am going wrong? It seems like this should be straight forward but have been struggling with it for a while now.

1
  • your role theory is incorrect, by using wp_insert_post you've bypassed any roles and capabilities so that's not the issue. I will note though that calling new WP_User( $user_id ) is extremely uncommon and weird to see, are you sure you didn't mean to use get_user_by? How are you testing this? All the information about roles etc are only relevant to the GUI here, they're a red herring/wild goose chase that's irrelevant to your problem
    – Tom J Nowell
    May 24, 2022 at 10:05

1 Answer 1

1

Couple things I've spotted:

  1. Your taxonomy registration register_taxonomy( 'document-category', 'Documents' should be register_taxonomy( 'document-category', 'document' - the second parameter is the post type name(s), not the post type label.

  2. If you're programmatically inserting posts then forget using tax_input in your wp_insert_post() data args. There's a hard-coded permissions check on the current user and there's nothing you can do to override it:

    // New-style support for all custom taxonomies.
    if ( ! empty( $postarr['tax_input'] ) ) {
        foreach ( $postarr['tax_input'] as $taxonomy => $tags ) {
            $taxonomy_obj = get_taxonomy( $taxonomy );

            if ( ! $taxonomy_obj ) {
                /* translators: %s: Taxonomy name. */
                _doing_it_wrong( __FUNCTION__, sprintf( __( 'Invalid taxonomy: %s.' ), $taxonomy ), '4.4.0' );
                continue;
            }

            // array = hierarchical, string = non-hierarchical.
            if ( is_array( $tags ) ) {
                $tags = array_filter( $tags );
            }

            if ( current_user_can( $taxonomy_obj->cap->assign_terms ) ) {
                wp_set_post_terms( $post_ID, $tags, $taxonomy );
            }
        }
    }

Instead take note from the code above and do it yourself:

$post_id = wp_insert_post( $user_post );

wp_set_post_terms( $post_id, [ 4 ], 'document-category' );
1
  • Thank you! Switching to wp_set_post_terms worked perfectly first time haha it was driving me crazy! And to Tom's comments the user role settings actually made no difference using tax_input
    – IcedQuick
    May 25, 2022 at 15:21

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.