Handling file uploads is a common requirement in web applications, but it presents its own challenges. This guide explores how to handle file uploads in PHP, including checking and increasing the maximum upload size, modifying PHP configurations, restricting file types, and validating uploads to enhance the security and efficiency of your applications.

How to check max file upload size in PHP

Before making any changes, it is essential to know your current upload limits. PHP controls file upload sizes with two configuration directives: upload_max_filesize and post_max_size. You can check these values by creating a simple PHP script:

<?php
echo 'upload_max_filesize: ' . ini_get('upload_max_filesize') . '<br>';
echo 'post_max_size: ' . ini_get('post_max_size') . '<br>';
?>

Save this script as check_upload_size.php and run it on your server. It will display the current maximum file upload size and the maximum post size allowed.

Alternatively, you can use the phpinfo() function to get a full overview of your PHP configuration:

<?php
phpinfo();
?>

Accessing this script in your browser will provide detailed information, including upload_max_filesize and post_max_size.

How to increase file upload size in PHP

If you need to allow larger file uploads, you will have to adjust the upload_max_filesize and post_max_size directives in your PHP configuration. Here is how you can do it:

Using .htaccess (if you are using apache)

Add the following lines to your .htaccess file:

php_value upload_max_filesize 20M
php_value post_max_size 25M

This sets the maximum upload file size to 20 megabytes and the maximum post size to 25 megabytes. Adjust the values according to your needs.

Using ini_set() in PHP scripts

You can also set these values directly in your PHP scripts using the ini_set() function:

<?php
ini_set('upload_max_filesize', '20M');
ini_set('post_max_size', '25M');
?>

Note that this method may not work on all server configurations, as some settings cannot be modified at runtime.

How to change max file upload size in php.ini on Ubuntu

If you have access to your server's php.ini file, you can make the changes there. Here is how to do it on an Ubuntu system:

  1. Locate your php.ini file. It is usually located in /etc/php/{version}/apache2/php.ini or /etc/php/{version}/cli/php.ini.

  2. Open the file in a text editor with root privileges:

    sudo nano /etc/php/{version}/apache2/php.ini
    
  3. Find the directives upload_max_filesize and post_max_size and modify them:

    upload_max_filesize = 20M
    post_max_size = 25M
    
  4. Save the file and exit the editor.

  5. Restart Apache to apply the changes:

    sudo systemctl restart apache2
    

Replace {version} with your PHP version (e.g., 7.4). After restarting Apache, your new settings will take effect.

Implementing file upload functionality in PHP

With the configuration set, you can now implement file upload functionality in your application.

HTML form

First, create an HTML form that allows users to upload files:

<form action="upload.php" method="post" enctype="multipart/form-data">
  <label for="file">Choose file to upload:</label>
  <input type="file" name="file" id="file" required />
  <input type="submit" value="Upload" />
</form>

Make sure to set enctype="multipart/form-data" in the form tag to handle file uploads.

PHP upload script

Next, create upload.php to handle the file upload:

<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
    if (isset($_FILES['file'])) {
        $uploadDirectory = 'uploads/';
        $fileTmpPath = $_FILES['file']['tmp_name'];
        $fileName = basename($_FILES['file']['name']);
        $uploadFilePath = $uploadDirectory . $fileName;

        // Ensure the upload directory exists and is writable
        if (!is_dir($uploadDirectory)) {
            mkdir($uploadDirectory, 0755, true);
        }

        if (move_uploaded_file($fileTmpPath, $uploadFilePath)) {
            echo 'File was successfully uploaded.';
        } else {
            echo 'There was an error uploading your file.';
        }
    } else {
        echo 'No file was uploaded.';
    }
}
?>

This script checks if a file was uploaded and attempts to move it to the uploads/ directory. Ensure that the uploads/ directory exists and has the correct permissions.

How to restrict file upload type in PHP

