When a form uploads a file, the file does not go into $_POST. PHP stores it in a temporary location and describes it in $_FILES.
A form that uploads a file needs two things:
<form action="upload.php" method="post" enctype="multipart/form-data">
<label for="photo">Photo</label>
<input type="file" id="photo" name="photo">
<button type="submit">Upload</button>
</form>
enctype="multipart/form-data" and method="post" are both required.
What $_FILES looks like
For a field named photo, PHP gives you five values.
<?php
$_FILES = [
"photo" => [
"name" => "holiday.jpg",
"type" => "image/jpeg",
"tmp_name" => "/tmp/phpA1B2C3",
"error" => 0,
"size" => 482133,
],
];
$file = $_FILES["photo"];
echo $file["name"] . " is " . round($file["size"] / 1024) . " KB";
holiday.jpg is 471 KB
| Key | Meaning | Trust it? |
|---|---|---|
name | Original file name | No, chosen by the visitor |
type | MIME type | No, sent by the browser |
tmp_name | Where PHP saved the upload | Yes, set by PHP |
error | Upload status code | Yes |
size | Size in bytes | Mostly (still check the real file) |
Check the error code first
| Code | Constant | Meaning |
|---|---|---|
| 0 | UPLOAD_ERR_OK | Success |
| 1 | UPLOAD_ERR_INI_SIZE | Larger than upload_max_filesize |
| 2 | UPLOAD_ERR_FORM_SIZE | Larger than the form’s MAX_FILE_SIZE |
| 3 | UPLOAD_ERR_PARTIAL | Only partly uploaded |
| 4 | UPLOAD_ERR_NO_FILE | No file was chosen |
| 6 | UPLOAD_ERR_NO_TMP_DIR | Missing temporary folder |
| 7 | UPLOAD_ERR_CANT_WRITE | Could not write to disk |
<?php
$_FILES = ["photo" => ["name" => "", "error" => UPLOAD_ERR_NO_FILE]];
if (($_FILES["photo"]["error"] ?? UPLOAD_ERR_NO_FILE) !== UPLOAD_ERR_OK) {
echo "No file was uploaded correctly.";
}
No file was uploaded correctly.
The golden rule
Never trust name or type. They are just text sent by the visitor. A file called photo.jpg can contain PHP code. The next chapter shows how to check and store uploads properly: File Uploads and Secure File Uploads.
Limits live in php.ini
upload_max_filesize and post_max_size set the size limits. If a large upload fails with no message, those are the first settings to check.