如何使用 Amazon S3 SDK 更新元数据

Posted

技术标签:

【中文标题】如何使用 Amazon S3 SDK 更新元数据【英文标题】:How to update metadata using Amazon S3 SDK 【发布时间】:2012-08-04 12:57:01 【问题描述】:

我使用的是亚马逊 AWS 开发工具包的 php 版本。我有一堆带有Expires 标头的文件;我想删除该标题并添加一个 Cache-control 标题。 update_object 函数让我可以添加标题但不能删除它们。

answers on this question 建议您可以在复制文件时更新文件的元数据,但我已经尝试过,但它不起作用。这是我使用的:

$response = $s3->copy_object(
    array(
        'bucket' => $bucket,
        'filename' => $file,
    ),
    array(
        'bucket' => $bucket,
        'filename' => $file2,
    ),
    array(
        'acl' => AmazonS3::ACL_PUBLIC,
        'headers' => array(
            'Content-Type' => 'image/jpeg',
            'Cache-Control' => 'public,max-age=30240000',
        ),
        'meta' => array(
            'x-fake-header' => 'something awesome is happening',
        ),
    )
);

但是,复制的对象具有与原始对象完全相同的标头(仅限 Expires 和 Content-Type)。我已经尝试了上述所有方式的组合(有和没有 Content-Type、Cache-control、meta 等)并得到相同的结果。

如何重置元数据?

【问题讨论】:

【参考方案1】:

我刚刚发现将对象复制到自身实际上确实正确地更改了标题。我将其复制到第二个文件以进行测试以避免覆盖原始文件。

但由于某些奇怪的原因,复制到不同的文件不会更改标题,但复制到同一个文件会。

【讨论】:

这措辞有点奇怪。为什么复制到不同的文件会“改变”任何标题?你的意思是它没有在新文件上设置标题? @alex 很抱歉,如果不清楚。它应该更改标头,因为在请求中设置了新标头。如果您使用 headers 参数复制到相同的文件名(例如 FileA.jpg -> FileA.jpg),它会更改标题,但如果您复制到不同的文件(例如 FileA.jpg -> FileB.jpg),则提供的标题是未设置。【参考方案2】:

根据 Jeffin P S 的回答(效果很好),我提出了一个通过克隆原始元数据对象来创建新元数据对象的版本。这样,特定于 AWS 的(非用户)元数据不会转换为用户元数据。不确定这是否是一个真正的问题,但这样似乎更合法。

ObjectMetadata metadataCopy = amazonS3Client.getObjectMetadata(bucketName, fileKey).clone();
metadataCopy.addUserMetadata("yourKey", "updateValue");
metadataCopy.addUserMetadata("otherKey", "newValue");

CopyObjectRequest request = new CopyObjectRequest(bucketName, fileKey, bucketName, fileKey)
      .withSourceBucketName(bucketName)
      .withSourceKey(fileKey)
      .withNewObjectMetadata(metadataCopy);

amazonS3Client.copyObject(request);

【讨论】:

【参考方案3】:

在 Java 中,您可以将对象复制到同一位置。 这里元数据不会在复制对象时复制。 您必须获取原始元数据并设置为复制请求。 更推荐使用此方法插入或更新 Amazon S3 对象的元数据

ObjectMetadata metadata = amazonS3Client.getObjectMetadata(bucketName, fileKey);
ObjectMetadata metadataCopy = new ObjectMetadata();
metadataCopy.addUserMetadata("yourKey", "updateValue");
metadataCopy.addUserMetadata("otherKey", "newValue");
metadataCopy.addUserMetadata("existingKey", metadata.getUserMetaDataOf("existingValue"));

CopyObjectRequest request = new CopyObjectRequest(bucketName, fileKey, bucketName, fileKey)
      .withSourceBucketName(bucketName)
      .withSourceKey(fileKey)
      .withNewObjectMetadata(metadataCopy);

amazonS3Client.copyObject(request);

【讨论】:

以上是关于如何使用 Amazon S3 SDK 更新元数据的主要内容,如果未能解决你的问题,请参考以下文章

Amazon S3 设置元数据使用 AWS SDK PHP v2 upload() 失败

使用 lambda 更新 amazon s3 对象元数据而不执行对象复制?

如何使用 amazon sdk 为虚域生成预签名的 Amazon S3 url?

如何判断我的文件是不是已使用他们的 SDK 从 Amazon S3 中成功删除?

如何在不使用 SDK 的情况下使用 .NET HttpClient 上传到 Amazon S3

如何在不使用 SDK 的情况下将文件从 Android 上传到 Amazon S3