Exemplo n.º 1
0
 protected function execute(InputInterface $input, OutputInterface $output)
 {
     $this->sourceUser = $input->getArgument('source-user');
     $this->destinationUser = $input->getArgument('destination-user');
     if (!$this->userManager->userExists($this->sourceUser)) {
         $output->writeln("<error>Unknown source user {$this->sourceUser}</error>");
         return;
     }
     if (!$this->userManager->userExists($this->destinationUser)) {
         $output->writeln("<error>Unknown destination user {$this->destinationUser}</error>");
         return;
     }
     $date = date('c');
     $this->finalTarget = "{$this->destinationUser}/files/transferred from {$this->sourceUser} on {$date}";
     // setup filesystem
     Filesystem::initMountPoints($this->sourceUser);
     Filesystem::initMountPoints($this->destinationUser);
     // analyse source folder
     $this->analyse($output);
     // collect all the shares
     $this->collectUsersShares($output);
     // transfer the files
     $this->transfer($output);
     // restore the shares
     $this->restoreShares($output);
 }
Exemplo n.º 2
0
 /**
  * Get the source cache of a shared file or folder
  *
  * @param string $target Shared target file path
  * @return \OC\Files\Cache\Cache
  */
 private function getSourceCache($target)
 {
     if ($target === false || $target === $this->storage->getMountPoint()) {
         $target = '';
     }
     $source = \OC_Share_Backend_File::getSource($target, $this->storage->getMountPoint(), $this->storage->getItemType());
     if (isset($source['path']) && isset($source['fileOwner'])) {
         try {
             \OC\Files\Filesystem::initMountPoints($source['fileOwner']);
         } catch (NoUserException $e) {
             \OC::$server->getLogger()->warning('The user \'' . $source['uid_owner'] . '\' of a share can\'t be retrieved.', array('app' => 'files_sharing'));
             return false;
         }
         $mounts = \OC\Files\Filesystem::getMountByNumericId($source['storage']);
         if (is_array($mounts) and !empty($mounts)) {
             $fullPath = $mounts[0]->getMountPoint() . $source['path'];
             list($storage, $internalPath) = \OC\Files\Filesystem::resolvePath($fullPath);
             if ($storage) {
                 $this->files[$target] = $internalPath;
                 $cache = $storage->getCache();
                 $this->storageId = $storage->getId();
                 $this->numericId = $cache->getNumericStorageId();
                 return $cache;
             }
         }
     }
     return false;
 }
 private static function checkUpdate($id)
 {
     $cacheItem = Cache::getById($id);
     if (is_null($cacheItem)) {
         return;
     }
     list($storageId, $internalPath) = $cacheItem;
     $mounts = Filesystem::getMountByStorageId($storageId);
     if (count($mounts) === 0) {
         //if the storage we need isn't mounted on default, try to find a user that has access to the storage
         $permissionsCache = new Permissions($storageId);
         $users = $permissionsCache->getUsers($id);
         if (count($users) === 0) {
             return;
         }
         Filesystem::initMountPoints($users[0]);
         $mounts = Filesystem::getMountByStorageId($storageId);
         if (count($mounts) === 0) {
             return;
         }
     }
     $storage = $mounts[0]->getStorage();
     $watcher = new Watcher($storage);
     $watcher->checkUpdate($internalPath);
 }
Exemplo n.º 4
0
 /**
  * Correct the parent folders' ETags for all users shared the file at $target
  *
  * @param string $target
  */
 public static function correctFolders($target)
 {
     $uid = \OCP\User::getUser();
     $uidOwner = \OC\Files\Filesystem::getOwner($target);
     $info = \OC\Files\Filesystem::getFileInfo($target);
     // Correct Shared folders of other users shared with
     $users = \OCP\Share::getUsersItemShared('file', $info['fileid'], $uidOwner, true);
     if (!empty($users)) {
         while (!empty($users)) {
             $reshareUsers = array();
             foreach ($users as $user) {
                 if ($user !== $uidOwner) {
                     $etag = \OC\Files\Filesystem::getETag('');
                     \OCP\Config::setUserValue($user, 'files_sharing', 'etag', $etag);
                     // Look for reshares
                     $reshareUsers = array_merge($reshareUsers, \OCP\Share::getUsersItemShared('file', $info['fileid'], $user, true));
                 }
             }
             $users = $reshareUsers;
         }
         // Correct folders of shared file owner
         $target = substr($target, 8);
         if ($uidOwner !== $uid && ($source = \OC_Share_Backend_File::getSource($target))) {
             \OC\Files\Filesystem::initMountPoints($uidOwner);
             $source = '/' . $uidOwner . '/' . $source['path'];
             \OC\Files\Cache\Updater::correctFolder($source, $info['mtime']);
         }
     }
 }
