You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WordPress使用AJAX更新post_meta关联数组时数据库字段清空问题

问题核心原因

本次字段被清空最直接的原因是PHP端json_decode默认返回对象,而_wc_booking_pricing字段要求存储数组格式,格式不匹配导致更新失败直接写入空值。同时还存在其他潜在逻辑漏洞,完整问题如下:

  • 后端未校验传入的JSON有效性,空值/无效JSON解码后为null,直接存储就会清空字段
  • 前端输出JSON的div可能存在多余空白字符,导致JSON解析失败拿到空数组
  • 用循环计数器作为删除索引,删除一次后数组索引重排、页面索引未同步,后续删除会操作错误元素
  • 两层重复的ready事件包裹逻辑,可能导致初始化异常
修复步骤

1. 修改前端标记,改用原始数组键作为删除标识

避免计数器索引不匹配问题:

<?php
$response_cost = get_post_meta( 379, '_wc_booking_pricing', true );
?>
<!-- 输出JSON时去掉多余换行空白,加trim避免解析错误 -->
<div id="response-cost" class="hidden"><?php echo trim(json_encode( $response_cost, JSON_UNESCAPED_UNICODE )); ?></div>

<?php
// 直接用原始数组的键作为标识,不用计数器
foreach ($response_cost as $key => $response) { ?> 
    <tr id="array-<?php echo esc_attr($key); ?>">
        <!-- 其他表格列代码 -->
        <td><button class="remove-array" data-key="<?php echo esc_attr($key); ?>"><i class="fa fa-times"></i></button></td>
    </tr>
<?php }; ?>

2. 优化JS逻辑,加容错处理

去掉重复的ready事件,添加JSON解析容错,用键删除而不是splice适配关联数组:

(function($) {
    $(document).ready(function () {
        // 取文本后先trim去掉首尾空白
        const arrString = $('#response-cost').text().trim();
        let arr = [];
        // 加解析容错,避免无效JSON导致后续逻辑崩溃
        try {
            arr = JSON.parse(arrString);
        } catch (e) {
            console.error('定价数据解析失败', e);
            return;
        }

        $('.remove-array').click(function(){
            const targetKey = $(this).data("key");
            if (!arr.hasOwnProperty(targetKey)) return;

            // 删除对应键的元素
            delete arr[targetKey];
            const arr_stringify = JSON.stringify(arr);

            $.ajax({
                url: ajax_object.ajaxurl,
                type: 'POST',
                data:{
                    action: 'update_cost_rule_table_action',
                    stringified_arr: arr_stringify,
                },
                success: function( data ){
                    console.log( data );
                    // 删除成功后直接移除对应行,避免重复点击
                    $(this).closest('tr').remove();
                }.bind(this)
            });
        });
    });
})(jQuery);

3. 修复后端处理逻辑,加校验+返回数组

add_action( 'wp_ajax_update_cost_rule_table_action', 'update_cost_rule_table' );
add_action( 'wp_ajax_nopriv_update_cost_rule_table_action', 'update_cost_rule_table' );
function update_cost_rule_table(){
    // 先校验参数是否存在
    if (empty($_POST['stringified_arr'])) {
        wp_send_json_error('缺少提交数据');
    }
    // 第二个参数设为true,强制返回关联数组而不是对象
    $response_cost = json_decode(sanitize_text_field($_POST['stringified_arr']), true);
    // 校验解码是否成功
    if (json_last_error() !== JSON_ERROR_NONE || !is_array($response_cost)) {
        wp_send_json_error('数据格式错误');
    }
    // WC原生字段用update_post_meta更稳妥,不需要调用ACF的update_field
    update_post_meta(379, '_wc_booking_pricing', $response_cost);
    wp_send_json_success('更新成功');
}

4. 脚本入队优化(可选)

加版本号避免缓存导致修改不生效:

function gt21_scripts() {
    // 最后一个参数设为true,把脚本放到页脚加载,避免DOM未加载就执行
    wp_register_script( 'cost-rule', get_template_directory_uri() . '/js/cost-rule.js', array( 'jquery' ), '1.0', true );
    wp_enqueue_script( 'cost-rule' );
    wp_localize_script( 'cost-rule', 'ajax_object', array( 'ajaxurl' => admin_url( 'admin-ajax.php' ) ) );
};
add_action( 'wp_enqueue_scripts', 'gt21_scripts' );

内容的提问来源于stack exchange,提问作者Eric Brockman

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.29 11:27:03