Skip to content

Multiple use of new FileBag($_FILES) throws an Exception #36319

Closed
@scmika

Description

@scmika

Symfony version(s) affected: 2.0 till master (The FileBag.php has not changed for a long time on that part)

Description
The repeated use of new FileBag($_FILES) might result in a FileNotFoundException. This has been a problem on one of our customers installations when changing from Shopware 5.5.10 to 5.6.6 due to its different handling of requests with cache active. This might be a Shopware specific handling error, but the provided solution seems small enough to prevent more problems than it might create.

How to reproduce

  1. Create an file upload field on a form.
  2. Upload any file on the form. Have the handling action do the following three things during the same PHP call.
  3. Use new FileBag($_FILES) to parse the files.
  4. Move the resulting UploadedFile object using the "move" method.
  5. Use new FileBag($_FILES) again.

On a Shopware 5.6.6 frontend this happens with HTTP Cache activated on custom controllers and methods as the cache does a second run through the code after the first one finished (and possibly moved some uploaded files).

Possible Solution
On "FileBag.php" the "$file = new UploadFile($file['tmp_name'], $file['name'], $file['type'], $file['size'], $file['error']);" line should be replaced with a code like this:

$key = $file['tmp_name'];
static $processedFiles;
if ( !isset($processedFiles) ) {
  $processedFiles = [];
}
if ( isset($processedFiles[$key]) ) {
  $file = $processedFiles[$key];
} else {
  $file = new UploadedFile($file['tmp_name'], $file['name'], $file['type'], $file['size'], $file['error']);
  $processedFiles[$key] = $file;
}

If you want to keep it backwards (PHP 5.6 or lower) compatible, the static variable could be put into the class context as a private variable. This change creates a static cache for "UploadedFile" objects to keep the same UploadedFile instances available with multiple instances of FileBag. Since the "move_uploaded_file" happens somewhere in the code, the second call would not find the file any more.

Additional Concerns
If you are concerned about performance (memory leaks on large upload forms), you could add a static flag to not use this cache. This should however not pose a problem as the objects don't store the content but just some meta data.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions