[TASK] CGL: Fix a series of minor indentation issues
[Packages/TYPO3.CMS.git] / typo3 / sysext / core / Classes / Resource / ResourceStorage.php
index b29ba90..def4d7e 100644 (file)
@@ -14,11 +14,12 @@ namespace TYPO3\CMS\Core\Resource;
  * The TYPO3 project - inspiring people to share!
  */
 
-use TYPO3\CMS\Core\Database\DatabaseConnection;
+use TYPO3\CMS\Core\Database\ConnectionPool;
+use TYPO3\CMS\Core\Log\LogManager;
 use TYPO3\CMS\Core\Registry;
+use TYPO3\CMS\Core\Resource\Exception\ExistingTargetFileNameException;
 use TYPO3\CMS\Core\Resource\Exception\InvalidTargetFolderException;
 use TYPO3\CMS\Core\Resource\Index\FileIndexRepository;
-use TYPO3\CMS\Core\Resource\Index\Indexer;
 use TYPO3\CMS\Core\Resource\OnlineMedia\Helpers\OnlineMediaHelperRegistry;
 use TYPO3\CMS\Core\Utility\GeneralUtility;
 use TYPO3\CMS\Core\Utility\PathUtility;
@@ -100,7 +101,7 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @var array
      */
-    protected $fileMounts = array();
+    protected $fileMounts = [];
 
     /**
      * The file permissions of the user (and their group) merged together and
@@ -108,7 +109,7 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @var array
      */
-    protected $userPermissions = array();
+    protected $userPermissions = [];
 
     /**
      * The capabilities of this storage as defined in the storage record.
@@ -152,7 +153,7 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @var array
      */
