Jim E Russel
Jim E Russel

Reputation: 495

Vue / Laravel / Vuetify - Append multiple files inside an array

I have an array of data (parent) in which each element have their own row.files array (children). When submitting the form, only one children file is captured for each parent data array.

Template

<v-form  ref="form" @submit.prevent="save()">
  <v-btn type="submit" >Submit</v-btn>
  <v-col cols="3" v-for="row in chunk" :key="row.id">
    <v-file-input
      v-model="row.files"
      counter
      multiple
      small-chips
    >
    </v-file-input>
  </v-col>
</v-form>

 save() {
   for( let i = 0; i < this.rows.length; i++ ) {
     let formData = new FormData()
       if(this.rows[i].files) {
         for( let j = 0; j < this.rows[i].files.length; j++ ) {
           formData.append('file', this.rows[i].files[j])
         }
       }
      axios.post('/api/performance', formData, { headers: { 'Content-Type': 'multipart/form-data' }})
    }
 }

Controller

public function store(Request $request)
  {
    if($request->file('file')) {
      $file = $request->file;
      $filename = $file->getClientOriginalName();
      $path = hash( 'sha256', time());
      if(Storage::disk('employee_objective')->put($path.'/'.$filename, File::get($file))) {
        $input['employee_objective_kpa_id'] = $objectiveKPA->id;
        $input['filename'] = $filename;
        $input['mime'] = $file->getClientMimeType();
        $input['path'] = $path;
        $input['size'] = $file->getClientSize();
        EmployeeObjectiveFile::create($input);
      }

    }
  }

It works if the upload is a standalone and not inside an array.

for( let i = 0; i < this.files.length; i++ ) {
  let formData = new FormData();
  formData.append('file', this.files[i]);

  axios.post('/api/performance', formData, { headers: { 'Content-Type': 'multipart/form-data' }})
    })
  }

Upvotes: 0

Views: 692

Answers (1)

Igor Moraru
Igor Moraru

Reputation: 7729

When appending to formData, if there are multiple files, you should append [] to files key:

formData.append('file[]', this.rows[i].files[j])

so it append to the array of files, otherwise you are rewriting the file property on each iteration.

Then in backend, you access the files like that:

$files = $request->file('file');
foreach ($files as $file) {

    // Do the work for each file

}

Upvotes: 2

Related Questions