Skip to content

Commit

Permalink
make assemblystream seekable
Browse files Browse the repository at this point in the history
Signed-off-by: Robin Appelman <robin@icewind.nl>
  • Loading branch information
icewind1991 committed Mar 12, 2019
1 parent aff13a2 commit 693754f
Show file tree
Hide file tree
Showing 2 changed files with 52 additions and 2 deletions.
39 changes: 37 additions & 2 deletions apps/dav/lib/Upload/AssemblyStream.php
Original file line number Diff line number Diff line change
Expand Up @@ -83,12 +83,47 @@ public function stream_open($path, $mode, $options, &$opened_path) {
}

/**
* @param string $offset
* @param int $offset
* @param int $whence
* @return bool
*/
public function stream_seek($offset, $whence = SEEK_SET) {
return false;
if ($whence === SEEK_CUR) {
$offset = $this->stream_tell() + $offset;
} else if ($whence === SEEK_END) {
$offset = $this->size + $offset;
}

if ($offset > $this->size) {
throw new \Exception('invalid offset');
return false;
}

$nodeIndex = 0;
$nodeStart = 0;
while (true) {
if (!isset($this->nodes[$nodeIndex + 1])) {
break;
}
$node = $this->nodes[$nodeIndex];
if ($nodeStart + $node->getSize() > $offset) {
break;
}
$nodeIndex++;
$nodeStart += $node->getSize();
}

$stream = $this->getStream($this->nodes[$nodeIndex]);
$nodeOffset = $offset - $nodeStart;
if(fseek($stream, $nodeOffset) === -1) {
return false;
}
$this->currentNode = $nodeIndex;
$this->currentNodeRead = $nodeOffset;
$this->currentStream = $stream;
$this->pos = $offset;

return true;
}

/**
Expand Down
15 changes: 15 additions & 0 deletions apps/dav/tests/unit/Upload/AssemblyStreamTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,21 @@ public function testGetContentsFread($expected, $nodes) {
$this->assertEquals($expected, $content);
}

/**
* @dataProvider providesNodes()
*/
public function testSeek($expected, $nodes) {
$stream = \OCA\DAV\Upload\AssemblyStream::wrap($nodes);

$offset = floor(strlen($expected) * 0.6);
if(fseek($stream, $offset) === -1) {
$this->fail('fseek failed');
}

$content = stream_get_contents($stream);
$this->assertEquals(substr($expected, $offset), $content);
}

function providesNodes() {
$data8k = $this->makeData(8192);
$dataLess8k = $this->makeData(8191);
Expand Down

0 comments on commit 693754f

Please sign in to comment.