如何仅将目录下许多子目录中的文件复制到 GCP 中的另一个项目存储桶中?

Posted

技术标签:

【中文标题】如何仅将目录下许多子目录中的文件复制到 GCP 中的另一个项目存储桶中?【英文标题】:How to copy only files from many subdirectory under the directory to another project bucket in GCP? 【发布时间】:2018-12-27 10:43:53 【问题描述】:

我的 Google Cloud 存储分区中有大量数据。我必须将所有文件复制到另一个项目存储桶。但主要问题是,在这个存储桶中,我创建了一些文件夹,在这个文件夹下有许多子文件夹,所有子文件夹都有数据。因此,当我使用普通的 gsutil 复制命令时,它会复制所有数据以及文件夹。 我需要帮助来解决这个问题。因为从一个项目复制到另一个项目存储桶需要太多时间。

【问题讨论】:

不清楚是什么问题。是复制时间过长还是复制了不想复制的文件? 【参考方案1】:

您可以使用此命令将所有文件都放在根路径中。

gsutil cp 'gs://[YOUR_FIRST_BUCKET_NAME]/*' gs://[YOUR_SECOND_BUCKET_NAME]

如果您的存储桶中有嵌套目录,请使用以下命令:

gsutil cp -r 'gs://[YOUR_FIRST_BUCKET_NAME]/*' gs://[YOUR_SECOND_BUCKET_NAME]

注意第一个命令周围的单引号。 如果您需要更多高级功能,可以查看Wildcard Names。

【讨论】:

【参考方案2】:

您可以使用Google Data Transfer Service

它是Google Cloud Storage 子类别中的第二个选项。

【讨论】:

但我必须将所有文件从一个项目存储桶复制到另一个项目存储桶。在这种转移方式中,我无法选择目的地。 @ChandanThakur 如果你有写权限,你可以转移。【参考方案3】:

使用不带 -r 选项的 gsutil cp 命令。

-R 和 -r 选项是同义词。导致目录, 要递归复制的存储桶和存储桶子目录。 如果您忽略使用此选项进行上传,gsutil 将 复制它找到的任何文件并跳过任何目录。相似地, 忽略为下载指定此选项将导致 gsutil 复制当前存储桶目录中的任何对象 级别,并跳过任何子目录。

【讨论】:

当我忽略 -R 和 -r 时,我会收到类似省略前缀的错误。 当您必须从存储桶而不是存储桶/文件夹/子文件夹/文件中复制文件时,这很有用。在这里,我必须将文件从存储桶/文件夹/子文件夹/文件复制到另一个项目存储桶。【参考方案4】:

如果我理解得很好,您希望将所有文件从一个存储桶复制到另一个存储桶,但您不希望具有相同的层次结构,而是希望将所有文件都放在根路径中。

现在没有办法用 gsutil 做到这一点,但你可以用脚本做到这一点,这里有我的解决方案:

from google.cloud import storage
bucketOrigin = storage.Client().get_bucket("<BUCKET_ID_ORIGIN>")
bucketDestination = storage.Client().get_bucket("<BUCKET_ID_DESTINATION")
for blob in bucketOrigin.list_blobs():
    strfile=blob.download_as_string()
    blobDest = bucketDestination.blob(blob.name[blob.name.rfind("/")+1:])
    blobDest.upload_from_string(strfile)

【讨论】:

【参考方案5】:

正如Akash Dathan 所述,您可以使用云存储传输服务 来移动您的存储桶内容。我建议您查看此Moving and Renaming Buckets 指南,您可以在其中找到执行此任务所需的步骤。

请记住以下要求:

Transfer Service 服务帐户必须具有读取权限 您的来源并写入您的目的地。 如果您要删除源文件,则 Transfer Service 的服务帐户将需要对源文件的删除权限。 如果您的服务帐户没有这些 权限,但必须由存储桶所有者授予。

注意。如果您对源存储桶和目标存储桶拥有 'storage.buckets.setIamPolicy' 权限,则创建传输作业将授予该服务帐户具有完成转移所需的源和目标权限。

【讨论】:

【参考方案6】:

您可以列出子文件夹中的所有文件并使用split() 方法获取文件名。然后您可以使用copy() 方法将文件复制到另一个存储桶。以下方法删除所有子文件夹:

    const [files] = await storage.bucket(srcBucketName).getFiles();
    files.forEach((file) => 
      let fileName = file.name.split("/").pop();
      if (fileName) 
        file.copy(storage.bucket(destBucketName).file(`$prefix/$fileName`));

    );

【讨论】:

以上是关于如何仅将目录下许多子目录中的文件复制到 GCP 中的另一个项目存储桶中?的主要内容,如果未能解决你的问题,请参考以下文章

将文件从 GCP 复制到 docker 容器

如何使用 Maven pom 仅将 jar 文件下载到特定目录?

如何仅将输入文件的选定列复制到jcl排序中的输出文件

如何仅将提交的文件名导出到 git 中的 txt 文件? [复制]

处理多个文件时如何使inotify等待

Xcode iOS Build - 仅将特定子文件夹复制为捆绑资源