php实现异步图片上传
使用Ajax与FormData实现异步上传
在PHP中实现异步图片上传,可以通过前端Ajax结合FormData对象发送文件数据,后端PHP接收并处理。以下是具体实现方法:
创建HTML表单:
<form id="uploadForm" enctype="multipart/form-data">
<input type="file" name="image" id="image" accept="image/*">
<button type="submit">上传</button>
</form>
<div id="progress"></div>
<div id="result"></div>
前端JavaScript代码:
document.getElementById('uploadForm').addEventListener('submit', function(e) {
e.preventDefault();
let formData = new FormData(this);
let xhr = new XMLHttpRequest();
xhr.upload.addEventListener('progress', function(event) {
if (event.lengthComputable) {
let percent = Math.round((event.loaded / event.total) * 100);
document.getElementById('progress').innerHTML = '上传进度: ' + percent + '%';
}
});
xhr.onreadystatechange = function() {
if (xhr.readyState === 4) {
document.getElementById('result').innerHTML = xhr.responseText;
}
};
xhr.open('POST', 'upload.php', true);
xhr.send(formData);
});
PHP后端处理脚本
创建upload.php处理上传:

<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_FILES['image'])) {
$targetDir = "uploads/";
$targetFile = $targetDir . basename($_FILES["image"]["name"]);
$uploadOk = 1;
$imageFileType = strtolower(pathinfo($targetFile, PATHINFO_EXTENSION));
// 检查是否为真实图片
$check = getimagesize($_FILES["image"]["tmp_name"]);
if ($check === false) {
echo "文件不是有效的图片";
$uploadOk = 0;
}
// 检查文件大小(限制为5MB)
if ($_FILES["image"]["size"] > 5000000) {
echo "文件过大";
$uploadOk = 0;
}
// 允许特定格式
$allowedTypes = ['jpg', 'png', 'jpeg', 'gif'];
if (!in_array($imageFileType, $allowedTypes)) {
echo "只允许上传JPG, JPEG, PNG和GIF文件";
$uploadOk = 0;
}
// 检查上传标志
if ($uploadOk == 0) {
echo "文件未上传";
} else {
if (move_uploaded_file($_FILES["image"]["tmp_name"], $targetFile)) {
echo "文件". htmlspecialchars(basename($_FILES["image"]["name"])). "上传成功";
} else {
echo "上传过程中发生错误";
}
}
}
?>
使用jQuery简化实现
如果项目中使用jQuery,可以简化前端代码:
$('#uploadForm').submit(function(e) {
e.preventDefault();
let formData = new FormData(this);
$.ajax({
url: 'upload.php',
type: 'POST',
data: formData,
processData: false,
contentType: false,
xhr: function() {
let xhr = new XMLHttpRequest();
xhr.upload.addEventListener('progress', function(event) {
if (event.lengthComputable) {
let percent = Math.round((event.loaded / event.total) * 100);
$('#progress').text('上传进度: ' + percent + '%');
}
}, false);
return xhr;
},
success: function(response) {
$('#result').html(response);
}
});
});
安全注意事项
实现异步图片上传时需要注意以下安全措施:

确保上传目录不可执行脚本
// 在uploads目录下放置.htaccess文件
// 内容为:
Options -Indexes
php_flag engine off
对文件名进行安全处理
$fileName = uniqid() . '.' . $imageFileType;
$targetFile = $targetDir . $fileName;
限制上传文件类型
$finfo = finfo_open(FILEINFO_MIME_TYPE);
$mime = finfo_file($finfo, $_FILES["image"]["tmp_name"]);
finfo_close($finfo);
$allowedMimes = ['image/jpeg', 'image/png', 'image/gif'];
if (!in_array($mime, $allowedMimes)) {
die("不允许的文件类型");
}






