我们在AWS S3存储桶中有数百个没有设置内容处理的对象。
我正在使用Ruby aws-sdk gem。
如何在不重新上传文件的情况下为这些对象添加或更改内容处置?
我试过了
obj.write(:content_disposition => 'attachment')
obj.copy_from(obj.key, :content_disposition => 'attachment')
以及copy_to(),move_to(),但这些似乎都不适用于向对象添加内容处置。在少数情况下,对象似乎根本没有被修改(修改时间没有改变),在其他情况下,对象文件已损坏!
我知道使用的替代方法:response_content_disposition 当通过HTTP请求s3对象时,它设置了Content-Disposition标头
obj.url_for(:read, :response_content_disposition => "attachment")
谢谢!
答案 0 :(得分:1)
我们通过更改aws-sdk源代码找到了解决方案。
在s3 / s3_object.rb
中将以下行添加到copy_from()(类似于:content_type的处理方式)
if options[:content_disposition]
copy_opts[:content_disposition] = options[:content_disposition]
copy_opts[:metadata_directive] = "REPLACE"
end
另外,在s3 / client.rb
中添加下面标有
的行object_method(:copy_object, :put,
:header_options => {
:copy_source => 'x-amz-copy-source',
:cache_control => 'Cache-Control',
:metadata_directive => 'x-amz-metadata-directive',
:storage_class => 'x-amz-storage-class',
:server_side_encryption => 'x-amz-server-side-encryption',
:content_type => 'Content-Type',
:content_disposition => 'Content-Disposition', # add this line here
}) do
完成上述操作后,您可以执行以下操作,为现有对象添加内容处置:
obj.copy_from(obj.key, :content_disposition => 'attachment', :content_type => 'image/png', :acl => :public_read)
答案 1 :(得分:0)
对于后代,这里是一个基于cli的解决方案。如果首先列出/mybucket/brand_img/ios/
中的对象,然后将每个项目的内容处置设置为文件名。我需要这个,因为我的文件名有' @'在他们中,我不想强迫客户端对路径进行url编码。
aws s3 ls s3://mybucket/brand_img/ios/|awk {'print $4'} > objects.txt
while read line; do aws s3api copy-object --bucket mybucket \
--copy-source /mybucket/brand_img/ios/$line --key brand_img/ios/$line \
--metadata-directive REPLACE --metadata Content-Disposition=$line --acl public-read; done < objects.txt