A free and open-source book on ZF3 for beginners

10.6. InputFilter Container & File Uploads

As you might remember, the filters and validators attached to a form model are typically stored in an InputFilter container which consists of inputs (an input is typically represented by the Input class belonging to the Zend\InputFilter namespace). For usual form fields, the filters are executed before validators, and validators are executed after filters.

However, for file uploads, there are some important differences:

  1. for storing validation rules for uploaded files, a special class called FileInput should be utilized instead of the Input class;
  2. and, validators are applied before filters (!).

10.6.1. FileInput

For storing validation rules for uploaded files, you must use the FileInput class instead of the usual Input class.

In your form model's addInputFilter() private method, you add the validation rules for the file input as follows:

        'type'     => 'Zend\InputFilter\FileInput',
        'name'     => 'file',  // Element's name.
        'required' => true,    // Whether the field is required.
        'filters'  => [        // Filters.
            // Put filter info here.   
        'validators' => [      // Validators.
            // Put validator info here.

Above, we set the "type" key (line 2) with the value Zend\InputFilter\FileInput class name. The rest of keys is analogous to those we used before when adding validation rules for a form model.

The behaviour of FileInput class differs from the Input in the following aspects:

  1. It expects the data you pass as input to be in the $_FILES array format (an array entry with tmp_name, error, type keys).

  2. A Zend\Validator\File\Upload validator is automatically inserted before all other validators into the validator chain of the input.

  3. The validators inserted to the validator chain of the input are executed before the filters inserted into its filter chain. This is opposite to the behaviour of the Input class.

10.6.2. Executing Validators before Filters

For usual form fields, the filters are typically executed before validators, and validators are executed after filters. However, for file uploads, this sequence is opposite.

For file uploads, validators are executed before filters. This behaviour is inverse to the usual behaviour.

When working with uploaded files, we first need to check that data extracted from $_FILES super-global array is correct, and then do anything else with the files (moving the file into a storage directory, renaming it, etc.) Because of that, file validators need to be run first turn, and filters to be executed last.

To see how this is performed, recall the typical workflow for a form:

When using a FileInput input, the workflow is the same, however it is important to understand what happens on each of its steps:

Please note that for FileInput input, the attached filters are only run if the getData() method is called.

When you use both Input and FileInput inputs in your form's input filter (which is a common case), the filters are still executed first for usual inputs, but validators are executed first for file inputs.