Exemplo n.º 5
0
 /**
  * get the UID of the owner of the file and the path to the file relative to
  * owners files folder
  *
  * @param string $filename
  * @return array
  * @throws \OC\User\NoUserException
  */
 public static function getUidAndFilename($filename)
 {
     $uid = Filesystem::getOwner($filename);
     $userManager = \OC::$server->getUserManager();
     // if the user with the UID doesn't exists, e.g. because the UID points
     // to a remote user with a federated cloud ID we use the current logged-in
     // user. We need a valid local user to create the versions
     if (!$userManager->userExists($uid)) {
         $uid = User::getUser();
     }
     Filesystem::initMountPoints($uid);
     if ($uid != User::getUser()) {
         $info = Filesystem::getFileInfo($filename);
         $ownerView = new View('/' . $uid . '/files');
         try {
             $filename = $ownerView->getPath($info['fileid']);
             // make sure that the file name doesn't end with a trailing slash
             // can for example happen single files shared across servers
             $filename = rtrim($filename, '/');
         } catch (NotFoundException $e) {
             $filename = null;
         }
     }
     return [$uid, $filename];
 }
Exemplo n.º 6
0
 /**
  * create unique target
  * @param string $filePath
  * @param string $shareWith
  * @param string $exclude
  * @return string
  */
 public function generateTarget($filePath, $shareWith, $exclude = null)
 {
     $shareFolder = \OCA\Files_Sharing\Helper::getShareFolder();
     $target = \OC\Files\Filesystem::normalizePath($shareFolder . '/' . basename($filePath));
     // for group shares we return the target right away
     if ($shareWith === false) {
         return $target;
     }
     \OC\Files\Filesystem::initMountPoints($shareWith);
     $view = new \OC\Files\View('/' . $shareWith . '/files');
     if (!$view->is_dir($shareFolder)) {
         $dir = '';
         $subdirs = explode('/', $shareFolder);
         foreach ($subdirs as $subdir) {
             $dir = $dir . '/' . $subdir;
             if (!$view->is_dir($dir)) {
                 $view->mkdir($dir);
             }
         }
     }
     $excludeList = \OCP\Share::getItemsSharedWithUser('file', $shareWith, self::FORMAT_TARGET_NAMES);
     if (is_array($exclude)) {
         $excludeList = array_merge($excludeList, $exclude);
     }
     return \OCA\Files_Sharing\Helper::generateUniqueTarget($target, $excludeList, $view);
 }
Exemplo n.º 7
0
/**
 * update script for the removal of the logical "Shared" folder, we create physical "Shared" folder and
 * update the users file_target so that it doesn't make any difference for the user
 * @note parameters are just for testing, please ignore them
 */
function removeSharedFolder($mkdirs = true, $chunkSize = 99)
{
    $query = OCP\DB::prepare('SELECT * FROM `*PREFIX*share`');
    $result = $query->execute();
    $view = new \OC\Files\View('/');
    $users = array();
    $shares = array();
    //we need to set up user backends
    OC_User::useBackend(new OC_User_Database());
    OC_Group::useBackend(new OC_Group_Database());
    OC_App::loadApps(array('authentication'));
    //we need to set up user backends, otherwise creating the shares will fail with "because user does not exist"
    while ($row = $result->fetchRow()) {
        //collect all user shares
        if ((int) $row['share_type'] === 0 && ($row['item_type'] === 'file' || $row['item_type'] === 'folder')) {
            $users[] = $row['share_with'];
            $shares[$row['id']] = $row['file_target'];
        } else {
            if ((int) $row['share_type'] === 1 && ($row['item_type'] === 'file' || $row['item_type'] === 'folder')) {
                //collect all group shares
                $users = array_merge($users, \OC_group::usersInGroup($row['share_with']));
                $shares[$row['id']] = $row['file_target'];
            } else {
                if ((int) $row['share_type'] === 2) {
                    $shares[$row['id']] = $row['file_target'];
                }
            }
        }
    }
    $unique_users = array_unique($users);
    if (!empty($unique_users) && !empty($shares)) {
        // create folder Shared for each user
        if ($mkdirs) {
            foreach ($unique_users as $user) {
                \OC\Files\Filesystem::initMountPoints($user);
                if (!$view->file_exists('/' . $user . '/files/Shared')) {
                    $view->mkdir('/' . $user . '/files/Shared');
                }
            }
        }
        $chunkedShareList = array_chunk($shares, $chunkSize, true);
        $connection = \OC_DB::getConnection();
        foreach ($chunkedShareList as $subList) {
            $statement = "UPDATE `*PREFIX*share` SET `file_target` = CASE `id` ";
            //update share table
            $ids = implode(',', array_keys($subList));
            foreach ($subList as $id => $target) {
                $statement .= "WHEN " . $connection->quote($id, \PDO::PARAM_INT) . " THEN " . $connection->quote('/Shared' . $target, \PDO::PARAM_STR);
            }
            $statement .= ' END WHERE `id` IN (' . $ids . ')';
            $query = OCP\DB::prepare($statement);
            $query->execute(array());
        }
        // set config to keep the Shared folder as the default location for new shares
        \OCA\Files_Sharing\Helper::setShareFolder('/Shared');
    }
}
Exemplo n.º 8
0
 public function testChangeLock()
 {
     Filesystem::initMountPoints($this->recipientUid);
     $recipientView = new View('/' . $this->recipientUid . '/files');
     $recipientView->lockFile('bar.txt', ILockingProvider::LOCK_SHARED);
     $recipientView->changeLock('bar.txt', ILockingProvider::LOCK_EXCLUSIVE);
     $recipientView->unlockFile('bar.txt', ILockingProvider::LOCK_EXCLUSIVE);
     $this->assertTrue(true);
 }
 /**
  * @param IRequest $request
  * @param string $user
  * @param string $path
  */
 public function __construct(IRequest $request, $user, $path)
 {
     $this->request = $request;
     $this->user = $user;
     $this->path = $path;
     Filesystem::initMountPoints($user);
     $this->view = new View('/' . $user);
     if (!$this->view->file_exists($path)) {
         $this->setStatus(Http::STATUS_NOT_FOUND);
     }
 }
