前端表單關鍵點
<form method="post" action="change.php" enctype="multipart/form-data">
<input type="hidden" name="MAX_FILE_SIZE" value="2000000" />
<input name="file" type="file" />
<input type="submit" name="submit" value="submit" />
</form>
- enctype="multipart/form-data":必須設定,否則
$_FILES 為空。
- MAX_FILE_SIZE:隱藏欄位限制客戶端上傳大小(單位 Byte),此處 2MB;伺服器端仍需配合
php.ini 的 upload_max_filesize 與 post_max_size。
- type="file":瀏覽器渲染為「選擇檔案」按鈕。
後端處理流程 change.php
<?php
header("Content-Type: text/html; charset=utf-8");
function changeFile($oldfile) {
$newfile = $_FILES['file']['name'];
$ext = strtolower(substr(strrchr($newfile, '.'), 1));
$allow = ['jpg','gif','bmp','jpeg','png'];
if (!in_array($ext, $allow)) {
echo "<center>僅允許上傳:" . implode(',', $allow) . "</center>";
return;
}
if (file_exists($oldfile)) unlink($oldfile); // 刪除舊檔
if (is_uploaded_file($_FILES['file']['tmp_name'])) {
if (move_uploaded_file($_FILES['file']['tmp_name'], $oldfile)) {
echo "<center>上傳成功<br><img src='$oldfile'></center>";
} else {
echo "<center>移動檔案失敗,請檢查目錄權限</center>";
}
} else {
echo "<center>上傳失敗,檔案可能超過 2MB 或臨時目錄異常</center>";
}
}
changeFile("./files/1.png"); // 指定被替換的目標檔案路徑
?>
核心函式解析
| 函式/屬性 | 用途 |
$_FILES['file']['name'] | 原始檔名 |
$_FILES['file']['tmp_name'] | 伺服器暫存路徑 |
$_FILES['file']['size'] | 檔案大小 |
$_FILES['file']['type'] | MIME 型別 |
strrchr($str, '.') | 取最後一個 '.' 後字串(含點) |
substr(..., 1) | 去除點號,取得副檔名 |
is_uploaded_file() | 確認為 HTTP POST 上傳,防偽造 |
move_uploaded_file() | 將暫存檔移至永久路徑,自動檢查權限 |
安全與擴充建議
- 檔名隨機化:使用
uniqid() 或雜湊避免覆蓋、路徑遍歷。
- MIME 二次驗證:搭配
finfo_file() 檢測真實型別,防偽造副檔名。
- 尺寸壓縮:上傳後以 GD/Imagick 壓縮縮圖,節省頻寬。
- 儲存隔離:上傳目錄設定
open_basedir、禁用執行權限、配合 CDN 分發。