---
title: "Saving Uploaded Files in HTML5/Flash Uploader PHP"
canonical: https://www.aurigma.com/docs/us8/saving-uploaded-files-in-php-iuf.htm
product: "Upload Suite 8"
---

# Saving Uploaded Files in HTML5/Flash Uploader PHP

Supported technologies: ![Adobe Flash](https://www.aurigma.com/docs/us8/icons/flash.png)![HTML 5](https://www.aurigma.com/docs/us8/icons/html5.png)
 
As you know HTML5/Flash Uploader sends files and additional metadata from client computers to server side in HTTP POST requests. This approach requires server script to parse the received requests and handle uploaded data. Reading this topic you will get to know how to extract files and additional data sent by clients, save it all to file system on a server or handle in some other way. There are three approaches to perform this task:

- Uploading files to the specified folder on a server. This is the simplest way, it allows saving all uploaded files almost without coding. However, this method is not flexible enough, so do not use it if you need to access additional data (e.g. information about original files, additional fields, etc.).
- Extended processing of uploaded data using the [UploadHandler](https://www.aurigma.com/docs/us8/FH_T_P_UploadHandler.htm.md). This approach gives you flexible typed access to all data sent from client computers. It suites best for PHP applications because HTML5/Flash Uploader PHP classes offer server-side API allowing to accomplish any operation on the uploaded data in a usual for PHP developers way.
- Parsing POST requests using PHP predefined variables (**$\_FILES** and **$\_POST**). This method does not differ from the one when you are using form-based file upload in HTML (browse/upload buttons on your page). If you use it, you get untyped access to uploaded data, also this approach does not support automatic assembling files from chunks (if you enable them in the HTML5/Flash Uploader, of course). The main advantage of this method is that you do not have additional references to HTML5/Flash Uploader PHP in your application.

**Note** 
If you parse requests using PHP predefined variables and enable sending files by chunks you will have to write significant amount of non-trivial server-side code to assembly the files on your server. This way, we do not recommend enabling chunks if you use this method of handling requests.
 
**Note** 
For versions of PHP earlier than 6.0 disable the `magic_quotes_gpc` directive in your `php.ini` file.
 
Further in this topic every approach will be described in detail. Let us start with the **UploadHandler** class description.

## UploadHandler Class
 
All the HTML5/Flash Uploader PHP classes are located in the `/ImageUploaderFlashPHP/` folder. The key class is **UploadHandler**, which allows processing the data uploaded from client computers. This class has user-friendly API and functionality giving flexible typed access to these data. In order to use **UploadHandler** you have to include ` UploadHandler.class.php` into your upload handling script (see: [Quick Start with HTML5/Flash Uploader PHP](https://www.aurigma.com/docs/us8/quick-start-with-image-uploader-flash-php.htm.md)), for example, `upload.php`:
 ```
<?php
require_once "ImageUploaderFlashPHP/UploadHandler.class.php";
$handler = new UploadHandler();
?>
``` 
And specify URL to this script as a value of the [UploadSettings.ActionUrl](https://www.aurigma.com/docs/us8/FH_P_Aurigma_ImageUploaderFlash_UploadSettings_ActionUrl.htm.md) property (both absolute and relative URLs are supported) like it is shown below:
 ```
<?php
$uploader->getUploadSettings()->setActionUrl("upload.php");
?>
```

## Uploading Files to Specified Folder
 
This section describes the simplest way of handling uploaded data - autosave. This approach allows you to save all the uploaded files to the specified folder on your server without writing a lot of code. The **UploadHandler** class described in the previous section can save uploaded files automatically. You just create a new instance of this class in your upload handling script and call its [saveFiles(string)](https://www.aurigma.com/docs/us8/FH_M_P_UploadHandler_saveFiles_1_4d57a286.htm.md) method providing a path to the folder where uploaded files should be saved as a parameter. If the specified folder does not exist HTML5/Flash Uploader tries to create it.
 
If you need to process the saved files in some way, then a page specified in the [UploadSettings.RedirectUrl](https://www.aurigma.com/docs/us8/FH_P_P_UploadSettings_RedirectUrl.htm.md) setting is the right place for this. Just put your code there and it will be executed after the upload process is completed.
 
The example below shows how to save all the uploaded files.
 
The `upload.php` file:
 ```
<?php    
require_once "ImageUploaderFlashPHP/UploadHandler.class.php";

$handler = new UploadHandler();
$handler->saveFiles("Catalog/");
?>
``` 
And a script initializing the [ImageUploaderFlash](https://www.aurigma.com/docs/us8/FH_T_P_ImageUploaderFlash.htm.md) object must contain the following code:
 ```
<?php
$uploader->getUploadSettings()->setActionUrl("upload.php");
?>
``` 
### Filenames Conversions and Collisions
 
HTML5/Flash Uploader prepares files on client side in the way set by *converters*. Each converter specifies what to do with a file selected for upload: upload it as is or apply some transformation before upload (resize image down, extract and send icon associated with a file, or compress a file to ZIP format). [Converters](https://www.aurigma.com/docs/us8/FH_P_P_ImageUploaderFlash_Converters.htm.md) (except for `SourceFile` one) add suffixes to file names uploaded to a server. For example, the `name.ext_Thumbnail0.ext` filename is the result of applying `Mode="*.*=Thumbnail"` converter on `name.ext` file. For a full list of possible suffixes see the [ConvertedFile.Name](https://www.aurigma.com/docs/us8/FH_P_P_ConvertedFile_Name.htm.md) property description.
 
Filenames collisions may occur while saving uploaded files to a destination folder. If the destination folder already has a file with the same name as uploaded one, the uploaded file will be saved under its name appended by `_xx`, where `xx` is a number starting from `2`. For example, if there is a file with the name `name.ext` in the destination folder and a user tries to upload another file with the same name then uploaded file is saved as `name_02.ext` file. If ` name_02.ext` file exists as well then the recently uploaded file gets `name_03.ext` filename and so on.

## Extended Processing of Uploaded Data
 
This approach requires quite a bit of code, however, this method is more flexible than autosave described before. The main idea is to handle uploaded files and data in the callback functions specified by [FileUploadedCallback](https://www.aurigma.com/docs/us8/FH_P_P_UploadHandler_FileUploadedCallback.htm.md) and/or [AllFilesUploadedCallback](https://www.aurigma.com/docs/us8/FH_P_P_UploadHandler_AllFilesUploadedCallback.htm.md) settings of the mentioned before **UploadHandler** class. The first function is called each time a user-specified file is successfully uploaded. The second function is called when the whole upload session completes and all the files, metadata, and additional data are received on the server side. The first one is called as many times as number of files selected for upload, whereas the second one is called only once.
 
Now, when you understand the differences between these events, let us discuss how to create these event handlers. There are two steps to this process:
 
- creating skeleton callback function
- writing implementation of callback function

### Creating Skeleton Callback Functions
 
There is a requirement for the callback functions - they must have an argument, which gets an [UploadedFile](https://www.aurigma.com/docs/us8/FH_T_P_UploadedFile.htm.md) or an **UploadedFile** array value. The following example sets both, **FileUploadedCallback** and **AllFilesUploadedCallback**, callback functions, and enables request processing by calling the [processRequest()](https://www.aurigma.com/docs/us8/FH_M_P_UploadHandler_processRequest.htm.md) method:
 ```
<?php
require_once "ImageUploaderFlashPHP/UploadHandler.class.php";

$handler = new UploadHandler();
$handler->setFileUploadedCallback("saveUploadedFile");
$handler->setAllFilesUploadedCallback("saveAllUploadedFiles");
$handler->processRequest();

function saveAllUploadedFiles($uploadedFiles) {
    //...
    foreach ($uploadedFiles as $uploadedFile)
    {
        //...
    }
    //...
}

function saveUploadedFile($uploadedFile) {
    //...
}
?>
``` 
There is the example of callback function implementation below.
 
Also do not forget to set the [UploadSettings.ActionUrl](https://www.aurigma.com/docs/us8/FH_P_P_UploadSettings_ActionUrl.htm.md) property.
 
### Writing Implementation of Callback Functions
 
For better understanding let us separate description of the uploaded data handling into the following sections:
 
- files handling
- metadata handling

### Files Handling
 
The PHP server-side part of HTML5/Flash Uploader among its types has the **UploadedFile** class. This type holds all the data associated with a single file selected for upload (files prepared on client side by HTML5/Flash Uploader from the original file in accordance with converters set in the settings, additional fields, and other data). The **FileUploadedCallback** callback function gives access to an **UploadedFile** instance through the function argument. The **AllFilesUploadedCallback** callback function gives access to an array of **UploadedFile** objects also via its argument.
 
Now let us examine how to get access to uploaded files via the **UploadedFile** instances. Each **UploadedFile** object has associated collection of files prepared by HTML5/Flash Uploader converters on client side. Each of these files is represented by an instance of the [ConvertedFile](https://www.aurigma.com/docs/us8/FH_T_P_ConvertedFile.htm.md) type. This way, the collection of converted files associated with a particular file selected for upload is accessible via the [UploadedFile.ConvertedFiles](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_ConvertedFiles.htm.md) property.
 
Each **ConvertedFile** object has two main members to handle the file:
 
- the [FileContent](https://www.aurigma.com/docs/us8/FH_P_P_ConvertedFile_FileContent.htm.md) property for getting access to the file content
- the [moveTo(string)](https://www.aurigma.com/docs/us8/FH_M_P_ConvertedFile_moveTo_1_4d57a286.htm.md) method for moving the file to the specified location

### Metadata Handling
 
All the metadata uploaded along with a file is accessible through the [UploadedFile properties](https://www.aurigma.com/docs/us8/FH_Properties_T_P_UploadedFile.htm.md) and can be divided into the following groups:
 
#### Original File Information
 
This group includes properties containing information about the original file:
 
- [SourceCreatedDateTime](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_SourceCreatedDateTime.htm.md) and [SourceCreatedDateTimeLocal](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_SourceCreatedDateTimeLocal.htm.md) represent creation date of the original file.
- [SourceLastModifiedDateTime](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_SourceLastModifiedDateTime.htm.md) and [SourceLastModifiedDateTimeLocal](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_SourceLastModifiedDateTimeLocal.htm.md) represent last modification date of the original file.
- [SourceHeight](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_SourceHeight.htm.md) and [SourceWidth](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_SourceWidth.htm.md) represent dimensions of the original file (in pixels) if it is an image.
- [HorizontalResolution](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_HorizontalResolution.htm.md) and [VerticalResolution](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_VerticalResolution.htm.md) represent horizontal and vertical resolutions of the original file (in dpi) if it is an image.
- [SourceName](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_SourceName.htm.md) represents the original file name.
- [SourceSize](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_SourceSize.htm.md) represents the original file size.

#### Converted File Information
 
The **ConvertedFile** class provides access to some additional information along with access to the converted file itself. Its properties contain the following information:
 
- [Mode](https://www.aurigma.com/docs/us8/FH_P_P_ConvertedFile_Mode.htm.md) contains a converter type applied to create the converted file.
- [Size](https://www.aurigma.com/docs/us8/FH_P_P_ConvertedFile_Size.htm.md) represents size (in bytes) of the converted file.
- [Height](https://www.aurigma.com/docs/us8/FH_P_P_ConvertedFile_Height.htm.md) and [Width](https://www.aurigma.com/docs/us8/FH_P_P_ConvertedFile_Width.htm.md) represent dimensions of the created downsized image (in pixels) if the converter was set to resize an original image down.

#### User-defined Data
 
This group includes the following properties:
 
- [Angle](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_Angle.htm.md) contains the rotation angle of the uploaded file if it is an image.
- [Description](https://www.aurigma.com/docs/us8/FH_P_P_UploadedFile_Description.htm.md) contains a user-provided description of the uploaded file.
- [PackageFields](https://www.aurigma.com/docs/us8/FH_P_P_Package_PackageFields.htm.md) contains a collection of POST fields including the fields specified through the [ImageUploaderFlash.Metadata](https://www.aurigma.com/docs/us8/FH_P_P_ImageUploaderFlash_Metadata.htm.md) set of properties ([Metadata.AdditionalFormName](https://www.aurigma.com/docs/us8/FH_P_P_Metadata_AdditionalFormName.htm.md) and [Metadata.Exif](https://www.aurigma.com/docs/us8/FH_P_P_Metadata_Exif.htm.md)) and via the [metadata.addCustomField(String, String, Boolean)](https://www.aurigma.com/docs/us8/FH_M_J_$au_metadata_addCustomField_3_c43e5881.htm.md) client method.

#### Callback Function Example
 
This example is a **FileUploadedCallback** callback function which saves an original file and its resized copy to the `../Gallery/` and `../Gallery/Thumbnails/` folders respectively and writes some file-related information (filenames, image dimensions, user description, and etc.) to an XML file. This function is called only once when the whole upload session completes as it is set by the **AllFilesUploadedCallback** property.
 ```
<?php
function saveAllUploadedFiles($uploadedFiles) {

    $galleryPath = "Gallery/";
    $absGalleryPath = realpath($galleryPath);
    $absThumbnailsPath = realpath($galleryPath . DIRECTORY_SEPARATOR . "Thumbnails/");
    
    //Create or load XML file which will keep information about files (image dimensions, description, etc).
    $descriptions = new DOMDocument('1.0');
    if (file_exists($absGalleryPath . DIRECTORY_SEPARATOR . "Descriptions.xml"))
        $descriptions->load($absGalleryPath . DIRECTORY_SEPARATOR . "Descriptions.xml");
    else
        $descriptions->appendChild($descriptions->createElement("files"));
    
    foreach ($uploadedFiles as $uploadedFile)
    {
        $convertedFiles = $uploadedFile->getConvertedFiles();
        //Save original file.
        //It is the first file in ConvertedFiles collection as we set first converter mode to SourceFile.
        $sourceFile = $convertedFiles[0];
        getSafeFileName($absGalleryPath, rawurlencode($uploadedFile->getSourceName()));
        $sourceFile->moveTo($absGalleryPath . DIRECTORY_SEPARATOR . $sourceFileName);
        
        //Save thumbnail.
        //It is the second file in ConvertedFiles collection as we set second converter mode to Thumbnail.
        $thumbnailFile = $convertedFiles[1];
        $thumbnailFileName = getSafeFileName($absThumbnailsPath, rawurlencode($uploadedFile->getSourceName()));
        $thumbnailFile->moveTo($absThumbnailsPath . DIRECTORY_SEPARATOR . $thumbnailFileName);
        
        //Save file info.
        $xmlFile = $descriptions->createElement("file");
        $xmlFile->setAttribute("name", $sourceFileName);
        $xmlFile->setAttribute("thumbName", $thumbnailFileName);
        $xmlFile->setAttribute("width", $uploadedFile->getSourceWidth());
        $xmlFile->setAttribute("height", $uploadedFile->getSourceHeight());
        $xmlFile->setAttribute("description", $uploadedFile->getDescription());
        $descriptions->documentElement->appendChild($xmlFile);
    }
    $descriptions->save($absGalleryPath . DIRECTORY_SEPARATOR . "Descriptions.xml");
    
}

function getSafeFileName($path, $fileName) {
    // ...
}
?>
```

## Parsing POST Requests Using PHP Predefined Variables ($\_FILES and $\_POST)
 
The last way of handling uploaded files is to parse the upload request manually via the **$\_FILES** and **$\_POST** "superglobals". Before parsing the upload request should be converted to the standart RFC1867 format. To perform it you should link the `flashrequestfix.php` with the upload page and call the **preProcessRequest()**. There are two more functions in `flashrequestfix.php`:
 
- **postProcessRequest()** deletes temporary files. Call this function after parsing the POST requset.
- **moveFile($source, $destination)** saves file to the destination path. Use this function instead of **move\_uploaded\_file($filename, $destination)**.

**Note** 
If you do not call the **postProcessRequest()** function, temporary files will be accumulated on your server.
 
**Note** 
If you choose this approach we do not recommend enabling chunks, otherwise, you will have to write significant amount of non-trivial server-side code to assembly the files on your server.
 
To simplify accessing the POST request fields HTML5/Flash Uploader PHP provides the [PostFields](https://www.aurigma.com/docs/us8/FH_T_P_PostFields.htm.md) class. The following code sample demonstrates how to save original files, thumbnails, and original file-related information using described approach.
 
**Note** 
Server-side upload script should return a non-empty response.
 ```
<?php
require_once "ImageUploaderFlashPHP/PostFields.class.php";
require_once 'ImageUploaderFlashPHP/flashrequestfix.php';

preProcessRequest();

$galleryPath = "Gallery";
$absGalleryPath = realpath($galleryPath);
$absThumbnailsPath = realpath($galleryPath . DIRECTORY_SEPARATOR . "Thumbnails");

//Create or load XML file which will keep information about files (image dimensions, description, etc).
$descriptions = new DOMDocument('1.0');
if (file_exists($absGalleryPath . DIRECTORY_SEPARATOR . "Descriptions.xml"))
    $descriptions->load($absGalleryPath . DIRECTORY_SEPARATOR . "Descriptions.xml");
else
    $descriptions->appendChild($descriptions->createElement("files"));

$originalFileName = rawurlencode($_POST[sprintf(PostFields::sourceName,0)]);

//save source file
$sourceFileName = getSafeFileName($absGalleryPath, $originalFileName);
if (isset($_FILES[sprintf(PostFields::file, 0, 0)])) {
    moveFile($_FILES[sprintf(PostFields::file, 0, 0)]["tmp_name"], 
        $absGalleryPath . DIRECTORY_SEPARATOR . $sourceFileName);
}

//save thumbnail file
$thumbnailFileName = getSafeFileName($absThumbnailsPath, $originalFileName);
if (isset($_FILES[sprintf(PostFields::file, 1, 0)])) {
    moveFile($_FILES[sprintf(PostFields::file, 1, 0)]["tmp_name"], 
        $absThumbnailsPath . DIRECTORY_SEPARATOR . $thumbnailFileName);
}

//Save file info.
$xmlFile = $descriptions->createElement("file");
$xmlFile->setAttribute("name", $sourceFileName);
$xmlFile->setAttribute("thumbName", $thumbnailFileName);
$xmlFile->setAttribute("width", $_POST[sprintf(PostFields::sourceWidth, 0)]);
$xmlFile->setAttribute("height", $_POST[sprintf(PostFields::sourceHeight, 0)]);
$xmlFile->setAttribute("description", $_POST[sprintf(PostFields::description, 0)]);
$descriptions->documentElement->appendChild($xmlFile);

$descriptions->save($absGalleryPath . DIRECTORY_SEPARATOR . "Descriptions.xml");

postProcessRequest();

// Server-side upload script should return a non-empty response.
echo "complete";

function getSafeFileName($path, $fileName) {
    // ...
}
?>
``` 
Also do not forget to set the **UploadSettings.ActionUrl** property.

## See Also
 
### Reference
 
- [ImageUploaderFlash Class](https://www.aurigma.com/docs/us8/FH_T_P_ImageUploaderFlash.htm.md)
- [UploadHandler Class](https://www.aurigma.com/docs/us8/FH_T_P_UploadHandler.htm.md)
- [UploadSettings Class](https://www.aurigma.com/docs/us8/FH_T_P_UploadSettings.htm.md)
- [UploadedFile Class](https://www.aurigma.com/docs/us8/FH_T_P_UploadedFile.htm.md)
- [ConvertedFile Class](https://www.aurigma.com/docs/us8/FH_T_P_ConvertedFile.htm.md)
- [Package Class](https://www.aurigma.com/docs/us8/FH_T_P_Package.htm.md)
- [PostFields Class](https://www.aurigma.com/docs/us8/FH_T_P_PostFields.htm.md)

### Manual
 
- [Quick Start with HTML5/Flash Uploader PHP](https://www.aurigma.com/docs/us8/quick-start-with-image-uploader-flash-php.htm.md)
- [Configuring Common Upload Settings in HTML5/Flash Uploader](https://www.aurigma.com/docs/us8/configuring-common-upload-settings-iuf.htm.md)
- [Configuring Files to be Uploaded in HTML5/Flash Uploader](https://www.aurigma.com/docs/us8/configuring-files-to-be-uploaded-iuf.htm.md)