-    protected $fileAndFolderNameFilters = array();
+    protected $fileAndFolderNameFilters = [];
 
     /**
      * Levels numbers used to generate hashed subfolders in the processing folder
@@ -168,7 +169,7 @@ class ResourceStorage implements ResourceStorageInterface
     public function __construct(Driver\DriverInterface $driver, array $storageRecord)
     {
         $this->storageRecord = $storageRecord;
-        $this->configuration = ResourceFactory::getInstance()->convertFlexFormDataToConfigurationArray($storageRecord['configuration']);
+        $this->configuration = $this->getResourceFactoryInstance()->convertFlexFormDataToConfigurationArray($storageRecord['configuration']);
         $this->capabilities =
             ($this->storageRecord['is_browsable'] ? self::CAPABILITY_BROWSABLE : 0) |
             ($this->storageRecord['is_public'] ? self::CAPABILITY_PUBLIC : 0) |
@@ -180,9 +181,18 @@ class ResourceStorage implements ResourceStorageInterface
         try {
             $this->driver->processConfiguration();
         } catch (Exception\InvalidConfigurationException $e) {
-            // configuration error
-            // mark this storage as permanently unusable
-            $this->markAsPermanentlyOffline();
+            // Configuration error
+            $this->isOnline = false;
+
+            $message = sprintf(
+                'Failed initializing storage [%d] "%s", error: %s',
+                $this->getUid(),
+                $this->getName(),
+                $e->getMessage()
+            );
+
+            // create a dedicated logger instance because we need a logger in the constructor
+            GeneralUtility::makeInstance(LogManager::class)->getLogger(static::class)->error($message);
         }
         $this->driver->initialize();
         $this->capabilities = $this->driver->getCapabilities();
@@ -392,14 +402,18 @@ class ResourceStorage implements ResourceStorageInterface
      * Can only be modified by an admin.
      *
      * Typically, this is only done if the configuration is wrong.
-     *
-     * @return void
      */
     public function markAsPermanentlyOffline()
     {
         if ($this->getUid() > 0) {
             // @todo: move this to the storage repository
-            $this->getDatabaseConnection()->exec_UPDATEquery('sys_file_storage', 'uid=' . (int)$this->getUid(), array('is_online' => 0));
+            GeneralUtility::makeInstance(ConnectionPool::class)
+                ->getConnectionForTable('sys_file_storage')
+                ->update(
+                    'sys_file_storage',
+                    ['is_online' => 0],
+                    ['uid' => (int)$this->getUid()]
+                );
         }
         $this->storageRecord['is_online'] = 0;
         $this->isOnline = false;
@@ -410,8 +424,6 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * Non-permanent: This typically happens for remote storages
      * that are "flaky" and not available all the time.
-     *
-     * @return void
      */
     public function markAsTemporaryOffline()
     {
@@ -432,9 +444,8 @@ class ResourceStorage implements ResourceStorageInterface
      * @param array $additionalData
      *
      * @throws Exception\FolderDoesNotExistException
-     * @return void
      */
-    public function addFileMount($folderIdentifier, $additionalData = array())
+    public function addFileMount($folderIdentifier, $additionalData = [])
     {
         // check for the folder before we add it as a filemount
         if ($this->driver->folderExists($folderIdentifier) === false) {
@@ -443,7 +454,7 @@ class ResourceStorage implements ResourceStorageInterface
             throw new Exception\FolderDoesNotExistException('Folder for file mount ' . $folderIdentifier . ' does not exist.', 1334427099);
         }
         $data = $this->driver->getFolderInfoByIdentifier($folderIdentifier);
-        $folderObject = ResourceFactory::getInstance()->createFolderObject($this, $data['identifier'], $data['name']);
+        $folderObject = $this->getResourceFactoryInstance()->createFolderObject($this, $data['identifier'], $data['name']);
         // Use the canonical identifier instead of the user provided one!
         $folderIdentifier = $folderObject->getIdentifier();
         if (
@@ -455,11 +466,11 @@ class ResourceStorage implements ResourceStorageInterface
             return;
         }
         if (empty($additionalData)) {
-            $additionalData = array(
+            $additionalData = [
                 'path' => $folderIdentifier,
                 'title' => $folderIdentifier,
                 'folder' => $folderObject
-            );
+            ];
         } else {
             $additionalData['folder'] = $folderObject;
             if (!isset($additionalData['title'])) {
@@ -512,7 +523,8 @@ class ResourceStorage implements ResourceStorageInterface
                     $isWithinFileMount = true;
                     if (!$checkWriteAccess) {
                         break;
-                    } elseif (empty($fileMount['read_only'])) {
+                    }
+                    if (empty($fileMount['read_only'])) {
                         $writableFileMountAvailable = true;
                         break;
                     }
@@ -549,7 +561,6 @@ class ResourceStorage implements ResourceStorageInterface
      * Sets the user permissions of the storage.
      *
      * @param array $userPermissions
-     * @return void
      */
     public function setUserPermissions(array $userPermissions)
     {
@@ -603,11 +614,11 @@ class ResourceStorage implements ResourceStorageInterface
             return false;
         }
         $isReadCheck = false;
-        if (in_array($action, array('read', 'copy', 'move', 'replace'), true)) {
+        if (in_array($action, ['read', 'copy', 'move', 'replace'], true)) {
             $isReadCheck = true;
         }
         $isWriteCheck = false;
-        if (in_array($action, array('add', 'write', 'move', 'rename', 'replace', 'delete'), true)) {
+        if (in_array($action, ['add', 'write', 'move', 'rename', 'replace', 'delete'], true)) {
             $isWriteCheck = true;
         }
         // Check 3: Does the user have the right to perform the action?
@@ -667,11 +678,11 @@ class ResourceStorage implements ResourceStorageInterface
         }
 
         $isReadCheck = false;
-        if (in_array($action, array('read', 'copy'), true)) {
+        if (in_array($action, ['read', 'copy'], true)) {
             $isReadCheck = true;
         }
         $isWriteCheck = false;
-        if (in_array($action, array('add', 'move', 'write', 'delete', 'rename'), true)) {
+        if (in_array($action, ['add', 'move', 'write', 'delete', 'rename'], true)) {
             $isWriteCheck = true;
         }
         // Check 2: Does the user has the right to perform the action?
@@ -708,42 +719,13 @@ class ResourceStorage implements ResourceStorageInterface
     protected function checkFileExtensionPermission($fileName)
     {
         $fileName = $this->driver->sanitizeFileName($fileName);
-        $isAllowed = GeneralUtility::verifyFilenameAgainstDenyPattern($fileName);
-        if ($isAllowed && $this->evaluatePermissions) {
-            $fileExtension = strtolower(PathUtility::pathinfo($fileName, PATHINFO_EXTENSION));
-            // Set up the permissions for the file extension
-            $fileExtensionPermissions = $GLOBALS['TYPO3_CONF_VARS']['BE']['fileExtensions']['webspace'];
-            $fileExtensionPermissions['allow'] = GeneralUtility::uniqueList(strtolower($fileExtensionPermissions['allow']));
-            $fileExtensionPermissions['deny'] = GeneralUtility::uniqueList(strtolower($fileExtensionPermissions['deny']));
-            if ($fileExtension !== '') {
-                // If the extension is found amongst the allowed types, we return TRUE immediately
-                if ($fileExtensionPermissions['allow'] === '*' || GeneralUtility::inList($fileExtensionPermissions['allow'], $fileExtension)) {
-                    return true;
-                }
-                // If the extension is found amongst the denied types, we return FALSE immediately
-                if ($fileExtensionPermissions['deny'] === '*' || GeneralUtility::inList($fileExtensionPermissions['deny'], $fileExtension)) {
-                    return false;
-                }
-                // If no match we return TRUE
-                return true;
-            } else {
-                if ($fileExtensionPermissions['allow'] === '*') {
-                    return true;
-                }
-                if ($fileExtensionPermissions['deny'] === '*') {
-                    return false;
-                }
-                return true;
-            }
-        }
-        return $isAllowed;
+        return GeneralUtility::verifyFilenameAgainstDenyPattern($fileName);
     }
 
     /**
      * Assures read permission for given folder.
      *
      * @param Folder $folder If a folder is given, mountpoints are checked. If not only user folder read permissions are checked.
-     * @return void
      * @throws Exception\InsufficientFolderAccessPermissionsException
      */
     protected function assureFolderReadPermission(Folder $folder = null)
@@ -754,12 +736,11 @@ class ResourceStorage implements ResourceStorageInterface
                     'You are not allowed to read folders',
                     1430657869
                 );
-            } else {
-                throw new Exception\InsufficientFolderAccessPermissionsException(
+            }
+            throw new Exception\InsufficientFolderAccessPermissionsException(
                     'You are not allowed to access the given folder: "' . $folder->getName() . '"',
                     1375955684
                 );
-            }
         }
     }
 
@@ -768,7 +749,6 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param Folder $folder If a folder is given, mountpoints are checked. If not only user folder delete permissions are checked.
      * @param bool $checkDeleteRecursively
-     * @return void
      * @throws Exception\InsufficientFolderAccessPermissionsException
      * @throws Exception\InsufficientFolderWritePermissionsException
      * @throws Exception\InsufficientUserPermissionsException
@@ -798,7 +778,6 @@ class ResourceStorage implements ResourceStorageInterface
      * Assures read permission for given file.
      *
      * @param FileInterface $file
-     * @return void
      * @throws Exception\InsufficientFileAccessPermissionsException
      * @throws Exception\IllegalFileExtensionException
      */
@@ -822,7 +801,6 @@ class ResourceStorage implements ResourceStorageInterface
      * Assures write permission for given file.
      *
      * @param FileInterface $file
-     * @return void
      * @throws Exception\IllegalFileExtensionException
      * @throws Exception\InsufficientFileWritePermissionsException
      * @throws Exception\InsufficientUserPermissionsException
@@ -842,7 +820,6 @@ class ResourceStorage implements ResourceStorageInterface
      * Assure replace permission for given file.
      *
      * @param FileInterface $file
-     * @return void
      * @throws Exception\InsufficientFileWritePermissionsException
      * @throws Exception\InsufficientFolderWritePermissionsException
      */
@@ -862,7 +839,6 @@ class ResourceStorage implements ResourceStorageInterface
      * Assures delete permission for given file.
      *
      * @param FileInterface $file
-     * @return void
      * @throws Exception\IllegalFileExtensionException
      * @throws Exception\InsufficientFileWritePermissionsException
      * @throws Exception\InsufficientFolderWritePermissionsException
@@ -894,7 +870,6 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param Folder $targetFolder The target folder where the file should be written
      * @param string $targetFileName The file name which should be written into the storage
-     * @return void
      *
      * @throws Exception\InsufficientFolderWritePermissionsException
      * @throws Exception\IllegalFileExtensionException
@@ -924,7 +899,6 @@ class ResourceStorage implements ResourceStorageInterface
      * @param Folder $targetFolder The target folder where the file should be uploaded
      * @param string $targetFileName the destination file name $_FILES['file1']['name']
      * @param int $uploadedFileSize
-     * @return void
      *
      * @throws Exception\InsufficientFolderWritePermissionsException
      * @throws Exception\UploadException
@@ -957,13 +931,12 @@ class ResourceStorage implements ResourceStorageInterface
      * @param FileInterface $file
      * @param Folder $targetFolder
      * @param string $targetFileName
-     * @return void
      */
     protected function assureFileMovePermissions(FileInterface $file, Folder $targetFolder, $targetFileName)
     {
         // Check if targetFolder is within this storage
         if ($this->getUid() !== $targetFolder->getStorage()->getUid()) {
-            throw new \RuntimeException('The target folder is not in the same storage. Target folder given: "' . $targetFolder . '"', 1422553107);
+            throw new \RuntimeException('The target folder is not in the same storage. Target folder given: "' . $targetFolder->getIdentifier() . '"', 1422553107);
         }
         // Check for a valid file extension
         if (!$this->checkFileExtensionPermission($targetFileName)) {
@@ -988,7 +961,6 @@ class ResourceStorage implements ResourceStorageInterface
      * @throws Exception\IllegalFileExtensionException
      * @throws Exception\InsufficientFileReadPermissionsException
      * @throws Exception\InsufficientUserPermissionsException
-     * @return void
      */
     protected function assureFileRenamePermissions(FileInterface $file, $targetFileName)
     {
@@ -1022,7 +994,6 @@ class ResourceStorage implements ResourceStorageInterface
      * @throws Exception\IllegalFileExtensionException
      * @throws Exception\InsufficientFileReadPermissionsException
      * @throws Exception\InsufficientUserPermissionsException
-     * @return void
      */
     protected function assureFileCopyPermissions(FileInterface $file, Folder $targetFolder, $targetFileName)
     {
@@ -1050,7 +1021,6 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FolderInterface $folderToCopy
      * @param FolderInterface $targetParentFolder
-     * @return void
      *
      * @throws Exception
      * @throws Exception\InsufficientFolderWritePermissionsException
@@ -1094,7 +1064,6 @@ class ResourceStorage implements ResourceStorageInterface
      * @throws Exception\InsufficientFileReadPermissionsException
      * @throws Exception\InsufficientUserPermissionsException
      * @throws \RuntimeException
-     * @return void
      */
     protected function assureFolderMovePermissions(FolderInterface $folderToMove, FolderInterface $targetParentFolder)
     {
@@ -1171,18 +1140,25 @@ class ResourceStorage implements ResourceStorageInterface
         $targetFileName = $this->emitPreFileAddSignal($targetFileName, $targetFolder, $localFilePath);
 
         $this->assureFileAddPermissions($targetFolder, $targetFileName);
+
+        $replaceExisting = false;
         if ($conflictMode->equals(DuplicationBehavior::CANCEL) && $this->driver->fileExistsInFolder($targetFileName, $targetFolder->getIdentifier())) {
             throw new Exception\ExistingTargetFileNameException('File "' . $targetFileName . '" already exists in folder ' . $targetFolder->getIdentifier(), 1322121068);
-        } elseif ($conflictMode->equals(DuplicationBehavior::RENAME)) {
+        }
+        if ($conflictMode->equals(DuplicationBehavior::RENAME)) {
             $targetFileName = $this->getUniqueName($targetFolder, $targetFileName);
+        } elseif ($conflictMode->equals(DuplicationBehavior::REPLACE) && $this->driver->fileExistsInFolder($targetFileName, $targetFolder->getIdentifier())) {
+            $replaceExisting = true;
         }
 
         $fileIdentifier = $this->driver->addFile($localFilePath, $targetFolder->getIdentifier(), $targetFileName, $removeOriginal);
-        $file = ResourceFactory::getInstance()->getFileObjectByStorageAndIdentifier($this->getUid(), $fileIdentifier);
+        $file = $this->getResourceFactoryInstance()->getFileObjectByStorageAndIdentifier($this->getUid(), $fileIdentifier);
 
+        if ($replaceExisting && $file instanceof File) {
+            $this->getIndexer()->updateIndexEntry($file);
+        }
         if ($this->autoExtractMetadataEnabled()) {
-            $indexer = GeneralUtility::makeInstance(Indexer::class, $this);
-            $indexer->extractMetaData($file);
+            $this->getIndexer()->extractMetaData($file);
         }
 
         $this->emitPostFileAddSignal($file, $targetFolder);
@@ -1228,7 +1204,7 @@ class ResourceStorage implements ResourceStorageInterface
 
     /**
      * Creates a (cryptographic) hash for a fileIdentifier.
-
+     *
      * @param string $fileIdentifier
      * @param string $hash
      *
@@ -1271,7 +1247,7 @@ class ResourceStorage implements ResourceStorageInterface
         $publicUrl = null;
         if ($this->isOnline()) {
             // Pre-process the public URL by an accordant slot
-            $this->emitPreGeneratePublicUrlSignal($resourceObject, $relativeToCurrentScript, array('publicUrl' => &$publicUrl));
+            $this->emitPreGeneratePublicUrlSignal($resourceObject, $relativeToCurrentScript, ['publicUrl' => &$publicUrl]);
 
             if (
                 $publicUrl === null
@@ -1288,7 +1264,7 @@ class ResourceStorage implements ResourceStorageInterface
                 }
 
                 if ($publicUrl === null && $resourceObject instanceof FileInterface) {
-                    $queryParameterArray = array('eID' => 'dumpFile', 't' => '');
+                    $queryParameterArray = ['eID' => 'dumpFile', 't' => ''];
                     if ($resourceObject instanceof File) {
                         $queryParameterArray['f'] = $resourceObject->getUid();
                         $queryParameterArray['t'] = 'f';
@@ -1298,7 +1274,8 @@ class ResourceStorage implements ResourceStorageInterface
                     }
 
                     $queryParameterArray['token'] = GeneralUtility::hmac(implode('|', $queryParameterArray), 'resourceStorageDumpFile');
-                    $publicUrl = 'index.php?' . str_replace('+', '%20', http_build_query($queryParameterArray));
+                    $publicUrl = GeneralUtility::locationHeaderUrl(PathUtility::getAbsoluteWebPath(PATH_site . 'index.php'));
+                    $publicUrl .= '?' . http_build_query($queryParameterArray, '', '&', PHP_QUERY_RFC3986);
                 }
 
                 // If requested, make the path relative to the current script in order to make it possible
@@ -1382,25 +1359,21 @@ class ResourceStorage implements ResourceStorageInterface
      * @return array
      * @internal
      */
-    public function getFileInfoByIdentifier($identifier, array $propertiesToExtract = array())
+    public function getFileInfoByIdentifier($identifier, array $propertiesToExtract = [])
     {
         return $this->driver->getFileInfoByIdentifier($identifier, $propertiesToExtract);
     }
 
     /**
      * Unsets the file and folder name filters, thus making this storage return unfiltered filelists.
-     *
-     * @return void
      */
     public function unsetFileAndFolderNameFilters()
     {
-        $this->fileAndFolderNameFilters = array();
+        $this->fileAndFolderNameFilters = [];
     }
 
     /**
      * Resets the file and folder name filters to the default values defined in the TYPO3 configuration.
-     *
-     * @return void
      */
     public function resetFileAndFolderNameFiltersToDefault()
     {
@@ -1450,7 +1423,7 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param string $fileName
      * @param Folder $folder
-     * @return NULL|File|ProcessedFile
+     * @return File|ProcessedFile|null
      */
     public function getFileInFolder($fileName, Folder $folder)
     {
@@ -1479,10 +1452,10 @@ class ResourceStorage implements ResourceStorageInterface
 
         $rows = $this->getFileIndexRepository()->findByFolder($folder);
 
-        $filters = $useFilters == true ? $this->fileAndFolderNameFilters : array();
+        $filters = $useFilters == true ? $this->fileAndFolderNameFilters : [];
         $fileIdentifiers = array_values($this->driver->getFilesInFolder($folder->getIdentifier(), $start, $maxNumberOfItems, $recursive, $filters, $sort, $sortRev));
 
-        $items = array();
+        $items = [];
         foreach ($fileIdentifiers as $identifier) {
             if (isset($rows[$identifier])) {
                 $fileObject = $this->getFileFactory()->getFileObject($rows[$identifier]['uid'], $rows[$identifier]);
@@ -1509,7 +1482,7 @@ class ResourceStorage implements ResourceStorageInterface
      */
     public function getFileIdentifiersInFolder($folderIdentifier, $useFilters = true, $recursive = false)
     {
-        $filters = $useFilters == true ? $this->fileAndFolderNameFilters : array();
+        $filters = $useFilters == true ? $this->fileAndFolderNameFilters : [];
         return $this->driver->getFilesInFolder($folderIdentifier, 0, 0, $recursive, $filters);
     }
 
@@ -1523,7 +1496,7 @@ class ResourceStorage implements ResourceStorageInterface
     public function countFilesInFolder(Folder $folder, $useFilters = true, $recursive = false)
     {
         $this->assureFolderReadPermission($folder);
-        $filters = $useFilters ? $this->fileAndFolderNameFilters : array();
+        $filters = $useFilters ? $this->fileAndFolderNameFilters : [];
         return $this->driver->countFilesInFolder($folder->getIdentifier(), $recursive, $filters);
     }
 
@@ -1535,7 +1508,7 @@ class ResourceStorage implements ResourceStorageInterface
      */
     public function getFolderIdentifiersInFolder($folderIdentifier, $useFilters = true, $recursive = false)
     {
-        $filters = $useFilters == true ? $this->fileAndFolderNameFilters : array();
+        $filters = $useFilters == true ? $this->fileAndFolderNameFilters : [];
         return $this->driver->getFoldersInFolder($folderIdentifier, 0, 0, $recursive, $filters);
     }
 
@@ -1562,7 +1535,7 @@ class ResourceStorage implements ResourceStorageInterface
     public function getProcessingFolders()
     {
         if ($this->processingFolders === null) {
-            $this->processingFolders = array();
+            $this->processingFolders = [];
             $this->processingFolders[] = $this->getProcessingFolder();
             /** @var $storageRepository StorageRepository */
             $storageRepository = GeneralUtility::makeInstance(StorageRepository::class);
@@ -1570,11 +1543,11 @@ class ResourceStorage implements ResourceStorageInterface
             foreach ($allStorages as $storage) {
                 // To circumvent the permission check of the folder, we use the factory to create it "manually" instead of directly using $storage->getProcessingFolder()
                 // See #66695 for details
-                list($storageUid, $processingFolderIdentifier) = GeneralUtility::trimExplode(':', $storage->getStorageRecord()['processingfolder']);
+                list($storageUid, $processingFolderIdentifier) = array_pad(GeneralUtility::trimExplode(':', $storage->getStorageRecord()['processingfolder']), 2, null);
                 if (empty($processingFolderIdentifier) || (int)$storageUid !== $this->getUid()) {
                     continue;
                 }
-                $potentialProcessingFolder = ResourceFactory::getInstance()->getInstance()->createFolderObject($this, $processingFolderIdentifier, $processingFolderIdentifier);
+                $potentialProcessingFolder = $this->getResourceFactoryInstance()->getInstance()->createFolderObject($this, $processingFolderIdentifier, $processingFolderIdentifier);
                 if ($potentialProcessingFolder->getStorage() === $this && $potentialProcessingFolder->getIdentifier() !== $this->getProcessingFolder()->getIdentifier()) {
                     $this->processingFolders[] = $potentialProcessingFolder;
                 }
@@ -1638,7 +1611,6 @@ class ResourceStorage implements ResourceStorageInterface
      * @param bool $asDownload If set Content-Disposition attachment is sent, inline otherwise
      * @param string $alternativeFilename the filename for the download (if $asDownload is set)
      * @param string $overrideMimeType If set this will be used as Content-Type header instead of the automatically detected mime type.
-     * @return void
      */
     public function dumpFileContents(FileInterface $file, $asDownload = false, $alternativeFilename = null, $overrideMimeType = null)
     {
@@ -1651,8 +1623,9 @@ class ResourceStorage implements ResourceStorageInterface
         // Cache-Control header is needed here to solve an issue with browser IE8 and lower
         // See for more information: http://support.microsoft.com/kb/323308
         header("Cache-Control: ''");
-        header('Last-Modified: ' .
-            gmdate('D, d M Y H:i:s', array_pop($this->driver->getFileInfoByIdentifier($file->getIdentifier(), array('mtime')))) . ' GMT',
+        header(
+            'Last-Modified: ' .
+            gmdate('D, d M Y H:i:s', array_pop($this->driver->getFileInfoByIdentifier($file->getIdentifier(), ['mtime']))) . ' GMT',
             true,
             200
         );
@@ -1705,7 +1678,7 @@ class ResourceStorage implements ResourceStorageInterface
         $this->assureFileAddPermissions($targetFolderObject, $fileName);
         $newFileIdentifier = $this->driver->createFile($fileName, $targetFolderObject->getIdentifier());
         $this->emitPostFileCreateSignal($newFileIdentifier, $targetFolderObject);
-        return ResourceFactory::getInstance()->getFileObjectByStorageAndIdentifier($this->getUid(), $newFileIdentifier);
+        return $this->getResourceFactoryInstance()->getFileObjectByStorageAndIdentifier($this->getUid(), $newFileIdentifier);
     }
 
     /**
@@ -1729,7 +1702,7 @@ class ResourceStorage implements ResourceStorageInterface
             }
         }
         // Mark the file object as deleted
-        if ($fileObject instanceof File) {
+        if ($fileObject instanceof AbstractFile) {
             $fileObject->setDeleted();
         }
 
@@ -1778,7 +1751,7 @@ class ResourceStorage implements ResourceStorageInterface
             $tempPath = $file->getForLocalProcessing();
             $newFileObjectIdentifier = $this->driver->addFile($tempPath, $targetFolder->getIdentifier(), $sanitizedTargetFileName);
         }
-        $newFileObject = ResourceFactory::getInstance()->getFileObjectByStorageAndIdentifier($this->getUid(), $newFileObjectIdentifier);
+        $newFileObject = $this->getResourceFactoryInstance()->getFileObjectByStorageAndIdentifier($this->getUid(), $newFileObjectIdentifier);
         $this->emitPostFileCopySignal($file, $targetFolder);
         return $newFileObject;
     }
@@ -1824,13 +1797,13 @@ class ResourceStorage implements ResourceStorageInterface
                 if (!$file instanceof AbstractFile) {
                     throw new \RuntimeException('The given file is not of type AbstractFile.', 1384209025);
                 }
-                $file->updateProperties(array('identifier' => $newIdentifier));
+                $file->updateProperties(['identifier' => $newIdentifier]);
             } else {
                 $tempPath = $file->getForLocalProcessing();
                 $newIdentifier = $this->driver->addFile($tempPath, $targetFolder->getIdentifier(), $sanitizedTargetFileName);
                 $sourceStorage->driver->deleteFile($file->getIdentifier());
                 if ($file instanceof File) {
-                    $file->updateProperties(array('storage' => $this->getUid(), 'identifier' => $newIdentifier));
+                    $file->updateProperties(['storage' => $this->getUid(), 'identifier' => $newIdentifier]);
                 }
             }
             $this->getIndexer()->updateIndexEntry($file);
@@ -1846,16 +1819,12 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param string $targetFileName
-     *
-     * @throws Exception\InsufficientFileWritePermissionsException
-     * @throws Exception\InsufficientFileReadPermissionsException
-     * @throws Exception\InsufficientUserPermissionsException
+     * @param string $conflictMode
      * @return FileInterface
+     * @throws ExistingTargetFileNameException
      */
-    public function renameFile($file, $targetFileName)
+    public function renameFile($file, $targetFileName, $conflictMode = DuplicationBehavior::RENAME)
     {
-        // @todo add $conflictMode setting
-
         // The name should be different from the current.
         if ($file->getName() === $targetFileName) {
             return $file;
@@ -1864,13 +1833,26 @@ class ResourceStorage implements ResourceStorageInterface
         $this->assureFileRenamePermissions($file, $sanitizedTargetFileName);
         $this->emitPreFileRenameSignal($file, $sanitizedTargetFileName);
 
+        $conflictMode = DuplicationBehavior::cast($conflictMode);
+
         // Call driver method to rename the file and update the index entry
         try {
             $newIdentifier = $this->driver->renameFile($file->getIdentifier(), $sanitizedTargetFileName);
             if ($file instanceof File) {
-                $file->updateProperties(array('identifier' => $newIdentifier));
+                $file->updateProperties(['identifier' => $newIdentifier]);
             }
             $this->getIndexer()->updateIndexEntry($file);
+        } catch (ExistingTargetFileNameException $exception) {
+            if ($conflictMode->equals(DuplicationBehavior::RENAME)) {
+                $newName = $this->getUniqueName($file->getParentFolder(), $sanitizedTargetFileName);
+                $file = $this->renameFile($file, $newName);
+            } elseif ($conflictMode->equals(DuplicationBehavior::CANCEL)) {
+                throw $exception;
+            } elseif ($conflictMode->equals(DuplicationBehavior::REPLACE)) {
+                $sourceFileIdentifier = substr($file->getCombinedIdentifier(), 0, strrpos($file->getCombinedIdentifier(), '/') + 1) . $targetFileName;
+                $sourceFile = $this->getResourceFactoryInstance()->getFileObjectFromCombinedIdentifier($sourceFileIdentifier);
+                $file = $this->replaceFile($sourceFile, PATH_site . $file->getPublicUrl());
+            }
         } catch (\RuntimeException $e) {
         }
 
@@ -1893,9 +1875,6 @@ class ResourceStorage implements ResourceStorageInterface
     public function replaceFile(FileInterface $file, $localFilePath)
     {
         $this->assureFileReplacePermissions($file);
-        if (!$this->checkFileExtensionPermission($localFilePath)) {
-            throw new Exception\IllegalFileExtensionException('Source file extension not allowed.', 1378132239);
-        }
         if (!file_exists($localFilePath)) {
             throw new \InvalidArgumentException('File "' . $localFilePath . '" does not exist.', 1325842622);
         }
@@ -1905,8 +1884,7 @@ class ResourceStorage implements ResourceStorageInterface
             $this->getIndexer()->updateIndexEntry($file);
         }
         if ($this->autoExtractMetadataEnabled()) {
-            $indexer = GeneralUtility::makeInstance(Indexer::class, $this);
-            $indexer->extractMetaData($file);
+            $this->getIndexer()->extractMetaData($file);
         }
         $this->emitPostFileReplaceSignal($file, $localFilePath);
 
@@ -1955,8 +1933,8 @@ class ResourceStorage implements ResourceStorageInterface
      */
     protected function getAllFileObjectsInFolder(Folder $folder)
     {
-        $files = array();
-        $folderQueue = array($folder);
+        $files = [];
+        $folderQueue = [$folder];
         while (!empty($folderQueue)) {
             $folder = array_shift($folderQueue);
             foreach ($folder->getSubfolders() as $subfolder) {
@@ -2015,7 +1993,7 @@ class ResourceStorage implements ResourceStorageInterface
         // Update the identifier and storage of all file objects
         foreach ($fileObjects as $oldIdentifier => $fileObject) {
             $newIdentifier = $fileMappings[$oldIdentifier];
-            $fileObject->updateProperties(array('storage' => $this->getUid(), 'identifier' => $newIdentifier));
+            $fileObject->updateProperties(['storage' => $this->getUid(), 'identifier' => $newIdentifier]);
             $this->getIndexer()->updateIndexEntry($fileObject);
         }
         $returnObject = $this->getFolder($fileMappings[$folderToMove->getIdentifier()]);
@@ -2035,7 +2013,7 @@ class ResourceStorage implements ResourceStorageInterface
      */
     protected function moveFolderBetweenStorages(Folder $folderToMove, Folder $targetParentFolder, $newFolderName)
     {
-        throw new \RuntimeException('Not yet implemented');
+        throw new \RuntimeException('Not yet implemented', 1476046361);
     }
 
     /**
@@ -2092,7 +2070,7 @@ class ResourceStorage implements ResourceStorageInterface
      */
     protected function copyFolderBetweenStorages(Folder $folderToCopy, Folder $targetParentFolder, $newFolderName)
     {
-        throw new \RuntimeException('Not yet implemented.');
+        throw new \RuntimeException('Not yet implemented.', 1476046386);
     }
 
     /**
@@ -2126,7 +2104,7 @@ class ResourceStorage implements ResourceStorageInterface
         // Update the identifier of all file objects
         foreach ($fileObjects as $oldIdentifier => $fileObject) {
             $newIdentifier = $fileMappings[$oldIdentifier];
-            $fileObject->updateProperties(array('identifier' => $newIdentifier));
+            $fileObject->updateProperties(['identifier' => $newIdentifier]);
             $this->getIndexer()->updateIndexEntry($fileObject);
         }
         $returnObject = $this->getFolder($fileMappings[$folderObject->getIdentifier()]);
@@ -2201,7 +2179,7 @@ class ResourceStorage implements ResourceStorageInterface
      */
     public function getFoldersInFolder(Folder $folder, $start = 0, $maxNumberOfItems = 0, $useFilters = true, $recursive = false, $sort = '', $sortRev = false)
     {
-        $filters = $useFilters == true ? $this->fileAndFolderNameFilters : array();
+        $filters = $useFilters == true ? $this->fileAndFolderNameFilters : [];
 
         $folderIdentifiers = $this->driver->getFoldersInFolder($folder->getIdentifier(), $start, $maxNumberOfItems, $recursive, $filters, $sort, $sortRev);
 
@@ -2212,7 +2190,7 @@ class ResourceStorage implements ResourceStorageInterface
                 unset($folderIdentifiers[$processingIdentifier]);
             }
         }
-        $folders = array();
+        $folders = [];
         foreach ($folderIdentifiers as $folderIdentifier) {
             $folders[$folderIdentifier] = $this->getFolder($folderIdentifier, true);
         }
@@ -2229,7 +2207,7 @@ class ResourceStorage implements ResourceStorageInterface
     public function countFoldersInFolder(Folder $folder, $useFilters = true, $recursive = false)
     {
         $this->assureFolderReadPermission($folder);
-        $filters = $useFilters ? $this->fileAndFolderNameFilters : array();
+        $filters = $useFilters ? $this->fileAndFolderNameFilters : [];
         return $this->driver->countFoldersInFolder($folder->getIdentifier(), $recursive, $filters);
     }
 
@@ -2327,7 +2305,7 @@ class ResourceStorage implements ResourceStorageInterface
     public function getFolder($identifier, $returnInaccessibleFolderObject = false)
     {
         $data = $this->driver->getFolderInfoByIdentifier($identifier);
-        $folder = ResourceFactory::getInstance()->createFolderObject($this, $data['identifier'], $data['name']);
+        $folder = $this->getResourceFactoryInstance()->createFolderObject($this, $data['identifier'], $data['name']);
 
         try {
             $this->assureFolderReadPermission($folder);
@@ -2338,7 +2316,10 @@ class ResourceStorage implements ResourceStorageInterface
                 $parentPermissions = $this->driver->getPermissions($this->driver->getParentFolderIdentifierOfIdentifier($identifier));
                 if ($parentPermissions['r']) {
                     $folder = GeneralUtility::makeInstance(
-                        InaccessibleFolder::class, $this, $data['identifier'], $data['name']
+                        InaccessibleFolder::class,
+                        $this,
+                        $data['identifier'],
+                        $data['name']
                     );
                 }
             }
@@ -2400,9 +2381,8 @@ class ResourceStorage implements ResourceStorageInterface
         if ($respectFileMounts && !empty($this->fileMounts)) {
             $mount = reset($this->fileMounts);
             return $mount['folder'];
-        } else {
-            return ResourceFactory::getInstance()->createFolderObject($this, $this->driver->getRootLevelFolder(), '');
         }
+        return $this->getResourceFactoryInstance()->createFolderObject($this, $this->driver->getRootLevelFolder(), '');
     }
 
     /**
@@ -2414,7 +2394,7 @@ class ResourceStorage implements ResourceStorageInterface
      */
     protected function emitSanitizeFileNameSignal($fileName, Folder $targetFolder)
     {
-        list($fileName) = $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_SanitizeFileName, array($fileName, $targetFolder, $this, $this->driver));
+        list($fileName) = $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_SanitizeFileName, [$fileName, $targetFolder, $this, $this->driver]);
         return $fileName;
     }
 
@@ -2428,7 +2408,7 @@ class ResourceStorage implements ResourceStorageInterface
      */
     protected function emitPreFileAddSignal($targetFileName, Folder $targetFolder, $sourceFilePath)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFileAdd, array(&$targetFileName, $targetFolder, $sourceFilePath, $this, $this->driver));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFileAdd, [&$targetFileName, $targetFolder, $sourceFilePath, $this, $this->driver]);
         return $targetFileName;
     }
 
@@ -2437,11 +2417,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param Folder $targetFolder
-     * @return void
      */
     protected function emitPostFileAddSignal(FileInterface $file, Folder $targetFolder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFileAdd, array($file, $targetFolder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFileAdd, [$file, $targetFolder]);
     }
 
     /**
@@ -2449,11 +2428,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param Folder $targetFolder
-     * @return void
      */
     protected function emitPreFileCopySignal(FileInterface $file, Folder $targetFolder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFileCopy, array($file, $targetFolder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFileCopy, [$file, $targetFolder]);
     }
 
     /**
@@ -2461,11 +2439,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param Folder $targetFolder
-     * @return void
      */
     protected function emitPostFileCopySignal(FileInterface $file, Folder $targetFolder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFileCopy, array($file, $targetFolder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFileCopy, [$file, $targetFolder]);
     }
 
     /**
@@ -2473,11 +2450,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param Folder $targetFolder
-     * @return void
      */
     protected function emitPreFileMoveSignal(FileInterface $file, Folder $targetFolder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFileMove, array($file, $targetFolder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFileMove, [$file, $targetFolder]);
     }
 
     /**
@@ -2486,11 +2462,10 @@ class ResourceStorage implements ResourceStorageInterface
      * @param FileInterface $file
      * @param Folder $targetFolder
      * @param FolderInterface $originalFolder
-     * @return void
      */
     protected function emitPostFileMoveSignal(FileInterface $file, Folder $targetFolder, FolderInterface $originalFolder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFileMove, array($file, $targetFolder, $originalFolder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFileMove, [$file, $targetFolder, $originalFolder]);
     }
 
     /**
@@ -2498,11 +2473,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param $targetFolder
-     * @return void
      */
     protected function emitPreFileRenameSignal(FileInterface $file, $targetFolder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFileRename, array($file, $targetFolder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFileRename, [$file, $targetFolder]);
     }
 
     /**
@@ -2510,11 +2484,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param string $sanitizedTargetFileName
-     * @return void
      */
     protected function emitPostFileRenameSignal(FileInterface $file, $sanitizedTargetFileName)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFileRename, array($file, $sanitizedTargetFileName));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFileRename, [$file, $sanitizedTargetFileName]);
     }
 
     /**
@@ -2522,11 +2495,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param $localFilePath
-     * @return void
      */
     protected function emitPreFileReplaceSignal(FileInterface $file, $localFilePath)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFileReplace, array($file, $localFilePath));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFileReplace, [$file, $localFilePath]);
     }
 
     /**
@@ -2534,11 +2506,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param string $localFilePath
-     * @return void
      */
     protected function emitPostFileReplaceSignal(FileInterface $file, $localFilePath)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFileReplace, array($file, $localFilePath));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFileReplace, [$file, $localFilePath]);
     }
 
     /**
@@ -2549,29 +2520,27 @@ class ResourceStorage implements ResourceStorageInterface
      */
     protected function emitPostFileCreateSignal($newFileIdentifier, Folder $targetFolder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFileCreate, array($newFileIdentifier, $targetFolder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFileCreate, [$newFileIdentifier, $targetFolder]);
     }
 
     /**
      * Emits the file pre-deletion signal.
      *
      * @param FileInterface $file
-     * @return void
      */
     protected function emitPreFileDeleteSignal(FileInterface $file)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFileDelete, array($file));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFileDelete, [$file]);
     }
 
     /**
      * Emits the file post-deletion signal
      *
      * @param FileInterface $file
-     * @return void
      */
     protected function emitPostFileDeleteSignal(FileInterface $file)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFileDelete, array($file));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFileDelete, [$file]);
     }
 
     /**
@@ -2579,11 +2548,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param FileInterface $file
      * @param mixed $content
-     * @return void
      */
     protected function emitPostFileSetContentsSignal(FileInterface $file, $content)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFileSetContents, array($file, $content));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFileSetContents, [$file, $content]);
     }
 
     /**
@@ -2591,22 +2559,20 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param Folder $targetFolder
      * @param string $name
-     * @return void
      */
     protected function emitPreFolderAddSignal(Folder $targetFolder, $name)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFolderAdd, array($targetFolder, $name));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFolderAdd, [$targetFolder, $name]);
     }
 
     /**
      * Emits the folder post-add signal.
      *
      * @param Folder $folder
-     * @return void
      */
     protected function emitPostFolderAddSignal(Folder $folder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFolderAdd, array($folder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFolderAdd, [$folder]);
     }
 
     /**
@@ -2615,11 +2581,10 @@ class ResourceStorage implements ResourceStorageInterface
      * @param Folder $folder
      * @param Folder $targetFolder
      * @param $newName
-     * @return void
      */
     protected function emitPreFolderCopySignal(Folder $folder, Folder $targetFolder, $newName)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFolderCopy, array($folder, $targetFolder, $newName));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFolderCopy, [$folder, $targetFolder, $newName]);
     }
 
     /**
@@ -2628,11 +2593,10 @@ class ResourceStorage implements ResourceStorageInterface
      * @param Folder $folder
      * @param Folder $targetFolder
      * @param $newName
-     * @return void
      */
     protected function emitPostFolderCopySignal(Folder $folder, Folder $targetFolder, $newName)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFolderCopy, array($folder, $targetFolder, $newName));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFolderCopy, [$folder, $targetFolder, $newName]);
     }
 
     /**
@@ -2641,11 +2605,10 @@ class ResourceStorage implements ResourceStorageInterface
      * @param Folder $folder
      * @param Folder $targetFolder
      * @param $newName
-     * @return void
      */
     protected function emitPreFolderMoveSignal(Folder $folder, Folder $targetFolder, $newName)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFolderMove, array($folder, $targetFolder, $newName));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFolderMove, [$folder, $targetFolder, $newName]);
     }
 
     /**
@@ -2655,11 +2618,10 @@ class ResourceStorage implements ResourceStorageInterface
      * @param Folder $targetFolder
      * @param string $newName
      * @param Folder $originalFolder
-     * @return void
      */
     protected function emitPostFolderMoveSignal(Folder $folder, Folder $targetFolder, $newName, Folder $originalFolder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFolderMove, array($folder, $targetFolder, $newName, $originalFolder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFolderMove, [$folder, $targetFolder, $newName, $originalFolder]);
     }
 
     /**
@@ -2667,11 +2629,10 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param Folder $folder
      * @param string $newName
-     * @return void
      */
     protected function emitPreFolderRenameSignal(Folder $folder, $newName)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFolderRename, array($folder, $newName));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFolderRename, [$folder, $newName]);
     }
 
     /**
@@ -2679,33 +2640,30 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param Folder $folder
      * @param string $newName
-     * @return void
      */
     protected function emitPostFolderRenameSignal(Folder $folder, $newName)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFolderRename, array($folder, $newName));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFolderRename, [$folder, $newName]);
     }
 
     /**
      * Emits the folder pre-deletion signal.
      *
      * @param Folder $folder
-     * @return void
      */
     protected function emitPreFolderDeleteSignal(Folder $folder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreFolderDelete, array($folder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreFolderDelete, [$folder]);
     }
 
     /**
      * Emits folder post-deletion signal..
      *
      * @param Folder $folder
-     * @return void
      */
     protected function emitPostFolderDeleteSignal(Folder $folder)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PostFolderDelete, array($folder));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PostFolderDelete, [$folder]);
     }
 
     /**
@@ -2717,15 +2675,15 @@ class ResourceStorage implements ResourceStorageInterface
      */
     protected function emitPreGeneratePublicUrlSignal(ResourceInterface $resourceObject, $relativeToCurrentScript, array $urlData)
     {
-        $this->getSignalSlotDispatcher()->dispatch(ResourceStorage::class, self::SIGNAL_PreGeneratePublicUrl, array($this, $this->driver, $resourceObject, $relativeToCurrentScript, $urlData));
+        $this->getSignalSlotDispatcher()->dispatch(self::class, self::SIGNAL_PreGeneratePublicUrl, [$this, $this->driver, $resourceObject, $relativeToCurrentScript, $urlData]);
     }
 
     /**
      * Returns the destination path/fileName of a unique fileName/foldername in that path.
      * If $theFile exists in $theDest (directory) the file have numbers appended up to $this->maxNumber. Hereafter a unique string will be appended.
-     * This function is used by fx. TCEmain when files are attached to records and needs to be uniquely named in the uploads/* folders
+     * This function is used by fx. DataHandler when files are attached to records and needs to be uniquely named in the uploads/* folders
      *
-     * @param Folder $folder
+     * @param FolderInterface $folder
      * @param string $theFile The input fileName to check
      * @param bool $dontCheckForUnique If set the fileName is returned with the path prepended without checking whether it already existed!
      *
@@ -2733,7 +2691,7 @@ class ResourceStorage implements ResourceStorageInterface
      * @return string A unique fileName inside $folder, based on $theFile.
      * @see \TYPO3\CMS\Core\Utility\File\BasicFileUtility::getUniqueName()
      */
