10

I am using wp_insert_post and all the fields are working except tax_input is working. Is there something wrong with my code?

$customtax =  array(
'product_link' => $link,
'product_price' => $price,
'product_description' => $desc );
$my_post = array(
  'post_title'    => $title,
  'post_content'  => $content,
  'post_type'     => 'products',
  'tax_input' => $customtax
);

Thank you in advance

7 Answers 7

27

The most common reason is that you run this code without user context (cron, etc). Within wp_insert_post() context WP will check if user has permissions to a taxonomy. No user equals no permissions equals no terms being assigned.

The workaround is to create post first, then assign terms to it. When terms are assigned explicitly via API method (such as wp_set_object_terms()) the permissions check is not performed.

2
  • So the workaround is to the wp_insert_post() without the tax_input and then once that's completed, use wp_set_object_terms()? But what if that's not possible? For example, a plugin that let's you filter the args for wp_insert_post() but has no hook for once that's completed. This answer might work but it feels far from ideal. There's something quirky about wp_insert_post() and 'tax_input'. Certainly, there's a true clean slate solution. Commented Dec 28, 2016 at 16:13
  • Thank you! I was pulling my hair out wondering why it was working for me (logged in), and not users (not logged in). (I'm trying to add a cpt after a form submission.) It should probably be mentioned in the docs, coz its not obvious at all.
    – Studocwho
    Commented Sep 19 at 19:40
11

It turns out that tax_input does not work if a user does not have the capabilities to work with a custom taxonomy:

wp-includes/post.php (wp_insert_post): enter image description here

So either add the correct caps or use wp_set_object_terms()

4

As you said in comment that plugin will do the filters and don't have hook, I think plugin must have wp_insert_post hook anyway. Otherwise how do you insert the post ? I am answering this after so long time cause I faced the same issue and found the only one way.

$new_id = wp_insert_post($post_arr, true);
$status = wp_set_object_terms($new_id, $term_id, 'location');

here location is the term slug. Someday someone will get this helpful..

1

When using tax_input for post insertion, be sure to use term taxonomy id, since slugs or names seem to be thrown away

$my_post = array(
'post_title'    => $title,
'post_content'  => $content,
'post_type'     => 'products',
'tax_input' => array('myTax', array(4,458,11478)),
);
1

The question is old, still I spent quite some time to figure out that insert post (wp_insert_post) show this behaviour when used inside the cron action.

Insert post and then wp_set_object_terms is a good workaround, however, setting the current user before inserting post also worked for me

$user_id = 1;
$user = get_user_by( 'id', $user_id );
wp_set_current_user( $user_id, $user->user_login);

$new_id = wp_insert_post($my_post);
1
  • This didn't work for me Commented Nov 7, 2023 at 22:50
0

As @Rarst said WordPress checks during the wp_insert_post() if a current user has permission to add taxonomy terms. You also see from the post.php Line:3352

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

If you are running the wp_insert_post code without having a logged in user you can set a current user by using the wp_set_current_user() method.

    $user = get_user_by('ID', $user_id);

    if( $user ){

         wp_set_current_user( $user_id, $user->user_login );

    }
0

Maybe the wp_insert_post() function has changed,or maybe nobody has looked in its code, but the answer nowadays is:

$customtax =  array(
 'myTax' => array(1,2,3),
);

$my_post = array(
  'post_title'    => $title,
  'post_content'  => $content,
  'post_type'     => 'products',
  'tax_input' => $customtax
);

Where 1,2,3 are IDs of the tax terms.

And yes, current user should be able to assign terms, otherwise try to use wp_set_object_terms() function after wp_insert_post().

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.