Mostafa Norzade
Mostafa Norzade

Reputation: 1766

How convert the $_FILES array to the cleaner array?

I use below loop in form for saving data :

<form action="#" method="post" enctype="multipart/form-data">
    <?php foreach ($sites as $site) { ?>
        <div>
            <div>
                <input type="text" name="entry[<?= $site['id'] ?>][date]" id="repDate<?= $site['id'] ?>">
            </div>
            <div>
                <input type="file" name="entry[<?= $site['id'] ?>][file]" id="repFile<?= $site['id'] ?>">
            </div>
        </div>
    <?php } ?>
</form>

The output of the above code is as follows :

array(1) {
  ["entry"]=>
  array(5) {
    ["name"]=>
    array(2) {
      [37]=>
      array(1) {
        ["file"]=>
        string(30) "my-file-test.docx"
      }
      [38]=>
      array(1) {
        ["file"]=>
        string(56) "resources_views.php"
      }
    }
    ["type"]=>
    array(2) {
      [37]=>
      array(1) {
        ["file"]=>
        string(71) "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
      }
      [38]=>
      array(1) {
        ["file"]=>
        string(17) "application/x-php"
      }
    }
    ["tmp_name"]=>
    array(2) {
      [37]=>
      array(1) {
        ["file"]=>
        string(14) "/tmp/phpahucFZ"
      }
      [38]=>
      array(1) {
        ["file"]=>
        string(14) "/tmp/phptnDGQR"
      }
    }
    ["error"]=>
    array(2) {
      [37]=>
      array(1) {
        ["file"]=>
        int(0)
      }
      [38]=>
      array(1) {
        ["file"]=>
        int(0)
      }
    }
    ["size"]=>
    array(2) {
      [37]=>
      array(1) {
        ["file"]=>
        int(12023)
      }
      [38]=>
      array(1) {
        ["file"]=>
        int(18174)
      }
    }
  }
}

This array is the output of the above code.

Can somebody tell me how can I iterate this array in a sane way?

I want the same below output :

Array
(
    [0] => Array
        (
            [name] => foo.txt
            [type] => text/plain
            [tmp_name] => /tmp/phpYzdqkD
            [error] => 0
            [size] => 123
        )

    [1] => Array
        (
            [name] => bar.txt
            [type] => text/plain
            [tmp_name] => /tmp/phpeEwEWG
            [error] => 0
            [size] => 456
        )
)

I use below link but not work for me :

How can I iterate PHP $_FILES array?

Uploading multiple files

Thanks for the help.

Upvotes: 0

Views: 67

Answers (3)

Michel
Michel

Reputation: 4157

You could change the names of the inputs, so the array becomes cleaner:

name="entry[<?= $site['id'] ?>][date]"
in:
name="date[<?= $site['id'] ?>]"

and 
name="entry[<?= $site['id'] ?>][file]" 
in:
name="file[<?= $site['id'] ?>]" 

The $_FILES array then should be looking like:

[file]=>
  [name]     => [ 37=>... , 38=> ... ],
  [type]     => [ 37=>... , 38=> ... ],
  [tmp_name] => [ 37=>... , 38=> ... ],
  [error]    => [ 37=>... , 38=> ... ],
  [size]     => [ 37=>... , 38=> ... ],

Then it's simply looping:

foreach($_FILES['file'] as $key=>$array){
foreach($array as $nr=>$value){
  $my_files[$nr][$key] = $value;
}
}

Upvotes: 0

Rahul
Rahul

Reputation: 18557

Here is the simple snippet,

$result = [];
foreach ($_FILES['entry'] as $key => $value) {
    foreach ($value as $key1 => $value1) {
        $result[$key1][$key] = $value1['file'];    // fetching $key1 index and its file
    }
}
// if you want to reset indexes,
// $result = array_values($result);

Demo

Output

Array
(
    [37] => Array
        (
            [name] => my-file-test.docx
            [type] => application/vnd.openxmlformats-officedocument.wordprocessingml.document
            [tmp_name] => /tmp/phpahucFZ
            [error] => 0
            [size] => 12023
        )

    [38] => Array
        (
            [name] => resources_views.php
            [type] => application/x-php
            [tmp_name] => /tmp/phptnDGQR
            [error] => 0
            [size] => 18174
        )

)

Upvotes: 2

Grabatui
Grabatui

Reputation: 281

Yeah, php's $_FILES is insane staff :)

You can iterate by, for example, name's indexes:

$entries = $_FILES['entry'];

$result = [];
foreach (array_keys($entries['name']) as $index) {
    $row = [];
    // Use all possible keys
    foreach (['name', 'type', 'tmp_name', 'error', 'size'] as $key) {
        $row[$key] = $entries[$key][$index]['file'];
    }

    $result[$index] = $row;
}

var_dump($result);

Upvotes: 1

Related Questions