[TASK] Move RecordHistory into DataHandling namespace
[Packages/TYPO3.CMS.git] / typo3 / sysext / recycler / Classes / Controller / DeletedRecordsController.php
1 <?php
2
3 namespace TYPO3\CMS\Recycler\Controller;
4
5 /*
6 * This file is part of the TYPO3 CMS project.
7 *
8 * It is free software; you can redistribute it and/or modify it under
9 * the terms of the GNU General Public License, either version 2
10 * of the License, or any later version.
11 *
12 * For the full copyright and license information, please read the
13 * LICENSE.txt file that was distributed with this source code.
14 *
15 * The TYPO3 project - inspiring people to share!
16 */
17
18 use TYPO3\CMS\Backend\Utility\BackendUtility;
19 use TYPO3\CMS\Core\Cache\CacheManager;
20 use TYPO3\CMS\Core\Database\ConnectionPool;
21 use TYPO3\CMS\Core\DataHandling\DataHandler;
22 use TYPO3\CMS\Core\DataHandling\History\RecordHistoryStore;
23 use TYPO3\CMS\Core\Imaging\Icon;
24 use TYPO3\CMS\Core\Imaging\IconFactory;
25 use TYPO3\CMS\Core\Utility\GeneralUtility;
26 use TYPO3\CMS\Recycler\Utility\RecyclerUtility;
27
28 /**
29 * Deleted Records View
30 */
31 class DeletedRecordsController
32 {
33 /**
34 * @var \TYPO3\CMS\Core\Cache\Frontend\FrontendInterface
35 */
36 protected $runtimeCache;
37
38 /**
39 * @var DataHandler
40 */
41 protected $tce;
42
43 public function __construct()
44 {
45 $this->runtimeCache = $this->getMemoryCache();
46 $this->tce = GeneralUtility::makeInstance(DataHandler::class);
47 }
48
49 /**
50 * Transforms the rows for the deleted records
51 *
52 * @param array $deletedRowsArray Array with table as key and array with all deleted rows
53 * @return array JSON array
54 */
55 public function transform($deletedRowsArray)
56 {
57 $jsonArray = [
58 'rows' => []
59 ];
60
61 if (is_array($deletedRowsArray)) {
62 $lang = $this->getLanguageService();
63 $iconFactory = GeneralUtility::makeInstance(IconFactory::class);
64
65 foreach ($deletedRowsArray as $table => $rows) {
66 foreach ($rows as $row) {
67 $pageTitle = $this->getPageTitle((int)$row['pid']);
68 $backendUserName = $this->getBackendUser((int)$row[$GLOBALS['TCA'][$table]['ctrl']['cruser_id']]);
69 $userIdWhoDeleted = $this->getUserWhoDeleted($table, (int)$row['uid']);
70
71 $jsonArray['rows'][] = [
72 'uid' => $row['uid'],
73 'pid' => $row['pid'],
74 'icon' => $iconFactory->getIconForRecord($table, $row, Icon::SIZE_SMALL)->render(),
75 'pageTitle' => $pageTitle,
76 'table' => $table,
77 'crdate' => BackendUtility::datetime($row[$GLOBALS['TCA'][$table]['ctrl']['crdate']]),
78 'tstamp' => BackendUtility::datetime($row[$GLOBALS['TCA'][$table]['ctrl']['tstamp']]),
79 'owner' => htmlspecialchars($backendUserName),
80 'owner_uid' => $row[$GLOBALS['TCA'][$table]['ctrl']['cruser_id']],
81 'tableTitle' => $lang->sL($GLOBALS['TCA'][$table]['ctrl']['title']),
82 'title' => htmlspecialchars(BackendUtility::getRecordTitle($table, $row)),
83 'path' => RecyclerUtility::getRecordPath($row['pid']),
84 'delete_user_uid' => $userIdWhoDeleted,
85 'delete_user' => $this->getBackendUser($userIdWhoDeleted),
86 'isParentDeleted' => $table === 'pages' ? RecyclerUtility::isParentPageDeleted($row['pid']) : false
87 ];
88 }
89 }
90 }
91 return $jsonArray;
92 }
93
94 /**
95 * Gets the page title of the given page id
96 *
97 * @param int $pageId
98 * @return string
99 */
100 protected function getPageTitle($pageId)
101 {
102 $cacheId = 'recycler-pagetitle-' . $pageId;
103 if ($this->runtimeCache->has($cacheId)) {
104 $pageTitle = $this->runtimeCache->get($cacheId);
105 } else {
106 if ($pageId === 0) {
107 $pageTitle = $GLOBALS['TYPO3_CONF_VARS']['SYS']['sitename'];
108 } else {
109 $recordInfo = $this->tce->recordInfo('pages', $pageId, 'title');
110 $pageTitle = $recordInfo['title'];
111 }
112 $this->runtimeCache->set($cacheId, $pageTitle);
113 }
114 return $pageTitle;
115 }
116
117 /**
118 * Gets the username of a given backend user
119 *
120 * @param int $userId uid of user
121 * @return string
122 */
123 protected function getBackendUser(int $userId): string
124 {
125 if ($userId === 0) {
126 return '';
127 }
128 $cacheId = 'recycler-user-' . $userId;
129 if ($this->runtimeCache->has($cacheId)) {
130 $username = $this->runtimeCache->get($cacheId);
131 } else {
132 $backendUser = BackendUtility::getRecord('be_users', $userId, 'username', '', false);
133 $username = $backendUser['username'];
134 $this->runtimeCache->set($cacheId, $username);
135 }
136 return $username;
137 }
138
139 /**
140 * Get the user uid of the user who deleted the record
141 *
142 * @param string $table table name
143 * @param int $uid uid of record
144 * @return int
145 */
146 protected function getUserWhoDeleted(string $table, int $uid): int
147 {
148 $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)
149 ->getQueryBuilderForTable('sys_history');
150 $queryBuilder->select('userid')
151 ->from('sys_history')
152 ->where(
153 $queryBuilder->expr()->eq(
154 'tablename',
155 $queryBuilder->createNamedParameter($table, \PDO::PARAM_STR)
156 ),
157 $queryBuilder->expr()->eq(
158 'usertype',
159 $queryBuilder->createNamedParameter('BE', \PDO::PARAM_STR)
160 ),
161 $queryBuilder->expr()->eq(
162 'recuid',
163 $queryBuilder->createNamedParameter($uid, \PDO::PARAM_INT)
164 ),
165 $queryBuilder->expr()->eq(
166 'actiontype',
167 $queryBuilder->createNamedParameter(RecordHistoryStore::ACTION_DELETE, \PDO::PARAM_INT)
168 )
169 )
170 ->setMaxResults(1);
171
172 return (int)$queryBuilder->execute()->fetchColumn(0);
173 }
174
175 /**
176 * Returns an instance of LanguageService
177 *
178 * @return \TYPO3\CMS\Core\Localization\LanguageService
179 */
180 protected function getLanguageService()
181 {
182 return $GLOBALS['LANG'];
183 }
184
185 /**
186 * Create and returns an instance of the CacheManager
187 *
188 * @return CacheManager
189 */
190 protected function getCacheManager()
191 {
192 return GeneralUtility::makeInstance(CacheManager::class);
193 }
194
195 /**
196 * Gets an instance of the memory cache.
197 *
198 * @return \TYPO3\CMS\Core\Cache\Frontend\FrontendInterface
199 */
200 protected function getMemoryCache()
201 {
202 return $this->getCacheManager()->getCache('cache_runtime');
203 }
204 }