Discuz附件上传失败主因是PHP临时目录权限不足或upload_tmp_dir未显式配置,导致move_uploaded_file失败;需检查并设置独立可写tmp目录、同步调大upload_max_filesize/post_max_size/client_max_body_size,再确认data/attachment路径权限与磁盘空间。

Discuz发帖附件上传失败的典型现象
点击“上传附件”后无反应、进度条卡住、提示“上传失败”或直接跳转回编辑页,后台日志里常出现 upload_tmp_dir 相关警告或 PHP Warning: move_uploaded_file(): Unable to move 错误。这不是Discuz配置问题,而是PHP底层上传链路断在了系统临时目录环节。
检查并修复 upload_tmp_dir 权限与归属
宝塔默认不会显式设置 upload_tmp_dir,PHP会 fallback 到系统默认临时目录(如 /tmp),但该目录往往被设为 root:root 且权限为 1777 —— 这会导致 PHP-FPM 以网站运行用户(如 www)身份无法写入临时文件。
- 先确认当前生效的临时目录:
php -i | grep upload_tmp_dir,若为空,说明用的是系统默认值 - 检查
/tmp权限:ls -ld /tmp,正常应为drwxrwxrwt 1 root root ... /tmp;但部分云服务器或加固环境会改成drwxr-xr-x,这就必须改 - 推荐做法:不依赖
/tmp,在宝塔面板中为该站点单独指定一个可写的临时目录,例如/www/wwwroot/bbs.example.com/tmp - 创建目录并授权:
mkdir -p /www/wwwroot/bbs.example.com/tmp && chown www:www /www/wwwroot/bbs.example.com/tmp && chmod 755 /www/wwwroot/bbs.example.com/tmp - 在站点的PHP配置中添加:
upload_tmp_dir = /www/wwwroot/bbs.example.com/tmp,然后重启PHP
同步检查 post_max_size 和 upload_max_filesize
即使临时目录可写,如果这两个值太小,也会在上传中途被PHP截断,且通常不报明确错误,只表现为“无声失败”。Discuz附件功能对这两个值敏感度高于普通表单。
-
upload_max_filesize控制单个文件上限,post_max_size必须 ≥ 它(还要预留表单字段开销),建议设为20M和24M - 注意:宝塔面板中修改的是PHP配置,但有些用户会误改Nginx的
client_max_body_size—— 这个也必须同步调大,否则请求根本到不了PHP层,Nginx会直接返回413 Request Entity Too Large - 验证是否生效:在站点根目录放一个
info.php,内容为<?php phpinfo(); ?>,访问后搜索关键词确认数值已更新
Discuz自身附件路径与磁盘空间容易被忽略
临时目录和PHP限制都通了,上传仍失败?下一步盯死Discuz的附件保存路径。它默认存到 /data/attachment,这个目录的父路径(通常是 /www/wwwroot/...)如果磁盘满、inode耗尽、或 data 目录权限不是 www:www,move操作照样失败。
立即学习“PHP免费学习笔记(深入)”;
- 检查磁盘剩余:
df -h和df -i - 确认
/www/wwwroot/bbs.example.com/data/attachment存在且可写:ls -ld /www/wwwroot/bbs.example.com/data/attachment,应为drwxr-xr-x 3 www www类似结构 - 如果该目录不存在,Discuz不会自动创建,需手动建好并赋权:
mkdir -p /www/wwwroot/bbs.example.com/data/attachment && chown -R www:www /www/wwwroot/bbs.example.com/data - Discuz后台「站长」→「数据库」→「升级」里有时会因附件表损坏导致上传逻辑异常,可尝试执行
repair table pre_forum_attachment(仅当确定是DB问题时)
upload_max_filesize、post_max_size、client_max_body_size)→ 最后落到Discuz附件落地目录的磁盘与权限。中间任意一环断掉,上传就静默失败。



















