融合接口
功能说明
分片上传步骤较多,包括初始化、文件切片、各个分片上传、完成上传。分片复制包括了初始化、源对象信息获取、各个分片复制、完成复制。为了简化分片上传和复制,PHP SDK 提供了对分片上传和分片复制的封装。Aws\S3\MultipartUploader 接口提供了简洁的分片上传方式,Aws\S3\MultiPartCopy 接口提供了简洁的分片复制方式。在使用这些封装接口的同时,您同样可以配置一些参数,控制分片的大小、并发数。
代码示例
使用 MultipartUploader 进行分片上传:
public function MultiPartUpload()
{
$file_Path = '<your-file-path>';
$bucket = '<your-bucket-name>';
$objectName = '<your-object-key>';
$uploader = new Aws\S3\MultipartUploader($this->s3Client, $file_Path, [
'bucket' => $bucket,
'key' => $objectName,
'concurrency' => 5, // 设置上传分片 UploadPart 操作的最大并行数量,默认为5.
'part_size' => 5242880, // 设置分片大小,默认为5M.
'acl' => 'public-read', // 设置ACL,参考值private | public-read
'before_initiate' => function(\Aws\Command $command)
{
$command['ContentType'] = 'text/json'; // 设置content-type
},
]);
try {
$result = $uploader->upload();
echo "Upload complete: {$result['ObjectURL']}" . "\n";
} catch (Aws\Exception\MultipartUploadException $e) {
echo $e->getMessage() . "\n";
}
}
使用 MultiPartCopy 进行分片复制:
public function MultiPartCopy()
{
$src_bucket = '<source-bucket-name>'; //从此桶复制
$src_key = '<source-object-key>'; //复制的对象名
$dst_bucket = '<your-bucket-name>'; //目标桶
$dst_key = '<your-object-key>'; //目标对象名
$source = '/'.$src_bucket.'/'.$src_key;
$uploader = new Aws\S3\MultiPartCopy($this->s3Client, $source, [
'bucket' => $dst_bucket,
'key' => $dst_key,
'concurrency' => 5, // 设置上传分片 UploadPart 操作的最大并行数量,默认为5.
'part_size' => 5242880, // 设置分片大小,默认为5M.
'acl' => 'public-read', // 设置ACL,参考值private | public-read
'before_initiate' => function(\Aws\Command $command)
{
$command['ContentType'] = 'text/json'; // 设置content-type
},
]);
try {
$result = $uploader->upload();
echo "Upload complete: {$result['ObjectURL']}" . "\n";
} catch (Aws\Exception\MultipartUploadException $e) {
echo $e->getMessage() . "\n";
}
}
关于Content-Type的配置
Content-Type用于标识文件的资源类型,比如image/png
, image/jpg
是图片类型,video/mpeg
, video/mp4
是视频类型,text/plain
, text/html
是文本类型, 浏览器针对不同的Content-Type会有不同的操作,比如图片类型可以预览,视频类型可以播放,文本类型可以直接打开。application/octet-stream
类型会直接打开下载窗口。
有些用户反馈图片和视频无法预览的问题,主要就是Content-Type没有正确设置导致的;Content-Type参数需要用户主动设置,默认是application/octet-stream
。在php sdk中,可以根据对象key值后缀扩展名来决定文件的Content-Type,可参考 mime.php 。
请求参数
参数 | 类型 | 说明 |
---|---|---|
bucket | string | 桶名 |
key | string | 对象名 |
acl | string | private,public-read,public-read-write |
concurrency | int | 并发数 |
part_size | int | 分片大小,默认5MB |
before_initiate | 函数 | 用于设置content-type |
初始化分片上传任务
功能说明
分片上传操作可以将超过5GB的大文件分割后上传,分片上传对象首先需要发起分片上传请求获取一个upload id。
代码示例
// createMultipartUpload
$result = $this->s3Client->createMultipartUpload([
'Bucket' => '<your-bucket-name>',
'Key' => '<your-object-key>',
//'ACL' => 'public-read',
]);
$uploadId = $result['UploadId'];
请求参数
createMultipartUpload 可设置的参数如下:
参数 | 类型 | 说明 | 是否必要 |
---|---|---|---|
bucket | String | 桶名称 | 是 |
key | String | 对象的key | 是 |
ACL | String | 配置上传对象的预定义的标准ACL信息,详细说明见 设置对象访问权限 一节 | 否 |
返回结果
返回的属性如下:
参数 | 类型 | 说明 |
---|---|---|
Bucket | string | 执行分片上传的桶的名称 |
Key | string | 本次分片上传对象的名称 |
UploadId | string | 本次生成分片上传任务的id |
上传分片
功能说明
初始化分片上传任务后,指定分片上传任务的id可以上传分片数据,可以将大文件分割成分片后上传,除了最后一个分片,每个分片的数据大小为5MB~5GB,每个分片上传任务最多上传10000个分片。
代码示例
$file_Path = '<your-file-path>';
$bucket = '<your-bucket-name>';
$objectName = '<your-object-key>';
// uploadPart
$file = fopen($file_Path, 'r');
$partNumber = 1;
while (!feof($file)) {
// 创建分片复制请求
$result = $this->s3Client->uploadPart([
'Bucket' => $bucket,
'Key' => $objectName,
'UploadId' => $uploadId, //uploadId从createMultipartUpload返回值获取
'PartNumber' => $partNumber, //设置分片号
'Body' => fread($file, 5 * 1024 * 1024), //读取文件分片,分片大小为5M
]);
$parts['Parts'][$partNumber] = [
// 记录ETag
'PartNumber' => $partNumber,
'ETag' => $result['ETag'],
];
echo "Uploading part {$partNumber}" . "\n";
$partNumber++;
}
fclose($file);
请求参数
uploadPart 可设置的参数如下:
参数 | 类型 | 说明 | 是否必要 |
---|---|---|---|
Bucket | string | 执行分片上传的桶的名称 | 是 |
Key | string | 对象的key | 是 |
Body | string | 分片的数据 | 是 |
PartNumber | int | 说明当前数据在文件中所属的分片,大于等于1,小于等于10000 | 是 |
UploadId | string | 通过 CreateMultipartUpload 操作获取的UploadId,与一个分片上传的对象对应 | 是 |
返回结果
参数 | 类型 | 说明 |
---|---|---|
ETag | string | 本次上传分片对应的Entity Tag |
合并分片
功能说明
合并指定分片上传任务id对应任务中已上传的对象分片,使之成为一个完整的文件。
代码示例
// completeMultipartUpload
$result = $this->s3Client->completeMultipartUpload([
'Bucket' => '<your-bucket-name>',
'Key' => '<your-object-key>',
'UploadId' => '<your-upload-id>',
'MultipartUpload' => $parts,
]);
echo $result;
echo "Upload success";
请求参数
completeMultipartUpload可设置的参数如下:
参数 | 类型 | 说明 | 是否必要 |
---|---|---|---|
Bucket | string | 执行分片上传的桶的名称 | 是 |
Key | string | 对象的key | 是 |
MultipartUpload | string array | 每个已上传的分片的PartNumber和对应的ETag,生成方式可查看 分片上传-上传分片 一节的代码示例 | 是 |
UploadId | string | 通过CreateMultipartUpload操作获取的UploadId,与一个对象的分片上传对应 | 是 |
返回结果
参数 | 类型 | 说明 |
---|---|---|
Bucket | String | 执行分片上传的桶的名称 |
Key | String | 对象的key |
Etag | String | 本次上传对象后对应的Entity Tag |
Location | String | 合并生成对象的URI信息 |
VersionId | String | 上传对象后相应的版本ID |
列举分片上传任务
功能说明
列举分片上传操作可以列出一个桶中正在进行的分片上传,这些分片上传的请求已经发起,但是还没完成或者被中止。listMultipartUploads 操作可以通过指定maxUploads参数来设置返回分片上传信息的数量,maxUploads参数的最大值和默认值均为1000。如果返回结果中的isTruncated字段为true,表示还有符合条件的分片上传信息没有列出,可以通过设置请求中的keyMarker和uploadIdMarker参数,来列出符合筛选条件的正在上传的分片信息。
代码示例
public function ListMultipartUploads()
{
$result = $this->s3Client->listMultipartUploads([
'Bucket' => '<your-bucket-name>',
]);
echo $result;
}
如果list大于1000,则可以使用 getPaginator 接口列举所有分片上传任务。列举所有分片上传任务示例代码如下:
public function ListMultipartUploads2()
{
try {
$results = $this->s3Client->getPaginator('ListMultipartUploads', [
'Bucket' => '<your-bucket-name>',
]);
foreach ($results as $result) {
foreach ($result['Uploads'] as $upload) {
echo 'object key: ' . $upload['Key'] . "\n";
echo 'uploadId: ' . $upload['UploadId'] . "\n";
}
}
} catch (S3Exception $e) {
echo $e->getMessage() . "\n";
}
}
请求参数
listMultipartUploads 可设置的参数如下:
参数 | 类型 | 说明 | 是否必要 |
---|---|---|---|
Bucket | string | 执行本操作的桶名称 | 是 |
返回结果
参数 | 类型 | 说明 |
---|---|---|
Bucket | string | 执行本操作的桶名称。 |
Uploads | upload array | 包含了零个或多个已初始化的上传分片信息的数组。数组中的每一项包含了分片初始化时间、分片上传操作发起者、对象key、对象拥有者、存储类型和uploadId等息 |
列举已上传的分片
功能说明
列举已上传分片操作可以列出一个分片上传操作中已经上传完毕但是还未合并的分片信息。请求中需要提供object key和 upload id,返回的结果最多包含1000个已上传的分片信息,默认返回1000个,可以通过设置maxParts参数的值指定返回结果中分片信息的数量。如果已上传的分片信息的数量多于1000个,则返回结果中的isTruncated字段为true,可用通过设置partNumberMarker参数获取partNumber大于该参数的分片信息。
代码示例
public function ListParts()
{
$bucket = '<your-bucket-name>';
$objectName = '<your-object-key>';
$uploadId = '<your-upload-id>';
$result = $this->s3Client->listParts([
'Bucket' => $bucket,
'Key' => $objectName,
'UploadId' => $uploadId,
]);
echo $result;
}
如果 list 大于1000,则可以使用 getPaginator 接口列举所有分片。列举所有分片示例代码如下:
public function ListParts2()
{
$bucket = '<your-bucket-name>';
$objectName = '<your-object-key>';
$uploadId = '<your-upload-id>';
try {
$results = $this->s3Client->getPaginator('ListParts', [
'Bucket' => $bucket,
'Key' => $objectName,
'UploadId' => $uploadId,
]);
foreach ($results as $result) {
foreach ($result['Parts'] as $part) {
echo 'part number:' . $part['PartNumber'] . "\n";
echo 'ETag:' . $part['ETag'] . "\n";
echo 'size' . $part['Size'] . "\n";
}
}
} catch (S3Exception $e) {
echo $e->getMessage() . "\n";
}
}
请求参数
ListPartsRequest 可设置的参数如下:
参数 | 类型 | 说明 | 是否必要 |
---|---|---|---|
Bucket | string | 执行本操作的桶名称 | 是 |
Key | string | 对象的key | 是 |
UploadId | string | 需要查询分片信息的uploadid | 是 |
返回结果
参数 | 类型 | 说明 |
---|---|---|
Bucket | string | 执行本操作的桶名称 |
Key | string | 本次分片上传对象的名称 |
Parts | Part array | 包含了已上传分片信息的数组,数组中的每一项包含了该分片的Entity tag、最后修改时间、PartNumber和大小等信息 |
UploadId | string | 需要查询的分片上传操作Id |
复制分片
功能说明
复制分片操作可以从一个已存在的对象中复制指定分片的数据。您可以使用 uploadPartCopy 复制分片。在复制分片前,需要使用 createMultipartUpload 接口获取一个upload id,在完成复制和上传分片操作之后,需要使用 completeMultipartUpload 操作组装分片成为一个对象。当复制的对象大小超过5GB,必须使用复制分片操作完成对象的复制。除了最后一个分片外,每个复制分片的大小范围是[5MB,5GB]。
代码示例
// copyPart
$desBucket = '<your-bucket-name>'; //目标桶
$desKeyName = '<your-object-key>'; //目标对象名
$srcBucket = '<source-bucket-name>'; //从此桶复制
$srcKeyName = '<source-object-key>'; //复制的对象名
$result = $this->s3Client->uploadPartCopy([
'Bucket' => $desBucket,
'Key' => $desKeyName,
'CopySource' => '/' . $srcBucket . '/' . $srcKeyName,
'UploadId' => $uploadId, //uploadId从createMultipartUpload返回值获取
'PartNumber' => $partNumber, //设置分片号
'CopySourceRange' => 'bytes=' . $firstByte . '-' . $lastByte, //复制文件分片的数据范围
]);
echo $result;
$parts['Parts'][$partNumber] = [
// 记录ETag
'PartNumber' => $partNumber,
'ETag' => $result['CopyPartResult']['ETag'],
];
echo "Uploading part {$partNumber}" . "\n";
请求参数
uploadPartCopy 可设置的参数如下:
参数 | 类型 | 说明 | 是否必要 |
---|---|---|---|
Bucket | string | 目标桶名称 | 是 |
Key | string | 目标对象key | 是 |
CopySource | string | URL格式的复制对象数据来源,包含了桶名称和对象key的信息,二者之间使用正斜杆(/)分割,versionId可选参数用于指定原对象的版本。例如,"/foo/boo?versionId=11111"表示复制foo桶中的boo对象,其版本id为11111。如果不指定versionId参数,则默认复制当前版本的对象数据 | 是 |
CopySourceRange | string | 指定本次分片复制的数据范围,必须是"bytes=first-last"的格式,例如"bytes=0-9"表示复制原对象中前10字节的数据,只有当复制的分片大小大于5MB的时候有效 | 是 |
PartNumber | int | 说明本次分片复制的数据在原对象中所属的部分 | 是 |
UploadId | string | 与本次复制操作相应的分片上传Id | 是 |
返回结果
参数 | 类型 | 说明 |
---|---|---|
ETag | string | 包含复制分片的Entity Tag |
取消分片上传任务
功能说明
取消分片上传任务操作用于终止一个分片上传。当一个分片上传被中止后,不会再有数据通过与之相应的upload id上传,同时已经被上传的分片所占用的空间会被释放。执行取消分片上传任务操作后,正在上传的分片可能会上传成功也可能会被中止,所以必要的情况下需要执行多次取消分片上传任务操作去释放全部上传成功的分片所占用的空间。可以通过执行列举已上传分片操作来确认所有中止分片上传后所有已上传分片的空间是否被被释放。
代码示例
public function abortMultipartUpload() {
//UploadId从createMultipartUpload中获取
$bucket = '<your-bucket-name>';
$keyname = '<your-object-key>';
$uploadId = '<your-upload-id';
$result = $this->s3Client->abortMultipartUpload([
'Bucket' => $bucket,
'Key' => $keyname,
'UploadId' => $uploadId,
]);
echo $result;
}
请求参数
abortMultipartUpload 可设置的参数如下:
参数 | 类型 | 说明 | 是否必要 |
---|---|---|---|
Bucket | string | 执行本操作的桶名称 | 是 |
Key | string | 分片上传的对象的key | 是 |
UploadId | string | 指定需要终止的分片上传的id | 是 |