-    protected function getUniqueName(Folder $folder, $theFile, $dontCheckForUnique = false)
+    protected function getUniqueName(FolderInterface $folder, $theFile, $dontCheckForUnique = false)
     {
         static $maxNumber = 99, $uniqueNamePrefix = '';
         // Fetches info about path, name, extension of $theFile
@@ -2870,27 +2828,47 @@ class ResourceStorage implements ResourceStorageInterface
             try {
                 if (strpos($processingFolder, ':') !== false) {
                     list($storageUid, $processingFolderIdentifier) = explode(':', $processingFolder, 2);
-                    $storage = ResourceFactory::getInstance()->getStorageObject($storageUid);
+                    $storage = $this->getResourceFactoryInstance()->getStorageObject($storageUid);
                     if ($storage->hasFolder($processingFolderIdentifier)) {
                         $this->processingFolder = $storage->getFolder($processingFolderIdentifier);
                     } else {
-                        $this->processingFolder = $storage->createFolder(ltrim($processingFolderIdentifier, '/'));
+                        $rootFolder = $storage->getRootLevelFolder(false);
+                        $currentEvaluatePermissions = $storage->getEvaluatePermissions();
+                        $storage->setEvaluatePermissions(false);
+                        $this->processingFolder = $storage->createFolder(
+                            ltrim($processingFolderIdentifier, '/'),
+                            $rootFolder
+                        );
+                        $storage->setEvaluatePermissions($currentEvaluatePermissions);
                     }
                 } else {
                     if ($this->driver->folderExists($processingFolder) === false) {
-                        $this->processingFolder = $this->createFolder($processingFolder);
+                        $rootFolder = $this->getRootLevelFolder(false);
+                        $currentEvaluatePermissions = $this->evaluatePermissions;
+                        $this->evaluatePermissions = false;
+                        $this->processingFolder = $this->createFolder(
+                            $processingFolder,
+                            $rootFolder
+                        );
+                        $this->evaluatePermissions = $currentEvaluatePermissions;
                     } else {
                         $data = $this->driver->getFolderInfoByIdentifier($processingFolder);
-                        $this->processingFolder = ResourceFactory::getInstance()->createFolderObject($this, $data['identifier'], $data['name']);
+                        $this->processingFolder = $this->getResourceFactoryInstance()->createFolderObject($this, $data['identifier'], $data['name']);
                     }
                 }
             } catch (Exception\InsufficientFolderWritePermissionsException $e) {
                 $this->processingFolder = GeneralUtility::makeInstance(
-                    InaccessibleFolder::class, $this, $processingFolder, $processingFolder
+                    InaccessibleFolder::class,
+                    $this,
+                    $processingFolder,
+                    $processingFolder
                 );
             } catch (Exception\ResourcePermissionsUnavailableException $e) {
                 $this->processingFolder = GeneralUtility::makeInstance(
-                    InaccessibleFolder::class, $this, $processingFolder, $processingFolder
+                    InaccessibleFolder::class,
+                    $this,
+                    $processingFolder,
+                    $processingFolder
                 );
             }
         }
