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

如何在WooCommerce中通过PHP永久更新购物车自定义字段?

解决WooCommerce购物车旅游票种数量永久保存问题

直接修改WC()->cart->cart_contents数组仅会在当前请求的内存中生效,不会自动同步到session或数据库。要实现持久化修改,需要遵循WooCommerce的购物车更新机制,以下是完整的解决方案:

核心问题分析

WooCommerce购物车数据默认存储在用户session中(登录用户会同步到用户元数据),仅修改数组不会触发持久化操作,必须调用WooCommerce提供的方法完成session更新。

完整实现代码

1. 注册WordPress Ajax端点(PHP后端)

// 注册Ajax接口,支持登录/未登录用户
add_action('wp_ajax_update_ticket_qty', 'update_ticket_quantity_in_cart');
add_action('wp_ajax_nopriv_update_ticket_qty', 'update_ticket_quantity_in_cart');

function update_ticket_quantity_in_cart() {
    // 验证请求合法性(防CSRF攻击)
    if (!isset($_POST['nonce']) || !wp_verify_nonce($_POST['nonce'], 'update_ticket_qty_nonce')) {
        wp_send_json_error(['message' => '非法请求']);
    }

    // 接收并过滤前端参数
    $cart_item_key = sanitize_text_field($_POST['cart_item_key']);
    $ticket_index = intval($_POST['ticket_index']); // 0=成人票,1=儿童票
    $new_qty = intval($_POST['new_qty']);

    // 确保购物车初始化完成
    if (!WC()->cart) {
        wp_send_json_error(['message' => '购物车未加载']);
    }

    // 检查目标购物车项是否存在
    if (!isset(WC()->cart->cart_contents[$cart_item_key])) {
        wp_send_json_error(['message' => '购物车项不存在']);
    }

    // 修改票种数量
    $cart_item = &WC()->cart->cart_contents[$cart_item_key];
    if (isset($cart_item['ttbm_ticket_info'][$ticket_index])) {
        $cart_item['ttbm_ticket_info'][$ticket_index]['ticket_qty'] = $new_qty;

        // 关键:将修改同步到session,实现持久化
        WC()->cart->set_session();

        // 重新计算购物车总价(可选,根据票种是否影响价格决定)
        WC()->cart->calculate_totals();

        wp_send_json_success([
            'message' => '票种数量更新成功',
            'cart_total' => WC()->cart->get_cart_total()
        ]);
    } else {
        wp_send_json_error(['message' => '目标票种不存在']);
    }
}

2. 前端请求示例(配合你的现有JS)

// 发送更新请求的函数
function submitTicketQtyUpdate(cartItemKey, ticketIndex, newQty) {
    jQuery.ajax({
        url: ajaxurl, // WordPress全局变量,无需手动定义
        method: 'POST',
        data: {
            action: 'update_ticket_qty',
            nonce: jQuery('#update_ticket_qty_nonce').val(), // 页面中需输出nonce字段
            cart_item_key: cartItemKey,
            ticket_index: ticketIndex,
            new_qty: newQty
        },
        success: function(res) {
            if (res.success) {
                // 这里更新你的前端购物车显示
                console.log(res.data.message);
                jQuery('.cart-total').text(res.data.cart_total);
            } else {
                alert(res.data.message);
            }
        },
        error: function() {
            alert('更新失败,请重试');
        }
    });
}

// 在购物车页面模板中输出nonce(必须添加)
// <?php wp_nonce_field('update_ticket_qty_nonce', 'update_ticket_qty_nonce'); ?>

关键注意事项

  • Nonce验证:必须添加,这是WordPress Ajax的安全标准流程,防止恶意请求。
  • set_session()方法:这是你之前代码缺失的核心步骤,调用后WooCommerce会将修改后的购物车数据写入session,登录用户会自动同步到数据库的用户元数据。
  • 参数过滤:所有前端传入的参数必须经过sanitize_*或类型转换处理,避免安全风险。
  • 总价计算:如果票种数量影响产品价格,必须调用calculate_totals()重新计算购物车金额、税费等数据。

内容的提问来源于stack exchange,提问作者Вадим Турчинович

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.17 19:52:34