繁体   English   中英

如何从 Firebase 存储下载整个文件夹?

[英]How to download entire folder from Firebase Storage?

我想从 Firebase 存储下载整个文件夹。 我可以使用DownloadURL下载单个文件,如下所示,但它不适用于文件夹。

var storageRef = firebase.storage().ref();

// Create a reference to the file we want to download
var starsRef = storageRef.child(path);

// Get the download URL
starsRef.getDownloadURL().then(function(url) {
  // Insert url into an <img> tag to "download"
  ImageUrl = url;

  console.log(ImageUrl);
}).catch(function(error) {
  switch (error.code) {
    case 'storage/object_not_found':
      // File doesn't exist
      break;

    case 'storage/unauthorized':
      // User doesn't have permission to access the object
      break;

    case 'storage/canceled':
      // User canceled the upload
      break;

    case 'storage/unknown':
      // Unknown error occurred, inspect the server response
      break;
  }
});

如何从 Firebase 下载整个文件夹?

您可以使用gsutil下载整个存储桶

gsutil -m cp -R gs://<bucket_name> .

Firebase 存储中没有用于下载文件夹中所有文件的 API。 您必须逐个下载文件,或创建一个包含所有文件的 zip 文件。

正如Lahiru 的回答所示,它可以通过gsutils来完成,但这是一个服务器端操作——而不是你在客户端应用程序中运行的东西。

有关的:

Windows的命令gustil !!!

gsutil cp -r gs://<bucket_name>.appspot.com/OBJECT_NAME "D:\path"

使用适用于 PowerShell 的云工具

REF 安装窗口 >> https://cloud.google.com/storage/docs/gsutil_install

您可以通过创建一个 zip 文件来下载该文件夹。

这是一个示例函数:

import JSZip from 'jszip';
import { saveAs } from 'file-saver';
import {
  getStorage,
  listAll,
  ref,
  getDownloadURL,
  getMetadata,
} from 'firebase/storage';
import { auth } from '../../Firebase';

export const downloadFolderAsZip = async () => {
  const jszip = new JSZip();
  const storage = getStorage();
  const folderRef = ref(
    storage,
    'images'
  );
  const folder = await listAll(folderRef);
  const promises = folder.items
    .map(async (item) => {
      const file = await getMetadata(item);
      const fileRef = ref(storage, item.fullPath);
      const fileBlob = await getDownloadURL(fileRef).then((url) => {
        return fetch(url).then((response) => response.blob());
      });
      jszip.file(file.name, fileBlob);
    })
    .reduce((acc, curr) => acc.then(() => curr), Promise.resolve());
  await promises;
  const blob = await jszip.generateAsync({ type: 'blob' });
  saveAs(blob, 'download.zip');
};

有关在 zip 文件中包含子文件夹的递归解决方案,请参阅以下示例。 您将实例化一个 jszip object,等待 function 的承诺,它压缩文件并遍历目录,然后保存 zip。 如果内容是文件(“项目”),则将其压缩到 jszip object 中。 如果是文件夹(“前缀”),则使用新的子路径再次调用 function,传入相同的 jszip object。 为了进一步改进,如果您的内容对于listAll来说太多,您可能希望获取带有list和分页的内容,因为listAll限制检索。

import JSZip from 'jszip';
import { saveAs } from 'file-saver';
import {
  getStorage, ref, getBlob, listAll,
} from "firebase/storage";

const addFilesFromDirectoryToZip = async (directoryPath = "", zip) => {
  const storage = getStorage();
 
  const directoryContentsRef = ref(
    storage,
    directoryPath
  );
  const directoryContents = await listAll(directoryContentsRef);

  for (const file of directoryContents.items) {
    const fileRef = ref(storage, file.fullPath);
    const fileBlob = await getBlob(fileRef)
    zip.file(file.fullPath, fileBlob);
  }

  for (const folder of directoryContents.prefixes) {
    await addFilesFromDirectoryToZip(folder.fullPath, zip);
  };
};

export const downloadFolderAsZip = async (directoryPath = "") => {
  const zip = new JSZip();

  await addFilesFromDirectoryToZip(directoryPath, zip);

  const blob = await zip.generateAsync({ type: "blob" });
  const name = directoryPath.split('/').pop();
  saveAs(blob, name);
};

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM