7ba501767e99919263a420b56e80567741b1b395
[Packages/TYPO3.CMS.git] / typo3 / sysext / backend / Classes / Controller / File / ReplaceFileController.php
1 <?php
2 namespace TYPO3\CMS\Backend\Controller\File;
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\Backend\Template\DocumentTemplate;
18 use TYPO3\CMS\Backend\Utility\BackendUtility;
19 use TYPO3\CMS\Backend\Utility\IconUtility;
20 use TYPO3\CMS\Core\Resource\Exception\InsufficientFileAccessPermissionsException;
21 use TYPO3\CMS\Core\Resource\Folder;
22 use TYPO3\CMS\Core\Resource\ResourceFactory;
23 use TYPO3\CMS\Core\Utility\GeneralUtility;
24 use TYPO3\CMS\Lang\LanguageService;
25
26 /**
27 * Script Class for the rename-file form
28 */
29 class ReplaceFileController {
30
31 /**
32 * Document template object
33 *
34 * @var \TYPO3\CMS\Backend\Template\DocumentTemplate
35 */
36 public $doc;
37
38 /**
39 * Name of the filemount
40 *
41 * @var string
42 */
43 public $title;
44
45 /**
46 * sys_file uid
47 *
48 * @var int
49 */
50 public $uid;
51
52 /**
53 * The file or folder object that should be renamed
54 *
55 * @var \TYPO3\CMS\Core\Resource\ResourceInterface $fileOrFolderObject
56 */
57 protected $fileOrFolderObject;
58
59 /**
60 * Return URL of list module.
61 *
62 * @var string
63 */
64 public $returnUrl;
65
66 /**
67 * Accumulating content
68 *
69 * @var string
70 */
71 public $content;
72
73 /**
74 * Constructor
75 */
76 public function __construct() {
77 $GLOBALS['SOBE'] = $this;
78 $GLOBALS['BACK_PATH'] = '';
79
80 $this->init();
81 }
82
83 /**
84 * Init
85 *
86 * @return void
87 * @throws \RuntimeException
88 * @throws InsufficientFileAccessPermissionsException
89 */
90 protected function init() {
91 // Initialize GPvars:
92 $this->uid = (int) GeneralUtility::_GP('uid');
93
94 $this->returnUrl = GeneralUtility::sanitizeLocalUrl(GeneralUtility::_GP('returnUrl'));
95 // Cleaning and checking uid
96 if ($this->uid > 0) {
97 $this->fileOrFolderObject = ResourceFactory::getInstance()->retrieveFileOrFolderObject('file:' . $this->uid);
98 }
99 if (!$this->fileOrFolderObject) {
100 $title = $this->getLanguageService()->sL('LLL:EXT:lang/locallang_mod_file_list.xlf:paramError', TRUE);
101 $message = $this->getLanguageService()->sL('LLL:EXT:lang/locallang_mod_file_list.xlf:targetNoDir', TRUE);
102 throw new \RuntimeException($title . ': ' . $message, 1436895930);
103 }
104 if ($this->fileOrFolderObject->getStorage()->getUid() === 0) {
105 throw new InsufficientFileAccessPermissionsException('You are not allowed to access files outside your storages', 1436895931);
106 }
107
108 // If a folder should be renamed, AND the returnURL should go to the old directory name, the redirect is forced
109 // so the redirect will NOT end in a error message
110 // this case only happens if you select the folder itself in the foldertree and then use the clickmenu to
111 // rename the folder
112 if ($this->fileOrFolderObject instanceof Folder) {
113 $parsedUrl = parse_url($this->returnUrl);
114 $queryParts = GeneralUtility::explodeUrl2Array(urldecode($parsedUrl['query']));
115 if ($queryParts['id'] === $this->fileOrFolderObject->getCombinedIdentifier()) {
116 $this->returnUrl = str_replace(urlencode($queryParts['id']), urlencode($this->fileOrFolderObject->getStorage()->getRootLevelFolder()->getCombinedIdentifier()), $this->returnUrl);
117 }
118 }
119 // Setting icon and title
120 $icon = IconUtility::getSpriteIcon('apps-filetree-root');
121 $this->title = $icon . htmlspecialchars($this->fileOrFolderObject->getStorage()->getName()) . ': ' . htmlspecialchars($this->fileOrFolderObject->getIdentifier());
122 // Setting template object
123 $this->doc = GeneralUtility::makeInstance(DocumentTemplate::class);
124 $this->doc->setModuleTemplate('EXT:backend/Resources/Private/Templates/file_replace.html');
125 $this->doc->backPath = $GLOBALS['BACK_PATH'];
126 $this->doc->JScode = $this->doc->wrapScriptTags('
127 function backToList() { //
128 top.goToModule("file_list");
129 }
130 ');
131 }
132
133 /**
134 * Main function, rendering the content of the rename form
135 *
136 * @return void
137 */
138 public function main() {
139 // Make page header:
140 $this->content = $this->doc->startPage($this->getLanguageService()->sL('LLL:EXT:lang/locallang_core.xlf:file_replace.php.pagetitle'));
141 $pageContent = $this->doc->header($this->getLanguageService()->sL('LLL:EXT:lang/locallang_core.xlf:file_replace.php.pagetitle'));
142 $pageContent .= $this->doc->spacer(5);
143 $pageContent .= $this->doc->divider(5);
144
145 $code = '<form action="' . htmlspecialchars(BackendUtility::getModuleUrl('tce_file')) . '" role="form" method="post" name="editform" enctype="' . $GLOBALS['TYPO3_CONF_VARS']['SYS']['form_enctype'] . '">';
146
147 // Making the formfields for renaming:
148 $code .= '
149 <div class="form-group">
150 <input type="checkbox" value="1" id="keepFilename" name="file[replace][1][keepFilename]"> <label for="keepFilename">' . $this->getLanguageService()->sL('LLL:EXT:lang/locallang_core.xlf:file_replace.php.keepfiletitle') . '</label>
151 </div>
152
153 <div class="form-group">
154 <label for="file_replace">' . $this->getLanguageService()->sL('LLL:EXT:lang/locallang_core.xlf:file_replace.php.selectfile') . '</label>
155 <div class="input-group col-xs-6">
156 <input type="text" name="fakefile" id="fakefile" class="form-control input-xlarge" readonly>
157 <a class="input-group-addon btn btn-primary" onclick="TYPO3.jQuery(\'#file_replace\').click();">' . $this->getLanguageService()->sL('LLL:EXT:lang/locallang_core.xlf:file_replace.php.browse') . '</a>
158 </div>
159 <input class="form-control" type="file" id="file_replace" multiple="false" name="replace_1" style="visibility: hidden;" />
160 </div>
161
162 <script>
163 TYPO3.jQuery(\'#file_replace\').change(function(){
164 TYPO3.jQuery(\'#fakefile\').val(TYPO3.jQuery(this).val());
165 });
166 </script>
167
168 <input type="hidden" name="overwriteExistingFiles" value="1" />
169 <input type="hidden" name="file[replace][1][data]" value="1" />
170 <input type="hidden" name="file[replace][1][uid]" value="' . $this->uid . '" />
171 ';
172 // Making submit button:
173 $code .= '
174 <div class="form-group">
175 <input class="btn btn-primary" type="submit" value="' . $this->getLanguageService()->sL('LLL:EXT:lang/locallang_core.xlf:file_replace.php.submit', TRUE) . '" />
176 <input class="btn btn-danger" type="submit" value="' . $this->getLanguageService()->sL('LLL:EXT:lang/locallang_core.xlf:labels.cancel', TRUE) . '" onclick="backToList(); return false;" />
177 <input type="hidden" name="redirect" value="' . htmlspecialchars($this->returnUrl) . '" />
178 ' . \TYPO3\CMS\Backend\Form\FormEngine::getHiddenTokenField('tceAction') . '
179 </div>
180 ';
181 $code .= '</form>';
182 // Add the HTML as a section:
183 $pageContent .= $code;
184 $docHeaderButtons = array(
185 'back' => ''
186 );
187 $docHeaderButtons['csh'] = BackendUtility::cshItem('xMOD_csh_corebe', 'file_rename', $GLOBALS['BACK_PATH']);
188 // Back
189 if ($this->returnUrl) {
190 $docHeaderButtons['back'] = '<a href="' . htmlspecialchars(GeneralUtility::linkThisUrl($this->returnUrl))
191 . '" class="typo3-goBack" title="' . $this->getLanguageService()->sL('LLL:EXT:lang/locallang_core.xlf:labels.goBack', TRUE) . '">'
192 . IconUtility::getSpriteIcon('actions-view-go-back')
193 . '</a>';
194 }
195 // Add the HTML as a section:
196 $markerArray = array(
197 'CSH' => $docHeaderButtons['csh'],
198 'FUNC_MENU' => BackendUtility::getFuncMenu($this->id, 'SET[function]', $this->MOD_SETTINGS['function'], $this->MOD_MENU['function']),
199 'CONTENT' => $pageContent,
200 'PATH' => $this->title
201 );
202 $this->content .= $this->doc->moduleBody(array(), $docHeaderButtons, $markerArray);
203 $this->content .= $this->doc->endPage();
204 $this->content = $this->doc->insertStylesAndJS($this->content);
205 }
206
207 /**
208 * Outputting the accumulated content to screen
209 *
210 * @return void
211 */
212 public function printContent() {
213 echo $this->content;
214 }
215
216 /**
217 * @return LanguageService
218 */
219 protected function getLanguageService() {
220 return $GLOBALS['LANG'];
221 }
222 }