[TASK][!!!] Extend FAL Api for more efficient usage 63/25363/4
authorSteffen Ritter <info@rs-websystems.de>
Wed, 13 Nov 2013 09:03:49 +0000 (10:03 +0100)
committerSteffen Ritter <info@rs-websystems.de>
Wed, 13 Nov 2013 16:09:45 +0000 (17:09 +0100)
This changeset extends the Driver-API to allow the ResourceStorage
to list Files in a Folder (recursively) without getting the whole
FileInformation array. Extracting the FileInformation is very
expensive in terms of IO and runtime.

Additionally when doing IndexMaintenance it might be useful to
check if the File changed (content-wise) and therefore must be
hashed. While indexing you might not yet have a FileObject
since you are just about to create it. Therefore a HashFile
Method in ResourceStorage is extended to do that just based on
the Identifier.

Since this change already breaks the Driver API and we decided
that architecturally it is not wise, that the driver knows
about object and not only about identifiers, the hash method
is changed accordingly there, too.

Since only the ResourceStorage is allowed to access the Driver
objects directly this is only relevant for custom driver
implementations.

Releases: 6.2
Resolves: #53585
Change-Id: I6ec47e9071550826aab4f4886700772254cfc8d0
Reviewed-on: https://review.typo3.org/25363
Reviewed-by: Steffen Ritter
Tested-by: Steffen Ritter
typo3/sysext/core/Classes/Resource/Driver/AbstractDriver.php
typo3/sysext/core/Classes/Resource/Driver/LocalDriver.php
typo3/sysext/core/Classes/Resource/ResourceStorage.php

index ef41420..7d679f0 100644 (file)
@@ -246,11 +246,11 @@ abstract class AbstractDriver {
         * Creates a (cryptographic) hash for a file.
         *
         * @abstract
-        * @param FileInterface $file
+        * @param string $fileIdentifier
         * @param string $hashAlgorithm The hash algorithm to use
         * @return string
         */
-       abstract public function hash(FileInterface $file, $hashAlgorithm);
+       abstract public function hash($fileIdentifier, $hashAlgorithm);
 
        /**
         * Hashes a file identifier, taking the case sensitivity of the file system
@@ -519,14 +519,26 @@ abstract class AbstractDriver {
         * @param array $filenameFilterCallbacks The method callbacks to use for filtering the items
         * @param array $fileData Two-dimensional, identifier-indexed array of file index records from the database
         * @param boolean $recursive
+        * @deprecated since TYPO3 CMS 6.2 LTS, will be removed 2 versions Later
         * @return array
         */
-       // TODO add unit tests
        public function getFileList($path, $start = 0, $numberOfItems = 0, array $filenameFilterCallbacks = array(), $fileData = array(), $recursive = FALSE) {
+               \TYPO3\CMS\Core\Utility\GeneralUtility::logDeprecatedFunction();
                return $this->getDirectoryItemList($path, $start, $numberOfItems, $filenameFilterCallbacks, $this->fileListCallbackMethod, $fileData, $recursive);
        }
 
        /**
+        * Returns a list of files inside the specified path
+        *
+        * @param string $folderIdentifier
+        * @param boolean $recursive
+        * @param array $filenameFilterCallbacks The method callbacks to use for filtering the items
+        * @return array of FileIdentifiers
+        */
+       abstract public function getFileIdentifierListInFolder($folderIdentifier, $recursive = FALSE, array $filenameFilterCallbacks = array());
+
+
+       /**
         * Copies a file to a temporary path and returns that path.
         *
         * @abstract
index 03ca9d7..a195e83 100644 (file)
@@ -380,6 +380,38 @@ class LocalDriver extends AbstractHierarchicalFilesystemDriver {
        }
 
        /**
+        * Returns a list of files inside the specified path
+        *
+        * @param string $folderIdentifier
+        * @param boolean $recursive
+        * @param array $filenameFilterCallbacks The method callbacks to use for filtering the items
+        *
+        * @return array of FileIdentifiers
+        */
+       public function getFileIdentifierListInFolder($folderIdentifier, $recursive = FALSE, array $filenameFilterCallbacks = array()) {
+               return array_values($this->getDirectoryItemList($folderIdentifier, 0, 0, $filenameFilterCallbacks, 'getFileList_itemCallbackIdentifierOnly', array(), $recursive));
+       }
+
+
+       /**
+        * Handler for items in a file list.
+        *
+        * @param string $fileName
+        * @param string $path
+        * @return array
+        */
+       protected function getFileList_itemCallbackIdentifierOnly($fileName, $path) {
+               $file = $path . $fileName;
+               $filePath = $this->getAbsolutePath($file);
+               if (!is_file($filePath)) {
+                       return array('', array());
+               }
+               return array($file, $file);
+       }
+
+
+
+       /**
         * Handler for items in a file list.
         *
         * @param string $fileName
@@ -601,22 +633,22 @@ class LocalDriver extends AbstractHierarchicalFilesystemDriver {
        /**
         * Creates a (cryptographic) hash for a file.
         *
-        * @param FileInterface $file
+        * @param string $fileIdentifier
         * @param string $hashAlgorithm The hash algorithm to use
         * @return string
         * @throws \RuntimeException
         * @throws \InvalidArgumentException
         */
-       public function hash(FileInterface $file, $hashAlgorithm) {
+       public function hash($fileIdentifier, $hashAlgorithm) {
                if (!in_array($hashAlgorithm, $this->getSupportedHashAlgorithms())) {
                        throw new \InvalidArgumentException('Hash algorithm "' . $hashAlgorithm . '" is not supported.', 1304964032);
                }
                switch ($hashAlgorithm) {
                        case 'sha1':
-                               $hash = sha1_file($this->getAbsolutePath($file));
+                               $hash = sha1_file($this->getAbsolutePath($fileIdentifier));
                                break;
                        case 'md5':
-                               $hash = md5_file($this->getAbsolutePath($file));
+                               $hash = md5_file($this->getAbsolutePath($fileIdentifier));
                                break;
                        default:
                                throw new \RuntimeException('Hash algorithm ' . $hashAlgorithm . ' is not implemented.', 1329644451);
index 5257c0c..0b35ee8 100644 (file)
@@ -1136,11 +1136,23 @@ class ResourceStorage {
         * Creates a (cryptographic) hash for a file.
         *
         * @param FileInterface $fileObject
-        * @param $hash
+        * @param string $hash
         * @return string
         */
        public function hashFile(FileInterface $fileObject, $hash) {
-               return $this->driver->hash($fileObject, $hash);
+               return $this->hashFileByIdentifier($fileObject->getIdentifier(), $hash);
+       }
+
+       /**
+        * Creates a (cryptographic) hash for a fileIdentifier.
+
+        * @param string $fileIdentifier
+        * @param string $hash
+        *
+        * @return string
+        */
+       public function hashFileByIdentifier($fileIdentifier, $hash) {
+               return $this->driver->hash($fileIdentifier, $hash);
        }
 
        /**
@@ -1235,6 +1247,7 @@ class ResourceStorage {
         *
         * @param FileInterface $fileObject
         * @return array
+        * @internal
         */
        public function getFileInfo(FileInterface $fileObject) {
                return $this->driver->getFileInfo($fileObject);
@@ -1244,12 +1257,12 @@ class ResourceStorage {
         * Get information about a file by its identifier
         *
         * @param string $identifier
-        *
+        * @param array $propertiesToExtract
         * @return array
         * @internal
         */
-       public function getFileInfoByIdentifier($identifier) {
-               return $this->driver->getFileInfoByIdentifier($identifier);
+       public function getFileInfoByIdentifier($identifier, array $propertiesToExtract = array()) {
+               return $this->driver->getFileInfoByIdentifier($identifier, $propertiesToExtract);
        }
 
        /**
@@ -1328,6 +1341,19 @@ class ResourceStorage {
                return $items;
        }
 
+
+       /**
+        * @param string $folderIdentifier
+        * @param boolean $useFilters
+        * @param boolean $recursive
+        *
+        * @return array
+        */
+       public function getFileIdentifiersInFolder($folderIdentifier, $useFilters = TRUE, $recursive = FALSE) {
+               $filters = $useFilters == TRUE ? $this->fileAndFolderNameFilters : array();
+               return $this->driver->getFileIdentifierListInFolder($folderIdentifier, $recursive, $filters);
+       }
+
        /**
         * Returns TRUE if the specified file exists.
         *
@@ -2386,4 +2412,13 @@ class ResourceStorage {
                }
                return $this->processingFolder;
        }
+
+       /**
+        * Gets the driver Type configured for this storage
+        *
+        * @return string
+        */
+       public function getDriverType() {
+               return $this->storageRecord['driver'];
+       }
 }