Documentation TYPO3 par Ameos |
00001 <?php 00002 /*************************************************************** 00003 * Copyright notice 00004 * 00005 * (c) 1999-2007 Kasper Skaarhoj (kasperYYYY@typo3.com) 00006 * All rights reserved 00007 * 00008 * This script is part of the TYPO3 project. The TYPO3 project is 00009 * free software; you can redistribute it and/or modify 00010 * it under the terms of the GNU General Public License as published by 00011 * the Free Software Foundation; either version 2 of the License, or 00012 * (at your option) any later version. 00013 * 00014 * The GNU General Public License can be found at 00015 * http://www.gnu.org/copyleft/gpl.html. 00016 * A copy is found in the textfile GPL.txt and important notices to the license 00017 * from the author is found in LICENSE.txt distributed with these scripts. 00018 * 00019 * 00020 * This script is distributed in the hope that it will be useful, 00021 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00022 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00023 * GNU General Public License for more details. 00024 * 00025 * This copyright notice MUST APPEAR in all copies of the script! 00026 ***************************************************************/ 00083 require_once (PATH_t3lib.'class.t3lib_tsparser.php'); 00084 require_once (PATH_t3lib.'class.t3lib_matchcondition.php'); 00085 00086 00087 00088 00089 00090 00091 00092 00093 00094 00095 00096 00097 00098 00099 00100 00109 class t3lib_TStemplate { 00110 00111 // Debugging, analysis: 00112 var $tt_track = 1; // If set, the global tt-timeobject is used to log the performance. 00113 var $forceTemplateParsing=0; // If set, the template is always rendered. Used from Admin Panel. 00114 00115 // Backend Analysis modules settings: 00116 var $matchAlternative=array(); // This array is passed on to matchObj by generateConfig(). If it holds elements, they are used for matching instead. See commment at the match-class. Used for backend modules only. Never frontend! 00117 var $matchAll=0; // If set, the match-class matches everything! Used for backend modules only. Never frontend! 00118 var $parseEditorCfgField=0; // If set, the Backend Editor Configuration TypoScript is also parsed (this is not needed for the frontend) 00119 var $backend_info = 0; 00120 var $getFileName_backPath=''; // Set from the backend - used to set an absolute path (PATH_site) so that relative resources are properly found with getFileName() 00121 00122 // Externally set breakpoints (used by Backend Modules) 00123 var $ext_constants_BRP=0; 00124 var $ext_config_BRP=0; 00125 var $ext_editorcfg_BRP=0; 00126 var $ext_regLinenumbers=FALSE; 00127 00128 // Constants: 00129 var $uplPath = 'uploads/tf/'; 00130 var $tempPath = 'typo3temp/'; 00131 var $menuclasses = 'gmenu,tmenu,imgmenu,jsmenu'; 00132 00133 // Set Internally: 00134 var $whereClause = ''; // This MUST be initialized by the init() function 00135 var $debug = 0; 00136 var $allowedPaths = array(); // This is the only paths (relative!!) that are allowed for resources in TypoScript. Should all be appended with '/'. You can extend these by the global array TYPO3_CONF_VARS. See init() function. 00137 var $currentPageData = ''; // Contains "currentPageData" when rendered/fetched from cache. See getCurrentPageData() 00138 var $simulationHiddenOrTime=0; // See init(); Set if preview of some kind is enabled. 00139 00140 var $loaded = 0; // Set, if the TypoScript template structure is loaded and OK, see ->start() 00141 var $setup = Array( // Default TypoScript Setup code 00142 'styles.' => Array ( 00143 'insertContent' => 'CONTENT', 00144 'insertContent.' => Array ( 00145 'table' => 'tt_content', 00146 'select.' => Array ( 00147 'orderBy' => 'sorting', 00148 'where' => 'colPos=0', 00149 'languageField' => 'sys_language_uid' 00150 ) 00151 ) 00152 ), 00153 'config.' => Array ( 00154 'extTarget' => '_top', 00155 'stat' => 1, 00156 'stat_typeNumList' => '0,1' 00157 ) 00158 ); 00159 var $flatSetup = Array ( 00160 ); 00161 var $const = Array ( // Default TypoScript Constants code: 00162 '_clear' => '<img src="clear.gif" width="1" height="1" alt="" />', 00163 '_blackBorderWrap' => '<table border="0" bgcolor="black" cellspacing="0" cellpadding="1"><tr><td> | </td></tr></table>', 00164 '_tableWrap' => '<table border="0" cellspacing="0" cellpadding="0"> | </table>', 00165 '_tableWrap_DEBUG' => '<table border="1" cellspacing="0" cellpadding="0"> | </table>', 00166 '_stdFrameParams' => 'frameborder="no" marginheight="0" marginwidth="0" noresize="noresize"', 00167 '_stdFramesetParams' => 'border="0" framespacing="0" frameborder="no"' 00168 ); 00169 00170 00171 // For fetching TypoScript code from template hierarchy before parsing it. Each array contains code field values from template records/files: 00172 var $config = array(); // Setup field 00173 var $constants = array(); // Constant field 00174 var $editorcfg = array(); // Backend Editor Configuration field 00175 00176 var $hierarchyInfo = array(); // For Template Analyser in backend 00177 var $hierarchyInfoToRoot = array(); // For Template Analyser in backend (setup content only) 00178 var $nextLevel=0; // Next-level flag (see runThroughTemplates()) 00179 var $rootId; // The Page UID of the root page 00180 var $rootLine; // The rootline from current page to the root page 00181 var $absoluteRootLine; // Rootline all the way to the root. Set but runThroughTemplates 00182 var $outermostRootlineIndexWithTemplate=0; // A pointer to the last entry in the rootline where a template was found. 00183 var $rowSum; // Array of arrays with title/uid of templates in hierarchy 00184 var $resources=''; // Resources for the template hierarchy in a comma list 00185 var $sitetitle=''; // The current site title field. 00186 var $sections; // Tracking all conditions found during parsing of TypoScript. Used for the "all" key in currentPageData 00187 var $sectionsMatch; // Tracking all matching conditions found 00188 00189 // Backend: ts_analyzer 00190 var $clearList_const=array(); 00191 var $clearList_setup=array(); 00192 var $clearList_editorcfg=array(); 00193 var $parserErrors=array(); 00194 var $setup_constants = array(); 00195 00196 // Other: 00197 var $fileCache = Array(); // Used by getFileName for caching of references to file resources 00198 var $frames = Array(); // Keys are frame names and values are type-values, which must be used to refer correctly to the content of the frames. 00199 var $MPmap = ''; // Contains mapping of Page id numbers to MP variables. 00200 00201 00202 00203 00211 function init() { 00212 // $this->whereClause is used only to select templates from sys_template. 00213 // $GLOBALS['SIM_EXEC_TIME'] is used so that we're able to simulate a later time as a test... 00214 $this->whereClause='AND deleted=0 '; 00215 if (!$GLOBALS['TSFE']->showHiddenRecords) { 00216 $this->whereClause.='AND hidden=0 '; 00217 } 00218 if ($GLOBALS['TSFE']->showHiddenRecords || $GLOBALS['SIM_EXEC_TIME']!=$GLOBALS['EXEC_TIME']) { // Set the simulation flag, if simulation is detected! 00219 $this->simulationHiddenOrTime=1; 00220 } 00221 $this->whereClause.= 'AND (starttime<='.$GLOBALS['SIM_EXEC_TIME'].') AND (endtime=0 OR endtime>'.$GLOBALS['SIM_EXEC_TIME'].')'; 00222 if (!$GLOBALS['TYPO3_CONF_VARS']['GFX']['gdlib']) { 00223 $this->menuclasses='tmenu,jsmenu,gmenu'; 00224 } 00225 00226 // Sets the paths from where TypoScript resources are allowed to be used: 00227 $this->allowedPaths = Array ('media/','fileadmin/','uploads/','typo3temp/','t3lib/fonts/',TYPO3_mainDir.'ext/',TYPO3_mainDir.'sysext/','typo3conf/ext/'); 00228 if ($GLOBALS['TYPO3_CONF_VARS']['FE']['addAllowedPaths']) { 00229 $pathArr = t3lib_div::trimExplode(',',$GLOBALS['TYPO3_CONF_VARS']['FE']['addAllowedPaths'],1); 00230 while(list(,$p)=each($pathArr)) { 00231 // Once checked for path, but as this may run from typo3/mod/web/ts/ dir, that'll not work!! So the paths ar uncritically included here. 00232 $this->allowedPaths[] = $p; 00233 } 00234 } 00235 } 00236 00249 function getCurrentPageData() { 00250 $res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('content', 'cache_pagesection', 'page_id='.intval($GLOBALS['TSFE']->id).' AND mpvar_hash='.t3lib_div::md5int($GLOBALS['TSFE']->MP)); 00251 if ($row = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res)) { 00252 $this->currentPageData = unserialize($row['content']); 00253 } else { 00254 $this->currentPageData = 'none'; 00255 } 00256 return $this->currentPageData; 00257 } 00258 00266 function matching($cc) { 00267 if (is_array($cc['all'])) { 00268 reset($cc['all']); 00269 $matchObj = t3lib_div::makeInstance('t3lib_matchCondition'); 00270 $matchObj->altRootLine=$cc['rootLine']; 00271 while(list($key,$pre)=each($cc['all'])) { 00272 if ($matchObj->match($pre)) { 00273 $sectionsMatch[$key]=$pre; 00274 } 00275 } 00276 $cc['match']=$sectionsMatch; 00277 } 00278 return $cc; 00279 } 00280 00290 function start($theRootLine) { 00291 if (is_array($theRootLine)) { 00292 $setupData=''; 00293 $cc=Array(); 00294 $hash=''; 00295 $this->runThroughTemplates($theRootLine); 00296 00297 // Getting the currentPageData if not already found 00298 if (!$this->currentPageData && !$GLOBALS['TSFE']->no_cache) { 00299 $this->getCurrentPageData(); 00300 } 00301 00302 // This is about getting the hash string which is used to fetch the cached TypoScript template. 00303 // If there was some cached currentPageData that's good (it gives us the hash), 00304 // However if the actual rowSum and the rowSum of currentPageData is different from each other, thats a problem, and we should re-make the current page data. 00305 if (is_array($this->currentPageData) && 00306 !strcmp(serialize($this->rowSum), serialize($this->currentPageData['rowSum'])) // The two ROWsums must NOT be different from each other - which they will be if start/endtime or hidden has changed! 00307 ) { 00308 // If currentPageData was actually there, we match the result... 00309 $cc['all'] = $this->currentPageData['all']; 00310 $cc['rowSum'] = $this->currentPageData['rowSum']; 00311 $cc = $this->matching($cc); 00312 $hash = md5(serialize($cc)); 00313 } else { 00314 // If currentPageData was not there, we first find $rowSum (freshly generated). After that we try to see, if rowSum is stored with a list of all matching-parameters. If so we match the result 00315 $rowSumHash = md5('ROWSUM:'.serialize($this->rowSum)); 00316 $result = t3lib_pageSelect::getHash($rowSumHash, 0); 00317 if ($result) { 00318 $cc['all'] = unserialize($result); 00319 $cc['rowSum'] = $this->rowSum; 00320 $cc = $this->matching($cc); 00321 $hash = md5(serialize($cc)); 00322 } 00323 } 00324 00325 if ($hash) { 00326 // Get TypoScript setup array 00327 $setupData = t3lib_pageSelect::getHash($hash, 0); 00328 } 00329 00330 if ($hash && $setupData && !$this->forceTemplateParsing) { 00331 // If TypoScript setup structure was cached we unserialize it here: 00332 $this->setup = unserialize($setupData); 00333 } else { 00334 // Make configuration 00335 $this->generateConfig(); 00336 00337 // This stores the template hash thing 00338 $cc=Array(); 00339 $cc['all']=$this->sections; // All sections in the template at this point is found 00340 $cc['rowSum']=$this->rowSum; // The line of templates is collected 00341 $cc = $this->matching($cc); 00342 00343 $hash = md5(serialize($cc)); 00344 00345 // This stores the data. 00346 t3lib_pageSelect::storeHash($hash, serialize($this->setup), 'TS TEMPLATE'); 00347 00348 if ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('TS template size, serialized: '.strlen(serialize($this->setup)).' bytes'); 00349 00350 $rowSumHash = md5('ROWSUM:'.serialize($this->rowSum)); 00351 t3lib_pageSelect::storeHash($rowSumHash, serialize($cc['all']), 'TMPL CONDITIONS - AL'); 00352 } 00353 // Add rootLine 00354 $cc['rootLine'] = $this->rootLine; 00355 // Make global and save. 00356 $GLOBALS['TSFE']->all=$cc; 00357 00358 if (!$this->simulationHiddenOrTime && !$GLOBALS['TSFE']->no_cache) { // Only save currentPageData, if we're not simulating by hidden/starttime/endtime 00359 $dbFields = array( 00360 'content' => serialize($cc), 00361 'tstamp' => $GLOBALS['EXEC_TIME'] 00362 ); 00363 $mpvar_hash = t3lib_div::md5int($GLOBALS['TSFE']->MP); 00364 $GLOBALS['TYPO3_DB']->exec_UPDATEquery('cache_pagesection', 'page_id=' . intval($GLOBALS['TSFE']->id) . ' AND mpvar_hash=' . $mpvar_hash, $dbFields); 00365 if ($GLOBALS['TYPO3_DB']->sql_affected_rows() == 0) { 00366 $dbFields['page_id'] = intval($GLOBALS['TSFE']->id); 00367 $dbFields['mpvar_hash'] = $mpvar_hash; 00368 $GLOBALS['TYPO3_DB']->exec_INSERTquery('cache_pagesection', $dbFields); 00369 } 00370 } 00371 // If everything OK. 00372 if ($this->rootId && $this->rootLine && $this->setup) { 00373 $this->loaded = 1; 00374 } 00375 } 00376 } 00377 00378 00379 00380 00381 00382 00383 00384 00385 00386 00387 00388 00389 00390 00391 00392 /******************************************************************* 00393 * 00394 * Fetching TypoScript code text for the Template Hierarchy 00395 * 00396 *******************************************************************/ 00397 00408 function runThroughTemplates($theRootLine,$start_template_uid=0) { 00409 $this->constants = Array(); 00410 $this->config = Array(); 00411 $this->editorcfg = Array(); 00412 $this->rowSum = Array(); 00413 $this->hierarchyInfoToRoot = Array(); 00414 $this->absoluteRootLine=$theRootLine; // Is the TOTAL rootline 00415 00416 reset ($this->absoluteRootLine); 00417 $c=count($this->absoluteRootLine); 00418 for ($a=0;$a<$c;$a++) { 00419 if ($this->nextLevel) { // If some template loaded before has set a template-id for the next level, then load this template first! 00420 $res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('*', 'sys_template', 'uid='.intval($this->nextLevel).' '.$this->whereClause); 00421 $this->nextLevel = 0; 00422 if ($row = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res)) { 00423 $this->versionOL($row); 00424 if (is_array($row)) { 00425 $this->processTemplate($row,'sys_'.$row['uid'],$this->absoluteRootLine[$a]['uid'],'sys_'.$row['uid']); 00426 $this->outermostRootlineIndexWithTemplate=$a; 00427 } 00428 } 00429 $GLOBALS['TYPO3_DB']->sql_free_result($res); 00430 } 00431 $addC=''; 00432 if ($a==($c-1) && $start_template_uid) { // If first loop AND there is set an alternative template uid, use that 00433 $addC=' AND uid='.intval($start_template_uid); 00434 } 00435 00436 $res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('*', 'sys_template', 'pid='.intval($this->absoluteRootLine[$a]['uid']).$addC.' '.$this->whereClause,'','sorting',1); 00437 if ($row = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res)) { 00438 $this->versionOL($row); 00439 if (is_array($row)) { 00440 $this->processTemplate($row,'sys_'.$row['uid'],$this->absoluteRootLine[$a]['uid'],'sys_'.$row['uid']); 00441 $this->outermostRootlineIndexWithTemplate=$a; 00442 } 00443 } 00444 $GLOBALS['TYPO3_DB']->sql_free_result($res); 00445 $this->rootLine[] = $this->absoluteRootLine[$a]; 00446 } 00447 } 00448 00461 function processTemplate($row, $idList,$pid,$templateID='',$templateParent='') { 00462 // Adding basic template record information to rowSum array 00463 $this->rowSum[]=Array($row['uid'],$row['title'],$row['tstamp']); 00464 00465 // Processing "Clear"-flags 00466 if ($row['clear']) { 00467 $clConst = $row['clear']&1; 00468 $clConf = $row['clear']&2; 00469 if ($clConst) { 00470 $this->constants = Array(); 00471 $this->clearList_const=array(); 00472 } 00473 if ($clConf) { 00474 $this->config = Array(); 00475 $this->hierarchyInfoToRoot = Array(); 00476 $this->clearList_setup=array(); 00477 00478 $this->editorcfg = Array(); 00479 $this->clearList_editorcfg=array(); 00480 } 00481 } 00482 00483 // Include static records (static_template) or files (from extensions) (#1/2) 00484 if (!$row['includeStaticAfterBasedOn']) { // NORMAL inclusion, The EXACT same code is found below the basedOn inclusion!!! 00485 $this->includeStaticTypoScriptSources($idList,$templateID,$pid,$row); 00486 } 00487 00488 // Include "Based On" sys_templates: 00489 if (trim($row['basedOn'])) { // 'basedOn' is a list of templates to include 00490 // Manually you can put this value in the field and then the based_on ID will be taken from the $_GET var defined by '=....'. 00491 // Example: If $row['basedOn'] is 'EXTERNAL_BASED_ON_TEMPLATE_ID=based_on_uid', then the global var, based_on_uid - given by the URL like '&based_on_uid=999' - is included instead! 00492 // This feature allows us a hack to test/demonstrate various included templates on the same set of content bearing pages. Used by the "freesite" extension. 00493 $basedOn_hackFeature = explode('=',$row['basedOn']); 00494 if ($basedOn_hackFeature[0]=='EXTERNAL_BASED_ON_TEMPLATE_ID' && $basedOn_hackFeature[1]) { 00495 $id = intval(t3lib_div::_GET($basedOn_hackFeature[1])); 00496 if ($id && !t3lib_div::inList($idList,'sys_'.$id)) { // if $id is not allready included ... 00497 $res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('*', 'sys_template', 'uid='.$id.' '.$this->whereClause); 00498 if ($subrow = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res)) { // there was a template, then we fetch that 00499 $this->versionOL($subrow); 00500 if (is_array($subrow)) { 00501 $this->processTemplate($subrow,$idList.',sys_'.$id,$pid, 'sys_'.$id,$templateID); 00502 } 00503 } 00504 $GLOBALS['TYPO3_DB']->sql_free_result($res); 00505 } 00506 } else { // NORMAL OPERATION: 00507 $basedOnArr = t3lib_div::intExplode(',',$row['basedOn']); 00508 while(list(,$id)=each($basedOnArr)) { // traversing list 00509 if (!t3lib_div::inList($idList,'sys_'.$id)) { // if $id is not allready included ... 00510 $res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('*', 'sys_template', 'uid='.intval($id).' '.$this->whereClause); 00511 if ($subrow = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res)) { // there was a template, then we fetch that 00512 $this->versionOL($subrow); 00513 if (is_array($subrow)) { 00514 $this->processTemplate($subrow,$idList.',sys_'.$id,$pid, 'sys_'.$id,$templateID); 00515 } 00516 } 00517 $GLOBALS['TYPO3_DB']->sql_free_result($res); 00518 } 00519 } 00520 } 00521 } 00522 00523 // Include static records (static_template) or files (from extensions) (#2/2) 00524 if ($row['includeStaticAfterBasedOn']) { 00525 $this->includeStaticTypoScriptSources($idList,$templateID,$pid,$row); 00526 } 00527 00528 // Creating hierarchy information; Used by backend analysis tools 00529 $this->hierarchyInfo[] = $this->hierarchyInfoToRoot[] = array( 00530 'root'=>trim($row['root']), 00531 'next'=>$row['nextLevel'], 00532 'clConst'=>$clConst, 00533 'clConf'=>$clConf, 00534 'templateID'=>$templateID, 00535 'templateParent'=>$templateParent, 00536 'title'=>$row['title'], 00537 'uid'=>$row['uid'], 00538 'pid'=>$row['pid'], 00539 'configLines' => substr_count($row['config'], chr(10))+1 00540 ); 00541 00542 // Adding the content of the fields constants (Constants), config (Setup) and editorcfg (Backend Editor Configuration) to the internal arrays. 00543 $this->constants[] = $row['constants']; 00544 $this->config[] = $row['config']; 00545 if ($this->parseEditorCfgField) $this->editorcfg[] = $row['editorcfg']; 00546 00547 // For backend analysis (Template Analyser) provide the order of added constants/config/editorcfg template IDs 00548 $this->clearList_const[]=$templateID; 00549 $this->clearList_setup[]=$templateID; 00550 if ($this->parseEditorCfgField) $this->clearList_editorcfg[]=$templateID; 00551 00552 // Add resources and sitetitle if found: 00553 if (trim($row['resources'])) { 00554 $this->resources = $row['resources'].','.$this->resources; 00555 } 00556 if (trim($row['sitetitle'])) { 00557 $this->sitetitle = $row['sitetitle']; 00558 } 00559 // If the template record is a Rootlevel record, set the flag and clear the template rootLine (so it starts over from this point) 00560 if (trim($row['root'])) { 00561 $this->rootId = $pid; 00562 $this->rootLine = Array(); 00563 } 00564 // If a template is set to be active on the next level set this internal value to point to this UID. (See runThroughTemplates()) 00565 if ($row['nextLevel']) { 00566 $this->nextLevel = $row['nextLevel']; 00567 } else { 00568 $this->nextLevel = 0; 00569 } 00570 } 00571 00582 function includeStaticTypoScriptSources($idList,$templateID,$pid,$row) { 00583 // Static Template Records (static_template): include_static is a list of static templates to include 00584 if (trim($row['include_static'])) { 00585 $include_staticArr = t3lib_div::intExplode(',',$row['include_static']); 00586 reset($include_staticArr); 00587 while(list(,$id)=each($include_staticArr)) { // traversing list 00588 if (!t3lib_div::inList($idList,'static_'.$id)) { // if $id is not allready included ... 00589 $res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('*', 'static_template', 'uid='.intval($id)); 00590 if ($subrow = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res)) { // there was a template, then we fetch that 00591 $subrow = $this->prependStaticExtra($subrow); 00592 $this->processTemplate($subrow,$idList.',static_'.$id,$pid,'static_'.$id,$templateID); 00593 } 00594 $GLOBALS['TYPO3_DB']->sql_free_result($res); 00595 } 00596 } 00597 } 00598 00599 // Static Template Files (Text files from extensions): include_static_file is a list of static files to include (from extensions) 00600 if (trim($row['include_static_file'])) { 00601 $include_static_fileArr = t3lib_div::trimExplode(',',$row['include_static_file'],1); 00602 reset($include_static_fileArr); 00603 while(list(,$ISF_file)=each($include_static_fileArr)) { // traversing list 00604 $ISF_file = trim($ISF_file); 00605 if (substr($ISF_file,0,4)=='EXT:') { 00606 list($ISF_extKey,$ISF_localPath) = explode('/',substr($ISF_file,4),2); 00607 if (strcmp($ISF_extKey,'') && t3lib_extMgm::isLoaded($ISF_extKey) && strcmp($ISF_localPath,'')) { 00608 $ISF_localPath = ereg_replace('\/$','',$ISF_localPath).'/'; 00609 $ISF_filePath = t3lib_extMgm::extPath($ISF_extKey).$ISF_localPath; 00610 if (@is_dir($ISF_filePath)) { 00611 $mExtKey = str_replace('_','',$ISF_extKey.'/'.$ISF_localPath); 00612 $subrow=array( 00613 'constants'=> @is_file($ISF_filePath.'constants.txt') ?t3lib_div::getUrl($ISF_filePath.'constants.txt'):'', 00614 'config'=> @is_file($ISF_filePath.'setup.txt') ?t3lib_div::getUrl($ISF_filePath.'setup.txt'):'', 00615 'editorcfg'=> @is_file($ISF_filePath.'editorcfg.txt') ?t3lib_div::getUrl($ISF_filePath.'editorcfg.txt'):'', 00616 'include_static'=> @is_file($ISF_filePath.'include_static.txt')?implode(',',array_unique(t3lib_div::intExplode(',',t3lib_div::getUrl($ISF_filePath.'include_static.txt')))):'', 00617 'include_static_file'=> @is_file($ISF_filePath.'include_static_file.txt')?implode(',',array_unique(explode(',',t3lib_div::getUrl($ISF_filePath.'include_static_file.txt')))):'', 00618 'title' => $ISF_file, 00619 'uid' => $mExtKey 00620 ); 00621 $subrow = $this->prependStaticExtra($subrow); 00622 00623 $this->processTemplate($subrow,$idList.',ext_'.$mExtKey,$pid, 'ext_'.$mExtKey,$templateID); 00624 } 00625 } 00626 } 00627 } 00628 } 00629 00630 $this->addExtensionStatics($idList,$templateID,$pid,$row); 00631 } 00632 00644 function addExtensionStatics($idList,$templateID,$pid,$row) { 00645 global $TYPO3_LOADED_EXT; 00646 00647 if ($row['static_file_mode']==1 || ($row['static_file_mode']==0 && substr($templateID,0,4)=='sys_' && $row['root'])) { 00648 reset($TYPO3_LOADED_EXT); 00649 while(list($extKey,$files)=each($TYPO3_LOADED_EXT)) { 00650 if (is_array($files) && ($files['ext_typoscript_constants.txt'] || $files['ext_typoscript_setup.txt'] || $files['ext_typoscript_editorcfg.txt'])) { 00651 $mExtKey = str_replace('_','',$extKey); 00652 $subrow=array( 00653 'constants'=> $files['ext_typoscript_constants.txt']?t3lib_div::getUrl($files['ext_typoscript_constants.txt']):'', 00654 'config'=> $files['ext_typoscript_setup.txt']?t3lib_div::getUrl($files['ext_typoscript_setup.txt']):'', 00655 'editorcfg'=> $files['ext_typoscript_editorcfg.txt']?t3lib_div::getUrl($files['ext_typoscript_editorcfg.txt']):'', 00656 'title' => $extKey, 00657 'uid' => $mExtKey 00658 ); 00659 $subrow = $this->prependStaticExtra($subrow); 00660 00661 $this->processTemplate($subrow,$idList.',ext_'.$mExtKey,$pid, 'ext_'.$mExtKey,$templateID); 00662 } 00663 } 00664 } 00665 } 00666 00677 function prependStaticExtra($subrow) { 00678 $subrow['config'].=$GLOBALS['TYPO3_CONF_VARS']['FE']['defaultTypoScript_setup.'][$subrow['uid']]; 00679 $subrow['editorcfg'].=$GLOBALS['TYPO3_CONF_VARS']['FE']['defaultTypoScript_editorcfg.'][$subrow['uid']]; 00680 $subrow['constants'].=$GLOBALS['TYPO3_CONF_VARS']['FE']['defaultTypoScript_constants.'][$subrow['uid']]; 00681 return $subrow; 00682 } 00683 00690 function versionOL(&$row) { 00691 if (is_object($GLOBALS['TSFE'])) { // Frontend: 00692 $GLOBALS['TSFE']->sys_page->versionOL('sys_template',$row); 00693 } else { // Backend: 00694 t3lib_BEfunc::workspaceOL('sys_template',$row); 00695 } 00696 } 00697 00698 00699 00700 00701 00702 00703 00704 00705 00706 00707 00708 00709 00710 00711 00712 00713 00714 /******************************************************************* 00715 * 00716 * Parsing TypoScript code text from Template Records into PHP array 00717 * 00718 *******************************************************************/ 00719 00727 function generateConfig() { 00728 // Add default TS for all three code types: 00729 array_unshift($this->constants,''.$GLOBALS['TYPO3_CONF_VARS']['FE']['defaultTypoScript_constants']); // Adding default TS/constants 00730 array_unshift($this->config,''.$GLOBALS['TYPO3_CONF_VARS']['FE']['defaultTypoScript_setup']); // Adding default TS/setup 00731 array_unshift($this->editorcfg,''.$GLOBALS['TYPO3_CONF_VARS']['FE']['defaultTypoScript_editorcfg']); // Adding default TS/editorcfg 00732 00733 // Parse the TypoScript code text for include-instructions! 00734 $this->procesIncludes(); 00735 00736 // These vars are also set lateron... 00737 $this->setup['resources']= $this->resources; 00738 $this->setup['sitetitle']= $this->sitetitle; 00739 00740 00741 00742 // **************************** 00743 // Parse TypoScript Constants 00744 // **************************** 00745 00746 // Initialize parser and match-condition classes: 00747 $constants = t3lib_div::makeInstance('t3lib_TSparser'); 00748 $constants->breakPointLN=intval($this->ext_constants_BRP); 00749 $constants->setup = $this->const; 00750 $constants->setup = $this->mergeConstantsFromPageTSconfig($constants->setup); 00751 $matchObj = t3lib_div::makeInstance('t3lib_matchCondition'); 00752 $matchObj->matchAlternative = $this->matchAlternative; 00753 $matchObj->matchAll = $this->matchAll; // Matches ALL conditions in TypoScript 00754 00755 // Traverse constants text fields and parse them 00756 foreach($this->constants as $str) { 00757 $constants->parse($str,$matchObj); 00758 } 00759 00760 // Read out parse errors if any 00761 $this->parserErrors['constants']=$constants->errors; 00762 00763 // Then flatten the structure from a multi-dim array to a single dim array with all constants listed as key/value pairs (ready for substitution) 00764 $this->flatSetup = Array(); 00765 $this->flattenSetup($constants->setup,'',''); 00766 00767 00768 00769 // *********************************************** 00770 // Parse TypoScript Setup (here called "config") 00771 // *********************************************** 00772 // Initialize parser and match-condition classes: 00773 $config = t3lib_div::makeInstance('t3lib_TSparser'); 00774 $config->breakPointLN = intval($this->ext_config_BRP); 00775 $config->regLinenumbers = $this->ext_regLinenumbers; 00776 $config->setup = $this->setup; 00777 00778 // Transfer information about conditions found in "Constants" and which of them returned true. 00779 $config->sections = $constants->sections; 00780 $config->sectionsMatch = $constants->sectionsMatch; 00781 00782 // Traverse setup text fields and concatenate them into one, single string separated by a [GLOBAL] condition 00783 $all=''; 00784 foreach($this->config as $str) { 00785 $all.="\n[GLOBAL]\n".$str; 00786 } 00787 00788 // Substitute constants in the Setup code: 00789 if ($this->tt_track) $GLOBALS['TT']->push('Substitute Constants ('.count($this->flatSetup).')'); 00790 $all = $this->substituteConstants($all); 00791 if ($this->tt_track) $GLOBALS['TT']->pull(); 00792 00793 // Searching for possible unsubstituted constants left (only for information) 00794 if (strstr($all,'{$')) { 00795 $findConst = explode('{$',$all); 00796 $theConstList=Array(); 00797 next($findConst); 00798 while(list(,$constVal)=each($findConst)) { 00799 $constLen=t3lib_div::intInRange(strcspn($constVal,'}'),0,50); 00800 $theConstList[]='{$'.substr($constVal,0,$constLen+1); 00801 } 00802 if ($this->tt_track) $GLOBALS['TT']->setTSlogMessage(implode(',',$theConstList).': Constants may remain un-substituted!!',2); 00803 } 00804 00805 // Logging the textual size of the TypoScript Setup field text with all constants substituted: 00806 if ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('TypoScript template size as textfile: '.strlen($all).' bytes'); 00807 00808 // Finally parse the Setup field TypoScript code (where constants are now substituted) 00809 $config->parse($all,$matchObj); 00810 00811 // Read out parse errors if any 00812 $this->parserErrors['config']=$config->errors; 00813 00814 // Transfer the TypoScript array from the parser object to the internal $this->setup array: 00815 $this->setup = $config->setup; 00816 if ($this->backend_info) { 00817 $this->setup_constants = $constants->setup; // Used for backend purposes only 00818 } 00819 00820 00821 00822 00823 // ************************************************** 00824 // Parse Backend Editor Configuration (backend only) 00825 // ************************************************** 00826 if ($this->parseEditorCfgField) { 00827 $editorcfg = t3lib_div::makeInstance('t3lib_TSparser'); 00828 $editorcfg->breakPointLN=intval($this->ext_editorcfg_BRP); 00829 $editorcfg->setup = array(); // Empty as a start... 00830 00831 $all = implode("\n[GLOBAL]\n",$this->editorcfg); 00832 00833 // substitute constants in config 00834 $all = $this->substituteConstants($all); 00835 00836 // parse Config 00837 $matchObj->matchAll=1; // This should make sure that conditions are disabled. For now they are NOT active for the backend. 00838 $editorcfg->parse($all,$matchObj); 00839 $this->parserErrors['editorcfg']=$editorcfg->errors; 00840 $this->setup_editorcfg = $editorcfg->setup; 00841 } 00842 00843 00844 00845 00846 00847 // **************************************************************** 00848 // Final processing of the $this->setup TypoScript Template array 00849 // Basically: This is unsetting/setting of certain reserved keys. 00850 // **************************************************************** 00851 00852 // These vars are allready set after 'processTemplate', but because $config->setup overrides them (in the line above!), we set them again. They are not changed compared to the value they had in the top of the page! 00853 unset($this->setup['resources']); 00854 unset($this->setup['resources.']); 00855 $this->setup['resources']= implode(',',t3lib_div::trimExplode(',',$this->resources,1)); 00856 00857 unset($this->setup['sitetitle']); 00858 unset($this->setup['sitetitle.']); 00859 $this->setup['sitetitle']= $this->sitetitle; 00860 00861 // Unsetting some vars... 00862 unset($this->setup['types.']); 00863 unset($this->setup['types']); 00864 if (is_array($this->setup)) { 00865 reset ($this->setup); 00866 while(list($theKey,)=each($this->setup)) { 00867 if ($this->setup[$theKey]=='PAGE') { 00868 $tN = $this->setup[$theKey.'.']['typeNum']; 00869 if (isset($tN)) { 00870 $this->setup['types.'][$tN] = $theKey; 00871 } elseif(!$this->setup['types.'][0]) { // If there is no type 0 yet and typeNum was not set, we use the current object as the default 00872 $this->setup['types.'][0] = $theKey; 00873 } 00874 } 00875 } 00876 } 00877 unset($this->setup['styles.']); 00878 unset($this->setup['temp.']); 00879 unset($constants); 00880 00881 // Storing the conditions found/matched information: 00882 $this->sections = $config->sections; 00883 $this->sectionsMatch = $config->sectionsMatch; 00884 } 00885 00893 function procesIncludes() { 00894 reset($this->constants); 00895 while(list($k)=each($this->constants)) { 00896 $this->constants[$k]=t3lib_TSparser::checkIncludeLines($this->constants[$k]); 00897 } 00898 00899 reset($this->config); 00900 while(list($k)=each($this->config)) { 00901 $this->config[$k]=t3lib_TSparser::checkIncludeLines($this->config[$k]); 00902 } 00903 00904 reset($this->editorcfg); 00905 while(list($k)=each($this->editorcfg)) { 00906 $this->editorcfg[$k]=t3lib_TSparser::checkIncludeLines($this->editorcfg[$k]); 00907 } 00908 } 00909 00917 function mergeConstantsFromPageTSconfig($constArray) { 00918 $TSdataArray = array(); 00919 $TSdataArray[]=$GLOBALS['TYPO3_CONF_VARS']['BE']['defaultPageTSconfig']; // Setting default configuration: 00920 00921 for ($a=0;$a<=$this->outermostRootlineIndexWithTemplate;$a++) { 00922 $TSdataArray[]=$this->absoluteRootLine[$a]['TSconfig']; 00923 } 00924 // Parsing the user TS (or getting from cache) 00925 $TSdataArray = t3lib_TSparser::checkIncludeLines_array($TSdataArray); 00926 $userTS = implode(chr(10).'[GLOBAL]'.chr(10),$TSdataArray); 00927 00928 $parseObj = t3lib_div::makeInstance('t3lib_TSparser'); 00929 $parseObj->parse($userTS); 00930 00931 if (is_array($parseObj->setup['TSFE.']['constants.'])) { 00932 $constArray = t3lib_div::array_merge_recursive_overrule($constArray,$parseObj->setup['TSFE.']['constants.']); 00933 } 00934 return $constArray; 00935 } 00936 00946 function flattenSetup($setupArray, $prefix, $resourceFlag) { 00947 if (is_array($setupArray)) { 00948 reset($setupArray); 00949 while(list($key,$val)=each($setupArray)) { 00950 if ($prefix || substr($key,0,16)!='TSConstantEditor') { // We don't want 'TSConstantEditor' in the flattend setup on the first level (190201) 00951 if (is_array($val)) { 00952 $this->flattenSetup($val,$prefix.$key, ($key=='file.')); 00953 } elseif ($resourceFlag) { 00954 $this->flatSetup[$prefix.$key] = $this->getFileName($val); 00955 } else { 00956 $this->flatSetup[$prefix.$key] = $val; 00957 } 00958 } 00959 } 00960 } 00961 } 00962 00970 function substituteConstants($all) { 00971 if ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('Constants to substitute: '.count($this->flatSetup)); 00972 00973 $noChange = false; 00974 // recursive substitution of constants (up to 10 nested levels) 00975 for ($i = 0; $i < 10 && !$noChange; $i++) { 00976 $old_all = $all; 00977 $all = preg_replace_callback('/\{\$(.[^}]*)\}/', array($this, 'substituteConstantsCallBack'), $all); 00978 if ($old_all == $all) { 00979 $noChange = true; 00980 } 00981 } 00982 00983 return $all; 00984 } 00985 00993 function substituteConstantsCallBack($matches) { 00994 // replace {$CONST} if found in $this->flatSetup, else leave unchanged 00995 return isset($this->flatSetup[$matches[1]]) && !is_array($this->flatSetup[$matches[1]]) ? $this->flatSetup[$matches[1]] : $matches[0]; 00996 } 00997 00998 00999 01000 01001 01002 01003 01004 01005 01006 01007 /******************************************************************* 01008 * 01009 * Various API functions, used from elsewhere in the frontend classes 01010 * 01011 *******************************************************************/ 01012 01024 function splitConfArray($conf,$splitCount) { 01025 01026 // Initialize variables: 01027 $splitCount = intval($splitCount); 01028 $conf2 = Array(); 01029 01030 if ($splitCount && is_array($conf)) { 01031 01032 // Initialize output to carry at least the keys: 01033 for ($aKey=0;$aKey<$splitCount;$aKey++) { 01034 $conf2[$aKey] = array(); 01035 } 01036 01037 // Recursive processing of array keys: 01038 foreach($conf as $cKey => $val) { 01039 if (is_array($val)) { 01040 $tempConf = $this->splitConfArray($val,$splitCount); 01041 foreach($tempConf as $aKey => $val) { 01042 $conf2[$aKey][$cKey] = $val; 01043 } 01044 } 01045 } 01046 01047 // Splitting of all values on this level of the TypoScript object tree: 01048 foreach($conf as $cKey => $val) { 01049 if (!is_array($val)) { 01050 if (!strstr($val,'|*|') && !strstr($val,'||')) { 01051 for ($aKey=0;$aKey<$splitCount;$aKey++) { 01052 $conf2[$aKey][$cKey] = $val; 01053 } 01054 } else { 01055 $main = explode ('|*|',$val); 01056 $mainCount = count($main); 01057 01058 $lastC = 0; 01059 $middleC = 0; 01060 $firstC = 0; 01061 01062 if ($main[0]) { 01063 $first = explode('||',$main[0]); 01064 $firstC = count($first); 01065 } 01066 if ($main[1]) { 01067 $middle = explode('||',$main[1]); 01068 $middleC = count($middle); 01069 } 01070 if ($main[2]) { 01071 $last = explode('||',$main[2]); 01072 $lastC = count($last); 01073 $value = $last[0]; 01074 } 01075 01076 for ($aKey=0;$aKey<$splitCount;$aKey++) { 01077 if ($firstC && isset($first[$aKey])) { 01078 $value = $first[$aKey]; 01079 } elseif ($middleC) { 01080 $value = $middle[($aKey-$firstC)%$middleC]; 01081 } 01082 if ($lastC && $lastC>=($splitCount-$aKey)) { 01083 $value = $last[$lastC-($splitCount-$aKey)]; 01084 } 01085 $conf2[$aKey][$cKey] = trim($value); 01086 } 01087 } 01088 } 01089 } 01090 } 01091 return $conf2; 01092 } 01093 01101 function getFileName($fileFromSetup) { 01102 $file = trim($fileFromSetup); 01103 if (!$file) { 01104 return; 01105 } elseif (strstr($file,'../')) { 01106 if ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('File path "'.$file.'" contained illegal string "../"!',3); 01107 return; 01108 } 01109 // cache 01110 $hash = md5($file); 01111 if (isset($this->fileCache[$hash])) { 01112 return $this->fileCache[$hash]; 01113 } 01114 01115 if (!strcmp(substr($file,0,4),'EXT:')) { 01116 $newFile=''; 01117 list($extKey,$script)=explode('/',substr($file,4),2); 01118 if ($extKey && t3lib_extMgm::isLoaded($extKey)) { 01119 $extPath=t3lib_extMgm::extPath($extKey); 01120 $newFile=substr($extPath,strlen(PATH_site)).$script; 01121 } 01122 if (!@is_file(PATH_site.$newFile)) { 01123 if ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('Extension media file "'.$newFile.'" was not found!',3); 01124 return; 01125 } else $file=$newFile; 01126 } 01127 01128 // find 01129 if (strstr($file,'/')) { // here it is manual media 01130 if(!strcmp(substr($file,0,6),'media/')) $file = 'typo3/sysext/cms/tslib/'.$file; 01131 if (@is_file($this->getFileName_backPath.$file)) { 01132 $outFile = $file; 01133 $fileInfo = t3lib_div::split_fileref($outFile); 01134 reset($this->allowedPaths); 01135 $OK=0; 01136 while(list(,$val)=each($this->allowedPaths)) { 01137 if (substr($fileInfo['path'],0,strlen($val))==$val){$OK=1; break;} 01138 } 01139 if ($OK) { 01140 $this->fileCache[$hash]=$outFile; 01141 return $outFile; 01142 } elseif ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('"'.$file.'" was not located in the allowed paths: ('.implode(',',$this->allowedPaths).')',3); 01143 } elseif ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('"'.$this->getFileName_backPath.$file.'" is not a file (non-uploads/.. resource, did not exist).',3); 01144 } else { // Here it is uploaded media: 01145 $outFile = $this->extractFromResources($this->setup['resources'],$file); 01146 if ($outFile) { 01147 if (@is_file($this->uplPath.$outFile)) { 01148 $this->fileCache[$hash] = $this->uplPath.$outFile; 01149 return $this->uplPath.$outFile; 01150 } elseif ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('"'.$this->uplPath.$outFile.'" is not a file (did not exist).',3); 01151 } elseif ($this->tt_track) $GLOBALS['TT']->setTSlogMessage('"'.$file.'" is not a file (uploads/.. resource).',3); 01152 } 01153 } 01154 01164 function extractFromResources($res,$file) { 01165 if (t3lib_div::inList($res,$file)) { 01166 $outFile = $file; 01167 } elseif (strstr($file,'*')) { 01168 $fileparts=explode('*',$file); 01169 $c=count($fileparts); 01170 $files = explode(',',$res); 01171 while(list(,$val)=each($files)) { 01172 $test = trim($val); 01173 if (ereg('^'.quotemeta($fileparts[0]).'.*'.quotemeta($fileparts[$c-1]).'$', $test)) { 01174 $outFile = $test; 01175 break; 01176 } 01177 } 01178 } 01179 return $outFile; 01180 } 01181 01192 function checkFile($name,$menuArr) { 01193 reset ($menuArr); 01194 while (list($aKey,)=each($menuArr)) { 01195 $menuArr[$aKey][$name] = $this->getFileName($menuArr[$aKey][$name]); 01196 } 01197 return $menuArr; 01198 } 01199 01209 function printTitle($title,$no_title=0,$titleFirst=0) { 01210 $st = trim($this->setup['sitetitle']) ? $this->setup['sitetitle']:''; 01211 $title = $no_title ? '' : $title; 01212 if ($titleFirst) { 01213 $temp=$st; 01214 $st=$title; 01215 $title=$temp; 01216 } 01217 if ($title && $st) { 01218 return $st.': '.$title; 01219 } else { 01220 return $st.$title; 01221 } 01222 } 01223 01232 function fileContent($fName) { 01233 $incFile = $this->getFileName($fName); 01234 if ($incFile) { 01235 return @file_get_contents($incFile); 01236 } 01237 } 01238 01247 function wrap($content,$wrap) { 01248 if ($wrap) { 01249 $wrapArr = explode('|', $wrap); 01250 return trim($wrapArr[0]).$content.trim($wrapArr[1]); 01251 } else return $content; 01252 } 01253 01261 function removeQueryString($url) { 01262 if (substr($url,-1)=='?') { 01263 return substr($url,0,-1); 01264 } else { 01265 return $url; 01266 } 01267 } 01268 01278 function sortedKeyList($setupArr, $acceptOnlyProperties=FALSE) { 01279 $keyArr = Array(); 01280 01281 reset($setupArr); 01282 while(list($key,)=each($setupArr)) { 01283 $ikey = intval($key); 01284 if (!strcmp($ikey,$key) || $acceptOnlyProperties) { 01285 $keyArr[] = $ikey; 01286 } 01287 } 01288 01289 $keyArr = array_unique($keyArr); 01290 sort($keyArr); 01291 return $keyArr; 01292 } 01293 01294 01295 01296 01297 01298 01299 01300 01301 01302 01303 /******************************************************************* 01304 * 01305 * Functions for creating links 01306 * 01307 *******************************************************************/ 01308 01325 function linkData($page,$oTarget,$no_cache,$script,$overrideArray='',$addParams='',$typeOverride='') { 01326 global $TYPO3_CONF_VARS; 01327 01328 $LD = Array(); 01329 01330 // Overriding some fields in the page record and still preserves the values by adding them as parameters. Little strange function. 01331 if (is_array($overrideArray)) { 01332 foreach($overrideArray as $theKey => $theNewVal) { 01333 $addParams.= '&real_'.$theKey.'='.rawurlencode($page[$theKey]); 01334 $page[$theKey] = $theNewVal; 01335 } 01336 } 01337 01338 // Adding Mount Points, "&MP=", parameter for the current page if any is set: 01339 if (!strstr($addParams,'&MP=')) { 01340 if (trim($GLOBALS['TSFE']->MP_defaults[$page['uid']])) { // Looking for hardcoded defaults: 01341 $addParams.= '&MP='.rawurlencode(trim($GLOBALS['TSFE']->MP_defaults[$page['uid']])); 01342 } elseif ($GLOBALS['TSFE']->config['config']['MP_mapRootPoints']) { // Else look in automatically created map: 01343 $m = $this->getFromMPmap($page['uid']); 01344 if ($m) { 01345 $addParams.= '&MP='.rawurlencode($m); 01346 } 01347 } 01348 } 01349 01350 // Setting ID/alias: 01351 if (!$script) {$script = $GLOBALS['TSFE']->config['mainScript'];} 01352 if ($page['alias']) { 01353 $LD['url'] = $script.'?id='.rawurlencode($page['alias']); 01354 } else { 01355 $LD['url'] = $script.'?id='.$page['uid']; 01356 } 01357 // Setting target 01358 $LD['target'] = trim($page['target']) ? trim($page['target']) : $oTarget; 01359 01360 // typeNum 01361 $typeNum = $this->setup[$LD['target'].'.']['typeNum']; 01362 if (!t3lib_div::testInt($typeOverride) && intval($GLOBALS['TSFE']->config['config']['forceTypeValue'])) { 01363 $typeOverride = intval($GLOBALS['TSFE']->config['config']['forceTypeValue']); 01364 } 01365 if (strcmp($typeOverride,'')) { $typeNum = $typeOverride; } // Override... 01366 if ($typeNum) { 01367 $LD['type'] = '&type='.intval($typeNum); 01368 } else { 01369 $LD['type'] = ''; 01370 } 01371 $LD['orig_type'] = $LD['type']; // Preserving the type number. Will not be cleared if simulateStaticDocuments. 01372 01373 // noCache 01374 $LD['no_cache'] = (trim($page['no_cache']) || $no_cache) ? '&no_cache=1' : ''; 01375 01376 // linkVars 01377 if ($GLOBALS['TSFE']->config['config']['uniqueLinkVars']) { 01378 if ($addParams) { 01379 $LD['linkVars'] = t3lib_div::implodeArrayForUrl('',t3lib_div::explodeUrl2Array($GLOBALS['TSFE']->linkVars.$addParams)); 01380 } else { 01381 $LD['linkVars'] = $GLOBALS['TSFE']->linkVars; 01382 } 01383 } else { 01384 $LD['linkVars'] = $GLOBALS['TSFE']->linkVars.$addParams; 01385 } 01386 01387 // If simulateStaticDocuments is enabled: 01388 if ($GLOBALS['TSFE']->config['config']['simulateStaticDocuments']) { 01389 $LD['type'] = ''; 01390 $LD['url'] = ''; 01391 01392 // MD5/base64 method limitation: 01393 $remainLinkVars=''; 01394 $flag_simulateStaticDocuments_pEnc = t3lib_div::inList('md5,base64',$GLOBALS['TSFE']->config['config']['simulateStaticDocuments_pEnc']) && !$LD['no_cache']; 01395 if ($flag_simulateStaticDocuments_pEnc) { 01396 list($LD['linkVars'], $remainLinkVars) = $GLOBALS['TSFE']->simulateStaticDocuments_pEnc_onlyP_proc($LD['linkVars']); 01397 } 01398 01399 $LD['url'].=$GLOBALS['TSFE']->makeSimulFileName( 01400 $page['title'], 01401 $page['alias'] ? $page['alias'] : $page['uid'], 01402 intval($typeNum), 01403 $LD['linkVars'], 01404 $LD['no_cache'] ? true : false 01405 ); 01406 01407 if ($flag_simulateStaticDocuments_pEnc) { 01408 $LD['linkVars']=$remainLinkVars; 01409 } 01410 if ($GLOBALS['TSFE']->config['config']['simulateStaticDocuments']=='PATH_INFO') { 01411 $LD['url'] = str_replace('.','/',$LD['url']); 01412 $LD['url'] = 'index.php/'.$LD['url'].'/?'; 01413 } else { 01414 $LD['url'].= '.html?'; 01415 } 01416 } 01417 01418 // Add absRefPrefix if exists. 01419 $LD['url'] = $GLOBALS['TSFE']->absRefPrefix.$LD['url']; 01420 01421 // If the special key 'sectionIndex_uid' (added 'manually' in tslib/menu.php to the page-record) is set, then the link jumps directly to a section on the page. 01422 $LD['sectionIndex'] = $page['sectionIndex_uid'] ? '#c'.$page['sectionIndex_uid'] : ''; 01423 01424 // Compile the normal total url 01425 $LD['totalURL']= $this->removeQueryString($LD['url'].$LD['type'].$LD['no_cache'].$LD['linkVars'].$GLOBALS['TSFE']->getMethodUrlIdToken).$LD['sectionIndex']; 01426 01427 // Call post processing function for link rendering: 01428 if (is_array($TYPO3_CONF_VARS['SC_OPTIONS']['t3lib/class.t3lib_tstemplate.php']['linkData-PostProc'])) { 01429 $_params = array( 01430 'LD' => &$LD, 01431 'args' => array('page'=>$page, 'oTarget'=>$oTarget, 'no_cache'=>$no_cache, 'script'=>$script, 'overrideArray'=>$overrideArray, 'addParams'=>$addParams, 'typeOverride'=>$typeOverride), 01432 'typeNum' => $typeNum 01433 ); 01434 foreach ($TYPO3_CONF_VARS['SC_OPTIONS']['t3lib/class.t3lib_tstemplate.php']['linkData-PostProc'] as $_funcRef) { 01435 t3lib_div::callUserFunction($_funcRef,$_params,$this); 01436 } 01437 } 01438 01439 // Return the LD-array 01440 return $LD; 01441 } 01442 01452 function getFromMPmap($pageId=0) { 01453 01454 // Create map if not found already: 01455 if (!is_array($this->MPmap)) { 01456 $this->MPmap = array(); 01457 01458 $rootPoints = t3lib_div::trimExplode(',', strtolower($GLOBALS['TSFE']->config['config']['MP_mapRootPoints']),1); 01459 foreach($rootPoints as $p) { // Traverse rootpoints: 01460 if ($p == 'root') { 01461 $p = $this->rootLine[0]['uid']; 01462 $initMParray = array(); 01463 if ($this->rootLine[0]['_MOUNT_OL'] && $this->rootLine[0]['_MP_PARAM']) { 01464 $initMParray[] = $this->rootLine[0]['_MP_PARAM']; 01465 } 01466 } 01467 $this->initMPmap_create($p,$initMParray); 01468 } 01469 } 01470 01471 // Finding MP var for Page ID: 01472 if ($pageId) { 01473 if (is_array($this->MPmap[$pageId]) && count($this->MPmap[$pageId])) { 01474 return implode(',',$this->MPmap[$pageId]); 01475 } 01476 } 01477 } 01478 01488 function initMPmap_create($id,$MP_array=array(),$level=0) { 01489 01490 $id = intval($id); 01491 if($id<=0) return; 01492 01493 // First level, check id 01494 if (!$level) { 01495 01496 // Find mount point if any: 01497 $mount_info = $GLOBALS['TSFE']->sys_page->getMountPointInfo($id); 01498 01499 // Overlay mode: 01500 if (is_array($mount_info) && $mount_info['overlay']) { 01501 $MP_array[] = $mount_info['MPvar']; 01502 $id = $mount_info['mount_pid']; 01503 } 01504 01505 // Set mapping information for this level: 01506 $this->MPmap[$id] = $MP_array; 01507 01508 // Normal mode: 01509 if (is_array($mount_info) && !$mount_info['overlay']) { 01510 $MP_array[] = $mount_info['MPvar']; 01511 $id = $mount_info['mount_pid']; 01512 } 01513 } 01514 01515 if ($id && $level<20) { 01516 01517 $nextLevelAcc = array(); 01518 01519 // Select and traverse current level pages: 01520 $res = $GLOBALS['TYPO3_DB']->exec_SELECTquery( 01521 'uid,pid,doktype,mount_pid,mount_pid_ol', 01522 'pages', 01523 'pid='.intval($id).' AND deleted=0 AND doktype!=255 AND doktype!=6' // 255 = Garbage bin, 6 = Backend User Section 01524 ); 01525 while ($row = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res)) { 01526 01527 // Find mount point if any: 01528 $next_id = $row['uid']; 01529 $next_MP_array = $MP_array; 01530 $mount_info = $GLOBALS['TSFE']->sys_page->getMountPointInfo($next_id, $row); 01531 01532 // Overlay mode: 01533 if (is_array($mount_info) && $mount_info['overlay']) { 01534 $next_MP_array[] = $mount_info['MPvar']; 01535 $next_id = $mount_info['mount_pid']; 01536 } 01537 01538 if (!isset($this->MPmap[$next_id])) { 01539 01540 // Set mapping information for this level: 01541 $this->MPmap[$next_id] = $next_MP_array; 01542 01543 // Normal mode: 01544 if (is_array($mount_info) && !$mount_info['overlay']) { 01545 $next_MP_array[] = $mount_info['MPvar']; 01546 $next_id = $mount_info['mount_pid']; 01547 } 01548 01549 // Register recursive call 01550 // (have to do it this way since ALL of the current level should be registered BEFORE the sublevel at any time) 01551 $nextLevelAcc[] = array($next_id,$next_MP_array); 01552 } 01553 } 01554 01555 // Call recursively, if any: 01556 foreach($nextLevelAcc as $pSet) { 01557 $this->initMPmap_create($pSet[0],$pSet[1],$level+1); 01558 } 01559 } 01560 } 01561 } 01562 01563 01564 if (defined('TYPO3_MODE') && $TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['t3lib/class.t3lib_tstemplate.php']) { 01565 include_once($TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['t3lib/class.t3lib_tstemplate.php']); 01566 } 01567 ?>