laravellaravel-5.8quasar-frameworkquasarlaravel-filesystem

Quasar q-uploader with Laravel not recognizing the file while q-file works


I was able to get q-file to upload a single image and my Laravel API is handling it perfectly. Of course I need multiple files uploaded at once so I'm trying to switch to q-uploader and when I log the response the file shows as [object File].

I also tried using $request->file('attachment') in the FileController but it returns null.

    <q-uploader
      :factory="uploadFactory"
      label="Upload Images/Files"
      color="primary"
      multiple
    />

Then in my FileController.php:

public function upload(Request $request) {
  \Log::info($request);
}

returns:

array (
  'attachment' => '[object File]',
  'fileable_type' => 'App\\Task',
  'fileable_id' => '27375',
  'vessel_id' => '1',
)

My factory to upload:

uploadFactory (file) {
  let data = new FormData()
  data.append('attachment', file)
  data.append('fileable_type', 'App\\Task')
  data.append('fileable_id', this.task.id)
  data.append('vessel_id', this.vessel.id)
  return new Promise((resolve, reject) => {
    this.$axios.post('/api/file/upload', data, { headers: { 'Content-Type': 'multipart/form-data' } }).then(response => {
      console.log(response)
      resolve(null)
    }).catch(error => {
      if (error) {
        console.log(error)
      }
    })
  })
},

When I try this with the q-file:

    <q-file color="primary" v-model="attachments" label="Images/Files" outlined>
      <template v-slot:prepend>
        <q-icon name="attach_file" />
      </template>
      <template v-slot:after v-if="canUpload">
        <q-btn
          color="primary"
          dense
          icon="cloud_upload"
          round
          @click="submitFiles"
          :disable="!canUpload"
          :loading="isUploading"
        />
      </template>
    </q-file>

It works and here's what I'm logging in Laravel for the request:

array (
'fileable_type' => 'App\\Task',
  'fileable_id' => '27375',
  'vessel_id' => '1',
  'attachments' => 
  Illuminate\Http\UploadedFile::__set_state(array(
     'test' => false,
     'originalName' => 'IMG_0126.jpg',
     'mimeType' => 'image/jpeg',
     'error' => 0,
     'hashName' => NULL,
  )),
)

Solution

  • probably you got the answer to this question already. But here is what I did. I had the same issue from q-uploader, send one file to laravel, and everything is OK. But I got stuck when sending multiple files. I had to consult info from various sources to arrange the hole process. So what I did is this:

    On my frontend:

    <q-uploader
                     :factory="uploadFiles"
                     :loading="uploadPercent"
                     :url="getUrl()"
                     @finish="finished"
                     label="Cargar Archivos (max 2MB)"
                     ref="uploader"
                     multiple
                     bordered
                     batch
                     accept=".png, .jpeg, .jpg, .doc, .docx, .xls, .xlsx, .ppt, .pptx, .csv, .pdf, pdf/*, image/*"
                     :max-file-size="2048000"
                     />
    

    On my method:

    uploadFiles(file){
            this.uploadPercentage = true
            let files = file
            console.log(files)
            let files_count = files.length + this.files.length
            if(files_count > 10){
               this.Notify(`El límite de archivos por tarea es de 10`,'negative')
               this.finished()
               return
            }
            const data = new FormData()
            for(var i = 0; i < files.length; i++){
               let file = files[i]
               data.append(`files[${i}]`, file)
            }
            data.append('teacher', this.teacher)
            data.append('homework', this.homework)
            return new Promise((resolve, reject) => {
               this.$axios.post(`${process.env.API}/homework/upload-files`, data,
               {
                  headers: { 'content-type': 'multipart/form-data' },
                  processData: false,  contentType: false
               })
               .then(res => {
                  resolve(null)
                  this.uploadPercentage = false
                  this.files = res.data
                  this.Notify('Se subieron los archivos con éxito','positive')
               })
               .catch(err => {
                  reject(err)
                  this.errors = err.response.data.errors
                  this.uploadPercentage = false
                  this.Notify('No se pudieron cargar los archivos, o el formato de alguno de los archivos no es correcto, o alguno de los archivos pesa más de 2MB','negative')
               })
            })
         },
    

    And on my backend function, I only store the file (I'am storing it on the public folder instead of storage, because I have a shared hosting on this project), additionally you can add some code to save the file location to your Database:

    public function upload_files(Request $request)
    {
        $homework = DB::table('homeworks as h')
            ->join('teachers as t','t.id','=','h.teacher_id')
            ->join('users as u','u.id','=','t.teacher_id')
            ->select('h.id')
            ->where('h.code','=',$request->homework)
            ->where('u.code','=',$request->teacher)
            ->first();
    
        if(!$homework){
            return response()->json(['success'=>false,'msg'=>'Not avalid homework'],422);
        }
    
        try{
            DB::beginTransaction();
    
            $files = $request->file('files');
    
            if(!empty($files)){
                for($i = 0; $i < count($files); $i++){
                    $file = $files[$i];
                    $filename = $request->homework.'_'.uniqid('doc_').'.'.$file->getClientOriginalExtension();
                    $path = public_path('/uploads');
                    $file->move($path, $filename);
                }
            }
    
            DB::commit();
    
            return response()->json(['success' => true], 200);
        }
        catch (\Exception $e) 
        {
            DB::rollback();
            throw $e;
        }
    }