WordPress.org

Make WordPress Core

Opened 9 months ago

Last modified 5 months ago

#41751 new defect (bug)

save_post_{custom_post_type} not behaving exactly as save_post

Reported by: dipakbbsr Owned by:
Milestone: Awaiting Review Priority: normal
Severity: normal Version: 4.8.1
Component: Posts, Post Types Keywords:
Focuses: administration Cc:

Description

When save_post is fired, the code

get_post_meta( $post_id )

is getting all meta field values. But when same code is written inside save_post_{custom_post_type} action, the meta fields that are originally save to a post are coming. But the meta fields that are being updated in the post are not coming.

Note : I am creating a post from frontend with fewer custom fields and with status "draft". And when admin "publish" the post at backend i want to update other meta fields based on admin selection. But while save_post displays me all meta fields save_post_{custom_type} only shows the meta entries that are saved in db while post creation.

I hope i am clear enough to explain. Correct me if I am missed anything during coding.

Change History (4)

#1 @subrataemfluence
9 months ago

Welcome to Trac and thanks for the ticket!

Did you create this custom post type by hand using register_post_type? If yes, how are you handling meta_boxes for storing meta values against a post?

"But when same code is written inside save_post_{custom_post_type} action, the meta fields that are originally save to a post are coming. But the meta fields that are being updated in the post are not coming."

From above I assume you are able to update meta values somewhere, most likely in admin, but updated values are not showing up? Are you sure whether these values are actually getting updated?

You said your post is being saved as Draft in front end and being published from back end. When you update the values please can you check:

  1. New values are being saved in database? Can you check into wp_post_meta table using the post_id? Can you see the updated values against the original post id?
  2. It is not creating a revision.
  3. Does the status of original post change to Publish when you do this from admin?

#2 @subrataemfluence
9 months ago

  • Keywords reporter-feedback added

#3 @dipakbbsr
9 months ago

  • Keywords reporter-feedback removed

Hi,

I want to clarify as much as I can.

To answer your 1st question, "Yes, the post type is created by hand written code using register_post_type and i am attaching the properties below,

<?php
$args = array(
        'label'                 => __( 'Redeem', 'wp-coupon' ),
        'description'           => __( 'Post type is used to gather user data regarding a request to redeem reward points', 'wp-coupon' ),
        'labels'                => $labels,
        'supports'              => array( 'title', 'author', ),
        'hierarchical'          => false,
        'public'                => true,
        'show_ui'               => true,
        'show_in_menu'          => true,
        'menu_position'         => 5,
        'show_in_admin_bar'     => false,
        'show_in_nav_menus'     => true,
        'can_export'            => false,
        'has_archive'           => false,               
        'exclude_from_search'   => true,
        'publicly_queryable'    => true,
        'capability_type'       => 'page',
);
register_post_type( 'redeem', $args );

And the meta fields and meta boxes are handled by ACF Pro.

Meta fields for "Redeem" post types are,

  1. Shop Name
  2. Amount
  3. Redeem Status ( Default Pending & Will be updated to Accepted or Rejected by admin )
  4. Award Point ( When Accepted is selected by admin, he has to set a point that will be added to user meta when published )

Front end submission form is created by acf_form, Which only shows meta filed 1 & 2. Note : meta field 3 & 4 will only be updated when admin publish the post.

So now post is created with 2 meta fields in database, as acf_form is used it is not adding other meta fields which are not in form. Admin can see the post with status "Draft"and goes to edit that. Checks the Redeem Status to "Accepted" (Number 3 meta field), then gives a value for number 4 meta field (Award Point, which will be updated to user meta ) and clicks on submit.

Here Answering your other questions,

  1. Yes, new values are being saved to database.
  2. No revision is being created
  3. Yes, original ( that is one and only ) post's status changing to Publish.

Everything else is working fine except the code written inside action save_post_redeem

<?php
function save_update_redeem_requests( $post_id, $post, $update ) {
    
    $post_type = get_post_type($post_id);
    if ( "redeem" != $post_type ) 
        return;

    if( $post->post_status && $post->post_status == 'publish' ) {
        
        $points_to_add = get_post_meta( $post_id, 'reward_point', true );
        update_user_meta( $post->post_author, 'mycred_default', $points_to_add );
    }
}
add_action( 'save_post_redeem', 'save_update_redeem_requests', 12, 3 );

There are other condition like if status == accepted and similar things, i have omitted them to explain with less code, also i check everything with less code.

Point is above code works perfectly with save_post. But with save_post_redeem its unable to find value of 3rd and 4th meta field, that were not created while post creation, they are being updated now when admin wish to make the post publish. DB is updating but i cant get the meta fields for manipulation.

<?php
add_action( 'save_post', 'save_update_redeem_requests', 12, 3 );

Above code works superbly.

#4 @mklasen
5 months ago

Just ran into this myself.

  1. Create new CPT post in dashboard
  2. Enter post title + metadata in CMB2
  3. Save.

When hooking into save_post with priority 90, the get_post_meta($id) return is:

array(1) { ["_edit_last"]=> array(1) { [0]=> string(1) "1" } }

When hooking into save_post_{$post->post_type} with priority 90, the return is:

array(4) { ["_edit_lock"]=> array(1) { [0]=> string(12) "1514291087:1" } ["_edit_last"]=> array(1) { [0]=> string(1) "1" } ["_custom_meta_value_1"]=> array(1) { [0]=> string(5) "test1" } ["_custom_meta_value_2"]=> array(1) { [0]=> string(5) "test2" } }
Note: See TracTickets for help on using tickets.