WordPress点击Update后获取最新post_meta并更新关联字段问题
解决WordPress中ACF字段更新后获取旧值的问题
问题场景
- 基于WordPress自定义后台搭建HRM系统,包含多个自定义文章类型(CPT)
- 请假申请(
vosooliCPT)通过ACF下拉字段设置审批状态,状态变更时需同步更新关联的「出入记录」CPT的post_meta - 当前代码逻辑可行,但点击Update/Publish后,获取的是ACF字段的旧值,而非修改后的新值
用户原代码:
function update_vosooli_status_to_portal( $post_id, $post ) { global $wpdb,$post; // ID of second post that we should update it // The ID is stored in current post meta (custom field). $target_post_id = get_post_meta($post->ID, 'parvande_id_invosolli', true); // Getting value of Status field. This is getting also previous value. This is problem: $request_status = get_post_meta($post->ID, 'vosooli_status', true); // This is value when field is selected to approved // I'm using this to compare it with value of "$request_status" $request_status_approved = 'Approved Request'; // Check if "$request_status" is equal to "$request_status_approved" if( $request_status == $request_status_approved ) { // This will update another post meta in another post with custom value update_post_meta($target_post_id, 'parvandeh_completaion', 'The staff took leave'); } } // my CPT is "vosooli" so I used "publish_vosooli" to run functions when updating the post add_action( 'publish_vosooli', 'update_vosooli_status_to_portal', 10, 2 );
问题原因
你使用的publish_vosooli钩子触发时机过早,此时ACF的新值还未写入数据库,所以get_post_meta拿到的是打开编辑页时的旧值。
解决方案
方法1:用ACF专属钩子(最推荐)
ACF自带acf/save_post钩子,会在ACF字段保存完成后触发,把优先级设为20,确保字段已经写入数据库:
function update_vosooli_status_to_portal( $post_id ) { // 跳过自动保存和修订版本 if ( wp_is_post_autosave( $post_id ) || wp_is_post_revision( $post_id ) ) { return; } // 只处理vosooli类型的文章 if ( get_post_type( $post_id ) !== 'vosooli' ) { return; } // 用ACF的get_field直接获取最新值 $request_status = get_field( 'vosooli_status', $post_id ); $target_post_id = get_field( 'parvande_id_invosolli', $post_id ); $request_status_approved = 'Approved Request'; if ( $request_status == $request_status_approved && $target_post_id ) { update_post_meta( $target_post_id, 'parvandeh_completaion', 'The staff took leave' ); } } // 优先级设为20,确保ACF字段已保存 add_action( 'acf/save_post', 'update_vosooli_status_to_portal', 20 );
方法2:调整save_post钩子优先级
不想用ACF钩子的话,改用save_post_vosooli钩子,把优先级调高到20,让它在默认保存逻辑之后执行:
function update_vosooli_status_to_portal( $post_id, $post ) { // 跳过自动保存和修订版本 if ( wp_is_post_autosave( $post_id ) || wp_is_post_revision( $post_id ) ) { return; } // 获取最新的post_meta值 $request_status = get_post_meta( $post_id, 'vosooli_status', true ); $target_post_id = get_post_meta( $post_id, 'parvande_id_invosolli', true ); $request_status_approved = 'Approved Request'; if ( $request_status == $request_status_approved && $target_post_id ) { update_post_meta( $target_post_id, 'parvandeh_completaion', 'The staff took leave' ); } } // 用save_post_vosooli钩子,优先级设为20 add_action( 'save_post_vosooli', 'update_vosooli_status_to_portal', 20, 2 );
方法3:直接从POST数据取新值
如果需要更早触发逻辑,可以直接从$_POST里读提交的ACF值(记得做安全验证):
function update_vosooli_status_to_portal( $post_id, $post ) { // 跳过自动保存和修订版本 if ( wp_is_post_autosave( $post_id ) || wp_is_post_revision( $post_id ) ) { return; } // 验证用户权限和POST数据是否存在 if ( ! current_user_can( 'edit_post', $post_id ) || empty( $_POST['acf'] ) ) { return; } // 替换成你实际的ACF字段ID(在ACF编辑页能看到) $request_status = $_POST['acf']['field_xxxxxx']; $target_post_id = $_POST['acf']['field_yyyyyy']; $request_status_approved = 'Approved Request'; if ( $request_status == $request_status_approved && $target_post_id ) { update_post_meta( $target_post_id, 'parvandeh_completaion', 'The staff took leave' ); } } add_action( 'publish_vosooli', 'update_vosooli_status_to_portal', 10, 2 );
注意:方法3需要你去ACF字段编辑页面找到对应字段的ID,替换代码里的
field_xxxxxx和field_yyyyyy。
内容的提问来源于stack exchange,提问作者Ahmad Karimi
相关产品推荐
相关产品推荐