@@ -2924,7 +2902,10 @@ class ResourceStorage implements ResourceStorageInterface
                 if ($processingFolder->hasFolder($folderName)) {
                     $processingFolder = $processingFolder->getSubfolder($folderName);
                 } else {
+                    $currentEvaluatePermissions = $processingFolder->getStorage()->getEvaluatePermissions();
+                    $processingFolder->getStorage()->setEvaluatePermissions(false);
                     $processingFolder = $processingFolder->createFolder($folderName);
+                    $processingFolder->getStorage()->setEvaluatePermissions($currentEvaluatePermissions);
                 }
             }
         } catch (Exception\FolderDoesNotExistException $e) {
@@ -2938,7 +2919,7 @@ class ResourceStorage implements ResourceStorageInterface
      *
      * @param string $fileIdentifier
      * @param int $levels
-     * @return []
+     * @return string[]
      */
     protected function getNamesForNestedProcessingFolder($fileIdentifier, $levels)
     {
@@ -2975,7 +2956,6 @@ class ResourceStorage implements ResourceStorageInterface
 
     /**
      * @param bool $isDefault
-     * @return void
      */
     public function setDefault($isDefault)
     {
@@ -2991,10 +2971,20 @@ class ResourceStorage implements ResourceStorageInterface
     }
 
     /**
-     * @return DatabaseConnection
+     * @return ResourceFactory
+     */
+    public function getResourceFactoryInstance(): ResourceFactory
+    {
+        return ResourceFactory::getInstance();
+    }
+
+    /**
+     * Returns the current BE user.
+     *
+     * @return \TYPO3\CMS\Core\Authentication\BackendUserAuthentication
      */
-    protected function getDatabaseConnection()
+    protected function getBackendUser()
     {
-        return $GLOBALS['TYPO3_DB'];
+        return $GLOBALS['BE_USER'];
     }
 }