Skip to content

Commit fd33052

Browse files
committed
feat: 实现断点续传 API
1 parent 04de7c5 commit fd33052

File tree

2 files changed

+71
-2
lines changed

2 files changed

+71
-2
lines changed

src/Upyun/Uploader.php

Lines changed: 70 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,16 +22,84 @@ public function upload($path, $file, $params) {
2222
$stream = Psr7\stream_for($file);
2323
$size = $stream->getSize();
2424
$useBlock = $this->needUseBlock($size);
25+
2526
if(! $useBlock) {
2627
$req = new Rest($this->config);
2728
return $req->request('PUT', $path)
2829
->withHeaders($params)
2930
->withFile($stream)
3031
->send();
3132
} else {
32-
$req = new Multi($this->config);
33-
return $req->upload($path, $stream, Util::md5Hash($file), $params);
33+
return $this->pointUpload($path, $stream, $params);
34+
/**
35+
* 也可以使用分块上传替代, 不推荐使用
36+
*/
37+
//$req = new Multi($this->config);
38+
//return $req->upload($path, $stream, Util::md5Hash($file), $params);
39+
}
40+
}
41+
42+
/**
43+
* 断点续传
44+
* @param $path
45+
* @param $stream
46+
* @param $params
47+
*
48+
* @return mixed|\Psr\Http\Message\ResponseInterface
49+
* @throws \Exception
50+
*/
51+
private function pointUpload($path, $stream, $params) {
52+
$req = new Rest($this->config);
53+
$headers = array();
54+
if (is_array($params)) {
55+
foreach($params as $key => $val) {
56+
$headers['X-Upyun-Meta-' . $key] = $val;
57+
}
58+
}
59+
$res = $req->request('PUT', $path)
60+
->withHeaders(array_merge(array(
61+
'X-Upyun-Multi-Stage' => 'initiate',
62+
'X-Upyun-Multi-Type' => Psr7\mimetype_from_filename($path),
63+
'X-Upyun-Multi-Length' => $stream->getSize(),
64+
), $headers))
65+
->send();
66+
if ($res->getStatusCode() !== 204) {
67+
throw new \Exception('init request failed when poinit upload!');
68+
}
69+
70+
$init = Util::getHeaderParams($res->getHeaders());
71+
$uuid = $init['x-upyun-multi-uuid'];
72+
$blockSize = 1024 * 1024;
73+
$partId = 0;
74+
do {
75+
$fileBlock = $stream->read($blockSize);
76+
$res = $req->request('PUT', $path)
77+
->withHeaders(array(
78+
'X-Upyun-Multi-Stage' => 'upload',
79+
'X-Upyun-Multi-Uuid' => $uuid,
80+
'X-Upyun-Part-Id' => $partId
81+
))
82+
->withFile(Psr7\stream_for($fileBlock))
83+
->send();
84+
85+
if ($res->getStatusCode() !== 204) {
86+
throw new \Exception('upload request failed when poinit upload!');
87+
}
88+
$data = Util::getHeaderParams($res->getHeaders());
89+
$partId = $data['x-upyun-next-part-id'];
90+
} while($partId != -1);
91+
92+
$res = $req->request('PUT', $path)
93+
->withHeaders(array(
94+
'X-Upyun-Multi-Uuid' => $uuid,
95+
'X-Upyun-Multi-Stage' => 'complete'
96+
))
97+
->send();
98+
99+
if ($res->getStatusCode() != 204 && $res->getStatusCode() != 201) {
100+
throw new \Exception('end request failed when poinit upload!');
34101
}
102+
return $res;
35103
}
36104

37105
private function needUseBlock($fileSize) {

src/Upyun/Util.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ public static function trim($str) {
1313
public static function getHeaderParams($headers) {
1414
$params = [];
1515
foreach ($headers as $header => $value) {
16+
$header = strtolower($header);
1617
if(strpos($header, 'x-upyun-') !== false) {
1718
$params[$header] = $value[0];
1819
}

0 commit comments

Comments
 (0)