[英]Streaming decompression of S3 gzip source object to a S3 destination object using python?
给定 S3 中的一个大型gzip
对象,python3/boto3 中的内存高效(例如流)方法是什么来解压缩数据并将结果存储回另一个 S3 对象?
之前有一个类似的问题。 但是,所有答案都使用一种方法,其中首先将 gzip 文件的内容读入内存(例如ByteIO
)。 对于太大而无法放入主内存的对象,这些解决方案是不可行的。
对于大型 S3 对象,内容需要被读取、“即时”解压缩,然后写入不同的 S3 对象是某种分块方式。
预先感谢您的考虑和回应。
您可以将流方法与boto / s3 一起使用,但您必须定义自己的类文件对象 AFAIK。
幸运的是,有smart_open为您处理; 它还支持GCS、Azure、HDFS、SFTP等。
这是一个使用大量销售数据样本的示例:
import boto3
from smart_open import open
session = boto3.Session() # you need to set auth credentials here if you don't have them set in your environment
chunk_size = 1024 * 1024 # 1 MB
f_in = open("s3://mybucket/2m_sales_records.csv.gz", transport_params=dict(session=session), encoding="utf-8")
f_out = open("s3://mybucket/2m_sales_records.csv", "w", transport_params=dict(session=session))
byte_count = 0
while True:
data = f_in.read(chunk_size)
if not data:
break
f_out.write(data)
byte_count += len(data)
print(f"wrote {byte_count} bytes so far")
f_in.close()
f_out.close()
示例文件有200 万行,压缩为75 MB ,未压缩为238 MB 。
我将压缩文件上传到mybucket
并运行下载文件的代码,提取内存中的内容并将未压缩的数据上传回 S3。
在我的电脑上,这个过程大约需要78 秒(高度依赖于互联网连接速度)并且从未使用超过95 MB的内存; 我认为如果需要,您可以通过在smart_open 中覆盖 S3 分段上传的部分大小来降低内存要求。
DEFAULT_MIN_PART_SIZE = 50 * 1024**2
"""Default minimum part size for S3 multipart uploads"""
MIN_MIN_PART_SIZE = 5 * 1024 ** 2
"""The absolute minimum permitted by Amazon."""
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.