Подтвердить что ты не робот

Как загрузить файл с помощью window.fetch?

Если я хочу загрузить файл, что мне делать в блоке then ниже?

function downloadFile(token, fileId) {
  let url = `https://www.googleapis.com/drive/v2/files/${fileId}?alt=media`;
  return fetch(url, {
    method: 'GET',
    headers: {
      'Authorization': token
    }
  }).then(...);
}

Обратите внимание, что коды находятся на стороне клиента.

4b9b3361

Ответ 1

Я временно решу эту проблему, используя download.js и blob.

let download = require('./download.min');

...

function downloadFile(token, fileId) {
  let url = `https://www.googleapis.com/drive/v2/files/${fileId}?alt=media`;
  return fetch(url, {
    method: 'GET',
    headers: {
      'Authorization': token
    }
  }).then(function(resp) {
    return resp.blob();
  }).then(function(blob) {
    download(blob);
  });
}

Он работает для небольших файлов, но, возможно, не работает для больших файлов. Я думаю, что я должен больше Stream.

Ответ 2

РЕДАКТИРОВАТЬ: syg ответ лучше. Просто используйте библиотеку downloadjs.

Ответ, который я предоставил, хорошо работает в Chrome, но в Firefox и IE вам нужен другой вариант этого кода. Для этого лучше использовать библиотеку.


У меня была похожая проблема (нужно передать заголовок авторизации для загрузки файла, чтобы это решение не помогло).

Но на основании этого ответа вы можете использовать createObjectURL чтобы браузер сохранил файл, загруженный с помощью Fetch API.

getAuthToken()
    .then(token => {
        fetch("http://example.com/ExportExcel", {
            method: 'GET',
            headers: new Headers({
                "Authorization": "Bearer " + token
            })
        })
        .then(response => response.blob())
        .then(blob => {
            var url = window.URL.createObjectURL(blob);
            var a = document.createElement('a');
            a.href = url;
            a.download = "filename.xlsx";
            document.body.appendChild(a); // we need to append the element to the dom -> otherwise it will not work in firefox
            a.click();    
            a.remove();  //afterwards we remove the element again         
        });
    });

Ответ 3

Вот пример использования node-fetch для любого, кто находит это.

reportRunner({url, params = {}}) {
    let urlWithParams = '${url}?'
    Object.keys(params).forEach((key) => urlWithParams += '&${key}=${params[key]}')
    return fetch(urlWithParams)
        .then(async res => ({
            filename: res.headers.get('content-disposition').split('filename=')[1],
            blob: await res.blob()
        }))
        .catch(this.handleError)
}

Ответ 4

Использование dowloadjs. Это будет анализировать имя файла из заголовка.

fetch("yourURL", {
    method: "POST",
    body: JSON.stringify(search),
    headers: {
        "Content-Type": "application/json; charset=utf-8"
    }
    })
    .then(response => {
        if (response.status === 200) {
            filename = response.headers.get("content-disposition");
            filename = filename.match(/(?<=")(?:\\.|[^"\\])*(?=")/)[0];
            return response.blob();
        } else {
        return;
        }
    })
    .then(body => {
        download(body, filename, "application/octet-stream");
    });
};

Ответ 5

function download(dataurl, filename) {
  var a = document.createElement("a");
  a.href = dataurl;
  a.setAttribute("download", filename);
  a.click();
  return false;
}

download("data:text/html,HelloWorld!", "helloWorld.txt");

Ответ 6

Я попробовал window.fetch, но это оказалось сложно с моим приложением REACT

Теперь я просто изменил window.location.href и добавил параметры запроса, такие как jsonwebtoken и other stuff.


///==== client side code =====
var url = new URL('http://${process.env.REACT_APP_URL}/api/mix-sheets/list');
url.searchParams.append("interval",data.interval);
url.searchParams.append("jwt",token)

window.location.href=url;

// ===== server side code =====

// on the server i set the content disposition to a file
var list = encodeToCsv(dataToEncode);
res.set({"Content-Disposition":'attachment; filename=\"FileName.csv\"'});
res.status(200).send(list)

конечные результаты на самом деле оказываются довольно хорошими, окно делает запрос и загружает файл, а переключатель событий не перемещает страницу, как если бы вызов window.location.href был похож на вызов lowkey fetch().

Ответ 7

Что касается некоторых других ответов, вы можете использовать window.fetch и download.js, чтобы загрузить файл. Тем не менее, использование window.fetch с blob имеет ограничение на память, наложенное браузером, а download.js также имеет свои ограничения совместимости.

Если вам нужно скачать файл большого размера, вы не хотите помещать его в память клиентской части, чтобы подчеркнуть браузер, верно? Вместо этого вы, вероятно, предпочитаете скачать его через поток. В таком случае использование ссылки HTML для загрузки файла является одним из лучших/самых простых способов, особенно для загрузки файлов большого размера через поток.

Шаг первый: создать и стилизовать элемент ссылки

Вы можете сделать ссылку невидимой, но все же действующей.

HTML:

<a href="#" class="download-link" download>Download</a>

CSS:

.download-link {
  position: absolute;
  top: -9999px;
  left: -9999px;
  opacity: 0;
}

Шаг второй: Установите href ссылки и запустите событие click

JavaScript

let url = 'https://www.googleapis.com/drive/v2/files/${fileId}?alt=media';

const downloadLink = document.querySelector('.download-link')
downloadLink.href = url + '&ts=' + new Date().getTime() // Prevent cache
downloadLink.click()

Примечание: при необходимости вы можете динамически генерировать элемент ссылки.