[TASK] Deprecate FrontendEditingController
[Packages/TYPO3.CMS.git] / typo3 / sysext / core / Classes / FrontendEditing / FrontendEditingController.php
1 <?php
2 namespace TYPO3\CMS\Core\FrontendEditing;
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\Adminpanel\View\AdminPanelView;
18 use TYPO3\CMS\Backend\FrontendBackendUserAuthentication;
19 use TYPO3\CMS\Backend\Utility\BackendUtility;
20 use TYPO3\CMS\Core\Context\Context;
21 use TYPO3\CMS\Core\Context\LanguageAspect;
22 use TYPO3\CMS\Core\Database\ConnectionPool;
23 use TYPO3\CMS\Core\Database\Query\Restriction\EndTimeRestriction;
24 use TYPO3\CMS\Core\Database\Query\Restriction\FrontendGroupRestriction;
25 use TYPO3\CMS\Core\Database\Query\Restriction\HiddenRestriction;
26 use TYPO3\CMS\Core\Database\Query\Restriction\StartTimeRestriction;
27 use TYPO3\CMS\Core\DataHandling\DataHandler;
28 use TYPO3\CMS\Core\Type\Bitmask\Permission;
29 use TYPO3\CMS\Core\Utility\GeneralUtility;
30 use TYPO3\CMS\Frontend\Controller\TypoScriptFrontendController;
31
32 /**
33 * Controller class for frontend editing.
34 *
35 * @deprecated since TYPO3 v9, will be removed in TYPO3 v10.0. Functionality has been moved to EXT:feedit, FrontendBackendUserAuthentication and ContentObjectRenderer.
36 */
37 class FrontendEditingController
38 {
39 /**
40 * GET/POST parameters for the FE editing.
41 * Accessed as $GLOBALS['BE_USER']->frontendEdit->TSFE_EDIT, thus public
42 *
43 * @var array
44 */
45 public $TSFE_EDIT;
46
47 public function __construct()
48 {
49 trigger_error(__CLASS__ . ' will be removed in TYPO3 v10.0. Functionality has been moved to EXT:feedit, FrontendBackendUserAuthentication and ContentObjectRenderer.', E_USER_DEPRECATED);
50 }
51
52 /**
53 * Initializes configuration options.
54 */
55 public function initConfigOptions()
56 {
57 $this->TSFE_EDIT = GeneralUtility::_GP('TSFE_EDIT');
58 // Include classes for editing IF editing module in Admin Panel is open
59 if (((int)$this->getTypoScriptFrontendController()->displayEditIcons === 1
60 || (int)$this->getTypoScriptFrontendController()->displayFieldEditIcons === 1)
61 && $this->isEditAction()
62 ) {
63 $this->editAction();
64 }
65 }
66
67 /**
68 * Generates the "edit panels" which can be shown for a page or records on a page when the Admin Panel is enabled for a backend users surfing the frontend.
69 * With the "edit panel" the user will see buttons with links to editing, moving, hiding, deleting the element
70 * This function is used for the cObject EDITPANEL and the stdWrap property ".editPanel"
71 *
72 * @param string $content A content string containing the content related to the edit panel. For cObject "EDITPANEL" this is empty but not so for the stdWrap property. The edit panel is appended to this string and returned.
73 * @param array $conf TypoScript configuration properties for the editPanel
74 * @param string $currentRecord The "table:uid" of the record being shown. If empty string then $this->currentRecord is used. For new records (set by $conf['newRecordFromTable']) it's auto-generated to "[tablename]:NEW
75 * @param array $dataArray Alternative data array to use. Default is $this->data
76 * @return string The input content string with the editPanel appended. This function returns only an edit panel appended to the content string if a backend user is logged in (and has the correct permissions). Otherwise the content string is directly returned.
77 */
78 public function displayEditPanel($content, array $conf, $currentRecord, array $dataArray)
79 {
80 if ($conf['newRecordFromTable']) {
81 $currentRecord = $conf['newRecordFromTable'] . ':NEW';
82 $conf['allow'] = 'new';
83 $checkEditAccessInternals = false;
84 } else {
85 $checkEditAccessInternals = true;
86 }
87 list($table, $uid) = explode(':', $currentRecord);
88 // Page ID for new records, 0 if not specified
89 $newRecordPid = (int)$conf['newRecordInPid'];
90 $newUid = null;
91 if (!$conf['onlyCurrentPid'] || $dataArray['pid'] == $this->getTypoScriptFrontendController()->id) {
92 if ($table === 'pages') {
93 $newUid = $uid;
94 } else {
95 if ($conf['newRecordFromTable']) {
96 $newUid = $this->getTypoScriptFrontendController()->id;
97 if ($newRecordPid) {
98 $newUid = $newRecordPid;
99 }
100 } else {
101 $newUid = -1 * $uid;
102 }
103 }
104 }
105 if ($this->getTypoScriptFrontendController()->displayEditIcons && $table && $this->allowedToEdit($table, $dataArray, $conf, $checkEditAccessInternals) && $this->allowedToEditLanguage($table, $dataArray)) {
106 $editClass = $GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['typo3/classes/class.frontendedit.php']['edit'];
107 if ($editClass) {
108 $edit = GeneralUtility::makeInstance($editClass);
109 $allowedActions = $this->getAllowedEditActions($table, $conf, $dataArray['pid']);
110 $content = $edit->editPanel($content, $conf, $currentRecord, $dataArray, $table, $allowedActions, $newUid, $this->getHiddenFields($dataArray));
111 }
112 }
113 return $content;
114 }
115
116 /**
117 * Adds an edit icon to the content string. The edit icon links to FormEngine with proper parameters for editing the table/fields of the context.
118 * This implements TYPO3 context sensitive editing facilities. Only backend users will have access (if properly configured as well).
119 *
120 * @param string $content The content to which the edit icons should be appended
121 * @param string $params The parameters defining which table and fields to edit. Syntax is [tablename]:[fieldname],[fieldname],[fieldname],... OR [fieldname],[fieldname],[fieldname],... (basically "[tablename]:" is optional, default table is the one of the "current record" used in the function). The fieldlist is sent as "&columnsOnly=" parameter to FormEngine
122 * @param array $conf TypoScript properties for configuring the edit icons.
123 * @param string $currentRecord The "table:uid" of the record being shown. If empty string then $this->currentRecord is used. For new records (set by $conf['newRecordFromTable']) it's auto-generated to "[tablename]:NEW
124 * @param array $dataArray Alternative data array to use. Default is $this->data
125 * @param string $addUrlParamStr Additional URL parameters for the link pointing to FormEngine
126 * @return string The input content string, possibly with edit icons added (not necessarily in the end but just after the last string of normal content.
127 */
128 public function displayEditIcons($content, $params, array $conf = [], $currentRecord = '', array $dataArray = [], $addUrlParamStr = '')
129 {
130 // Check incoming params:
131 list($currentRecordTable, $currentRecordUID) = explode(':', $currentRecord);
132 list($fieldList, $table) = array_reverse(GeneralUtility::trimExplode(':', $params, true));
133 // Reverse the array because table is optional
134 if (!$table) {
135 $table = $currentRecordTable;
136 } elseif ($table != $currentRecordTable) {
137 // If the table is set as the first parameter, and does not match the table of the current record, then just return.
138 return $content;
139 }
140 $editUid = $dataArray['_LOCALIZED_UID'] ?: $currentRecordUID;
141 // Edit icons imply that the editing action is generally allowed, assuming page and content element permissions permit it.
142 if (!array_key_exists('allow', $conf)) {
143 $conf['allow'] = 'edit';
144 }
145 if ($this->getTypoScriptFrontendController()->displayFieldEditIcons && $table && $this->allowedToEdit($table, $dataArray, $conf) && $fieldList && $this->allowedToEditLanguage($table, $dataArray)) {
146 $editClass = $GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['typo3/classes/class.frontendedit.php']['edit'];
147 if ($editClass) {
148 $edit = GeneralUtility::makeInstance($editClass);
149 $content = $edit->editIcons($content, $params, $conf, $currentRecord, $dataArray, $addUrlParamStr, $table, $editUid, $fieldList);
150 }
151 }
152 return $content;
153 }
154
155 /*****************************************************
156 *
157 * Frontend Editing
158 *
159 ****************************************************/
160 /**
161 * Returns TRUE if an edit-action is sent from the Admin Panel
162 *
163 * @return bool
164 */
165 public function isEditAction()
166 {
167 if (is_array($this->TSFE_EDIT)) {
168 if ($this->TSFE_EDIT['cancel']) {
169 unset($this->TSFE_EDIT['cmd']);
170 } else {
171 $cmd = (string)$this->TSFE_EDIT['cmd'];
172 if (($cmd !== 'edit' || is_array($this->TSFE_EDIT['data']) && ($this->TSFE_EDIT['doSave'] || $this->TSFE_EDIT['update'] || $this->TSFE_EDIT['update_close'])) && $cmd !== 'new') {
173 // $cmd can be a command like "hide" or "move". If $cmd is "edit" or "new" it's an indication to show the formfields. But if data is sent with update-flag then $cmd = edit is accepted because edit may be sent because of .keepGoing flag.
174 return true;
175 }
176 }
177 }
178 return false;
179 }
180
181 /**
182 * Returns TRUE if an edit form is shown on the page.
183 *
184 * @return bool
185 */
186 public function isEditFormShown()
187 {
188 if (is_array($this->TSFE_EDIT)) {
189 $cmd = (string)$this->TSFE_EDIT['cmd'];
190 if ($cmd === 'edit' || $cmd === 'new') {
191 return true;
192 }
193 }
194 }
195
196 /**
197 * Management of the on-page frontend editing forms and edit panels.
198 * Basically taking in the data and commands and passes them on to the proper classes as they should be.
199 *
200 * @throws \UnexpectedValueException if TSFE_EDIT[cmd] is not a valid command
201 */
202 public function editAction()
203 {
204 // Commands
205 list($table, $uid) = explode(':', $this->TSFE_EDIT['record']);
206 $uid = (int)$uid;
207 $cmd = $this->TSFE_EDIT['cmd'];
208 // Look for some TSFE_EDIT data that indicates we should save.
209 if (($this->TSFE_EDIT['doSave'] || $this->TSFE_EDIT['update'] || $this->TSFE_EDIT['update_close']) && is_array($this->TSFE_EDIT['data'])) {
210 $cmd = 'save';
211 }
212 if ($cmd === 'save' || $cmd && $table && $uid && isset($GLOBALS['TCA'][$table])) {
213 // Hook for defining custom editing actions. Naming is incorrect, but preserves compatibility.
214 $_params = [];
215 foreach ($GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['t3lib/class.t3lib_tsfebeuserauth.php']['extEditAction'] ?? [] as $_funcRef) {
216 GeneralUtility::callUserFunction($_funcRef, $_params, $this);
217 }
218 // Perform the requested editing command.
219 $cmdAction = 'do' . ucwords($cmd);
220 if (is_callable([$this, $cmdAction])) {
221 $this->{$cmdAction}($table, $uid);
222 } else {
223 throw new \UnexpectedValueException('The specified frontend edit command (' . $cmd . ') is not valid.', 1225818120);
224 }
225 }
226 }
227
228 /**
229 * Hides a specific record.
230 *
231 * @param string $table The table name for the record to hide.
232 * @param int $uid The UID for the record to hide.
233 */
234 public function doHide($table, $uid)
235 {
236 $hideField = $GLOBALS['TCA'][$table]['ctrl']['enablecolumns']['disabled'];
237 if ($hideField) {
238 $recData = [];
239 $recData[$table][$uid][$hideField] = 1;
240 $dataHandler = GeneralUtility::makeInstance(DataHandler::class);
241 $dataHandler->start($recData, []);
242 $dataHandler->process_datamap();
243 }
244 }
245
246 /**
247 * Unhides (shows) a specific record.
248 *
249 * @param string $table The table name for the record to unhide.
250 * @param int $uid The UID for the record to unhide.
251 */
252 public function doUnhide($table, $uid)
253 {
254 $hideField = $GLOBALS['TCA'][$table]['ctrl']['enablecolumns']['disabled'];
255 if ($hideField) {
256 $recData = [];
257 $recData[$table][$uid][$hideField] = 0;
258 $dataHandler = GeneralUtility::makeInstance(DataHandler::class);
259 $dataHandler->start($recData, []);
260 $dataHandler->process_datamap();
261 }
262 }
263
264 /**
265 * Moves a record up.
266 *
267 * @param string $table The table name for the record to move.
268 * @param int $uid The UID for the record to hide.
269 */
270 public function doUp($table, $uid)
271 {
272 $this->move($table, $uid, 'up');
273 }
274
275 /**
276 * Moves a record down.
277 *
278 * @param string $table The table name for the record to move.
279 * @param int $uid The UID for the record to move.
280 */
281 public function doDown($table, $uid)
282 {
283 $this->move($table, $uid, 'down');
284 }
285
286 /**
287 * Moves a record after a given element. Used for drag.
288 *
289 * @param string $table The table name for the record to move.
290 * @param int $uid The UID for the record to move.
291 */
292 public function doMoveAfter($table, $uid)
293 {
294 $afterUID = $this->TSFE_EDIT['moveAfter'];
295 $this->move($table, $uid, '', $afterUID);
296 }
297
298 /**
299 * Moves a record
300 *
301 * @param string $table The table name for the record to move.
302 * @param int $uid The UID for the record to move.
303 * @param string $direction The direction to move, either 'up' or 'down'.
304 * @param int $afterUID The UID of record to move after. This is specified for dragging only.
305 */
306 protected function move($table, $uid, $direction = '', $afterUID = 0)
307 {
308 $dataHandlerCommands = [];
309 $sortField = $GLOBALS['TCA'][$table]['ctrl']['sortby'];
310 if ($sortField) {
311 // Get the current record
312 // Only fetch uid, pid and the fields that are necessary to detect the sorting factors
313 if (isset($GLOBALS['TCA'][$table]['ctrl']['copyAfterDuplFields'])) {
314 $copyAfterDuplicateFields = GeneralUtility::trimExplode(',', $GLOBALS['TCA'][$table]['ctrl']['copyAfterDuplFields'], true);
315 } else {
316 $copyAfterDuplicateFields = [];
317 }
318
319 $fields = $copyAfterDuplicateFields;
320 $fields[] = 'uid';
321 $fields[] = 'pid';
322 $fields[] = $sortField;
323 $fields = array_unique($fields);
324
325 $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)
326 ->getQueryBuilderForTable($table);
327 $queryBuilder->getRestrictions()->removeAll();
328
329 $currentRecord = $queryBuilder
330 ->select(...$fields)
331 ->from($table)
332 ->where($queryBuilder->expr()->eq(
333 'uid',
334 $queryBuilder->createNamedParameter($uid, \PDO::PARAM_INT)
335 ))
336 ->execute()
337 ->fetch();
338
339 if (is_array($currentRecord)) {
340 // Fetch the record before or after the current one
341 // to define the data handler commands
342 $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)
343 ->getQueryBuilderForTable($table);
344
345 $queryBuilder
346 ->select('uid', 'pid')
347 ->from($table)
348 ->where($queryBuilder->expr()->eq(
349 'pid',
350 $queryBuilder->createNamedParameter($currentRecord['pid'], \PDO::PARAM_INT)
351 ))
352 ->setMaxResults(2);
353
354 // Disable the default restrictions (but not all) if the admin panel is in preview mode
355 if ($this->getBackendUser()->adminPanel instanceof AdminPanelView && $this->getBackendUser()->adminPanel->extGetFeAdminValue('preview')) {
356 $queryBuilder->getRestrictions()
357 ->removeByType(StartTimeRestriction::class)
358 ->removeByType(EndTimeRestriction::class)
359 ->removeByType(HiddenRestriction::class)
360 ->removeByType(FrontendGroupRestriction::class);
361 }
362
363 if (!empty($copyAfterDuplicateFields)) {
364 foreach ($copyAfterDuplicateFields as $fieldName) {
365 $queryBuilder->andWhere($queryBuilder->expr()->eq(
366 $fieldName,
367 $queryBuilder->createNamedParameter($currentRecord[$fieldName], \PDO::PARAM_STR)
368 ));
369 }
370 }
371 if (!empty($direction)) {
372 if ($direction === 'up') {
373 $queryBuilder->andWhere(
374 $queryBuilder->expr()->lt(
375 $sortField,
376 $queryBuilder->createNamedParameter($currentRecord[$sortField], \PDO::PARAM_INT)
377 )
378 );
379 $queryBuilder->orderBy($sortField, 'DESC');
380 } else {
381 $queryBuilder->andWhere(
382 $queryBuilder->expr()->gt(
383 $sortField,
384 $queryBuilder->createNamedParameter($currentRecord[$sortField], \PDO::PARAM_INT)
385 )
386 );
387 $queryBuilder->orderBy($sortField, 'ASC');
388 }
389 }
390
391 $result = $queryBuilder->execute();
392 if ($recordBefore = $result->fetch()) {
393 if ($afterUID) {
394 $dataHandlerCommands[$table][$uid]['move'] = -$afterUID;
395 } elseif ($direction === 'down') {
396 $dataHandlerCommands[$table][$uid]['move'] = -$recordBefore['uid'];
397 } elseif ($recordAfter = $result->fetch()) {
398 // Must take the second record above...
399 $dataHandlerCommands[$table][$uid]['move'] = -$recordAfter['uid'];
400 } else {
401 // ... and if that does not exist, use pid
402 $dataHandlerCommands[$table][$uid]['move'] = $currentRecord['pid'];
403 }
404 } elseif ($direction === 'up') {
405 $dataHandlerCommands[$table][$uid]['move'] = $currentRecord['pid'];
406 }
407 }
408
409 // If any data handler commands were set, execute the data handler command
410 if (!empty($dataHandlerCommands)) {
411 $dataHandler = GeneralUtility::makeInstance(DataHandler::class);
412 $dataHandler->start([], $dataHandlerCommands);
413 $dataHandler->process_cmdmap();
414 }
415 }
416 }
417
418 /**
419 * Deletes a specific record.
420 *
421 * @param string $table The table name for the record to delete.
422 * @param int $uid The UID for the record to delete.
423 */
424 public function doDelete($table, $uid)
425 {
426 $cmdData[$table][$uid]['delete'] = 1;
427 if (!empty($cmdData)) {
428 $dataHandler = GeneralUtility::makeInstance(DataHandler::class);
429 $dataHandler->start([], $cmdData);
430 $dataHandler->process_cmdmap();
431 }
432 }
433
434 /**
435 * Saves a record based on its data array.
436 *
437 * @param string $table The table name for the record to save.
438 * @param int $uid The UID for the record to save.
439 */
440 public function doSave($table, $uid)
441 {
442 $data = $this->TSFE_EDIT['data'];
443 if (!empty($data)) {
444 $dataHandler = GeneralUtility::makeInstance(DataHandler::class);
445 $dataHandler->start($data, []);
446 $dataHandler->process_uploads($_FILES);
447 $dataHandler->process_datamap();
448 // Save the new UID back into TSFE_EDIT
449 $newUID = $dataHandler->substNEWwithIDs['NEW'];
450 if ($newUID) {
451 $this->TSFE_EDIT['newUID'] = $newUID;
452 }
453 }
454 }
455
456 /**
457 * Saves a record based on its data array and closes it.
458 * Note: This method is only a wrapper for doSave() but is needed so
459 *
460 * @param string $table The table name for the record to save.
461 * @param int $uid The UID for the record to save.
462 */
463 public function doSaveAndClose($table, $uid)
464 {
465 $this->doSave($table, $uid);
466 }
467
468 /**
469 * Stub for closing a record. No real functionality needed since content
470 * element rendering will take care of everything.
471 *
472 * @param string $table The table name for the record to close.
473 * @param int $uid The UID for the record to close.
474 */
475 public function doClose($table, $uid)
476 {
477 }
478
479 /**
480 * Checks whether the user has access to edit the language for the
481 * requested record.
482 *
483 * @param string $table The name of the table.
484 * @param array $currentRecord The record.
485 * @return bool
486 */
487 protected function allowedToEditLanguage($table, array $currentRecord)
488 {
489 // If no access right to record languages, return immediately
490 /** @var LanguageAspect $languageAspect */
491 $languageAspect = GeneralUtility::makeInstance(Context::class)->getAspect('language');
492 if ($table === 'pages') {
493 $lang = $languageAspect->getId();
494 } elseif ($table === 'tt_content') {
495 $lang = $languageAspect->getContentId();
496 } elseif ($GLOBALS['TCA'][$table]['ctrl']['languageField']) {
497 $lang = $currentRecord[$GLOBALS['TCA'][$table]['ctrl']['languageField']];
498 } else {
499 $lang = -1;
500 }
501 return $this->getBackendUser()->checkLanguageAccess($lang);
502 }
503
504 /**
505 * Checks whether the user is allowed to edit the requested table.
506 *
507 * @param string $table The name of the table.
508 * @param array $dataArray The data array.
509 * @param array $conf The configuration array for the edit panel.
510 * @param bool $checkEditAccessInternals Boolean indicating whether recordEditAccessInternals should not be checked. Defaults
511 * @return bool
512 */
513 protected function allowedToEdit($table, array $dataArray, array $conf, $checkEditAccessInternals = true)
514 {
515 // Unless permissions specifically allow it, editing is not allowed.
516 $mayEdit = false;
517 if ($checkEditAccessInternals) {
518 $editAccessInternals = $this->getBackendUser()->recordEditAccessInternals($table, $dataArray, false, false);
519 } else {
520 $editAccessInternals = true;
521 }
522 if ($editAccessInternals) {
523 if ($table === 'pages') {
524 if ($this->getBackendUser()->isAdmin() || $this->getBackendUser()->doesUserHaveAccess($dataArray, Permission::PAGE_EDIT)) {
525 $mayEdit = true;
526 }
527 } else {
528 if ($this->getBackendUser()->isAdmin() || $this->getBackendUser()->doesUserHaveAccess(BackendUtility::getRecord('pages', $dataArray['pid']), Permission::CONTENT_EDIT)) {
529 $mayEdit = true;
530 }
531 }
532 if (!$conf['onlyCurrentPid'] || $dataArray['pid'] == $this->getTypoScriptFrontendController()->id) {
533 // Permissions:
534 $types = GeneralUtility::trimExplode(',', strtolower($conf['allow']), true);
535 $allow = array_flip($types);
536 $perms = $this->getBackendUser()->calcPerms($this->getTypoScriptFrontendController()->page);
537 if ($table === 'pages') {
538 $allow = $this->getAllowedEditActions($table, $conf, $dataArray['pid'], $allow);
539 // Can only display editbox if there are options in the menu
540 if (!empty($allow)) {
541 $mayEdit = true;
542 }
543 } else {
544 $mayEdit = !empty($allow) && $perms & Permission::CONTENT_EDIT;
545 }
546 }
547 }
548 return $mayEdit;
549 }
550
551 /**
552 * Takes an array of generally allowed actions and filters that list based on page and content permissions.
553 *
554 * @param string $table The name of the table.
555 * @param array $conf The configuration array.
556 * @param int $pid The PID where editing will occur.
557 * @param string $allow Comma-separated list of actions that are allowed in general.
558 * @return array
559 */
560 protected function getAllowedEditActions($table, array $conf, $pid, $allow = '')
561 {
562 if (!$allow) {
563 $types = GeneralUtility::trimExplode(',', strtolower($conf['allow']), true);
564 $allow = array_flip($types);
565 }
566 if (!$conf['onlyCurrentPid'] || $pid == $this->getTypoScriptFrontendController()->id) {
567 // Permissions
568 $types = GeneralUtility::trimExplode(',', strtolower($conf['allow']), true);
569 $allow = array_flip($types);
570 $perms = $this->getBackendUser()->calcPerms($this->getTypoScriptFrontendController()->page);
571 if ($table === 'pages') {
572 // Rootpage
573 if (count($this->getTypoScriptFrontendController()->config['rootLine']) === 1) {
574 unset($allow['move']);
575 unset($allow['hide']);
576 unset($allow['delete']);
577 }
578 if (!($perms & Permission::PAGE_EDIT) || !$this->getBackendUser()->checkLanguageAccess(0)) {
579 unset($allow['edit']);
580 unset($allow['move']);
581 unset($allow['hide']);
582 }
583 if (!($perms & Permission::PAGE_DELETE)) {
584 unset($allow['delete']);
585 }
586 if (!($perms & Permission::PAGE_NEW)) {
587 unset($allow['new']);
588 }
589 }
590 }
591 return $allow;
592 }
593
594 /**
595 * Adds any extra Javascript includes needed for Front-end editing
596 *
597 * @return string
598 */
599 public function getJavascriptIncludes()
600 {
601 // No extra JS includes needed
602 return '';
603 }
604
605 /**
606 * Gets the hidden fields (array key=field name, value=field value) to be used in the edit panel for a particular content element.
607 * In the normal case, no hidden fields are needed but special controllers such as TemplaVoila need to track flexform pointers, etc.
608 *
609 * @param array $dataArray The data array for a specific content element.
610 * @return array
611 */
612 public function getHiddenFields(array $dataArray)
613 {
614 // No special hidden fields needed.
615 return [];
616 }
617
618 /**
619 * @return FrontendBackendUserAuthentication|null
620 */
621 protected function getBackendUser(): ?FrontendBackendUserAuthentication
622 {
623 return $GLOBALS['BE_USER'] instanceof FrontendBackendUserAuthentication ? $GLOBALS['BE_USER'] : null;
624 }
625
626 /**
627 * @return TypoScriptFrontendController
628 */
629 protected function getTypoScriptFrontendController(): TypoScriptFrontendController
630 {
631 return $GLOBALS['TSFE'];
632 }
633 }