PHP上传HTML表单文件至MariaDB LONGBLOB列失败求助
解决MariaDB LONGBLOB字段无法存储上传文件的问题
问题描述
尝试通过HTML表单将文件上传至MariaDB的buchzusammenfassung表,目前表中已成功生成包含idSchueler和idBuch的条目,但文件始终无法存入LONGBLOB类型的datei字段中。
现有代码
显示上传表单的PHP代码
<?php session_start(); if ($_SESSION["rolle"] === "schueler" && isset($_GET['id'])) { $buchId = $_GET['id']; $dbHost = '...'; $dbUser = '...'; $dbPass = '...'; $dbName = '...'; $conn = new mysqli($dbHost, $dbUser, $dbPass, $dbName); if ($conn->connect_error) { die("Verbindung zur Datenbank fehlgeschlagen: " . $conn->connect_error); } // 获取书籍信息 $sql = "SELECT title FROM buecher WHERE id = ?"; $stmt = $conn->prepare($sql); $stmt->bind_param("i", $buchId); $stmt->execute(); $result = $stmt->get_result(); if ($result->num_rows == 1) { $row = $result->fetch_assoc(); $buchtitel = $row['title']; // 输出上传表单 echo '<h2>Zusammenfassung für das Buch: ' . $buchtitel . '</h2>'; echo '<form action="upload_zusammenfassung.php" method="post" enctype="multipart/form-data">'; echo ' <input type="file" name="zusammenfassung" id="zusammenfassung">'; echo ' <input type="hidden" name="buch_id" value="' . $buchId . '">'; echo ' <input type="submit" value="Zusammenfassung hochladen">'; echo '</form>'; } else { echo "Buch nicht gefunden."; } $stmt->close(); } ?>
处理上传的PHP代码
<?php error_reporting(E_ALL); session_start(); if ($_SESSION["rolle"] === "schueler" && isset($_FILES['zusammenfassung']) && isset($_POST['buch_id'])) { // 连接数据库 $dbHost = '...'; $dbUser = '...'; $dbPass = '...'; $dbName = '...'; $conn = new mysqli($dbHost, $dbUser, $dbPass, $dbName); if ($conn->connect_error) { die("Verbindung zur Datenbank fehlgeschlagen: " . $conn->connect_error); } $buchId = $_POST['buch_id']; // 获取文件信息 $dateiTmpName = $_FILES['zusammenfassung']['tmp_name']; $dateiDaten = file_get_contents($dateiTmpName); // 根据用户名获取学生ID $schuelerBenutzername = $_SESSION["username"]; $sqlSchuelerId = "SELECT id_student FROM students WHERE newUsername = ?"; $stmtSchuelerId = $conn->prepare($sqlSchuelerId); $stmtSchuelerId->bind_param("s", $schuelerBenutzername); $stmtSchuelerId->execute(); $stmtSchuelerId->bind_result($schuelerId); $stmtSchuelerId->fetch(); $stmtSchuelerId->close(); // 插入文件到数据库 $sql = "INSERT INTO buchzusammenfassung (idSchueler, idBuch, datei) VALUES (?, ?, ?)"; $stmt = $conn->prepare($sql); $stmt->bind_param("iib", $schuelerId, $buchId, $dateiDaten); if ($stmt->execute()) { echo "Die Zusammenfassung wurde erfolgreich hochgeladen und in der Datenbank gespeichert."; } else { echo "Fehler beim Hochladen der Zusammenfassung."; } $stmt->close(); $conn->close(); } ?>
问题分析与解决方案
1. 缺失文件上传错误检查
现有代码未验证文件是否成功上传,若上传过程中出现错误(如临时文件丢失、大小超限),会导致file_get_contents读取失败,最终存入空值。
修复: 在处理上传的代码开头加入错误检查:
if ($_FILES['zusammenfassung']['error'] !== UPLOAD_ERR_OK) { die("文件上传失败,错误码:" . $_FILES['zusammenfassung']['error']); } // 检查临时文件是否存在 if (!file_exists($dateiTmpName)) { die("临时文件不存在"); } // 验证文件读取是否成功 $dateiDaten = file_get_contents($dateiTmpName); if ($dateiDaten === false) { die("无法读取上传文件"); }
2. Blob数据绑定方式错误
使用bind_param("iib", ...)直接绑定大文件数据时,若文件大小超过MySQL的数据包限制,会导致数据截断或无法写入。正确做法是配合send_long_data方法分块传递Blob数据。
修复: 修改插入数据的代码段:
// 预处理SQL语句 $sql = "INSERT INTO buchzusammenfassung (idSchueler, idBuch, datei) VALUES (?, ?, ?)"; $stmt = $conn->prepare($sql); if (!$stmt) { die("预处理语句创建失败:" . $conn->error); } // 绑定前两个参数,第三个Blob参数先设为null $stmt->bind_param("iiB", $schuelerId, $buchId, null); // 分块发送Blob数据 $stmt->send_long_data(2, $dateiDaten); // 执行插入 if ($stmt->execute()) { echo "摘要已成功上传并存储到数据库。"; } else { echo "上传失败:" . $stmt->error; }
3. 数据库与PHP配置限制
MariaDB配置: 检查
max_allowed_packet参数,若值过小会限制Blob数据的大小。执行以下SQL查询当前值:SHOW VARIABLES LIKE 'max_allowed_packet';若值小于文件大小,需修改
my.cnf(或my.ini):[mysqld] max_allowed_packet=64M重启MariaDB服务生效。
PHP配置: 检查
php.ini中以下参数,确保上传文件大小不被限制:upload_max_filesize:单个上传文件的最大大小post_max_size:POST请求的总大小(需大于upload_max_filesize)memory_limit:PHP可用内存上限(需足够读取文件)
4. 补充学生ID查询的错误检查
现有代码未验证学生ID是否查询成功,若用户名不存在会导致idSchueler为空,影响插入逻辑。
修复:
$stmtSchuelerId->execute(); $stmtSchuelerId->bind_result($schuelerId); if (!$stmtSchuelerId->fetch()) { die("未找到对应用户的学生ID"); } $stmtSchuelerId->close();
完整修复后的处理代码
<?php error_reporting(E_ALL); ini_set('display_errors', 1); // 开启错误显示,方便调试 session_start(); if ($_SESSION["rolle"] === "schueler" && isset($_FILES['zusammenfassung']) && isset($_POST['buch_id'])) { // 检查文件上传状态 if ($_FILES['zusammenfassung']['error'] !== UPLOAD_ERR_OK) { die("文件上传失败,错误码:" . $_FILES['zusammenfassung']['error']); } $dateiTmpName = $_FILES['zusammenfassung']['tmp_name']; // 验证临时文件存在性 if (!file_exists($dateiTmpName)) { die("临时文件丢失"); } // 读取文件内容 $dateiDaten = file_get_contents($dateiTmpName); if ($dateiDaten === false) { die("无法读取上传文件"); } // 数据库连接 $dbHost = '...'; $dbUser = '...'; $dbPass = '...'; $dbName = '...'; $conn = new mysqli($dbHost, $dbUser, $dbPass, $dbName); if ($conn->connect_error) { die("数据库连接失败:" . $conn->connect_error); } $buchId = $_POST['buch_id']; $schuelerBenutzername = $_SESSION["username"]; // 查询学生ID $sqlSchuelerId = "SELECT id_student FROM students WHERE newUsername = ?"; $stmtSchuelerId = $conn->prepare($sqlSchuelerId); $stmtSchuelerId->bind_param("s", $schuelerBenutzername); $stmtSchuelerId->execute(); $stmtSchuelerId->bind_result($schuelerId); if (!$stmtSchuelerId->fetch()) { die("未找到该用户的学生信息"); } $stmtSchuelerId->close(); // 插入Blob数据到数据库 $sql = "INSERT INTO buchzusammenfassung (idSchueler, idBuch, datei) VALUES (?, ?, ?)"; $stmt = $conn->prepare($sql); if (!$stmt) { die("预处理语句创建失败:" . $conn->error); } $stmt->bind_param("iiB", $schuelerId, $buchId, null); $stmt->send_long_data(2, $dateiDaten); if ($stmt->execute()) { echo "摘要已成功上传并存储到数据库。"; } else { echo "上传失败:" . $stmt->error; } $stmt->close(); $conn->close(); } else { die("权限不足或参数缺失"); } ?>
内容的提问来源于stack exchange,提问作者Ro Man
相关产品推荐
相关产品推荐

