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

PHP无法获取jQuery Ajax PUT请求提交的FormData表单数据

问题根因
  1. 核心错误:parse_str() 仅支持解析application/x-www-form-urlencoded格式的请求体,当前端通过FormData传参时,请求Content-Type为multipart/form-data,请求内容是带WebKitFormBoundary分隔符的分段格式,parse_str()无法识别这种结构,会把整段请求内容识别为单个键名,自然无法读取id等字段值。
  2. 额外隐藏bug:GET分支漏写break,会导致GET请求执行完getGebruiker()后继续向下执行createGebruiker()逻辑。
  3. POST请求能正常运行是因为PHP原生会自动解析multipart/form-data格式的POST请求,将数据写入$_POST全局变量,但PHP不会对PUT、DELETE请求做这类自动解析。DELETE请求之前能正常运行,大概率是因为传DELETE请求时用的不是FormData,而是urlencoded格式参数,可以被parse_str()正常识别。
修复方案

二选一即可,根据业务场景选择:

方案1:后端增加multipart格式PUT请求解析(推荐,兼容现有前端逻辑、支持文件上传)

替换PUT分支原有解析逻辑,同时补上GET分支缺失的break:

$requestMethod = $_SERVER['REQUEST_METHOD'];
switch ($requestMethod) {
    case "GET":
        getGebruiker();
        break; // 补全缺失的break
    case "POST":
        createGebruiker();
        break;
    case "PUT":
        $rawInput = file_get_contents('php://input');
        $contentType = $_SERVER['CONTENT_TYPE'] ?? '';
        $_PUT = [];

        // 识别multipart/form-data格式
        if (strpos($contentType, 'multipart/form-data') === 0) {
            preg_match('/boundary=(.*)$/', $contentType, $boundaryMatch);
            $boundary = $boundaryMatch[1] ?? '';
            if ($boundary) {
                $blocks = explode("--" . $boundary, $rawInput);
                foreach ($blocks as $block) {
                    $block = trim($block);
                    if (empty($block) || $block === '--') continue;
                    // 拆分字段头和字段值
                    [$header, $value] = explode("\r\n\r\n", $block, 2);
                    $value = rtrim($value, "\r\n");
                    // 提取字段名
                    if (preg_match('/name="([^"]+)"/', $header, $nameMatch)) {
                        $_PUT[$nameMatch[1]] = $value;
                    }
                }
            }
        } else {
            // 兼容x-www-form-urlencoded格式
            parse_str($rawInput, $_PUT);
        }

        print_r($_PUT);
        echo $_PUT['id'];
        updateGebruiker();
        break;
    case "DELETE":
        parse_str(file_get_contents("php://input"), $_DELETE);
        deleteGebruiker();
        break;
    default:
        exit();
}

方案2:前端改传urlencoded格式参数(仅适合无文件上传的表单)

如果表单不需要上传文件,可以去掉FormData,直接序列化表单为urlencoded格式,后端原有解析逻辑不需要修改:

$('#bewerkGebruikerForm').on('submit', function(event) {
    event.preventDefault();
    // 直接序列化表单为urlencoded格式
    const formData = $(this).serialize();

    $.ajax({
        url: 'http://localhost/P08/hoornhek/api/gebruiker.php',
        type: 'put',
        data: formData,
        dataType: 'json',
        success: function(response) {
            if(response['success']) {
                $('#bewerkGebruikerModal').hide();
                window.location.reload();
            } else {
                showErrors(response.errors);
            }
        },
        error: function(error) {
            showErrors(error.errors);
        }
    });
});

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.30 01:12:45