Ubuntu18.04下Nginx+PHP7.2-FPM上传文件时POST数据丢失求助
从你的描述来看,这个问题明显是Nginx与PHP-FPM之间的请求体传递出现了截断或解析错误——毕竟在Apache/mod_php环境下一切正常,说明代码逻辑本身没问题。下面是针对你场景的具体排查和解决步骤:
1. 先排查Nginx的请求体缓冲配置
Nginx默认会缓冲请求体后再传递给FastCGI,但如果缓冲配置不当,会导致大一点的请求(哪怕只有10KB)被截断:
- 检查你的Nginx server或location块中是否有
fastcgi_request_buffering off;,如果有,改成on:fastcgi_request_buffering on; - 同时调整FastCGI缓冲大小,避免因缓冲不足导致截断:
fastcgi_buffer_size 64k; fastcgi_buffers 4 64k;
2. 确保Nginx与PHP的文件大小限制匹配
虽然你说php.ini配置正常,但Nginx的client_max_body_size必须和PHP的upload_max_filesize、post_max_size保持一致,否则Nginx会直接拒绝请求或截断:
# 在server块中添加,值和php.ini中的对应参数一致,比如20M client_max_body_size 20M;
3. 检查FastCGI参数传递是否完整
Symfony文档的虚拟主机配置可能遗漏了关键的请求头参数,导致PHP无法正确解析multipart/form-data请求体。确保你的location ~ \.php$块中包含以下参数:
fastcgi_param CONTENT_TYPE $content_type; fastcgi_param CONTENT_LENGTH $content_length; fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name; fastcgi_param REQUEST_METHOD $request_method; fastcgi_param QUERY_STRING $query_string;
这几个参数是PHP正确解析POST请求和文件上传的核心,缺少任何一个都可能导致请求体解析异常。
4. 排查PHP-FPM的Socket权限(如果用Unix Socket)
如果你的PHP-FPM使用Unix Socket而非TCP连接,要确保Nginx进程有权限访问这个Socket文件:
- 打开PHP-FPM的
www.conf配置文件(通常在/etc/php/7.2/fpm/pool.d/下):listen = /run/php/php7.2-fpm.sock listen.owner = www-data listen.group = www-data listen.mode = 0660 - 确认Nginx的运行用户是
www-data(查看nginx.conf中的user指令),否则会导致请求传递失败。
5. 关于access.log中出现图片二进制的问题
这其实是请求处理失败的结果,而不是原因:当Nginx无法正确传递请求体给PHP-FPM时,可能会把未处理完的请求体(比如图片二进制)误当成新的请求URI,从而产生400/500状态码的日志。解决了前面的核心问题后,这个现象自然会消失。
6. 额外测试:简化表单排除代码影响
为了确认不是嵌套数组导致的解析问题,你可以先写一个极简的测试表单:
<?php var_dump($_POST, $_FILES); ?> <form method="post" enctype="multipart/form-data"> <input type="file" name="posterFrame"> <input type="text" name="duration" value="123"> <button type="submit">提交</button> </form>
如果这个简化表单仍然出现duration丢失的情况,说明问题完全在服务器配置;如果正常,再回头排查嵌套数组的解析(比如检查php.ini的max_input_vars是否足够,不过你的字段数量远低于默认值1000)。
最后:开启Nginx Debug日志(可选)
如果以上步骤都没解决问题,可以开启Nginx的Debug日志来追踪请求体的处理过程:
error_log /var/log/nginx/error_debug.log debug;
重新发送请求后,查看日志中关于fastcgi和request body的部分,就能找到截断或错误的具体原因。
内容的提问来源于stack exchange,提问作者user2792352

