何の話?
S3に5GB以上のファイルを、aws-sdk-phpのS3のputObjectを使ってアップロードしようとしたら、以下のエラーが出た。
1ファイルあたりのアップロードできる上限サイズは、5368709120byte(5.36870912GB)
なのに、
5506553726byte(5.506553726GB)
アップロードしようとしてると怒られている。
Error executing "PutObject" on "https://xxxx.s3.ap-northeast-1.amazonaws.com/path/filename";
AWS HTTP error: Client error: `PUT https://xxxx.s3.ap-northeast-1.amazonaws.com/path/filename` resulted in a `400 Bad Request`
<?xml version='1.0' encoding='utf-8'?>
<error>
<code>
EntityTooLarge
</code>
<message>
Your proposed upload exceeds the maxim (truncated...)
EntityTooLarge (client): Your proposed upload exceeds the maximum allowed size -
<?xml version='1.0' encoding='utf-8'?>
</message>
</error>
<error>
<code>
EntityTooLarge
</code>
<message>
Your proposed upload exceeds the maximum allowed size
</message>
<proposedsize>
5506553726
</proposedsize>
<maxsizeallowed>
5368709120
</maxsizeallowed>
<requestid>
DCB569101CF240C0
</requestid>
<hostid>
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
</hostid>
</error>
AWSのよくある質問を見ると
Q: どれほどの量のデータを保存できますか?
格納可能なデータの総量とオブジェクトの数には制限はありません。個別の Amazon S3 オブジェクトのサイズは、最低 0 バイトから最大 5 テラバイトまでさまざまです。1つの PUT にアップロード可能なオブジェクトの最大サイズは 5 GB です。100 MB 以上のオブジェクトの場合は、Multipart Upload 機能を使うことをお考えください。
総量とオブジェクトの数には制限はないが、1つの PUT にアップロード可能なオブジェクトの最大サイズは 5 GBらしい。
100 MB 以上のオブジェクトの場合は、Multipart Upload 機能を使うことをお考えください、とある。
MultipartUploaderとは
以下のサイトにMultipartUploader
を使って、5GB以上のファイルでもアップロードする方法が書いてある。
最大5TBのファイルまでアップロードできるらしい。
Amazon S3 オブジェクトのサイズの上限までってことか。
With a single PutObject operation, you can upload objects up to 5 GB in size. However, by using the multipart uploads (e.g., CreateMultipartUpload, UploadPart, CompleteMultipartUpload, AbortMultipartUpload), you can upload object up to 5 TB in size.
MultipartUploaderを使ってみる
composer
aws-sdk-phpがインストールされていることが前提。
composer以外の方法でインストールしてもOK。
{
"autoload": {
"psr-4": {
}
},
"require": {
"aws/aws-sdk-php": "3.*"
}
}
PHPのソースを作成
以下のソースで、5GB以上のファイルもアップロードできた。
<?php
require(dirname(__FILE__) . '/vendor/autoload.php');
use Aws\S3\S3Client;
use Aws\S3\MultipartUploader;
use Aws\Exception\MultipartUploadException;
$s3Client = S3Client::factory([
'version' => '2006-03-01',
'key' => 'xxxxxxxx',
'secret' => 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
'region' => 'ap-northeast-1'
]);
$bucketname = 'sample-bucket';
$from_path = './bigdata.csv';
$to_path = 'dirname/bigdata.csv';
$uploader = new MultipartUploader($s3Client, $from_path, [
'bucket' => $bucketname,
'key' => $to_path,
]);
try {
$result = $uploader->upload();
print_r($result);
echo $result['ObjectURL'];
} catch (MultipartUploadException $e) {
echo $e->getMessage();
}
以上