From 232872e40181c7822c837dfa3cae608cd2cd8860 Mon Sep 17 00:00:00 2001 From: Robin Appelman Date: Fri, 12 Jun 2015 18:44:48 +0200 Subject: add flysystem adapater --- lib/private/files/storage/flysystem.php | 188 ++++++++++++++++++++++++++++++++ 1 file changed, 188 insertions(+) create mode 100644 lib/private/files/storage/flysystem.php (limited to 'lib/private/files/storage') diff --git a/lib/private/files/storage/flysystem.php b/lib/private/files/storage/flysystem.php new file mode 100644 index 00000000000..6f25a2498af --- /dev/null +++ b/lib/private/files/storage/flysystem.php @@ -0,0 +1,188 @@ + + * This file is licensed under the Affero General Public License version 3 or + * later. + * See the COPYING-README file. + */ + +namespace OC\Files\Storage; + +use Icewind\Streams\CallbackWrapper; +use Icewind\Streams\IteratorDirectory; +use League\Flysystem\AdapterInterface; +use League\Flysystem\FileNotFoundException; +use League\Flysystem\Filesystem; +use League\Flysystem\Plugin\GetWithMetadata; + +abstract class Flysystem extends Common { + /** + * @var Filesystem + */ + protected $flysystem; + + /** + * @var string + */ + protected $root = ''; + + protected function buildFlySystem(AdapterInterface $adapter) { + $this->flysystem = new Filesystem($adapter); + $this->flysystem->addPlugin(new GetWithMetadata()); + } + + protected function buildPath($path) { + $fullPath = \OC\Files\Filesystem::normalizePath($this->root . '/' . $path); + return ltrim($fullPath, '/'); + } + + public function file_get_contents($path) { + return $this->flysystem->read($this->buildPath($path)); + } + + public function file_put_contents($path, $data) { + return $this->flysystem->put($this->buildPath($path), $data); + } + + public function file_exists($path) { + return $this->flysystem->has($this->buildPath($path)); + } + + public function unlink($path) { + if ($this->is_dir($path)) { + return $this->rmdir($path); + } + try { + return $this->flysystem->delete($this->buildPath($path)); + } catch (FileNotFoundException $e) { + return false; + } + } + + public function rename($source, $target) { + if ($this->file_exists($target)) { + $this->unlink($target); + } + return $this->flysystem->rename($this->buildPath($source), $this->buildPath($target)); + } + + public function copy($source, $target) { + if ($this->file_exists($target)) { + $this->unlink($target); + } + return $this->flysystem->copy($this->buildPath($source), $this->buildPath($target)); + } + + public function filesize($path) { + if ($this->is_dir($path)) { + return 0; + } else { + return $this->flysystem->getSize($this->buildPath($path)); + } + } + + public function mkdir($path) { + if ($this->file_exists($path)) { + return false; + } + return $this->flysystem->createDir($this->buildPath($path)); + } + + public function filemtime($path) { + return $this->flysystem->getTimestamp($this->buildPath($path)); + } + + public function rmdir($path) { + try { + return @$this->flysystem->deleteDir($this->buildPath($path)); + } catch (FileNotFoundException $e) { + return false; + } + } + + public function opendir($path) { + try { + $content = $this->flysystem->listContents($this->buildPath($path)); + } catch (FileNotFoundException $e) { + return false; + } + $names = array_map(function ($object) { + return $object['basename']; + }, $content); + return IteratorDirectory::wrap($names); + } + + public function fopen($path, $mode) { + $fullPath = $this->buildPath($path); + $useExisting = true; + switch ($mode) { + case 'r': + case 'rb': + try { + return $this->flysystem->readStream($fullPath); + } catch (FileNotFoundException $e) { + return false; + } + case 'w': + case 'wb': + $useExisting = false; + case 'a': + case 'ab': + case 'r+': + case 'w+': + case 'wb+': + case 'a+': + case 'x': + case 'x+': + case 'c': + case 'c+': + //emulate these + if ($useExisting and $this->file_exists($path)) { + if (!$this->isUpdatable($path)) { + return false; + } + $tmpFile = $this->getCachedFile($path); + } else { + if (!$this->isCreatable(dirname($path))) { + return false; + } + $tmpFile = \OCP\Files::tmpFile(); + } + $source = fopen($tmpFile, $mode); + return CallbackWrapper::wrap($source, null, null, function () use ($tmpFile, $fullPath) { + $this->flysystem->putStream($fullPath, fopen($tmpFile, 'r')); + unlink($tmpFile); + }); + } + return false; + } + + public function touch($path, $mtime = null) { + if ($this->file_exists($path)) { + return false; + } else { + $this->file_put_contents($path, ''); + return true; + } + } + + public function stat($path) { + $info = $this->flysystem->getWithMetadata($this->buildPath($path), ['timestamp', 'size']); + return [ + 'mtime' => $info['timestamp'], + 'size' => $info['size'] + ]; + } + + public function filetype($path) { + if ($path === '' or $path === '/' or $path === '.') { + return 'dir'; + } + try { + $info = $this->flysystem->getMetadata($this->buildPath($path)); + } catch (FileNotFoundException $e) { + return false; + } + return $info['type']; + } +} -- cgit v1.2.3 From 6cc65b53abdca0e21e61245194e2a67af5ee9b02 Mon Sep 17 00:00:00 2001 From: Robin Appelman Date: Fri, 3 Jul 2015 13:57:39 +0200 Subject: add phpdoc --- lib/private/files/storage/flysystem.php | 55 +++++++++++++++++++++++++++++++++ 1 file changed, 55 insertions(+) (limited to 'lib/private/files/storage') diff --git a/lib/private/files/storage/flysystem.php b/lib/private/files/storage/flysystem.php index 6f25a2498af..8be8739953d 100644 --- a/lib/private/files/storage/flysystem.php +++ b/lib/private/files/storage/flysystem.php @@ -15,6 +15,11 @@ use League\Flysystem\FileNotFoundException; use League\Flysystem\Filesystem; use League\Flysystem\Plugin\GetWithMetadata; +/** + * Generic adapter between flysystem adapters and owncloud's storage system + * + * To use: subclass and call $this->buildFlysystem with the flysystem adapter of choice + */ abstract class Flysystem extends Common { /** * @var Filesystem @@ -26,6 +31,11 @@ abstract class Flysystem extends Common { */ protected $root = ''; + /** + * Initialize the storage backend with a flyssytem adapter + * + * @param \League\Flysystem\AdapterInterface $adapter + */ protected function buildFlySystem(AdapterInterface $adapter) { $this->flysystem = new Filesystem($adapter); $this->flysystem->addPlugin(new GetWithMetadata()); @@ -36,18 +46,30 @@ abstract class Flysystem extends Common { return ltrim($fullPath, '/'); } + /** + * {@inheritdoc} + */ public function file_get_contents($path) { return $this->flysystem->read($this->buildPath($path)); } + /** + * {@inheritdoc} + */ public function file_put_contents($path, $data) { return $this->flysystem->put($this->buildPath($path), $data); } + /** + * {@inheritdoc} + */ public function file_exists($path) { return $this->flysystem->has($this->buildPath($path)); } + /** + * {@inheritdoc} + */ public function unlink($path) { if ($this->is_dir($path)) { return $this->rmdir($path); @@ -59,6 +81,9 @@ abstract class Flysystem extends Common { } } + /** + * {@inheritdoc} + */ public function rename($source, $target) { if ($this->file_exists($target)) { $this->unlink($target); @@ -66,6 +91,9 @@ abstract class Flysystem extends Common { return $this->flysystem->rename($this->buildPath($source), $this->buildPath($target)); } + /** + * {@inheritdoc} + */ public function copy($source, $target) { if ($this->file_exists($target)) { $this->unlink($target); @@ -73,6 +101,9 @@ abstract class Flysystem extends Common { return $this->flysystem->copy($this->buildPath($source), $this->buildPath($target)); } + /** + * {@inheritdoc} + */ public function filesize($path) { if ($this->is_dir($path)) { return 0; @@ -81,6 +112,9 @@ abstract class Flysystem extends Common { } } + /** + * {@inheritdoc} + */ public function mkdir($path) { if ($this->file_exists($path)) { return false; @@ -88,10 +122,16 @@ abstract class Flysystem extends Common { return $this->flysystem->createDir($this->buildPath($path)); } + /** + * {@inheritdoc} + */ public function filemtime($path) { return $this->flysystem->getTimestamp($this->buildPath($path)); } + /** + * {@inheritdoc} + */ public function rmdir($path) { try { return @$this->flysystem->deleteDir($this->buildPath($path)); @@ -100,6 +140,9 @@ abstract class Flysystem extends Common { } } + /** + * {@inheritdoc} + */ public function opendir($path) { try { $content = $this->flysystem->listContents($this->buildPath($path)); @@ -112,6 +155,9 @@ abstract class Flysystem extends Common { return IteratorDirectory::wrap($names); } + /** + * {@inheritdoc} + */ public function fopen($path, $mode) { $fullPath = $this->buildPath($path); $useExisting = true; @@ -157,6 +203,9 @@ abstract class Flysystem extends Common { return false; } + /** + * {@inheritdoc} + */ public function touch($path, $mtime = null) { if ($this->file_exists($path)) { return false; @@ -166,6 +215,9 @@ abstract class Flysystem extends Common { } } + /** + * {@inheritdoc} + */ public function stat($path) { $info = $this->flysystem->getWithMetadata($this->buildPath($path), ['timestamp', 'size']); return [ @@ -174,6 +226,9 @@ abstract class Flysystem extends Common { ]; } + /** + * {@inheritdoc} + */ public function filetype($path) { if ($path === '' or $path === '/' or $path === '.') { return 'dir'; -- cgit v1.2.3 From de4e4cb6ea9decd756a2c813c8a224df4c92dbd8 Mon Sep 17 00:00:00 2001 From: Robin Appelman Date: Fri, 3 Jul 2015 14:00:05 +0200 Subject: also dont download existing on fopen when using w+ and wb+ --- lib/private/files/storage/flysystem.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'lib/private/files/storage') diff --git a/lib/private/files/storage/flysystem.php b/lib/private/files/storage/flysystem.php index 8be8739953d..6d8dee10622 100644 --- a/lib/private/files/storage/flysystem.php +++ b/lib/private/files/storage/flysystem.php @@ -170,13 +170,13 @@ abstract class Flysystem extends Common { return false; } case 'w': + case 'w+': case 'wb': + case 'wb+': $useExisting = false; case 'a': case 'ab': case 'r+': - case 'w+': - case 'wb+': case 'a+': case 'x': case 'x+': -- cgit v1.2.3