‪TYPO3CMS  11.5
MetaDataRepository.php
Go to the documentation of this file.
1 <?php
2 
3 /*
4  * This file is part of the TYPO3 CMS project.
5  *
6  * It is free software; you can redistribute it and/or modify it under
7  * the terms of the GNU General Public License, either version 2
8  * of the License, or any later version.
9  *
10  * For the full copyright and license information, please read the
11  * LICENSE.txt file that was distributed with this source code.
12  *
13  * The TYPO3 project - inspiring people to share!
14  */
15 
17 
18 use Doctrine\DBAL\Platforms\PostgreSQL94Platform as PostgreSQLPlatform;
19 use Doctrine\DBAL\Platforms\SQLServer2012Platform as SQLServerPlatform;
20 use Psr\EventDispatcher\EventDispatcherInterface;
33 
41 {
45  protected ‪$tableName = 'sys_file_metadata';
46 
52  protected ‪$tableFields = [];
53 
57  protected ‪$eventDispatcher;
58 
59  public function ‪__construct(EventDispatcherInterface ‪$eventDispatcher)
60  {
61  $this->eventDispatcher = ‪$eventDispatcher;
62  }
63 
70  public function ‪findByFile(‪File $file)
71  {
72  $record = $this->‪findByFileUid($file->‪getUid());
73 
74  // It could be possible that the meta information is freshly
75  // created and inserted into the database. If this is the case
76  // we have to take care about correct meta information for width and
77  // height in case of an image.
78  // This logic can be transferred into a custom PSR-14 event listener in the future by just using
79  // the AfterMetaDataCreated event.
80  if (!empty($record['crdate']) && (int)$record['crdate'] === ‪$GLOBALS['EXEC_TIME']) {
81  if ($file->‪getType() === ‪File::FILETYPE_IMAGE && $file->‪getStorage()->‪getDriverType() === 'Local') {
82  $fileNameAndPath = $file->‪getForLocalProcessing(false);
83 
84  $imageInfo = GeneralUtility::makeInstance(ImageInfo::class, $fileNameAndPath);
85 
86  $additionalMetaInformation = [
87  'width' => $imageInfo->getWidth(),
88  'height' => $imageInfo->getHeight(),
89  ];
90 
91  $this->‪update($file->‪getUid(), $additionalMetaInformation);
92  }
93  $record = $this->‪findByFileUid($file->‪getUid());
94  }
95 
96  return $record;
97  }
98 
106  public function ‪findByFileUid($uid)
107  {
108  $uid = (int)$uid;
109  if ($uid <= 0) {
110  throw new ‪InvalidUidException('Metadata can only be retrieved for indexed files. UID: "' . $uid . '"', 1381590731);
111  }
112 
113  $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable($this->tableName);
114 
115  $queryBuilder->getRestrictions()->add(GeneralUtility::makeInstance(RootLevelRestriction::class));
116 
117  $record = $queryBuilder
118  ->select('*')
119  ->from($this->tableName)
120  ->where(
121  $queryBuilder->expr()->eq('file', $queryBuilder->createNamedParameter($uid, ‪Connection::PARAM_INT)),
122  $queryBuilder->expr()->in('sys_language_uid', $queryBuilder->createNamedParameter([0, -1], Connection::PARAM_INT_ARRAY))
123  )
124  ->executeQuery()
125  ->fetchAssociative();
126 
127  if (empty($record)) {
128  return [];
129  }
130 
131  return $this->eventDispatcher->dispatch(new ‪EnrichFileMetaDataEvent($uid, (int)$record['uid'], $record))->getRecord();
132  }
133 
141  public function ‪createMetaDataRecord($fileUid, array $additionalFields = [])
142  {
143  $emptyRecord = [
144  'file' => (int)$fileUid,
145  'pid' => 0,
146  'crdate' => ‪$GLOBALS['EXEC_TIME'],
147  'tstamp' => ‪$GLOBALS['EXEC_TIME'],
148  'cruser_id' => isset(‪$GLOBALS['BE_USER']->user['uid']) ? (int)‪$GLOBALS['BE_USER']->user['uid'] : 0,
149  'l10n_diffsource' => '',
150  ];
151  $additionalFields = array_intersect_key($additionalFields, $this->‪getTableFields());
152  $emptyRecord = array_merge($emptyRecord, $additionalFields);
153 
154  $connection = GeneralUtility::makeInstance(ConnectionPool::class)->getConnectionForTable($this->tableName);
155  $connection->insert(
156  $this->tableName,
157  $emptyRecord,
158  ['l10n_diffsource' => ‪Connection::PARAM_LOB]
159  );
160 
161  $record = $emptyRecord;
162  $record['uid'] = $connection->lastInsertId($this->tableName);
163 
164  return $this->eventDispatcher->dispatch(new ‪AfterFileMetaDataCreatedEvent($fileUid, (int)$record['uid'], $record))->getRecord();
165  }
166 
174  public function ‪update($fileUid, array $data)
175  {
176  $updateRow = array_intersect_key($data, $this->‪getTableFields());
177  if (array_key_exists('uid', $updateRow)) {
178  unset($updateRow['uid']);
179  }
180  $row = $this->‪findByFileUid($fileUid);
181  if (!empty($updateRow)) {
182  $updateRow['tstamp'] = time();
183  $connection = GeneralUtility::makeInstance(ConnectionPool::class)->getConnectionForTable($this->tableName);
184  $types = [];
185  $platform = $connection->getDatabasePlatform();
186  if ($platform instanceof SQLServerPlatform || $platform instanceof PostgreSQLPlatform) {
187  // mssql and postgres needs to set proper PARAM_LOB and others to update fields.
188  $tableDetails = $connection->createSchemaManager()->listTableDetails($this->tableName);
189  foreach ($updateRow as $columnName => $columnValue) {
190  $types[$columnName] = $tableDetails->getColumn($columnName)->getType()->getBindingType();
191  }
192  }
193  $connection->update(
194  $this->tableName,
195  $updateRow,
196  [
197  'uid' => (int)$row['uid'],
198  ],
199  $types
200  );
201 
202  $this->eventDispatcher->dispatch(new ‪AfterFileMetaDataUpdatedEvent($fileUid, (int)$row['uid'], array_merge($row, $updateRow)));
203  }
204  }
205 
211  public function ‪removeByFileUid($fileUid)
212  {
213  GeneralUtility::makeInstance(ConnectionPool::class)
214  ->getConnectionForTable($this->tableName)
215  ->delete(
216  $this->tableName,
217  [
218  'file' => (int)$fileUid,
219  ]
220  );
221 
222  $this->eventDispatcher->dispatch(new ‪AfterFileMetaDataDeletedEvent((int)$fileUid));
223  }
224 
230  protected function ‪getTableFields(): array
231  {
232  if (empty($this->tableFields)) {
233  $this->tableFields = GeneralUtility::makeInstance(ConnectionPool::class)
234  ->getConnectionForTable($this->tableName)
235  ->createSchemaManager()
236  ->listTableColumns($this->tableName);
237  }
238 
239  return ‪$this->tableFields;
240  }
241 
246  public static function ‪getInstance()
247  {
248  trigger_error(__CLASS__ . '::getInstance() will be removed in TYPO3 v12.0. Use Dependency Injection or GeneralUtility::makeInstance() if DI is not possible.', E_USER_DEPRECATED);
249  return GeneralUtility::makeInstance(self::class);
250  }
251 }
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository
Definition: MetaDataRepository.php:41
‪TYPO3\CMS\Core\Resource\AbstractFile\getType
‪int getType()
Definition: AbstractFile.php:291
‪TYPO3\CMS\Core\Database\Connection\PARAM_INT
‪const PARAM_INT
Definition: Connection.php:49
‪TYPO3\CMS\Core\Resource\AbstractFile\getForLocalProcessing
‪string getForLocalProcessing($writable=true)
Definition: AbstractFile.php:583
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\findByFileUid
‪array findByFileUid($uid)
Definition: MetaDataRepository.php:103
‪TYPO3\CMS\Core\Resource\ResourceStorage\getDriverType
‪string getDriverType()
Definition: ResourceStorage.php:2904
‪TYPO3\CMS\Core\Resource\Event\AfterFileMetaDataDeletedEvent
Definition: AfterFileMetaDataDeletedEvent.php:25
‪TYPO3\CMS\Core\Resource\Event\AfterFileMetaDataCreatedEvent
Definition: AfterFileMetaDataCreatedEvent.php:25
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\getTableFields
‪array getTableFields()
Definition: MetaDataRepository.php:227
‪TYPO3\CMS\Core\Resource\Exception\InvalidUidException
Definition: InvalidUidException.php:23
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\findByFile
‪array findByFile(File $file)
Definition: MetaDataRepository.php:67
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\removeByFileUid
‪removeByFileUid($fileUid)
Definition: MetaDataRepository.php:208
‪TYPO3\CMS\Core\Resource\AbstractFile\FILETYPE_IMAGE
‪const FILETYPE_IMAGE
Definition: AbstractFile.php:78
‪TYPO3\CMS\Core\Database\Query\Restriction\RootLevelRestriction
Definition: RootLevelRestriction.php:27
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\getInstance
‪static MetaDataRepository getInstance()
Definition: MetaDataRepository.php:243
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\__construct
‪__construct(EventDispatcherInterface $eventDispatcher)
Definition: MetaDataRepository.php:56
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\$eventDispatcher
‪EventDispatcherInterface $eventDispatcher
Definition: MetaDataRepository.php:54
‪TYPO3\CMS\Core\Resource\File
Definition: File.php:24
‪TYPO3\CMS\Core\Resource\AbstractFile\getUid
‪int getUid()
Definition: AbstractFile.php:203
‪TYPO3\CMS\Core\Resource\Event\EnrichFileMetaDataEvent
Definition: EnrichFileMetaDataEvent.php:26
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\$tableName
‪string $tableName
Definition: MetaDataRepository.php:44
‪TYPO3\CMS\Core\Resource\Index
Definition: ExtractorInterface.php:16
‪TYPO3\CMS\Core\Type\File\ImageInfo
Definition: ImageInfo.php:28
‪TYPO3\CMS\Core\Database\Connection
Definition: Connection.php:38
‪TYPO3\CMS\Core\SingletonInterface
Definition: SingletonInterface.php:22
‪$GLOBALS
‪$GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['adminpanel']['modules']
Definition: ext_localconf.php:25
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\$tableFields
‪array $tableFields
Definition: MetaDataRepository.php:50
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\update
‪update($fileUid, array $data)
Definition: MetaDataRepository.php:171
‪TYPO3\CMS\Core\Resource\Event\AfterFileMetaDataUpdatedEvent
Definition: AfterFileMetaDataUpdatedEvent.php:24
‪TYPO3\CMS\Core\Database\ConnectionPool
Definition: ConnectionPool.php:46
‪TYPO3\CMS\Core\Utility\GeneralUtility
Definition: GeneralUtility.php:50
‪TYPO3\CMS\Core\Resource\Index\MetaDataRepository\createMetaDataRecord
‪array createMetaDataRecord($fileUid, array $additionalFields=[])
Definition: MetaDataRepository.php:138
‪TYPO3\CMS\Core\Database\Connection\PARAM_LOB
‪const PARAM_LOB
Definition: Connection.php:59
‪TYPO3\CMS\Core\Resource\AbstractFile\getStorage
‪ResourceStorage getStorage()
Definition: AbstractFile.php:395