Exemplo n.º 10
0
 public static function getUidAndFilename($filename)
 {
     $uid = \OC\Files\Filesystem::getOwner($filename);
     \OC\Files\Filesystem::initMountPoints($uid);
     if ($uid != \OCP\User::getUser()) {
         $info = \OC\Files\Filesystem::getFileInfo($filename);
         $ownerView = new \OC\Files\View('/' . $uid . '/files');
         $filename = $ownerView->getPath($info['fileid']);
     }
     return array($uid, $filename);
 }
Exemplo n.º 11
0
 /**
  * @return Directory
  */
 private function impl()
 {
     $rootView = new View();
     $user = \OC::$server->getUserSession()->getUser();
     Filesystem::initMountPoints($user->getUID());
     if (!$rootView->file_exists('/' . $user->getUID() . '/uploads')) {
         $rootView->mkdir('/' . $user->getUID() . '/uploads');
     }
     $view = new View('/' . $user->getUID() . '/uploads');
     $rootInfo = $view->getFileInfo('');
     $impl = new Directory($view, $rootInfo);
     return $impl;
 }
Exemplo n.º 12
0
 /**
  * Returns the cache storage for the logged in user
  * @return \OC\Files\View cache storage
  */
 protected function getStorage()
 {
     if (isset($this->storage)) {
         return $this->storage;
     }
     if (\OC_User::isLoggedIn()) {
         \OC\Files\Filesystem::initMountPoints(\OC_User::getUser());
         $this->storage = new \OC\Files\View('/' . \OC_User::getUser() . '/cache');
         return $this->storage;
     } else {
         \OC_Log::write('core', 'Can\'t get cache storage, user not logged in', \OC_Log::ERROR);
         throw new \OC\ForbiddenException('Can\\t get cache storage, user not logged in');
     }
 }
Exemplo n.º 13
0
 private function init()
 {
     if ($this->initialized) {
         return;
     }
     $this->initialized = true;
     try {
         Filesystem::initMountPoints($this->newShare->getShareOwner());
         $sourcePath = $this->ownerView->getPath($this->newShare->getNodeId());
         list($this->sourceStorage, $sourceInternalPath) = $this->ownerView->resolvePath($sourcePath);
         $this->sourceRootInfo = $this->sourceStorage->getCache()->get($sourceInternalPath);
     } catch (\Exception $e) {
         $this->logger->logException($e);
     }
 }
Exemplo n.º 14
0
 /**
  * @param string $filename
  * @return array
  * @throws \OC\User\NoUserException
  */
 public static function getUidAndFilename($filename)
 {
     $uid = \OC\Files\Filesystem::getOwner($filename);
     \OC\Files\Filesystem::initMountPoints($uid);
     if ($uid != \OCP\User::getUser()) {
         $info = \OC\Files\Filesystem::getFileInfo($filename);
         $ownerView = new \OC\Files\View('/' . $uid . '/files');
         try {
             $filename = $ownerView->getPath($info['fileid']);
         } catch (NotFoundException $e) {
             $filename = null;
         }
     }
     return [$uid, $filename];
 }
Exemplo n.º 15
0
 /**
  * create unique target
  * @param string $filePath
  * @param string $shareWith
  * @param string $exclude
  * @return string
  */
 public function generateTarget($filePath, $shareWith, $exclude = null)
 {
     $target = '/' . basename($filePath);
     // for group shares we return the target right away
     if ($shareWith === false) {
         return $target;
     }
     \OC\Files\Filesystem::initMountPoints($shareWith);
     $view = new \OC\Files\View('/' . $shareWith . '/files');
     $excludeList = \OCP\Share::getItemsSharedWithUser('file', $shareWith, self::FORMAT_TARGET_NAMES);
     if (is_array($exclude)) {
         $excludeList = array_merge($excludeList, $exclude);
     }
     return \OCA\Files_Sharing\Helper::generateUniqueTarget($target, $excludeList, $view);
 }
