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

WordPress Ajax调用报400(Bad Request)错误求助

WordPress Ajax请求400错误排查与修复方案

问题背景

在WordPress环境中,指定页面(ID2614、2654)加载的JavaScript发起Ajax调用返回400(Bad Request),PHP处理函数AjaxSessionIDerzeugen完全未触发。已确认JS和PHP文件加载正常,Ajax URL正确,action参数配置无误,但钩子未生效。


1. 页面判断逻辑错误(functions.php)

原代码中页面判断使用了赋值运算符=而非比较运算符==,导致无论当前页面ID是什么,条件都会强制为真,可能引发不必要的代码加载冲突,甚至干扰其他页面的AJAX逻辑。

修复代码:

function LoadScriptsOnSpecificPages(){
    global $wp_query;
    $page_id = intval($wp_query->queried_object->ID);
    
    // Page ID 2614 = Buchung Auswahl Raum, Page ID 2654 = Buchung abschließen
    if (($page_id == 2614) || ($page_id == 2654)) {
        include get_stylesheet_directory() . '/custom/booking.php';
        // 修改脚本ID为唯一标识,避免与通用名称冲突
        wp_enqueue_script( 'booking-script', get_stylesheet_directory_uri() . '/custom/booking.js', array( 'jquery' ), 1.1, true);
    }
}
add_action('template_redirect', 'LoadScriptsOnSpecificPages');

2. AJAX钩子注册时机过晚(booking.php)

在template_redirect钩子中才引入booking.php,而wp_ajax_*系列钩子需要在init或更早的阶段完成注册,才能被WordPress的AJAX机制识别。当前注册时机延迟,导致钩子未被正确挂载。

修复方案:
将booking.php的引入移到functions.php的顶部(或after_setup_theme钩子中),确保钩子在WordPress初始化流程早期完成注册;或者直接把钩子注册代码迁移到functions.php中,避免延迟加载导致的钩子失效。

3. SQL语法错误(AjaxSessionIDerzeugen函数)

原SQL语句存在明显语法错误,即使函数被触发,也会因SQL执行失败导致异常,且当前代码未处理错误反馈。同时未使用WordPress内置的防注入机制,存在安全风险。

修复代码:

// Ajax Session ID erzeugen
function AjaxSessionIDerzeugen() {
    global $wpdb;
    
    // 验证nonce(后续步骤添加)
    if (!wp_verify_nonce($_POST['nonce'], 'booking_session_nonce')) {
        wp_send_json_error(array('message' => '无效的安全令牌'));
    }

    // 校验请求合法性
    if ( isset($_POST['action']) && $_POST['action'] === 'AjaxSessionIDerzeugen' ) {
        // 结合IP增强session_id唯一性
        $session_id = substr(md5(time() . $_SERVER["REMOTE_ADDR"]), 0, 10);
        // 使用$wpdb->prepare防止SQL注入,修复INSERT语法
        $strsql = $wpdb->prepare("INSERT INTO tbl_buchungen (session_id) VALUES (%s)", $session_id);
        $result = $wpdb->query($strsql);

        $arr = array();
        if ($result !== false) {
            $arr['pruefergebnis'] = "ok";
            $arr['session_id'] = $session_id;
        } else {
            $arr['pruefergebnis'] = "error";
            $arr['message'] = $wpdb->last_error;
        }

        // WordPress内置JSON输出函数,自动处理header和终止程序
        wp_send_json($arr);
    }
    wp_send_json_error(array('message' => '无效请求'));
}

4. 缺少CSRF安全验证(WordPress强制要求)

WordPress默认对未登录用户的AJAX请求要求CSRF令牌(nonce),缺少令牌会直接触发400错误,这是最常见的导致AJAX 400的原因。

修复步骤:

  1. 在PHP中添加nonce到脚本本地化数据(替代原define_ajax_url函数):
function booking_enqueue_scripts() {
    wp_localize_script( 'booking-script', 'bookingAjax', array(
        'ajaxurl' => admin_url('admin-ajax.php'),
        'nonce' => wp_create_nonce('booking_session_nonce')
    ) );
}
add_action('wp_enqueue_scripts', 'booking_enqueue_scripts');
  1. 修改JS中的AJAX请求:
if ((session_id == '') || (session_id == null)) {
    $.ajax({
        url: bookingAjax.ajaxurl,
        type: 'POST', // 指定POST方法,符合WordPress AJAX规范
        data: {
            'action':'AjaxSessionIDerzeugen',
            'nonce': bookingAjax.nonce // 携带安全令牌
        },
        success:function(antwort) {
            pruefergebnis = antwort.pruefergebnis;

            if (pruefergebnis == 'ok') {
                session_id = antwort.session_id;
                // 修正cookie过期时间格式,max-age更直观
                document.cookie = "session_id=" + session_id + "; max-age=3600; path=/";
            } else {
                window.alert(antwort.message || pruefergebnis);
            }
        },
        error: function(xhr, status, error){
            window.alert('请求错误: ' + error);
        }
    });
}

5. 无效代码干扰(AjaxSessionIDerzeugen函数)

原函数中存在无意义的callback:标签,虽然不会直接导致400错误,但属于无效代码,可能引发解析问题,建议直接移除。


内容的提问来源于stack exchange,提问作者Jörg

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.03 11:10:21