diff options
author | Vincent Petry <pvince81@owncloud.com> | 2016-09-08 11:50:04 +0200 |
---|---|---|
committer | Roeland Jago Douma <roeland@famdouma.nl> | 2016-09-13 09:29:02 +0200 |
commit | 1ab472b9ad29b77e67633c72ed950a99dfc639d1 (patch) | |
tree | 945a9f901acb69e2241460c4866e6575300e2ee3 /apps/dav/lib/Upload | |
parent | feb85981cd6815083ee095d4c91b6ce8fbdfd50e (diff) | |
download | nextcloud-server-1ab472b9ad29b77e67633c72ed950a99dfc639d1.tar.gz nextcloud-server-1ab472b9ad29b77e67633c72ed950a99dfc639d1.zip |
Improve chunk upload AssemblyStream performance
Diffstat (limited to 'apps/dav/lib/Upload')
-rw-r--r-- | apps/dav/lib/Upload/AssemblyStream.php | 39 |
1 files changed, 31 insertions, 8 deletions
diff --git a/apps/dav/lib/Upload/AssemblyStream.php b/apps/dav/lib/Upload/AssemblyStream.php index 5853adfa77b..3a18f91677d 100644 --- a/apps/dav/lib/Upload/AssemblyStream.php +++ b/apps/dav/lib/Upload/AssemblyStream.php @@ -50,6 +50,9 @@ class AssemblyStream implements \Icewind\Streams\File { /** @var int */ private $size; + /** @var resource */ + private $currentStream = null; + /** * @param string $path * @param string $mode @@ -102,16 +105,36 @@ class AssemblyStream implements \Icewind\Streams\File { * @return string */ public function stream_read($count) { + do { + if ($this->currentStream === null) { + list($node, $posInNode) = $this->getNodeForPosition($this->pos); + if (is_null($node)) { + // reached last node, no more data + return ''; + } + $this->currentStream = $this->getStream($node); + fseek($this->currentStream, $posInNode); + } - list($node, $posInNode) = $this->getNodeForPosition($this->pos); - if (is_null($node)) { - return null; - } - $stream = $this->getStream($node); + $data = fread($this->currentStream, $count); + // isset is faster than strlen + if (isset($data[$count - 1])) { + // we read the full count + $read = $count; + } else { + // reaching end of stream, which happens less often so strlen is ok + $read = strlen($data); + } - fseek($stream, $posInNode); - $data = fread($stream, $count); - $read = strlen($data); + if (feof($this->currentStream)) { + fclose($this->currentStream); + $this->currentNode = null; + $this->currentStream = null; + } + // if no data read, try again with the next node because + // returning empty data can make the caller think there is no more + // data left to read + } while ($read === 0); // update position $this->pos += $read; |