Exemplo n.º 16
0
 /**
  * return a user specific instance of \OCP\IAvatar
  * @see \OCP\IAvatar
  * @param string $userId the ownCloud user id
  * @return \OCP\IAvatar
  * @throws \Exception In case the username is potentially dangerous
  * @throws NotFoundException In case there is no user folder yet
  */
 public function getAvatar($userId)
 {
     $user = $this->userManager->get($userId);
     if (is_null($user)) {
         throw new \Exception('user does not exist');
     }
     /*
      * Fix for #22119
      * Basically we do not want to copy the skeleton folder
      */
     \OC\Files\Filesystem::initMountPoints($userId);
     $dir = '/' . $userId;
     /** @var Folder $folder */
     $folder = $this->rootFolder->get($dir);
     return new Avatar($folder, $this->l, $user, $this->logger);
 }
Exemplo n.º 17
0
 /**
  * walk up the users file tree and update the etags
  * @param string $user
  * @param string $path
  */
 private static function correctUsersFolder($user, $path)
 {
     // $path points to the mount point which is a virtual folder, so we start with
     // the parent
     $path = '/files' . dirname($path);
     \OC\Files\Filesystem::initMountPoints($user);
     $view = new \OC\Files\View('/' . $user);
     if ($view->file_exists($path)) {
         while ($path !== dirname($path)) {
             $etag = $view->getETag($path);
             $view->putFileInfo($path, array('etag' => $etag));
             $path = dirname($path);
         }
     } else {
         \OCP\Util::writeLog('files_sharing', 'can not update etags on ' . $path . ' for user ' . $user . '. Path does not exists', \OCP\Util::DEBUG);
     }
 }
Exemplo n.º 18
0
 /**
  * @brief Get the source file path for a shared file
  * @param string Shared target file path
  * @return string source file path or false if not found
  */
 private function getSourcePath($target)
 {
     $source = $this->getFile($target);
     if ($source) {
         if (!isset($source['fullPath'])) {
             \OC\Files\Filesystem::initMountPoints($source['fileOwner']);
             $mount = \OC\Files\Mount::findByNumericId($source['storage']);
             if ($mount) {
                 $this->files[$target]['fullPath'] = $mount->getMountPoint() . $source['path'];
             } else {
                 $this->files[$target]['fullPath'] = false;
             }
         }
         return $this->files[$target]['fullPath'];
     }
     return false;
 }
Exemplo n.º 19
0
 /**
  * Get all mountpoints applicable for the user and check for shares where we need to update the etags
  *
  * @param \OCP\IUser $user
  * @param \OCP\Files\Storage\IStorageFactory $storageFactory
  * @return \OCP\Files\Mount\IMountPoint[]
  */
 public function getMountsForUser(IUser $user, IStorageFactory $storageFactory)
 {
     $shares = \OCP\Share::getItemsSharedWithUser('file', $user->getUID());
     $propagator = $this->propagationManager->getSharePropagator($user->getUID());
     $propagator->propagateDirtyMountPoints($shares);
     $shares = array_filter($shares, function ($share) {
         return $share['permissions'] > 0;
     });
     return array_map(function ($share) use($user, $storageFactory) {
         Filesystem::initMountPoints($share['uid_owner']);
         // for updating etags for the share owner when we make changes to this share.
         $ownerPropagator = $this->propagationManager->getChangePropagator($share['uid_owner']);
         // for updating our etags when changes are made to the share from the owners side (probably indirectly by us trough another share)
         $this->propagationManager->listenToOwnerChanges($share['uid_owner'], $user->getUID());
         return new SharedMount('\\OC\\Files\\Storage\\Shared', '/' . $user->getUID() . '/' . $share['file_target'], array('propagator' => $ownerPropagator, 'share' => $share, 'user' => $user->getUID()), $storageFactory);
     }, $shares);
 }
Exemplo n.º 20
0
 /**
  * Get the source file path for a shared file
  *
  * @param string $target Shared target file path
  * @return string|false source file path or false if not found
  */
 public function getSourcePath($target)
 {
     $source = $this->getFile($target);
     if ($source) {
         if (!isset($source['fullPath'])) {
             \OC\Files\Filesystem::initMountPoints($source['fileOwner']);
             $mount = \OC\Files\Filesystem::getMountByNumericId($source['storage']);
             if (is_array($mount) && !empty($mount)) {
                 $this->files[$target]['fullPath'] = $mount[key($mount)]->getMountPoint() . $source['path'];
             } else {
                 $this->files[$target]['fullPath'] = false;
                 \OCP\Util::writeLog('files_sharing', "Unable to get mount for shared storage '" . $source['storage'] . "' user '" . $source['fileOwner'] . "'", \OCP\Util::ERROR);
             }
         }
         return $this->files[$target]['fullPath'];
     }
     return false;
 }
Exemplo n.º 21
0
	/**
	 * Returns the cache storage for the logged in user
	 *
	 * @return \OC\Files\View cache storage
	 * @throws \OC\ForbiddenException
	 * @throws \OC\User\NoUserException
	 */
	protected function getStorage() {
		if (isset($this->storage)) {
			return $this->storage;
		}
		if (\OC_User::isLoggedIn()) {
			$rootView = new View();
			$user = \OC::$server->getUserSession()->getUser();
			Filesystem::initMountPoints($user->getUID());
			if (!$rootView->file_exists('/' . $user->getUID() . '/cache')) {
				$rootView->mkdir('/' . $user->getUID() . '/cache');
			}
			$this->storage = new View('/' . $user->getUID() . '/cache');
			return $this->storage;
		} else {
			\OCP\Util::writeLog('core', 'Can\'t get cache storage, user not logged in', \OCP\Util::ERROR);
			throw new \OC\ForbiddenException('Can\t get cache storage, user not logged in');
		}
	}
