Загрузить файл по индексу объекта файлов

Я использую Vuejs для создания формы загрузки.

Проблема в том, что когда я загружаю ключ объекта, внутренний сервер получает пустой запрос: лайк axios.postForm(app_url() + 'api/upload', { files: e.target.files[key] }, api_config())

Но когда я загружаю следующее выражение (все файлы вместе), оно работает правильно: лайк axios.postForm(app_url() + 'api/upload', { files: e.target.files }, api_config())

В чем причина этой проблемы? и как я могу отправлять файлы на сервер отдельно и одновременно?

Вот код:

<script setup>
import uploadIcon from '../assets/images/direct-inbox.png';
import axios from 'axios';
import app_url from '../customJavascript/app_url';
import api_config from '../customJavascript/api_config';

const changeFile = (e) => {

  const all = [];

  for (const key in e.target.files) {

    if (typeof e.target.files[key] == 'object') {
      all.push(axios.postForm(app_url() + 'api/upload', { files: e.target.files }, api_config()));
    }

  }

  axios.all(all)
    .then(axios.spread((data1, data2) => {
      console.info('data1', data1, 'data2', data2)
    }));

}
</script>

<template>
  <div class = "main-card">
    <p class = "main-card-title">upload file</p>

    <div class = "mt-6 flex justify-center">


      <div class = "upload-card clickable focus:shadow-none">

        <div class = "relative text-center h-full flex flex-col justify-center align-center">
          <input type = "file" @change = "changeFile"
            class = "rounded-2xl cursor-pointer absolute right-0 top-0 w-full h-full opacity-0" multiple />
        </div>

      </div>

    </div>
  </div>
</template>


<style>
.upload-card {
  @apply w-11/12 lg:w-5/12 h-60 lg:h-60 rounded-2xl border-2 border-lightblue bg-white hover:shadow-lg;
}
.upload-card:hover button {
  @apply bg-primary;
}
</style>

Я поместил код вне цикла и отправил запрос только со статической переменной index. Я ожидал, что, возможно, цикл вызвал эту проблему, но это не так.

Это полностью зависит от бэкэнда. Ваша конечная точка /upload, скорее всего, ожидает запрос, содержащий определенную полезную нагрузку, например. массив файлов или FileList, а не один файл.

yoduh 12.04.2024 22:02

Серверная часть в порядке, это PHP Laravel

Farhad 12.04.2024 22:04
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
0
2
71
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

похоже, ваш сервер ожидает массив файлов. если вы хотите загружать файлы отдельными запросами, вам необходимо иметь это: { files: [e.target.files[key]] }

PS: вы также можете использовать функции фильтра + карты:

const all = e.target.files
   .filter((file) => typeof file === 'object')
   .map((file) => axios.postForm(app_url() + 'api/upload', { files: [file] }, api_config());

На самом деле я превратил объект файлов в массив, и с помощью цикла for of это сработало.

Farhad 12.04.2024 22:36

в вашем коде вы используете for in, а не for of

Boris Maslennikov 16.04.2024 10:54
Ответ принят как подходящий

В вашем коде e.target.files — это объект FileList [w3c] . Этот интерфейс представляет собой список объектов File [w3c].

Итерация не делает того, что вы думаете.

for (const key in e.target.files) // [for ••• in [mdn] statement]

Он перебирает указанную переменную по всем перечислимым свойствам FileList. См. пример [mdn].

Чтобы правильно перебрать значения FileList, используйте:

for (const file of e.target.files) // [for ••• of [mdn] statement]

Теперь он перебирает последовательность значений, полученных из объекта FileList.

И наконец, верен ли этот тест? [1]

if (typeof e.target.files[key] == 'object')

Технически, вы перебираете перечислимые свойства FileList и проверяете, является ли каждое свойство object.

Мне придется остановиться здесь. [2]


Чтобы загрузить данные по HTTP, тип данных должен быть правильно указан, чтобы сообщить серверу, как обрабатывать входящие данные. Это вы укажете в шапке вашего запроса. Заголовок Content-Type часто используется со значением multipart/form-data. Большинство серверов знают, что делать, когда получают это.

К счастью, axios справится со стрессом, когда вы используете axios.postForm().


[1] I had a feeling this will be asked.

[2] I stopped there because I couldn’t justify to myself why the code after the if statement is even there.

Другие вопросы по теме