diff --git a/api/src/Vfs/Filesystem/StreamWrapper.php b/api/src/Vfs/Filesystem/StreamWrapper.php index 71634ceb79..45e59f1a25 100644 --- a/api/src/Vfs/Filesystem/StreamWrapper.php +++ b/api/src/Vfs/Filesystem/StreamWrapper.php @@ -298,6 +298,36 @@ class StreamWrapper implements Vfs\StreamWrapperIface return $this->url_stat($this->opened_stream_url,0); } + /** + * Method called for symlink() + * + * @param string $target + * @param string $link + * @return boolean true on success false on error + */ + public static function symlink($target,$link) + { + $_target = Vfs::resolve_url($target); + $_link = Vfs::resolve_url($link); + // Check target & link are both filesystem, otherwise it needs to be in Sqlfs + $target_scheme = Vfs::parse_url($_target, PHP_URL_SCHEME); + $link_scheme = Vfs::parse_url($_link, PHP_URL_SCHEME); + if($target_scheme == static::SCHEME && $link_scheme == static::SCHEME) + { + $linked = symlink( + Vfs::parse_url($_target,PHP_URL_PATH), + Vfs::parse_url($_link, PHP_URL_PATH) + ); + clearstatcache(); + return $linked && is_link($_link); + } + else + { + $sqlfs = new Vfs\Sqlfs\StreamWrapper(); + return $sqlfs->symlink($target, $link); + } + } + /** * This method is called in response to unlink() calls on URL paths associated with the wrapper. * diff --git a/api/tests/Vfs/Filesystem/StreamWrapperTest.php b/api/tests/Vfs/Filesystem/StreamWrapperTest.php index 093e3036b2..75666277f7 100644 --- a/api/tests/Vfs/Filesystem/StreamWrapperTest.php +++ b/api/tests/Vfs/Filesystem/StreamWrapperTest.php @@ -43,6 +43,12 @@ class StreamWrapperTest extends Vfs\StreamWrapperBase $this->markTestSkipped("Filesystem StreamWrapper does not support giving access to a file by changing group permissions"); } + public function testSymlinkFromFolder($test_file = ''): void + { + // Pass a file inside the mountpoint. It doesn't need to exists + parent::testSymlinkFromFolder(static::$mountpoint . '/test'); + } + protected function mount(): void { $this->mountFilesystem(static::$mountpoint); diff --git a/api/tests/Vfs/StreamWrapperBase.php b/api/tests/Vfs/StreamWrapperBase.php index 3fcc4fbe91..8b414663cb 100644 --- a/api/tests/Vfs/StreamWrapperBase.php +++ b/api/tests/Vfs/StreamWrapperBase.php @@ -354,8 +354,8 @@ abstract class StreamWrapperBase extends LoggedInTest } $ns = explode('\\', __NAMESPACE__); $test_base_dir = $test_file . '/'.array_pop($ns).'/'.$this->getName(); - $source_dir = $test_base_dir . "/link_test"; - $link_dir = $test_base_dir . "/link_target"; + $source_dir = $test_base_dir . "/link_target"; + $link_dir = $test_base_dir . "/im_a_symlink"; // Check if backend supports it $url = Vfs::resolve_url_symlinks($test_base_dir,false,false);