Exemplo n.º 22
0
 protected function getStorage()
 {
     if (isset($this->storage)) {
         return $this->storage;
     }
     if (\OC_User::isLoggedIn()) {
         \OC\Files\Filesystem::initMountPoints(\OC_User::getUser());
         $subdir = 'cache';
         $view = new \OC\Files\View('/' . \OC_User::getUser());
         if (!$view->file_exists($subdir)) {
             $view->mkdir($subdir);
         }
         $this->storage = new \OC\Files\View('/' . \OC_User::getUser() . '/' . $subdir);
         return $this->storage;
     } else {
         \OC_Log::write('core', 'Can\'t get cache storage, user not logged in', \OC_Log::ERROR);
         return false;
     }
 }
Exemplo n.º 23
0
 /**
  * @brief Get the source cache of a shared file or folder
  * @param string $target Shared target file path
  * @return \OC\Files\Cache\Cache
  */
 private function getSourceCache($target)
 {
     $source = \OC_Share_Backend_File::getSource($target);
     if (isset($source['path']) && isset($source['fileOwner'])) {
         \OC\Files\Filesystem::initMountPoints($source['fileOwner']);
         $mount = \OC\Files\Mount::findByNumericId($source['storage']);
         if ($mount) {
             $fullPath = $mount->getMountPoint() . $source['path'];
             list($storage, $internalPath) = \OC\Files\Filesystem::resolvePath($fullPath);
             if ($storage) {
                 $this->files[$target] = $internalPath;
                 $cache = $storage->getCache();
                 $this->storageId = $storage->getId();
                 $this->numericId = $cache->getNumericStorageId();
                 return $cache;
             }
         }
     }
     return false;
 }
Exemplo n.º 24
0
	/**
	 * Get the source cache of a shared file or folder
	 *
	 * @param string $target Shared target file path
	 * @return \OC\Files\Cache\Cache
	 */
	private function getSourceCache($target) {
		if ($target === false || $target === $this->storage->getMountPoint()) {
			$target = '';
		}
		$source = \OC_Share_Backend_File::getSource($target, $this->storage->getMountPoint(), $this->storage->getItemType());
		if (isset($source['path']) && isset($source['fileOwner'])) {
			\OC\Files\Filesystem::initMountPoints($source['fileOwner']);
			$mounts = \OC\Files\Filesystem::getMountByNumericId($source['storage']);
			if (is_array($mounts) and !empty($mounts)) {
				$fullPath = $mounts[0]->getMountPoint() . $source['path'];
				list($storage, $internalPath) = \OC\Files\Filesystem::resolvePath($fullPath);
				if ($storage) {
					$this->files[$target] = $internalPath;
					$cache = $storage->getCache();
					$this->storageId = $storage->getId();
					$this->numericId = $cache->getNumericStorageId();
					return $cache;
				}
			}
		}
		return false;
	}
Exemplo n.º 25
0
/**
 * The FileCache Upgrade routine
 *
 * @param UpdateWatcher $watcher
 */
