[!!!][TASK] Remove deprecated code in EXT:core
[Packages/TYPO3.CMS.git] / typo3 / sysext / core / Classes / Resource / Filter / FileExtensionFilter.php
1 <?php
2 namespace TYPO3\CMS\Core\Resource\Filter;
3
4 /*
5 * This file is part of the TYPO3 CMS project.
6 *
7 * It is free software; you can redistribute it and/or modify it under
8 * the terms of the GNU General Public License, either version 2
9 * of the License, or any later version.
10 *
11 * For the full copyright and license information, please read the
12 * LICENSE.txt file that was distributed with this source code.
13 *
14 * The TYPO3 project - inspiring people to share!
15 */
16
17 use TYPO3\CMS\Core\DataHandling\DataHandler;
18 use TYPO3\CMS\Core\Resource\Driver\DriverInterface;
19 use TYPO3\CMS\Core\Resource\Exception\FileDoesNotExistException;
20 use TYPO3\CMS\Core\Resource\ResourceFactory;
21 use TYPO3\CMS\Core\Utility\GeneralUtility;
22
23 /**
24 * Utility methods for filtering filenames
25 */
26 class FileExtensionFilter
27 {
28 /**
29 * Allowed file extensions. If NULL, all extensions are allowed.
30 *
31 * @var array
32 */
33 protected $allowedFileExtensions;
34
35 /**
36 * Disallowed file extensions. If NULL, no extension is disallowed (i.e. all are allowed).
37 *
38 * @var array
39 */
40 protected $disallowedFileExtensions;
41
42 /**
43 * Entry method for use as DataHandler "inline" field filter
44 *
45 * @param array $parameters
46 * @param DataHandler $dataHandler
47 * @return array
48 */
49 public function filterInlineChildren(array $parameters, DataHandler $dataHandler)
50 {
51 $values = $parameters['values'];
52 if ($parameters['allowedFileExtensions']) {
53 $this->setAllowedFileExtensions($parameters['allowedFileExtensions']);
54 }
55 if ($parameters['disallowedFileExtensions']) {
56 $this->setDisallowedFileExtensions($parameters['disallowedFileExtensions']);
57 }
58 $cleanValues = [];
59 if (is_array($values)) {
60 foreach ($values as $value) {
61 if (empty($value)) {
62 continue;
63 }
64 $parts = GeneralUtility::revExplode('_', $value, 2);
65 $fileReferenceUid = $parts[count($parts) - 1];
66 try {
67 $fileReference = ResourceFactory::getInstance()->getFileReferenceObject($fileReferenceUid);
68 $file = $fileReference->getOriginalFile();
69 if ($this->isAllowed($file->getExtension())) {
70 $cleanValues[] = $value;
71 } else {
72 // Remove the erroneously created reference record again
73 $dataHandler->deleteAction('sys_file_reference', $fileReferenceUid);
74 }
75 } catch (FileDoesNotExistException $e) {
76 // do nothing
77 }
78 }
79 }
80 return $cleanValues;
81 }
82
83 /**
84 * Entry method for use as filelist filter.
85 *
86 * We have to use -1 as the „don't include“ return value, as call_user_func() will return FALSE
87 * if calling the method failed and thus we can't use that as a return value.
88 *
89 * @param string $itemName
90 * @param string $itemIdentifier
91 * @param string $parentIdentifier
92 * @param array $additionalInformation Additional information about the inspected item
93 * @param DriverInterface $driver
94 * @return bool|int -1 if the file should not be included in a listing
95 */
96 public function filterFileList($itemName, $itemIdentifier, $parentIdentifier, array $additionalInformation, DriverInterface $driver)
97 {
98 $returnCode = true;
99 // Early return in case no file filters are set at all
100 if ($this->allowedFileExtensions === null && $this->disallowedFileExtensions === null) {
101 return $returnCode;
102 }
103 // Check that this is a file and not a folder
104 if ($driver->fileExists($itemIdentifier)) {
105 try {
106 $fileInfo = $driver->getFileInfoByIdentifier($itemIdentifier, ['extension']);
107 } catch (\InvalidArgumentException $e) {
108 $fileInfo = [];
109 }
110 if (!$this->isAllowed($fileInfo['extension'] ?? '')) {
111 $returnCode = -1;
112 }
113 }
114 return $returnCode;
115 }
116
117 /**
118 * Checks whether a file is allowed according to the criteria defined in the class variables ($this->allowedFileExtensions etc.)
119 *
120 * @param string $fileExt
121 * @return bool
122 */
123 protected function isAllowed($fileExt)
124 {
125 $fileExt = strtolower($fileExt);
126 $result = true;
127 // Check allowed file extensions
128 if ($this->allowedFileExtensions !== null && !empty($this->allowedFileExtensions) && !in_array($fileExt, $this->allowedFileExtensions)) {
129 $result = false;
130 }
131 // Check disallowed file extensions
132 if ($this->disallowedFileExtensions !== null && !empty($this->disallowedFileExtensions) && in_array($fileExt, $this->disallowedFileExtensions)) {
133 $result = false;
134 }
135 return $result;
136 }
137
138 /**
139 * Set allowed file extensions
140 *
141 * @param mixed $allowedFileExtensions Comma-separated list or array, of allowed file extensions
142 */
143 public function setAllowedFileExtensions($allowedFileExtensions)
144 {
145 $this->allowedFileExtensions = $this->convertToLowercaseArray($allowedFileExtensions);
146 }
147
148 /**
149 * Set disallowed file extensions
150 *
151 * @param mixed $disallowedFileExtensions Comma-separated list or array, of allowed file extensions
152 */
153 public function setDisallowedFileExtensions($disallowedFileExtensions)
154 {
155 $this->disallowedFileExtensions = $this->convertToLowercaseArray($disallowedFileExtensions);
156 }
157
158 /**
159 * Converts mixed (string or array) input arguments into an array, NULL if empty.
160 *
161 * All array values will be converted to lower case.
162 *
163 * @param mixed $inputArgument Comma-separated list or array.
164 * @return array
165 */
166 protected function convertToLowercaseArray($inputArgument)
167 {
168 $returnValue = null;
169 if (is_array($inputArgument)) {
170 $returnValue = $inputArgument;
171 } elseif ((string)$inputArgument !== '') {
172 $returnValue = GeneralUtility::trimExplode(',', $inputArgument);
173 }
174
175 if (is_array($returnValue)) {
176 $returnValue = array_map('strtolower', $returnValue);
177 }
178
179 return $returnValue;
180 }
181 }