To enhance security, it is crucial to restrict the types of files that users can upload. You can achieve this by checking the file's MIME type and extension.

Update the upload.php script as follows:

<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
    if (isset($_FILES['file'])) {
        $uploadDirectory = 'uploads/';
        $allowedTypes = ['image/jpeg', 'image/png', 'application/pdf'];
        $allowedExtensions = ['jpg', 'jpeg', 'png', 'pdf'];

        $fileTmpPath = $_FILES['file']['tmp_name'];
        $fileName = basename($_FILES['file']['name']);
        $fileSize = $_FILES['file']['size'];
        $fileType = mime_content_type($fileTmpPath);
        $fileExtension = strtolower(pathinfo($fileName, PATHINFO_EXTENSION));

        // Check if file type and extension are allowed
        if (in_array($fileType, $allowedTypes) && in_array($fileExtension, $allowedExtensions)) {
            // Validate file upload
            $maxFileSize = 5 * 1024 * 1024; // 5 MB
            if ($fileSize > $maxFileSize) {
                echo 'File is too large.';
                exit;
            }

            // Check for upload errors
            if ($_FILES['file']['error'] !== UPLOAD_ERR_OK) {
                echo 'An error occurred during file upload.';
                exit;
            }

            // Sanitize file name
            $uniqueName = uniqid('', true) . '.' . $fileExtension;
            $uploadFilePath = $uploadDirectory . $uniqueName;

            // Ensure the upload directory exists and is writable
            if (!is_dir($uploadDirectory)) {
                mkdir($uploadDirectory, 0755, true);
            }

            if (move_uploaded_file($fileTmpPath, $uploadFilePath)) {
                echo 'File was successfully uploaded.';
            } else {
                echo 'There was an error uploading your file.';
            }
        } else {
            echo 'Invalid file type.';
            exit;
        }
    } else {
        echo 'No file was uploaded.';
    }
}
?>

This code checks if the uploaded file's MIME type and extension are in the list of allowed types, validates the file size, checks for upload errors, and sanitizes the file name to prevent overwriting existing files and protect against directory traversal attacks.

How to validate file uploads in PHP

Validating file uploads helps prevent malicious files from being uploaded. The previous script includes several validation steps:

  • Checking File Size: Enforce a maximum file size to prevent excessively large files from being uploaded.

    $maxFileSize = 5 * 1024 * 1024; // 5 MB
    if ($fileSize > $maxFileSize) {
        echo 'File is too large.';
        exit;
    }
    
  • Checking for Errors: Always check for upload errors to handle any issues during the file upload process.

    if ($_FILES['file']['error'] !== UPLOAD_ERR_OK) {
        echo 'An error occurred during file upload.';
        exit;
    }
    
  • Sanitizing File Names: Generate a unique file name to prevent overwriting existing files and guard against directory traversal attacks.

    $uniqueName = uniqid('', true) . '.' . $fileExtension;
    $uploadFilePath = $uploadDirectory . $uniqueName;
    

Best practices for secure file uploads

  • Use a Dedicated Upload Directory: Store uploaded files in a separate directory, preferably outside the web root.

  • Set Appropriate Permissions: Ensure that the upload directory has the correct permissions (0755) to prevent unauthorized access.

  • Disable Script Execution: Prevent execution of uploaded files by adding a .htaccess file in the upload directory:

    php_flag engine off
    Options -Indexes
    
  • Scan Files for Malware: Consider integrating a malware scanning tool like ClamAV to scan uploaded files.

  • Limit File Uploads: If your application does not require file uploads, disable the file upload functionality in PHP by setting file_uploads = Off in php.ini.

Conclusion

Handling file uploads in PHP requires careful attention to configuration and security practices. By increasing the upload size limits, restricting file types, validating uploads, and following secure coding practices, you can ensure that your application handles file uploads efficiently and securely.

If you are looking for a robust solution to handle file uploads and processing, consider using Transloadit, which offers reliable file uploading and encoding services.