function __doFileCacheUpgrade($watcher)
{
    try {
        $query = \OC_DB::prepare('
			SELECT DISTINCT `user`
			FROM `*PREFIX*fscache`
		');
        $result = $query->execute();
    } catch (\Exception $e) {
        return;
    }
    $users = $result->fetchAll();
    if (count($users) == 0) {
        return;
    }
    $step = 100 / count($users);
    $percentCompleted = 0;
    $lastPercentCompletedOutput = 0;
    $startInfoShown = false;
    foreach ($users as $userRow) {
        $user = $userRow['user'];
        \OC\Files\Filesystem::initMountPoints($user);
        \OC\Files\Cache\Upgrade::doSilentUpgrade($user);
        if (!$startInfoShown) {
            //We show it only now, because otherwise Info about upgraded apps
            //will appear between this and progress info
            $watcher->success('Updating filecache, this may take really long...');
            $startInfoShown = true;
        }
        $percentCompleted += $step;
        $out = floor($percentCompleted);
        if ($out != $lastPercentCompletedOutput) {
            $watcher->success('... ' . $out . '% done ...');
            $lastPercentCompletedOutput = $out;
        }
    }
    $watcher->success('Updated filecache');
}
Exemplo n.º 26
0
 /**
  * Get all mountpoints applicable for the user and check for shares where we need to update the etags
  *
  * @param \OCP\IUser $user
  * @param \OCP\Files\Storage\IStorageFactory $storageFactory
  * @return \OCP\Files\Mount\IMountPoint[]
  */
 public function getMountsForUser(IUser $user, IStorageFactory $storageFactory)
 {
     $shares = \OCP\Share::getItemsSharedWithUser('file', $user->getUID());
     $propagator = $this->propagationManager->getSharePropagator($user->getUID());
     $propagator->propagateDirtyMountPoints($shares);
     $shares = array_filter($shares, function ($share) {
         return $share['permissions'] > 0;
     });
     $shares = array_map(function ($share) use($user, $storageFactory) {
         try {
             Filesystem::initMountPoints($share['uid_owner']);
         } catch (NoUserException $e) {
             \OC::$server->getLogger()->warning('The user \'' . $share['uid_owner'] . '\' of share with ID \'' . $share['id'] . '\' can\'t be retrieved.', array('app' => 'files_sharing'));
             return null;
         }
         // for updating etags for the share owner when we make changes to this share.
         $ownerPropagator = $this->propagationManager->getChangePropagator($share['uid_owner']);
         // for updating our etags when changes are made to the share from the owners side (probably indirectly by us trough another share)
         $this->propagationManager->listenToOwnerChanges($share['uid_owner'], $user->getUID());
         return new SharedMount('\\OC\\Files\\Storage\\Shared', '/' . $user->getUID() . '/' . $share['file_target'], array('propagator' => $ownerPropagator, 'share' => $share, 'user' => $user->getUID()), $storageFactory);
     }, $shares);
     // array_filter removes the null values from the array
     return array_filter($shares);
 }
Exemplo n.º 27
0
 /**
  * get uid of the owners of the file and the path to the file
  * @param string $path Path of the file to check
  * @throws \Exception
  * @note $shareFilePath must be relative to data/UID/files. Files
  *       relative to /Shared are also acceptable
  * @return array
  */
 public function getUidAndFilename($path)
 {
     $pathinfo = pathinfo($path);
     $partfile = false;
     $parentFolder = false;
     if (array_key_exists('extension', $pathinfo) && $pathinfo['extension'] === 'part') {
         // if the real file exists we check this file
         $filePath = $this->userFilesDir . '/' . $pathinfo['dirname'] . '/' . $pathinfo['filename'];
         if ($this->view->file_exists($filePath)) {
             $pathToCheck = $pathinfo['dirname'] . '/' . $pathinfo['filename'];
         } else {
             // otherwise we look for the parent
             $pathToCheck = $pathinfo['dirname'];
             $parentFolder = true;
         }
         $partfile = true;
     } else {
         $pathToCheck = $path;
     }
     $view = new \OC\Files\View($this->userFilesDir);
     $fileOwnerUid = $view->getOwner($pathToCheck);
     // handle public access
     if ($this->isPublic) {
         return array($this->userId, $path);
     } else {
         // Check that UID is valid
         if (!\OCP\User::userExists($fileOwnerUid)) {
             throw new \Exception('Could not find owner (UID = "' . var_export($fileOwnerUid, 1) . '") of file "' . $path . '"');
         }
         // NOTE: Bah, this dependency should be elsewhere
         \OC\Files\Filesystem::initMountPoints($fileOwnerUid);
         // If the file owner is the currently logged in user
         if ($fileOwnerUid === $this->userId) {
             // Assume the path supplied is correct
             $filename = $path;
         } else {
             $info = $view->getFileInfo($pathToCheck);
             $ownerView = new \OC\Files\View('/' . $fileOwnerUid . '/files');
             // Fetch real file path from DB
             $filename = $ownerView->getPath($info['fileid']);
             if ($parentFolder) {
                 $filename = $filename . '/' . $pathinfo['filename'];
             }
             if ($partfile) {
                 $filename = $filename . '.' . $pathinfo['extension'];
             }
         }
         return array($fileOwnerUid, \OC\Files\Filesystem::normalizePath($filename));
     }
 }
Exemplo n.º 28
0
$linkedItem = \OCP\Share::getShareByToken($token);
if ($linkedItem === false || $linkedItem['item_type'] !== 'file' && $linkedItem['item_type'] !== 'folder') {
    \OC_Response::setStatus(\OC_Response::STATUS_NOT_FOUND);
    \OCP\Util::writeLog('core-preview', 'Passed token parameter is not valid', \OCP\Util::DEBUG);
    exit;
}
if (!isset($linkedItem['uid_owner']) || !isset($linkedItem['file_source'])) {
    \OC_Response::setStatus(\OC_Response::STATUS_INTERNAL_SERVER_ERROR);
    \OCP\Util::writeLog('core-preview', 'Passed token seems to be valid, but it does not contain all necessary information . ("' . $token . '")', \OCP\Util::WARN);
    exit;
}
$rootLinkItem = OCP\Share::resolveReShare($linkedItem);
$userId = $rootLinkItem['uid_owner'];
OCP\JSON::checkUserExists($rootLinkItem['uid_owner']);
\OC_Util::setupFS($userId);
\OC\Files\Filesystem::initMountPoints($userId);
$view = new \OC\Files\View('/' . $userId . '/files');
$pathId = $linkedItem['file_source'];
$path = $view->getPath($pathId);
if ($path === null) {
    \OC_Response::setStatus(\OC_Response::STATUS_NOT_FOUND);
    \OCP\Util::writeLog('core-preview', 'Could not resolve file for shared item', \OCP\Util::WARN);
    exit;
}
$pathInfo = $view->getFileInfo($path);
$sharedFile = null;
if ($linkedItem['item_type'] === 'folder') {
    $isValid = \OC\Files\Filesystem::isValidPath($file);
    if (!$isValid) {
        \OC_Response::setStatus(\OC_Response::STATUS_BAD_REQUEST);
        \OCP\Util::writeLog('core-preview', 'Passed filename is not valid, might be malicious (file:"' . $file . '";ip:"' . \OC::$server->getRequest()->getRemoteAddress() . '")', \OCP\Util::WARN);
Exemplo n.º 29
0
 /**
  * @brief Change a user's encryption passphrase
  * @param array $params keys: uid, password
  */
 public static function setPassphrase($params)
 {
     if (\OCP\App::isEnabled('files_encryption') === false) {
         return true;
     }
     // Only attempt to change passphrase if server-side encryption
     // is in use (client-side encryption does not have access to
     // the necessary keys)
     if (Crypt::mode() === 'server') {
         $view = new \OC_FilesystemView('/');
         $session = new \OCA\Encryption\Session($view);
         // Get existing decrypted private key
         $privateKey = $session->getPrivateKey();
         if ($params['uid'] === \OCP\User::getUser() && $privateKey) {
             // Encrypt private key with new user pwd as passphrase
             $encryptedPrivateKey = Crypt::symmetricEncryptFileContent($privateKey, $params['password']);
             // Save private key
             if ($encryptedPrivateKey) {
                 Keymanager::setPrivateKey($encryptedPrivateKey);
             } else {
                 \OCP\Util::writeLog('files_encryption', 'Could not update users encryption password', \OCP\Util::ERROR);
             }
             // NOTE: Session does not need to be updated as the
             // private key has not changed, only the passphrase
             // used to decrypt it has changed
         } else {
             // admin changed the password for a different user, create new keys and reencrypt file keys
             $user = $params['uid'];
             $util = new Util($view, $user);
             $recoveryPassword = isset($params['recoveryPassword']) ? $params['recoveryPassword'] : null;
             // we generate new keys if...
             // ...we have a recovery password and the user enabled the recovery key
             // ...encryption was activated for the first time (no keys exists)
             // ...the user doesn't have any files
             if ($util->recoveryEnabledForUser() && $recoveryPassword || !$util->userKeysExists() || !$view->file_exists($user . '/files')) {
                 // backup old keys
                 $util->backupAllKeys('recovery');
                 $newUserPassword = $params['password'];
                 // make sure that the users home is mounted
                 \OC\Files\Filesystem::initMountPoints($user);
                 $keypair = Crypt::createKeypair();
                 // Disable encryption proxy to prevent recursive calls
                 $proxyStatus = \OC_FileProxy::$enabled;
                 \OC_FileProxy::$enabled = false;
                 // Save public key
                 $view->file_put_contents('/public-keys/' . $user . '.public.key', $keypair['publicKey']);
                 // Encrypt private key empty passphrase
                 $encryptedPrivateKey = Crypt::symmetricEncryptFileContent($keypair['privateKey'], $newUserPassword);
                 // Save private key
                 $view->file_put_contents('/' . $user . '/files_encryption/' . $user . '.private.key', $encryptedPrivateKey);
                 if ($recoveryPassword) {
                     // if recovery key is set we can re-encrypt the key files
                     $util = new Util($view, $user);
                     $util->recoverUsersFiles($recoveryPassword);
                 }
                 \OC_FileProxy::$enabled = $proxyStatus;
             }
         }
     }
 }
Exemplo n.º 30
0
    /**
     * Find which users can access a shared item
     * @param string $path to the file
     * @param string $ownerUser owner of the file
     * @param boolean $includeOwner include owner to the list of users with access to the file
     * @param boolean $returnUserPaths Return an array with the user => path map
     * @param boolean $recursive take all parent folders into account (default true)
     * @return array
     * @note $path needs to be relative to user data dir, e.g. 'file.txt'
     *       not '/admin/data/file.txt'
     */
    public static function getUsersSharingFile($path, $ownerUser, $includeOwner = false, $returnUserPaths = false, $recursive = true)
    {
        Filesystem::initMountPoints($ownerUser);
        $shares = $sharePaths = $fileTargets = array();
        $publicShare = false;
        $remoteShare = false;
        $source = -1;
        $cache = false;
        $view = new \OC\Files\View('/' . $ownerUser . '/files');
        $meta = $view->getFileInfo($path);
        if ($meta) {
            $path = substr($meta->getPath(), strlen('/' . $ownerUser . '/files'));
        } else {
            // if the file doesn't exists yet we start with the parent folder
            $meta = $view->getFileInfo(dirname($path));
        }
        if ($meta !== false) {
            $source = $meta['fileid'];
            $cache = new \OC\Files\Cache\Cache($meta['storage']);
        }
        while ($source !== -1) {
            // Fetch all shares with another user
            if (!$returnUserPaths) {
                $query = \OC_DB::prepare('SELECT `share_with`, `file_source`, `file_target`
					FROM
					`*PREFIX*share`
					WHERE
					`item_source` = ? AND `share_type` = ? AND `item_type` IN (\'file\', \'folder\')');
                $result = $query->execute(array($source, self::SHARE_TYPE_USER));
            } else {
                $query = \OC_DB::prepare('SELECT `share_with`, `file_source`, `file_target`
				FROM
				`*PREFIX*share`
				WHERE
				`item_source` = ? AND `share_type` IN (?, ?) AND `item_type` IN (\'file\', \'folder\')');
                $result = $query->execute(array($source, self::SHARE_TYPE_USER, self::$shareTypeGroupUserUnique));
            }
            if (\OCP\DB::isError($result)) {
                \OCP\Util::writeLog('OCP\\Share', \OC_DB::getErrorMessage(), \OCP\Util::ERROR);
            } else {
                while ($row = $result->fetchRow()) {
                    $shares[] = $row['share_with'];
                    if ($returnUserPaths) {
                        $fileTargets[(int) $row['file_source']][$row['share_with']] = $row;
                    }
                }
            }
            // We also need to take group shares into account
            $query = \OC_DB::prepare('SELECT `share_with`, `file_source`, `file_target`
				FROM
				`*PREFIX*share`
				WHERE
				`item_source` = ? AND `share_type` = ? AND `item_type` IN (\'file\', \'folder\')');
            $result = $query->execute(array($source, self::SHARE_TYPE_GROUP));
            if (\OCP\DB::isError($result)) {
                \OCP\Util::writeLog('OCP\\Share', \OC_DB::getErrorMessage(), \OCP\Util::ERROR);
            } else {
                while ($row = $result->fetchRow()) {
                    $usersInGroup = \OC_Group::usersInGroup($row['share_with']);
                    $shares = array_merge($shares, $usersInGroup);
                    if ($returnUserPaths) {
                        foreach ($usersInGroup as $user) {
                            if (!isset($fileTargets[(int) $row['file_source']][$user])) {
                                // When the user already has an entry for this file source
                                // the file is either shared directly with him as well, or
                                // he has an exception entry (because of naming conflict).
                                $fileTargets[(int) $row['file_source']][$user] = $row;
                            }
                        }
                    }
                }
            }
            //check for public link shares
            if (!$publicShare) {
                $query = \OC_DB::prepare('
					SELECT `share_with`
					FROM `*PREFIX*share`
					WHERE `item_source` = ? AND `share_type` = ? AND `item_type` IN (\'file\', \'folder\')', 1);
                $result = $query->execute(array($source, self::SHARE_TYPE_LINK));
                if (\OCP\DB::isError($result)) {
                    \OCP\Util::writeLog('OCP\\Share', \OC_DB::getErrorMessage(), \OCP\Util::ERROR);
                } else {
                    if ($result->fetchRow()) {
                        $publicShare = true;
                    }
                }
            }
            //check for remote share
            if (!$remoteShare) {
                $query = \OC_DB::prepare('
					SELECT `share_with`
					FROM `*PREFIX*share`
					WHERE `item_source` = ? AND `share_type` = ? AND `item_type` IN (\'file\', \'folder\')', 1);
                $result = $query->execute(array($source, self::SHARE_TYPE_REMOTE));
                if (\OCP\DB::isError($result)) {
                    \OCP\Util::writeLog('OCP\\Share', \OC_DB::getErrorMessage(), \OCP\Util::ERROR);
                } else {
                    if ($result->fetchRow()) {
                        $remoteShare = true;
                    }
                }
            }
            // let's get the parent for the next round
            $meta = $cache->get((int) $source);
            if ($recursive === true && $meta !== false) {
                $source = (int) $meta['parent'];
            } else {
                $source = -1;
            }
        }
        // Include owner in list of users, if requested
        if ($includeOwner) {
            $shares[] = $ownerUser;
        }
        if ($returnUserPaths) {
            $fileTargetIDs = array_keys($fileTargets);
            $fileTargetIDs = array_unique($fileTargetIDs);
            if (!empty($fileTargetIDs)) {
                $query = \OC_DB::prepare('SELECT `fileid`, `path`
					FROM `*PREFIX*filecache`
					WHERE `fileid` IN (' . implode(',', $fileTargetIDs) . ')');
                $result = $query->execute();
                if (\OCP\DB::isError($result)) {
                    \OCP\Util::writeLog('OCP\\Share', \OC_DB::getErrorMessage(), \OCP\Util::ERROR);
                } else {
                    while ($row = $result->fetchRow()) {
                        foreach ($fileTargets[$row['fileid']] as $uid => $shareData) {
                            $sharedPath = $shareData['file_target'];
                            $sharedPath .= substr($path, strlen($row['path']) - 5);
                            $sharePaths[$uid] = $sharedPath;
                        }
                    }
                }
            }
            if ($includeOwner) {
                $sharePaths[$ownerUser] = $path;
            } else {
                unset($sharePaths[$ownerUser]);
            }
            return $sharePaths;
        }
        return array('users' => array_unique($shares), 'public' => $publicShare, 'remote' => $remoteShare);
    }