$this->logger = Server::get(LoggerInterface::class);
}
- /**
- * @param string $path
- * @return string correctly encoded path
- */
- private function normalizePath($path): string {
+ private function normalizePath(string $path): string {
$path = trim($path, '/');
if (!$path) {
return $path;
}
- private function isRoot($path): bool {
+ private function isRoot(string $path): bool {
return $path === '.';
}
- private function cleanKey($path): string {
+ private function cleanKey(string $path): string {
if ($this->isRoot($path)) {
return '/';
}
$this->filesCache = new CappedMemoryCache();
}
- private function invalidateCache($key): void {
+ private function invalidateCache(string $key): void {
unset($this->objectCache[$key]);
$keys = array_keys($this->objectCache->getData());
$keyLength = strlen($key);
*
* @throws \Exception
*/
- private function doesDirectoryExist($path): bool {
+ private function doesDirectoryExist(string $path): bool {
if ($path === '.' || $path === '') {
return true;
}
return false;
}
- protected function remove($path): bool {
+ protected function remove(string $path): bool {
// remember fileType to reduce http calls
$fileType = $this->filetype($path);
if ($fileType === 'dir') {
}
}
- public function mkdir($path): bool {
+ public function mkdir(string $path): bool {
$path = $this->normalizePath($path);
if ($this->is_dir($path)) {
return true;
}
- public function file_exists($path): bool {
+ public function file_exists(string $path): bool {
return $this->filetype($path) !== false;
}
- public function rmdir($path): bool {
+ public function rmdir(string $path): bool {
$path = $this->normalizePath($path);
if ($this->isRoot($path)) {
return $this->batchDelete();
}
- private function batchDelete($path = null): bool {
+ private function batchDelete(?string $path = null): bool {
// TODO explore using https://docs.aws.amazon.com/aws-sdk-php/v3/api/class-Aws.S3.BatchDelete.html
$params = [
'Bucket' => $this->bucket
return true;
}
- public function opendir($path) {
+ public function opendir(string $path) {
try {
$content = iterator_to_array($this->getDirectoryContent($path));
return IteratorDirectory::wrap(array_map(function (array $item) {
}
}
- public function stat($path): array|false {
+ public function stat(string $path): array|false {
$path = $this->normalizePath($path);
if ($this->is_dir($path)) {
* When the information is already present (e.g. opendir has been called before)
* this value is return. Otherwise a headObject is emitted.
*/
- private function getContentLength($path): int {
+ private function getContentLength(string $path): int {
if (isset($this->filesCache[$path])) {
return (int)$this->filesCache[$path]['ContentLength'];
}
* When the information is already present (e.g. opendir has been called before)
* this value is return. Otherwise a headObject is emitted.
*/
- private function getLastModified($path): string {
+ private function getLastModified(string $path): string {
if (isset($this->filesCache[$path])) {
return $this->filesCache[$path]['LastModified'];
}
return 'now';
}
- public function is_dir($path): bool {
+ public function is_dir(string $path): bool {
$path = $this->normalizePath($path);
if (isset($this->filesCache[$path])) {
}
}
- public function filetype($path): string|false {
+ public function filetype(string $path): string|false {
$path = $this->normalizePath($path);
if ($this->isRoot($path)) {
return false;
}
- public function getPermissions($path): int {
+ public function getPermissions(string $path): int {
$type = $this->filetype($path);
if (!$type) {
return 0;
return $type === 'dir' ? Constants::PERMISSION_ALL : Constants::PERMISSION_ALL - Constants::PERMISSION_CREATE;
}
- public function unlink($path): bool {
+ public function unlink(string $path): bool {
$path = $this->normalizePath($path);
if ($this->is_dir($path)) {
return true;
}
- public function fopen($path, $mode) {
+ public function fopen(string $path, string $mode) {
$path = $this->normalizePath($path);
switch ($mode) {
return false;
}
- public function touch($path, $mtime = null): bool {
+ public function touch(string $path, ?int $mtime = null): bool {
if (is_null($mtime)) {
$mtime = time();
}
return true;
}
- public function copy($source, $target, $isFile = null): bool {
+ public function copy(string $source, string $target, ?bool $isFile = null): bool {
$source = $this->normalizePath($source);
$target = $this->normalizePath($target);
return true;
}
- public function rename($source, $target): bool {
+ public function rename(string $source, string $target): bool {
$source = $this->normalizePath($source);
$target = $this->normalizePath($target);
return $this->id;
}
- public function writeBack($tmpFile, $path): bool {
+ public function writeBack(string $tmpFile, string $path): bool {
try {
$source = fopen($tmpFile, 'r');
$this->writeObject($path, $source, $this->mimeDetector->detectPath($path));
return true;
}
- public function getDirectoryContent($directory): \Traversable {
+ public function getDirectoryContent(string $directory): \Traversable {
$path = $this->normalizePath($directory);
if ($this->isRoot($path)) {
}
}
- public function hasUpdated($path, $time): bool {
+ public function hasUpdated(string $path, int $time): bool {
// for files we can get the proper mtime
if ($path !== '' && $object = $this->headObject($path)) {
$stat = $this->objectToMetaData($object);
return 'ftp::' . $this->username . '@' . $this->host . '/' . $this->root;
}
- protected function buildPath($path): string {
+ protected function buildPath(string $path): string {
return rtrim($this->root . '/' . $path, '/');
}
}
}
- public function filemtime($path): int|false {
+ public function filemtime(string $path): int|false {
$result = $this->getConnection()->mdtm($this->buildPath($path));
if ($result === -1) {
}
}
- public function filesize($path): false|int|float {
+ public function filesize(string $path): false|int|float {
$result = $this->getConnection()->size($this->buildPath($path));
if ($result === -1) {
return false;
}
}
- public function rmdir($path): bool {
+ public function rmdir(string $path): bool {
if ($this->is_dir($path)) {
$result = $this->getConnection()->rmdir($this->buildPath($path));
// recursive rmdir support depends on the ftp server
}
}
- /**
- * @param string $path
- */
- private function recursiveRmDir($path): bool {
+ private function recursiveRmDir(string $path): bool {
$contents = $this->getDirectoryContent($path);
$result = true;
foreach ($contents as $content) {
}
}
- public function stat($path): array|false {
+ public function stat(string $path): array|false {
if (!$this->file_exists($path)) {
return false;
}
];
}
- public function file_exists($path): bool {
+ public function file_exists(string $path): bool {
if ($path === '' || $path === '.' || $path === '/') {
return true;
}
return $this->filetype($path) !== false;
}
- public function unlink($path): bool {
+ public function unlink(string $path): bool {
switch ($this->filetype($path)) {
case 'dir':
return $this->rmdir($path);
}
}
- public function opendir($path) {
+ public function opendir(string $path) {
$files = $this->getConnection()->nlist($this->buildPath($path));
return IteratorDirectory::wrap($files);
}
- public function mkdir($path): bool {
+ public function mkdir(string $path): bool {
if ($this->is_dir($path)) {
return false;
}
return $this->getConnection()->mkdir($this->buildPath($path)) !== false;
}
- public function is_dir($path): bool {
+ public function is_dir(string $path): bool {
if ($path === '') {
return true;
}
}
}
- public function is_file($path): bool {
+ public function is_file(string $path): bool {
return $this->filesize($path) !== false;
}
- public function filetype($path): string|false {
+ public function filetype(string $path): string|false {
if ($this->is_dir($path)) {
return 'dir';
} elseif ($this->is_file($path)) {
}
}
- public function fopen($path, $mode) {
+ public function fopen(string $path, string $mode) {
$useExisting = true;
switch ($mode) {
case 'r':
return $stream;
}
- public function touch($path, $mtime = null): bool {
+ public function touch(string $path, ?int $mtime = null): bool {
if ($this->file_exists($path)) {
return false;
} else {
}
}
- public function rename($source, $target): bool {
+ public function rename(string $source, string $target): bool {
$this->unlink($target);
return $this->getConnection()->rename($this->buildPath($source), $this->buildPath($target));
}
- public function getDirectoryContent($directory): \Traversable {
+ public function getDirectoryContent(string $directory): \Traversable {
$files = $this->getConnection()->mlsd($this->buildPath($directory));
$mimeTypeDetector = \OC::$server->getMimeTypeDetector();
* @param string $host protocol://server:port
* @return array [$server, $port]
*/
- private function splitHost($host): array {
+ private function splitHost(string $host): array {
$input = $host;
if (!str_contains($host, '://')) {
// add a protocol to fix parse_url behavior with ipv6
return $this->user;
}
- /**
- * @param string $path
- */
- private function absPath($path): string {
+ private function absPath(string $path): string {
return $this->root . $this->cleanPath($path);
}
return false;
}
- protected function writeHostKeys($keys): bool {
+ protected function writeHostKeys(array $keys): bool {
try {
$keyPath = $this->hostKeysPath();
if ($keyPath && file_exists($keyPath)) {
return [];
}
- public function mkdir($path): bool {
+ public function mkdir(string $path): bool {
try {
return $this->getConnection()->mkdir($this->absPath($path));
} catch (\Exception $e) {
}
}
- public function rmdir($path): bool {
+ public function rmdir(string $path): bool {
try {
$result = $this->getConnection()->delete($this->absPath($path), true);
// workaround: stray stat cache entry when deleting empty folders
}
}
- public function opendir($path) {
+ public function opendir(string $path) {
try {
$list = $this->getConnection()->nlist($this->absPath($path));
if ($list === false) {
}
}
- public function filetype($path): string|false {
+ public function filetype(string $path): string|false {
try {
$stat = $this->getConnection()->stat($this->absPath($path));
if (!is_array($stat) || !array_key_exists('type', $stat)) {
return false;
}
- public function file_exists($path): bool {
+ public function file_exists(string $path): bool {
try {
return $this->getConnection()->stat($this->absPath($path)) !== false;
} catch (\Exception $e) {
}
}
- public function unlink($path): bool {
+ public function unlink(string $path): bool {
try {
return $this->getConnection()->delete($this->absPath($path), true);
} catch (\Exception $e) {
}
}
- public function fopen($path, $mode) {
+ public function fopen(string $path, string $mode) {
try {
$absPath = $this->absPath($path);
$connection = $this->getConnection();
return false;
}
- public function touch($path, $mtime = null): bool {
+ public function touch(string $path, ?int $mtime = null): bool {
try {
if (!is_null($mtime)) {
return false;
}
/**
- * @param string $path
- * @param string $target
* @throws \Exception
*/
- public function getFile($path, $target): void {
+ public function getFile(string $path, string $target): void {
$this->getConnection()->get($path, $target);
}
- public function rename($source, $target): bool {
+ public function rename(string $source, string $target): bool {
try {
if ($this->file_exists($target)) {
$this->unlink($target);
/**
* @return array{mtime: int, size: int, ctime: int}|false
*/
- public function stat($path): array|false {
+ public function stat(string $path): array|false {
try {
$stat = $this->getConnection()->stat($this->absPath($path));
}
}
- /**
- * @param string $path
- */
- public function constructUrl($path): string {
+ public function constructUrl(string $path): string {
// Do not pass the password here. We want to use the Net_SFTP object
// supplied via stream context or fail. We only supply username and
// hostname because this might show up in logs (they are not used).
return $url;
}
- public function file_put_contents($path, $data): int|float|false {
+ public function file_put_contents(string $path, mixed $data): int|float|false {
/** @psalm-suppress InternalMethod */
$result = $this->getConnection()->put($this->absPath($path), $data);
if ($result) {
}
}
- public function copy($source, $target): bool {
+ public function copy(string $source, string $target): bool {
if ($this->is_dir($source) || $this->is_dir($target)) {
return parent::copy($source, $target);
} else {
}
}
- public function getPermissions($path): int {
+ public function getPermissions(string $path): int {
$stat = $this->getConnection()->stat($this->absPath($path));
if (!$stat) {
return 0;
}
}
- public function getMetaData($path): ?array {
+ public function getMetaData(string $path): ?array {
$stat = $this->getConnection()->stat($this->absPath($path));
if (!$stat) {
return null;
/**
* Load the source from the stream context and return the context options
*
- * @param string $name
* @throws \BadMethodCallException
*/
- protected function loadContext($name) {
+ protected function loadContext(string $name) {
$context = stream_context_get_options($this->context);
if (isset($context[$name])) {
$context = $context[$name];
return $data;
}
- private function request_chunk($size) {
+ private function request_chunk(int $size) {
if ($this->pendingRead) {
$this->sftp->_get_sftp_packet();
}
/**
* Load the source from the stream context and return the context options
*
- * @param string $name
* @throws \BadMethodCallException
*/
- protected function loadContext($name) {
+ protected function loadContext(string $name) {
$context = stream_context_get_options($this->context);
if (isset($context[$name])) {
$context = $context[$name];
parent::__construct($params);
}
- private function splitUser($user): array {
+ private function splitUser(string $user): array {
if (str_contains($user, '/')) {
return explode('/', $user, 2);
} elseif (str_contains($user, '\\')) {
return 'smb::' . $this->server->getAuth()->getUsername() . '@' . $this->server->getHost() . '//' . $this->share->getName() . '/' . $this->root;
}
- /**
- * @param string $path
- */
- protected function buildPath($path): string {
+ protected function buildPath(string $path): string {
return Filesystem::normalizePath($this->root . '/' . $path, true, false, true);
}
- protected function relativePath($fullPath): ?string {
+ protected function relativePath(string $fullPath): ?string {
if ($fullPath === $this->root) {
return '';
} elseif (substr($fullPath, 0, strlen($this->root)) === $this->root) {
}
/**
- * @param string $path
* @throws StorageAuthException
* @throws \OCP\Files\NotFoundException
* @throws \OCP\Files\ForbiddenException
*/
- protected function getFileInfo($path): IFileInfo {
+ protected function getFileInfo(string $path): IFileInfo {
try {
$path = $this->buildPath($path);
$cached = $this->statCache[$path] ?? null;
}
/**
- * @param \Exception $e
* @throws StorageAuthException
*/
protected function throwUnavailable(\Exception $e): never {
/**
* get the acl from fileinfo that is relevant for the configured user
- *
- * @param IFileInfo $file
*/
private function getACL(IFileInfo $file): ?ACL {
$acls = $file->getAcls();
}
/**
- * @param string $path
* @return \Generator<IFileInfo>
* @throws StorageNotAvailableException
*/
- protected function getFolderContents($path): iterable {
+ protected function getFolderContents(string $path): iterable {
try {
$path = ltrim($this->buildPath($path), '/');
try {
}
}
- /**
- * @param IFileInfo $info
- */
- protected function formatInfo($info): array {
+ protected function formatInfo(IFileInfo $info): array {
$result = [
'size' => $info->getSize(),
'mtime' => $info->getMTime(),
* @param string $source the old name of the path
* @param string $target the new name of the path
*/
- public function rename($source, $target, $retry = true): bool {
+ public function rename(string $source, string $target, bool $retry = true): bool {
if ($this->isRootDir($source) || $this->isRootDir($target)) {
return false;
}
return $result;
}
- public function stat($path, $retry = true): array|false {
+ public function stat(string $path, bool $retry = true): array|false {
try {
$result = $this->formatInfo($this->getFileInfo($path));
} catch (\OCP\Files\ForbiddenException $e) {
/**
* Check if the path is our root dir (not the smb one)
- *
- * @param string $path the path
*/
- private function isRootDir($path): bool {
+ private function isRootDir(string $path): bool {
return $path === '' || $path === '/' || $path === '.';
}
return $this->share->getName() && (!$this->root || $this->root === '/');
}
- /**
- * @param string $path
- */
- public function unlink($path): bool {
+ public function unlink(string $path): bool {
if ($this->isRootDir($path)) {
return false;
}
/**
* check if a file or folder has been updated since $time
- *
- * @param string $path
- * @param int $time
*/
- public function hasUpdated($path, $time): bool {
+ public function hasUpdated(string $path, int $time): bool {
if (!$path and $this->root === '/') {
// mtime doesn't work for shares, but giving the nature of the backend,
// doing a full update is still just fast enough
}
/**
- * @param string $path
- * @param string $mode
* @return resource|false
*/
- public function fopen($path, $mode) {
+ public function fopen(string $path, string $mode) {
$fullPath = $this->buildPath($path);
try {
switch ($mode) {
}
}
- public function rmdir($path): bool {
+ public function rmdir(string $path): bool {
if ($this->isRootDir($path)) {
return false;
}
}
}
- public function touch($path, $mtime = null): bool {
+ public function touch(string $path, ?int $mtime = null): bool {
try {
if (!$this->file_exists($path)) {
$fh = $this->share->write($this->buildPath($path));
}
}
- public function getMetaData($path): ?array {
+ public function getMetaData(string $path): ?array {
try {
$fileInfo = $this->getFileInfo($path);
} catch (\OCP\Files\NotFoundException $e) {
return $data;
}
- public function opendir($path) {
+ public function opendir(string $path) {
try {
$files = $this->getFolderContents($path);
} catch (NotFoundException $e) {
return IteratorDirectory::wrap($names);
}
- public function getDirectoryContent($directory): \Traversable {
+ public function getDirectoryContent(string $directory): \Traversable {
try {
$files = $this->getFolderContents($directory);
foreach ($files as $file) {
}
}
- public function filetype($path): string|false {
+ public function filetype(string $path): string|false {
try {
return $this->getFileInfo($path)->isDirectory() ? 'dir' : 'file';
} catch (\OCP\Files\NotFoundException $e) {
}
}
- public function mkdir($path): bool {
+ public function mkdir(string $path): bool {
$path = $this->buildPath($path);
try {
$this->share->mkdir($path);
}
}
- public function file_exists($path): bool {
+ public function file_exists(string $path): bool {
try {
// Case sensitive filesystem doesn't matter for root directory
if ($this->caseSensitive === false && $path !== '') {
}
}
- public function isReadable($path): bool {
+ public function isReadable(string $path): bool {
try {
$info = $this->getFileInfo($path);
return $this->showHidden || !$info->isHidden();
}
}
- public function isUpdatable($path): bool {
+ public function isUpdatable(string $path): bool {
try {
$info = $this->getFileInfo($path);
// following windows behaviour for read-only folders: they can be written into
}
}
- public function isDeletable($path): bool {
+ public function isDeletable(string $path): bool {
try {
$info = $this->getFileInfo($path);
return ($this->showHidden || !$info->isHidden()) && !$info->isReadOnly();
}
}
- public function listen($path, callable $callback): void {
+ public function listen(string $path, callable $callback): void {
$this->notify($path)->listen(function (IChange $change) use ($callback) {
if ($change instanceof IRenameChange) {
return $callback($change->getType(), $change->getPath(), $change->getTargetPath());
});
}
- public function notify($path): SMBNotifyHandler {
+ public function notify(string $path): SMBNotifyHandler {
$path = '/' . ltrim($path, '/');
$shareNotifyHandler = $this->share->notify($this->buildPath($path));
return new SMBNotifyHandler($shareNotifyHandler, $this->root);
abstract class StreamWrapper extends \OC\Files\Storage\Common {
- /**
- * @param string $path
- * @return string|null
- */
- abstract public function constructUrl($path): ?string;
+ abstract public function constructUrl(string $path): ?string;
- public function mkdir($path): bool {
+ public function mkdir(string $path): bool {
return mkdir($this->constructUrl($path));
}
- public function rmdir($path): bool {
+ public function rmdir(string $path): bool {
if ($this->is_dir($path) && $this->isDeletable($path)) {
$dh = $this->opendir($path);
if (!is_resource($dh)) {
}
}
- public function opendir($path) {
+ public function opendir(string $path) {
return opendir($this->constructUrl($path));
}
- public function filetype($path): string|false {
+ public function filetype(string $path): string|false {
return @filetype($this->constructUrl($path));
}
- public function file_exists($path): bool {
+ public function file_exists(string $path): bool {
return file_exists($this->constructUrl($path));
}
- public function unlink($path): bool {
+ public function unlink(string $path): bool {
$url = $this->constructUrl($path);
$success = unlink($url);
// normally unlink() is supposed to do this implicitly,
return $success;
}
- public function fopen($path, $mode) {
+ public function fopen(string $path, string $mode) {
return fopen($this->constructUrl($path), $mode);
}
- public function touch($path, $mtime = null): bool {
+ public function touch(string $path, ?int $mtime = null): bool {
if ($this->file_exists($path)) {
if (is_null($mtime)) {
$fh = $this->fopen($path, 'a');
}
}
- /**
- * @param string $path
- * @param string $target
- */
- public function getFile($path, $target): bool {
+ public function getFile(string $path, string $target): bool {
return copy($this->constructUrl($path), $target);
}
- /**
- * @param string $target
- */
- public function uploadFile($path, $target): bool {
+ public function uploadFile(string $path, string $target): bool {
return copy($path, $this->constructUrl($target));
}
- public function rename($source, $target): bool {
+ public function rename(string $source, string $target): bool {
return rename($this->constructUrl($source), $this->constructUrl($target));
}
- public function stat($path): array|false {
+ public function stat(string $path): array|false {
return stat($this->constructUrl($path));
}
}
public const SUBCONTAINER_FILE = '.subcontainers';
- /**
- * translate directory path to container name
- *
- * @param string $path
- * @return string
- */
-
/**
* Fetches an object from the API.
* If the object is cached already or a
* failed "doesn't exist" response was cached,
* that one will be returned.
*
- * @param string $path
* @return StorageObject|false object
* or false if the object did not exist
* @throws \OCP\Files\StorageAuthException
/**
* Returns whether the given path exists.
*
- * @param string $path
- *
* @return bool true if the object exist, false otherwise
* @throws \OCP\Files\StorageAuthException
* @throws \OCP\Files\StorageNotAvailableException
*/
- private function doesObjectExist($path): bool {
+ private function doesObjectExist(string $path): bool {
return $this->fetchObject($path) !== false;
}
$this->mimeDetector = \OC::$server->get(IMimeTypeDetector::class);
}
- public function mkdir($path): bool {
+ public function mkdir(string $path): bool {
$path = $this->normalizePath($path);
if ($this->is_dir($path)) {
return true;
}
- public function file_exists($path): bool {
+ public function file_exists(string $path): bool {
$path = $this->normalizePath($path);
if ($path !== '.' && $this->is_dir($path)) {
return $this->doesObjectExist($path);
}
- public function rmdir($path): bool {
+ public function rmdir(string $path): bool {
$path = $this->normalizePath($path);
if (!$this->is_dir($path) || !$this->isDeletable($path)) {
return true;
}
- public function opendir($path) {
+ public function opendir(string $path) {
$path = $this->normalizePath($path);
if ($path === '.') {
}
}
- public function stat($path): array|false {
+ public function stat(string $path): array|false {
$path = $this->normalizePath($path);
if ($path === '.') {
return $stat;
}
- public function filetype($path) {
+ public function filetype(string $path) {
$path = $this->normalizePath($path);
if ($path !== '.' && $this->doesObjectExist($path)) {
}
}
- public function unlink($path): bool {
+ public function unlink(string $path): bool {
$path = $this->normalizePath($path);
if ($this->is_dir($path)) {
return true;
}
- public function fopen($path, $mode) {
+ public function fopen(string $path, string $mode) {
$path = $this->normalizePath($path);
switch ($mode) {
}
}
- public function touch($path, $mtime = null): bool {
+ public function touch(string $path, ?int $mtime = null): bool {
$path = $this->normalizePath($path);
if (is_null($mtime)) {
$mtime = time();
}
}
- public function copy($source, $target): bool {
+ public function copy(string $source, string $target): bool {
$source = $this->normalizePath($source);
$target = $this->normalizePath($target);
return true;
}
- public function rename($source, $target): bool {
+ public function rename(string $source, string $target): bool {
$source = $this->normalizePath($source);
$target = $this->normalizePath($target);
return $this->container;
}
- public function writeBack($tmpFile, $path): void {
+ public function writeBack(string $tmpFile, string $path): void {
$fileData = fopen($tmpFile, 'r');
$this->objectStore->writeObject($path, $fileData, $this->mimeDetector->detectPath($path));
// invalidate target object to force repopulation on fetch
unlink($tmpFile);
}
- public function hasUpdated($path, $time): bool {
+ public function hasUpdated(string $path, int $time): bool {
if ($this->is_file($path)) {
return parent::hasUpdated($path, $time);
}