调用S3 Python SDK的put_object时指定MetadataDirective报错
问题解决:S3上传文件元数据修改错误及参数问题
错误原因分析
MetadataDirective参数仅在boto3的S3客户端(boto3.client('s3'))的put_object方法中支持,你用的是S3资源(boto3.resource('s3')),所以会触发参数验证错误。- 你把
Content-Type放在Metadata字典里是错误的:S3会自动给Metadata中的键加上x-amz-meta-前缀,变成自定义元数据,而系统默认的Content-Type(binary/octet-stream)不会被覆盖,导致两种元数据并存。
修正后的代码
方式一:使用S3资源(推荐,更简洁)
直接将Content-Type作为独立参数传入put_object,不需要Metadata和MetadataDirective:
import boto3 BUCKET_NAME = 'mybucket' FILE_NAME = 'three-puppies.jpg' data = open(FILE_NAME, 'rb') session = boto3.Session(profile_name='default') s3 = session.resource('s3') # 通过session获取resource,确保使用指定的profile s3.Bucket(BUCKET_NAME).put_object( Key='new_puppies_file_withmtdt.jpg', Body=data, ContentType='image/jpeg' )
方式二:使用S3客户端
如果需要使用MetadataDirective(通常用于复制对象场景,上传新文件其实不需要),可以切换到客户端:
import boto3 BUCKET_NAME = 'mybucket' FILE_NAME = 'three-puppies.jpg' data = open(FILE_NAME, 'rb') session = boto3.Session(profile_name='default') s3_client = session.client('s3') s3_client.put_object( Bucket=BUCKET_NAME, Key='new_puppies_file_withmtdt.jpg', Body=data, ContentType='image/jpeg', MetadataDirective="REPLACE" )
效果说明
修正后,上传的文件元数据会变为:
系统定义 Content-Type image/jpeg
不会再生成x-amz-meta-content-type自定义元数据,符合你的预期。
内容的提问来源于stack exchange,提问作者Rahul Mishra
相关产品推荐
相关产品推荐

