Python如何将迭代器中的图像数据直接上传到AWS S3存储桶
解决方案
错误点梳理
s3.upload_fileobj方法要求传入可读的类文件对象作为输入,原有代码传入了可写的BufferedWriter对象,所以触发类型不支持的报错- 原有代码错误将图像二进制分片作为S3的对象存储键(key),逻辑不符合预期
- 处理二进制图像文件时,文件打开模式需要用
wb二进制写入模式,原有w文本模式属于不规范写法,可能在部分环境下出现乱码
无本地文件的直传实现
使用io.BytesIO在内存中封装图像迭代器的二进制数据,不需要写入本地磁盘,直接上传到S3即可,示例代码如下:
import boto3 import io # 初始化S3客户端 s3 = boto3.client('s3') # 获取图像数据迭代器 img_obj = gmaps.places_photo(ph, max_width=500, max_height=400) # 初始化内存二进制流 img_buffer = io.BytesIO() # 迭代写入所有图像分片到内存流 for chunk in img_obj: img_buffer.write(chunk) # 移动流指针到起始位置,否则上传的文件为空 img_buffer.seek(0) # 自定义S3存储路径,可根据需要修改后缀为.png或.jpeg s3_object_key = f'img/output_image_{c}.png' # 上传到S3,可通过ExtraArgs指定Content-Type方便浏览器预览 s3.upload_fileobj( img_buffer, 'mybucket', s3_object_key, ExtraArgs={'ContentType': 'image/png'} ) # 如果需要同时保存到本地,可添加以下代码,不需要可删除 with open(f'output_image_{c}.png', 'wb') as fp: fp.write(img_buffer.getvalue())
补充说明
- 普通大小的图片使用以上方案完全足够,若需要处理超大型图像,可以自行封装支持流式读取的迭代器对象传入
upload_fileobj,进一步降低内存占用 - 若需要存储为jpeg格式,只需要修改S3对象键的后缀,同时将
ContentType改为image/jpeg即可
内容的提问来源于stack exchange,提问作者kms
相关产品推荐
相关产品推荐

