[TASK] Disable compression for inlineJs in Backend
[Packages/TYPO3.CMS.git] / typo3 / backend.php
1 <?php
2 /***************************************************************
3 * Copyright notice
4 *
5 * (c) 2007-2011 Ingo Renner <ingo@typo3.org>
6 * All rights reserved
7 *
8 * This script is part of the TYPO3 project. The TYPO3 project is
9 * free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
13 *
14 * The GNU General Public License can be found at
15 * http://www.gnu.org/copyleft/gpl.html.
16 * A copy is found in the textfile GPL.txt and important notices to the license
17 * from the author is found in LICENSE.txt distributed with these scripts.
18 *
19 *
20 * This script is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * GNU General Public License for more details.
24 *
25 * This copyright notice MUST APPEAR in all copies of the script!
26 ***************************************************************/
27
28 require_once('init.php');
29 require_once('template.php');
30 require_once(PATH_typo3 . 'interfaces/interface.backend_toolbaritem.php');
31
32 require('classes/class.typo3logo.php');
33 require('classes/class.modulemenu.php');
34
35 // core toolbar items
36 require('classes/class.clearcachemenu.php');
37 require('classes/class.shortcutmenu.php');
38 require('classes/class.livesearch.php');
39
40 $GLOBALS['LANG']->includeLLFile('EXT:lang/locallang_misc.xml');
41
42
43 /**
44 * Class for rendering the TYPO3 backend version 4.2+
45 *
46 * @author Ingo Renner <ingo@typo3.org>
47 * @package TYPO3
48 * @subpackage core
49 */
50 class TYPO3backend {
51
52 protected $content;
53 protected $css;
54 protected $cssFiles;
55 protected $js;
56 protected $jsFiles;
57 protected $jsFilesAfterInline;
58 protected $toolbarItems;
59 private $menuWidthDefault = 190; // intentionally private as nobody should modify defaults
60 protected $menuWidth;
61 protected $debug;
62
63 /**
64 * Object for loading backend modules
65 *
66 * @var t3lib_loadModules
67 */
68 protected $moduleLoader;
69
70 /**
71 * module menu generating object
72 *
73 * @var ModuleMenu
74 */
75 protected $moduleMenu;
76
77 /**
78 * Pagerenderer
79 *
80 * @var t3lib_PageRenderer
81 */
82 protected $pageRenderer;
83
84 /**
85 * constructor
86 *
87 * @return void
88 */
89 public function __construct() {
90 // set debug flag for BE development only
91 $this->debug = intval($GLOBALS['TYPO3_CONF_VARS']['BE']['debug']) === 1;
92
93 // Initializes the backend modules structure for use later.
94 $this->moduleLoader = t3lib_div::makeInstance('t3lib_loadModules');
95 $this->moduleLoader->load($GLOBALS['TBE_MODULES']);
96
97 $this->moduleMenu = t3lib_div::makeInstance('ModuleMenu');
98
99 $this->pageRenderer = $GLOBALS['TBE_TEMPLATE']->getPageRenderer();
100 $this->pageRenderer->loadScriptaculous('builder,effects,controls,dragdrop');
101 $this->pageRenderer->loadExtJS();
102 $this->pageRenderer->enableExtJSQuickTips();
103
104
105 $this->pageRenderer->addJsInlineCode(
106 'consoleOverrideWithDebugPanel',
107 '//already done',
108 FALSE
109 );
110 $this->pageRenderer->addExtDirectCode();
111
112 // add default BE javascript
113 $this->js = '';
114 $this->jsFiles = array(
115 'common' => 'js/common.js',
116 'locallang' => $this->getLocalLangFileName(),
117 'modernizr' => 'contrib/modernizr/modernizr.min.js',
118 'swfupload' => 'contrib/swfupload/swfupload.js',
119 'swfupload.swfobject' => 'contrib/swfupload/plugins/swfupload.swfobject.js',
120 'swfupload.cookies' => 'contrib/swfupload/plugins/swfupload.cookies.js',
121 'swfupload.queue' => 'contrib/swfupload/plugins/swfupload.queue.js',
122 'md5' => 'md5.js',
123 'toolbarmanager' => 'js/toolbarmanager.js',
124 'modulemenu' => 'js/modulemenu.js',
125 'iecompatibility' => 'js/iecompatibility.js',
126 'flashupload' => 'js/flashupload.js',
127 'evalfield' => '../t3lib/jsfunc.evalfield.js',
128 'flashmessages' => '../t3lib/js/extjs/ux/flashmessages.js',
129 'tabclosemenu' => '../t3lib/js/extjs/ux/ext.ux.tabclosemenu.js',
130 'notifications' => '../t3lib/js/extjs/notifications.js',
131 'backend' => 'js/backend.js',
132 'loginrefresh' => 'js/loginrefresh.js',
133 'debugPanel' => 'js/extjs/debugPanel.js',
134 'viewport' => 'js/extjs/viewport.js',
135 'iframepanel' => 'js/extjs/iframepanel.js',
136 'modulepanel' => 'js/extjs/modulepanel.js',
137 'viewportConfiguration' => 'js/extjs/viewportConfiguration.js',
138 'util' => '../t3lib/js/extjs/util.js',
139 );
140
141 if ($this->debug) {
142 unset($this->jsFiles['loginrefresh']);
143 }
144
145 // add default BE css
146 $this->css = '';
147 $this->cssFiles = array();
148
149 $this->toolbarItems = array();
150 $this->initializeCoreToolbarItems();
151
152 $this->menuWidth = $this->menuWidthDefault;
153 if (isset($GLOBALS['TBE_STYLES']['dims']['leftMenuFrameW']) && (int) $GLOBALS['TBE_STYLES']['dims']['leftMenuFrameW'] != (int) $this->menuWidth) {
154 $this->menuWidth = (int) $GLOBALS['TBE_STYLES']['dims']['leftMenuFrameW'];
155 }
156
157 $this->executeHook('constructPostProcess');
158
159 // Add previously generated JS to the backend
160 if (isset($GLOBALS['TBE_MODULES']['_JSINIT']) && is_array($GLOBALS['TBE_MODULES']['_JSINIT'])) {
161 foreach ($GLOBALS['TBE_MODULES']['_JSINIT'] as $value) {
162 $this->js .= $value;
163 }
164 }
165 }
166
167 /**
168 * initializes the core toolbar items
169 *
170 * @return void
171 */
172 protected function initializeCoreToolbarItems() {
173
174 $coreToolbarItems = array(
175 'shortcuts' => 'ShortcutMenu',
176 'clearCacheActions' => 'ClearCacheMenu',
177 'liveSearch' => 'LiveSearch'
178 );
179
180 foreach($coreToolbarItems as $toolbarItemName => $toolbarItemClassName) {
181 $toolbarItem = t3lib_div::makeInstance($toolbarItemClassName, $this);
182
183 if(!($toolbarItem instanceof backend_toolbarItem)) {
184 throw new UnexpectedValueException('$toolbarItem "'.$toolbarItemName.'" must implement interface backend_toolbarItem', 1195126772);
185 }
186
187 if($toolbarItem->checkAccess()) {
188 $this->toolbarItems[$toolbarItemName] = $toolbarItem;
189 } else {
190 unset($toolbarItem);
191 }
192 }
193 }
194
195 /**
196 * main function generating the BE scaffolding
197 *
198 * @return void
199 */
200 public function render() {
201 $this->executeHook('renderPreProcess');
202
203 // prepare the scaffolding, at this point extension may still add javascript and css
204 $logo = t3lib_div::makeInstance('TYPO3Logo');
205 $logo->setLogo('gfx/typo3logo_mini.png');
206
207
208
209 // create backend scaffolding
210 $backendScaffolding = '
211 <div id="typo3-top-container" class="x-hide-display">
212 <div id="typo3-logo">'.$logo->render().'</div>
213 <div id="typo3-top" class="typo3-top-toolbar">' .
214 $this->renderToolbar() .
215 '</div>
216 </div>
217
218 ';
219
220 /******************************************************
221 * now put the complete backend document together
222 ******************************************************/
223
224 foreach($this->cssFiles as $cssFileName => $cssFile) {
225 $this->pageRenderer->addCssFile($cssFile);
226
227 // load addditional css files to overwrite existing core styles
228 if(!empty($GLOBALS['TBE_STYLES']['stylesheets'][$cssFileName])) {
229 $this->pageRenderer->addCssFile($GLOBALS['TBE_STYLES']['stylesheets'][$cssFileName]);
230 }
231 }
232
233 if(!empty($this->css)) {
234 $this->pageRenderer->addCssInlineBlock('BackendInlineCSS', $this->css);
235 }
236
237 foreach ($this->jsFiles as $jsFile) {
238 $this->pageRenderer->addJsFile($jsFile);
239 }
240
241
242 $this->generateJavascript();
243 $this->pageRenderer->addJsInlineCode('BackendInlineJavascript', $this->js, FALSE);
244
245 $this->loadResourcesForRegisteredNavigationComponents();
246
247 // add state provider
248 $GLOBALS['TBE_TEMPLATE']->setExtDirectStateProvider();
249 $states = $GLOBALS['BE_USER']->uc['BackendComponents']['States'];
250 //save states in BE_USER->uc
251 $extOnReadyCode = '
252 Ext.state.Manager.setProvider(new TYPO3.state.ExtDirectProvider({
253 key: "BackendComponents.States",
254 autoRead: false
255 }));
256 ';
257 if ($states) {
258 $extOnReadyCode .= 'Ext.state.Manager.getProvider().initState(' . json_encode($states) . ');';
259 }
260 $extOnReadyCode .= '
261 TYPO3.Backend = new TYPO3.Viewport(TYPO3.Viewport.configuration);
262 if (typeof console === "undefined") {
263 console = TYPO3.Backend.DebugConsole;
264 }
265 TYPO3.ContextHelpWindow.init();';
266 $this->pageRenderer->addExtOnReadyCode($extOnReadyCode);
267
268
269 // set document title:
270 $title = ($GLOBALS['TYPO3_CONF_VARS']['SYS']['sitename']
271 ? $GLOBALS['TYPO3_CONF_VARS']['SYS']['sitename'].' [TYPO3 '.TYPO3_version.']'
272 : 'TYPO3 '.TYPO3_version
273 );
274
275 $this->content = $backendScaffolding;
276 // Renders the module page
277 $this->content = $GLOBALS['TBE_TEMPLATE']->render(
278 $title,
279 $this->content
280 );
281
282 $hookConfiguration = array('content' => &$this->content);
283 $this->executeHook('renderPostProcess', $hookConfiguration);
284
285 echo $this->content;
286 }
287
288 /**
289 * Loads the css and javascript files of all registered navigation widgets
290 *
291 * @return void
292 */
293 protected function loadResourcesForRegisteredNavigationComponents() {
294 if (!is_array($GLOBALS['TBE_MODULES']['_navigationComponents'])) {
295 return;
296 }
297
298 $loadedComponents = array();
299 foreach ($GLOBALS['TBE_MODULES']['_navigationComponents'] as $module => $info) {
300 if (in_array($info['componentId'], $loadedComponents)) {
301 continue;
302 }
303 $loadedComponents[] = $info['componentId'];
304
305 $component = strtolower(substr($info['componentId'], strrpos($info['componentId'], '-') + 1));
306 $componentDirectory = 'components/' . $component . '/';
307
308 if ($info['isCoreComponent']) {
309 $absoluteComponentPath = PATH_t3lib . 'js/extjs/' . $componentDirectory;
310 $relativeComponentPath = '../' . str_replace(PATH_site, '', $absoluteComponentPath);
311 } else {
312 $absoluteComponentPath = t3lib_extMgm::extPath($info['extKey']) . $componentDirectory;
313 $relativeComponentPath = t3lib_extMgm::extRelPath($info['extKey']) . $componentDirectory;
314 }
315
316 $cssFiles = t3lib_div::getFilesInDir($absoluteComponentPath . 'css/', 'css');
317 if (file_exists($absoluteComponentPath . 'css/loadorder.txt')) {
318 //don't allow inclusion outside directory
319 $loadOrder = str_replace('../', '', t3lib_div::getUrl($absoluteComponentPath . 'css/loadorder.txt'));
320 $cssFilesOrdered = t3lib_div::trimExplode(LF, $loadOrder, TRUE);
321 $cssFiles = array_merge($cssFilesOrdered, $cssFiles);
322 }
323 foreach ($cssFiles as $cssFile) {
324 $this->pageRenderer->addCssFile($relativeComponentPath . 'css/' . $cssFile);
325 }
326
327 $jsFiles = t3lib_div::getFilesInDir($absoluteComponentPath . 'javascript/', 'js');
328 if (file_exists($absoluteComponentPath . 'javascript/loadorder.txt')) {
329 //don't allow inclusion outside directory
330 $loadOrder = str_replace('../', '', t3lib_div::getUrl($absoluteComponentPath . 'javascript/loadorder.txt'));
331 $jsFilesOrdered = t3lib_div::trimExplode(LF, $loadOrder, TRUE);
332 $jsFiles = array_merge($jsFilesOrdered, $jsFiles);
333 }
334
335 foreach ($jsFiles as $jsFile) {
336 $this->pageRenderer->addJsFile($relativeComponentPath . 'javascript/' . $jsFile);
337 }
338 }
339 }
340
341 /**
342 * renders the items in the top toolbar
343 *
344 * @return string top toolbar elements as HTML
345 */
346 protected function renderToolbar() {
347
348 // move search to last position
349 if (array_key_exists('liveSearch', $this->toolbarItems)) {
350 $search = $this->toolbarItems['liveSearch'];
351 unset($this->toolbarItems['liveSearch']);
352 $this->toolbarItems['liveSearch'] = $search;
353 }
354
355 $toolbar = '<ul id="typo3-toolbar">';
356 $toolbar.= '<li>'.$this->getLoggedInUserLabel().'</li>
357 <li><div id="logout-button" class="toolbar-item no-separator">'.$this->moduleMenu->renderLogoutButton().'</div></li>';
358
359 foreach($this->toolbarItems as $toolbarItem) {
360 $menu = $toolbarItem->render();
361 if ($menu) {
362 $additionalAttributes = $toolbarItem->getAdditionalAttributes();
363 $toolbar .= '<li' . $additionalAttributes . '>' .$menu. '</li>';
364 }
365 }
366
367 return $toolbar.'</ul>';
368 }
369
370 /**
371 * Gets the label of the BE user currently logged in
372 *
373 * @return string html code snippet displaying the currently logged in user
374 */
375 protected function getLoggedInUserLabel() {
376 $icon = t3lib_iconWorks::getSpriteIcon('status-user-' . ($GLOBALS['BE_USER']->isAdmin() ? 'admin' : 'backend'));
377
378 $label = $GLOBALS['BE_USER']->user['realName'] ?
379 $GLOBALS['BE_USER']->user['realName'] . ' (' . $GLOBALS['BE_USER']->user['username'] . ')' :
380 $GLOBALS['BE_USER']->user['username'];
381
382 // Link to user setup if it's loaded and user has access
383 $link = '';
384 if (t3lib_extMgm::isLoaded('setup') && $GLOBALS['BE_USER']->check('modules','user_setup')) {
385 $link = '<a href="#" onclick="top.goToModule(\'user_setup\');this.blur();return false;">';
386 }
387
388 $username = '">'.$link.$icon.'<span>'.htmlspecialchars($label).'</span>'.($link?'</a>':'');
389
390 // superuser mode
391 if ($GLOBALS['BE_USER']->user['ses_backuserid']) {
392 $username = ' su-user">'.$icon.
393 '<span title="' . $GLOBALS['LANG']->getLL('switchtouser') . '">' .
394 $GLOBALS['LANG']->getLL('switchtousershort') . ' </span>' .
395 '<span>' . htmlspecialchars($label) . '</span>';
396 }
397
398 return '<div id="username" class="toolbar-item no-separator'.$username.'</div>';
399 }
400
401 /**
402 * Returns the file name to the LLL JavaScript, containing the localized labels,
403 * which can be used in JavaScript code.
404 *
405 * @return string File name of the JS file, relative to TYPO3_mainDir
406 */
407 protected function getLocalLangFileName() {
408 $code = $this->generateLocalLang();
409 $filePath = 'typo3temp/locallang-BE-' . sha1($code) . '.js';
410 if (!file_exists(PATH_site . $filePath)) {
411 // writeFileToTypo3tempDir() returns NULL on success (please double-read!)
412 if (t3lib_div::writeFileToTypo3tempDir(PATH_site . $filePath, $code) !== NULL) {
413 throw new RuntimeException('LocalLangFile could not be written to ' . $filePath, 1295193026);
414 }
415 }
416 return '../' . $filePath;
417 }
418
419 /**
420 * Reads labels required in JavaScript code from the localization system and returns them as JSON
421 * array in TYPO3.LLL.
422 *
423 * @return string JavaScript code containing the LLL labels in TYPO3.LLL
424 */
425 protected function generateLocalLang() {
426 $coreLabels = array(
427 'waitTitle' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_logging_in') ,
428 'refresh_login_failed' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_failed'),
429 'refresh_login_failed_message' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_failed_message'),
430 'refresh_login_title' => sprintf($GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_title'), htmlspecialchars($GLOBALS['BE_USER']->user['username'])),
431 'login_expired' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.login_expired'),
432 'refresh_login_username' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_username'),
433 'refresh_login_password' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_password'),
434 'refresh_login_emptyPassword' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_emptyPassword'),
435 'refresh_login_button' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_button'),
436 'refresh_logout_button' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_logout_button'),
437 'please_wait' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.please_wait'),
438 'loadingIndicator' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:loadingIndicator'),
439 'be_locked' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.be_locked'),
440 'refresh_login_countdown_singular' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_countdown_singular'),
441 'refresh_login_countdown' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_countdown'),
442 'login_about_to_expire' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.login_about_to_expire'),
443 'login_about_to_expire_title' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.login_about_to_expire_title'),
444 'refresh_login_refresh_button' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_login_refresh_button'),
445 'refresh_direct_logout_button' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:mess.refresh_direct_logout_button'),
446 'tabs_closeAll' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:tabs.closeAll'),
447 'tabs_closeOther' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:tabs.closeOther'),
448 'tabs_close' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:tabs.close'),
449 'tabs_openInBrowserWindow' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:tabs.openInBrowserWindow'),
450 'csh_tooltip_loading' => $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.xml:csh_tooltip_loading'),
451 );
452
453 $labels = array(
454 'fileUpload' => array(
455 'windowTitle',
456 'buttonSelectFiles',
457 'buttonCancelAll',
458 'infoComponentMaxFileSize',
459 'infoComponentFileUploadLimit',
460 'infoComponentFileTypeLimit',
461 'infoComponentOverrideFiles',
462 'processRunning',
463 'uploadWait',
464 'uploadStarting',
465 'uploadProgress',
466 'uploadSuccess',
467 'errorQueueLimitExceeded',
468 'errorQueueFileSizeLimit',
469 'errorQueueZeroByteFile',
470 'errorQueueInvalidFiletype',
471 'errorUploadHttp',
472 'errorUploadMissingUrl',
473 'errorUploadIO',
474 'errorUploadSecurityError',
475 'errorUploadLimit',
476 'errorUploadFailed',
477 'errorUploadFileIDNotFound',
478 'errorUploadFileValidation',
479 'errorUploadFileCancelled',
480 'errorUploadStopped',
481 'allErrorMessageTitle',
482 'allErrorMessageText',
483 'allError401',
484 'allError2038',
485 ),
486 'liveSearch' => array(
487 'title',
488 'helpTitle',
489 'emptyText',
490 'loadingText',
491 'listEmptyText',
492 'showAllResults',
493 'helpDescription',
494 'helpDescriptionPages',
495 'helpDescriptionContent',
496 ),
497 'viewPort' => array(
498 'tooltipModuleMenuSplit',
499 'tooltipNavigationContainerSplitDrag',
500 'tooltipDebugPanelSplitDrag',
501
502 ),
503 );
504 $generatedLabels = array();
505 $generatedLabels['core'] = $coreLabels;
506
507 // first loop over all categories (fileUpload, liveSearch, ..)
508 foreach ($labels as $categoryName => $categoryLabels) {
509 // then loop over every single label
510 foreach ($categoryLabels as $label) {
511 // LLL identifier must be called $categoryName_$label, e.g. liveSearch_loadingText
512 $generatedLabels[$categoryName][$label] = $GLOBALS['LANG']->getLL($categoryName . '_' . $label);
513 }
514 }
515
516 // Convert labels/settings back to UTF-8 since json_encode() only works with UTF-8:
517 if ($GLOBALS['LANG']->charSet !== 'utf-8') {
518 $GLOBALS['LANG']->csConvObj->convArray($generatedLabels, $GLOBALS['LANG']->charSet, 'utf-8');
519 }
520
521 return 'TYPO3.LLL = ' . json_encode($generatedLabels) . ';';
522 }
523
524 /**
525 * Generates the JavaScript code for the backend.
526 *
527 * @return void
528 */
529 protected function generateJavascript() {
530
531 $pathTYPO3 = t3lib_div::dirname(t3lib_div::getIndpEnv('SCRIPT_NAME')).'/';
532
533 // If another page module was specified, replace the default Page module with the new one
534 $newPageModule = trim($GLOBALS['BE_USER']->getTSConfigVal('options.overridePageModule'));
535 $pageModule = t3lib_BEfunc::isModuleSetInTBE_MODULES($newPageModule) ? $newPageModule : 'web_layout';
536 if (!$GLOBALS['BE_USER']->check('modules', $pageModule)) {
537 $pageModule = '';
538 }
539
540 $menuFrameName = 'menu';
541 if($GLOBALS['BE_USER']->uc['noMenuMode'] === 'icons') {
542 $menuFrameName = 'topmenuFrame';
543 }
544
545 // determine security level from conf vars and default to super challenged
546 if ($GLOBALS['TYPO3_CONF_VARS']['BE']['loginSecurityLevel']) {
547 $this->loginSecurityLevel = $GLOBALS['TYPO3_CONF_VARS']['BE']['loginSecurityLevel'];
548 } else {
549 $this->loginSecurityLevel = 'superchallenged';
550 }
551
552 $t3Configuration = array(
553 'siteUrl' => t3lib_div::getIndpEnv('TYPO3_SITE_URL'),
554 'PATH_typo3' => $pathTYPO3,
555 'PATH_typo3_enc' => rawurlencode($pathTYPO3),
556 'username' => htmlspecialchars($GLOBALS['BE_USER']->user['username']),
557 'uniqueID' => t3lib_div::shortMD5(uniqid('')),
558 'securityLevel' => $this->loginSecurityLevel,
559 'TYPO3_mainDir' => TYPO3_mainDir,
560 'pageModule' => $pageModule,
561 'condensedMode' => $GLOBALS['BE_USER']->uc['condensedMode'] ? 1 : 0 ,
562 'inWorkspace' => $GLOBALS['BE_USER']->workspace !== 0 ? 1 : 0,
563 'workspaceFrontendPreviewEnabled' => $GLOBALS['BE_USER']->user['workspace_preview'] ? 1 : 0,
564 'veriCode' => $GLOBALS['BE_USER']->veriCode(),
565 'denyFileTypes' => PHP_EXTENSIONS_DEFAULT,
566 'moduleMenuWidth' => $this->menuWidth - 1,
567 'topBarHeight' => (isset($GLOBALS['TBE_STYLES']['dims']['topFrameH']) ? intval($GLOBALS['TBE_STYLES']['dims']['topFrameH']) : 30),
568 'showRefreshLoginPopup' => isset($GLOBALS['TYPO3_CONF_VARS']['BE']['showRefreshLoginPopup']) ? intval($GLOBALS['TYPO3_CONF_VARS']['BE']['showRefreshLoginPopup']) : FALSE,
569 'listModulePath' => t3lib_extMgm::isLoaded('recordlist') ? t3lib_extMgm::extRelPath('recordlist') . 'mod1/' : '',
570 'debugInWindow' => $GLOBALS['BE_USER']->uc['debugInWindow'] ? 1 : 0,
571 'ContextHelpWindows' => array(
572 'width' => 600,
573 'height' => 400
574 ),
575 'firstWebmountPid' => intval($GLOBALS['WEBMOUNTS'][0]),
576 );
577 if ($GLOBALS['LANG']->charSet !== 'utf-8') {
578 $t3Configuration['username'] = $GLOBALS['LANG']->csConvObj->conv($t3Configuration['username'], $GLOBALS['LANG']->charSet, 'utf-8');
579 }
580
581 $this->js .= '
582 TYPO3.configuration = ' . json_encode($t3Configuration) . ';
583
584 /**
585 * TypoSetup object.
586 */
587 function typoSetup() { //
588 this.PATH_typo3 = TYPO3.configuration.PATH_typo3;
589 this.PATH_typo3_enc = TYPO3.configuration.PATH_typo3_enc;
590 this.username = TYPO3.configuration.username;
591 this.uniqueID = TYPO3.configuration.uniqueID;
592 this.navFrameWidth = 0;
593 this.securityLevel = TYPO3.configuration.securityLevel;
594 this.veriCode = TYPO3.configuration.veriCode;
595 this.denyFileTypes = TYPO3.configuration.denyFileTypes;
596 }
597 var TS = new typoSetup();
598 //backwards compatibility
599 /**
600 * Frameset Module object
601 *
602 * Used in main modules with a frameset for submodules to keep the ID between modules
603 * Typically that is set by something like this in a Web>* sub module:
604 * if (top.fsMod) top.fsMod.recentIds["web"] = "\'.intval($this->id).\'";
605 * if (top.fsMod) top.fsMod.recentIds["file"] = "...(file reference/string)...";
606 */
607 function fsModules() { //
608 this.recentIds=new Array(); // used by frameset modules to track the most recent used id for list frame.
609 this.navFrameHighlightedID=new Array(); // used by navigation frames to track which row id was highlighted last time
610 this.currentMainLoaded="";
611 this.currentBank="0";
612 }
613 var fsMod = new fsModules();
614
615 top.goToModule = function(modName, cMR_flag, addGetVars) {
616 TYPO3.ModuleMenu.App.showModule(modName, addGetVars);
617 }
618 ' . $this->setStartupModule();
619
620 // Check editing of page:
621 $this->handlePageEditing();
622
623 }
624
625 /**
626 * Checking if the "&edit" variable was sent so we can open it for editing the page.
627 * Code based on code from "alt_shortcut.php"
628 *
629 * @return void
630 */
631 protected function handlePageEditing() {
632
633 if(!t3lib_extMgm::isLoaded('cms')) {
634 return;
635 }
636
637 // EDIT page:
638 $editId = preg_replace('/[^[:alnum:]_]/', '', t3lib_div::_GET('edit'));
639 $editRecord = '';
640
641 if($editId) {
642
643 // Looking up the page to edit, checking permissions:
644 $where = ' AND ('.$GLOBALS['BE_USER']->getPagePermsClause(2)
645 .' OR '.$GLOBALS['BE_USER']->getPagePermsClause(16).')';
646
647 if(t3lib_utility_Math::canBeInterpretedAsInteger($editId)) {
648 $editRecord = t3lib_BEfunc::getRecordWSOL('pages', $editId, '*', $where);
649 } else {
650 $records = t3lib_BEfunc::getRecordsByField('pages', 'alias', $editId, $where);
651
652 if(is_array($records)) {
653 $editRecord = reset($records);
654 t3lib_BEfunc::workspaceOL('pages', $editRecord);
655 }
656 }
657
658 // If the page was accessible, then let the user edit it.
659 if(is_array($editRecord) && $GLOBALS['BE_USER']->isInWebMount($editRecord['uid'])) {
660 // Setting JS code to open editing:
661 $this->js .= '
662 // Load page to edit:
663 window.setTimeout("top.loadEditId('.intval($editRecord['uid']).');", 500);
664 ';
665
666 // "Shortcuts" have been renamed to "Bookmarks"
667 // @deprecated remove shortcuts code in TYPO3 4.7
668 $shortcutSetPageTree = $GLOBALS['BE_USER']->getTSConfigVal('options.shortcut_onEditId_dontSetPageTree');
669 $bookmarkSetPageTree = $GLOBALS['BE_USER']->getTSConfigVal('options.bookmark_onEditId_dontSetPageTree');
670 if ($shortcutSetPageTree !== '') {
671 t3lib_div::deprecationLog('options.shortcut_onEditId_dontSetPageTree - since TYPO3 4.5, will be removed in TYPO3 4.7 - use options.bookmark_onEditId_dontSetPageTree instead');
672 }
673
674 // Checking page edit parameter:
675 if (!$shortcutSetPageTree && !$bookmarkSetPageTree) {
676
677 $shortcutKeepExpanded = $GLOBALS['BE_USER']->getTSConfigVal('options.shortcut_onEditId_keepExistingExpanded');
678 $bookmarkKeepExpanded = $GLOBALS['BE_USER']->getTSConfigVal('options.bookmark_onEditId_keepExistingExpanded');
679 $keepExpanded = ($shortcutKeepExpanded || $bookmarkKeepExpanded);
680
681 // Expanding page tree:
682 t3lib_BEfunc::openPageTree(intval($editRecord['pid']), !$keepExpanded);
683
684 if ($shortcutKeepExpanded) {
685 t3lib_div::deprecationLog('options.shortcut_onEditId_keepExistingExpanded - since TYPO3 4.5, will be removed in TYPO3 4.7 - use options.bookmark_onEditId_keepExistingExpanded instead');
686 }
687 }
688 } else {
689 $this->js .= '
690 // Warning about page editing:
691 alert('.$GLOBALS['LANG']->JScharCode(sprintf($GLOBALS['LANG']->getLL('noEditPage'), $editId)).');
692 ';
693 }
694 }
695 }
696
697 /**
698 * Sets the startup module from either GETvars module and mpdParams or user configuration.
699 *
700 * @return void
701 */
702 protected function setStartupModule() {
703 $startModule = preg_replace('/[^[:alnum:]_]/', '', t3lib_div::_GET('module'));
704
705 if(!$startModule) {
706 if ($GLOBALS['BE_USER']->uc['startModule']) {
707 $startModule = $GLOBALS['BE_USER']->uc['startModule'];
708 } elseif ($GLOBALS['BE_USER']->uc['startInTaskCenter']) {
709 $startModule = 'user_task';
710 }
711 }
712
713 $moduleParameters = t3lib_div::_GET('modParams');
714 if($startModule) {
715 return '
716 // start in module:
717 top.startInModule = [\'' . $startModule . '\', ' . t3lib_div::quoteJSvalue($moduleParameters) . '];
718 ';
719 } else {
720 return '';
721 }
722
723 }
724
725 /**
726 * adds a javascript snippet to the backend
727 *
728 * @param string javascript snippet
729 * @return void
730 */
731 public function addJavascript($javascript) {
732 // TODO do we need more checks?
733 if(!is_string($javascript)) {
734 throw new InvalidArgumentException('parameter $javascript must be of type string', 1195129553);
735 }
736
737 $this->js .= $javascript;
738 }
739
740 /**
741 * adds a javscript file to the backend after it has been checked that it exists
742 *
743 * @param string javascript file reference
744 * @return boolean TRUE if the javascript file was successfully added, FALSE otherwise
745 */
746 public function addJavascriptFile($javascriptFile) {
747 $jsFileAdded = FALSE;
748
749 //TODO add more checks if neccessary
750 if(file_exists(t3lib_div::resolveBackPath(PATH_typo3.$javascriptFile))) {
751 $this->jsFiles[] = $javascriptFile;
752 $jsFileAdded = TRUE;
753 }
754
755 return $jsFileAdded;
756 }
757
758 /**
759 * adds a css snippet to the backend
760 *
761 * @param string css snippet
762 * @return void
763 */
764 public function addCss($css) {
765 if(!is_string($css)) {
766 throw new InvalidArgumentException('parameter $css must be of type string', 1195129642);
767 }
768
769 $this->css .= $css;
770 }
771
772 /**
773 * adds a css file to the backend after it has been checked that it exists
774 *
775 * @param string the css file's name with out the .css ending
776 * @param string css file reference
777 * @return boolean TRUE if the css file was added, FALSE otherwise
778 */
779 public function addCssFile($cssFileName, $cssFile) {
780 $cssFileAdded = FALSE;
781
782 if(empty($this->cssFiles[$cssFileName])) {
783 $this->cssFiles[$cssFileName] = $cssFile;
784 $cssFileAdded = TRUE;
785 }
786
787 return $cssFileAdded;
788 }
789
790 /**
791 * adds an item to the toolbar, the class file for the toolbar item must be loaded at this point
792 *
793 * @param string toolbar item name, f.e. tx_toolbarExtension_coolItem
794 * @param string toolbar item class name, f.e. tx_toolbarExtension_coolItem
795 * @return void
796 */
797 public function addToolbarItem($toolbarItemName, $toolbarItemClassName) {
798 $toolbarItem = t3lib_div::makeInstance($toolbarItemClassName, $this);
799
800 if(!($toolbarItem instanceof backend_toolbarItem)) {
801 throw new UnexpectedValueException('$toolbarItem "'.$toolbarItemName.'" must implement interface backend_toolbarItem', 1195125501);
802 }
803
804 if($toolbarItem->checkAccess()) {
805 $this->toolbarItems[$toolbarItemName] = $toolbarItem;
806 } else {
807 unset($toolbarItem);
808 }
809 }
810
811 /**
812 * Executes defined hooks functions for the given identifier.
813 *
814 * These hook identifiers are valid:
815 * + constructPostProcess
816 * + renderPreProcess
817 * + renderPostProcess
818 *
819 * @param string $identifier Specific hook identifier
820 * @param array $hookConfiguration Additional configuration passed to hook functions
821 * @return void
822 */
823 protected function executeHook($identifier, array $hookConfiguration = array()) {
824 $options =& $GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['typo3/backend.php'];
825
826 if(isset($options[$identifier]) && is_array($options[$identifier])) {
827 foreach($options[$identifier] as $hookFunction) {
828 t3lib_div::callUserFunction($hookFunction, $hookConfiguration, $this);
829 }
830 }
831 }
832 }
833
834
835 // include XCLASS
836 if(defined('TYPO3_MODE') && $GLOBALS['TYPO3_CONF_VARS'][TYPO3_MODE]['XCLASS']['typo3/backend.php']) {
837 include_once($GLOBALS['TYPO3_CONF_VARS'][TYPO3_MODE]['XCLASS']['typo3/backend.php']);
838 }
839
840
841 // document generation
842 $TYPO3backend = t3lib_div::makeInstance('TYPO3backend');
843
844 // include extensions which may add css, javascript or toolbar items
845 if(is_array($GLOBALS['TYPO3_CONF_VARS']['typo3/backend.php']['additionalBackendItems'])) {
846 foreach($GLOBALS['TYPO3_CONF_VARS']['typo3/backend.php']['additionalBackendItems'] as $additionalBackendItem) {
847 include_once($additionalBackendItem);
848 }
849 }
850
851 $TYPO3backend->render();
852
853 ?>