我有一个 ECS Fargate 任务,该任务下载 S3 存储桶中的大约 200 万个 CSV,将它们压缩到单个 zip 存档中,然后将该存档保存到 S3。 CSV 约为 40kb。我在 Docker 容器中运行的代码如下。
但我收到错误“OSError: [Errno 28] 设备上没有剩余空间: '/app/data/temp/myfile.csv'”
Fargate 文档表示:“对于使用平台版本 1.4.0 或更高版本的 Fargate 任务上的 Amazon ECS,每个任务都会接收 20 GB 的临时存储”。 (https://docs.aws.amazon.com/AmazonECS/latest/developerguide/fargate-task-storage.html)
这就是我遇到磁盘错误的原因,因为 40kb * 2000000 个文件 = 80000000kb = 80Gb
我剩下的问题是如何从 S3 下载这些文件并压缩它们。有没有办法通过从并行容器生成多个 zip 文件来并行解决这个问题? (或者完全生成此 S3 存储桶的 zip 的更好方法)。
我可以通过这样做将它们一一下载:
aws s3 sync s3://mybucketname .
但是,一旦将它们全部下载到我的计算机上,我就无法在本地将它们压缩到一个文件中,我的计算机崩溃了(因此在 AWS 上执行此操作)。
谢谢
import boto3
import os
from botocore.exceptions import ClientError
import shutil
from configs import *
s3_resource = boto3.resource('s3')
s3_client = boto3.client('s3')
source_bucket = s3_resource.Bucket(bucket)
# download CSVs
for s3_object in source_bucket.objects.all():
path, filename = os.path.split(s3_object.key)
source_bucket.download_file(s3_object.key, f"temp/{filename}") # OSError: [Errno 28] No space left on device: '/app/data/temp/myfile.csv'
# archive
shutil.make_archive(f"temp/archive", 'zip', tmp_dir)
# save to s3
s3_client.upload_file(f"temp/archive.zip", bucket, "archive.zip")
最佳答案
自最近(2020 年 4 月)以来,ECS 和 Fargate 内置了对 EFS 的支持:
ECS tasks using EFS will automatically mount the file systems specified by the customer in the task definition and make them available to the containers in the task across all availability zones in the region. This enables persistent, shared storage to be defined and used at the task and container level in ECS.
因此,使用 EFS 可能是解决存储短缺问题的一种可能方法。
关于Python从S3下载/压缩文件: ECS Fargate hits storage limit,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63243741/