class.tslib_fe.php 138 KB
Newer Older
Kasper Skårhøj's avatar
Kasper Skårhøj committed
1
2
3
<?php
/***************************************************************
*  Copyright notice
4
*
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
5
*  (c) 1999-2004 Kasper Skaarhoj (kasperYYYY@typo3.com)
Kasper Skårhøj's avatar
Kasper Skårhøj committed
6
7
*  All rights reserved
*
8
*  This script is part of the TYPO3 project. The TYPO3 project is
Kasper Skårhøj's avatar
Kasper Skårhøj committed
9
10
11
12
*  free software; you can redistribute it and/or modify
*  it under the terms of the GNU General Public License as published by
*  the Free Software Foundation; either version 2 of the License, or
*  (at your option) any later version.
13
*
Kasper Skårhøj's avatar
Kasper Skårhøj committed
14
15
*  The GNU General Public License can be found at
*  http://www.gnu.org/copyleft/gpl.html.
16
*  A copy is found in the textfile GPL.txt and important notices to the license
Kasper Skårhøj's avatar
Kasper Skårhøj committed
17
18
*  from the author is found in LICENSE.txt distributed with these scripts.
*
19
*
Kasper Skårhøj's avatar
Kasper Skårhøj committed
20
21
22
23
24
25
26
*  This script is distributed in the hope that it will be useful,
*  but WITHOUT ANY WARRANTY; without even the implied warranty of
*  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
*  GNU General Public License for more details.
*
*  This copyright notice MUST APPEAR in all copies of the script!
***************************************************************/
27
/**
Kasper Skårhøj's avatar
Kasper Skårhøj committed
28
29
30
31
 * Class for the built TypoScript based Front End
 *
 * This class has a lot of functions and internal variable which are use from index_ts.php.
 * The class is instantiated as $GLOBALS['TSFE'] in index_ts.php.
32
33
 * The use of this class should be inspired by the order of function calls as found in index_ts.php.
 *
34
35
 * $Id$
 * Revised for TYPO3 3.6 June/2003 by Kasper Skaarhoj
Kasper Skårhøj's avatar
Kasper Skårhøj committed
36
37
 * XHTML compliant
 *
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
38
 * @author	Kasper Skaarhoj <kasperYYYY@typo3.com>
Kasper Skårhøj's avatar
Kasper Skårhøj committed
39
40
41
42
43
44
 */
/**
 * [CLASS/FUNCTION INDEX of SCRIPT]
 *
 *
 *
45
46
47
48
49
 *  200: class tslib_fe
 *  366:     function tslib_fe($TYPO3_CONF_VARS, $id, $type, $no_cache='', $cHash='', $jumpurl='',$MP='',$RDCT='')
 *  399:     function connectToMySQL()
 *  409:     function connectToDB()
 *  454:     function sendRedirect()
Kasper Skårhøj's avatar
Kasper Skårhøj committed
50
51
 *
 *              SECTION: Initializing, resolving page id
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
 *  492:     function initFEuser()
 *  542:     function initUserGroups()
 *  589:     function checkAlternativeIdMethods()
 *  641:     function clear_preview()
 *  654:     function determineId()
 *  772:     function fetch_the_id()
 *  867:     function getPageAndRootline()
 *  933:     function getPageShortcut($SC,$mode,$thisUid,$itera=20,$pageLog=array())
 *  983:     function checkRootlineForIncludeSection()
 * 1016:     function checkEnableFields($row)
 * 1034:     function checkPageGroupAccess($row, $groupList=NULL)
 * 1053:     function checkPagerecordForIncludeSection($row)
 * 1062:     function checkIfLoginAllowedInBranch()
 * 1090:     function setIDfromArgV()
 * 1106:     function getPageAndRootlineWithDomain($domainStartPage)
 * 1133:     function setSysPageWhereClause()
 * 1143:     function getPagesGroupClause()
 * 1154:     function findDomainRecord($recursive=0)
 * 1173:     function pageNotFoundAndExit($reason='')
 * 1187:     function pageNotFoundHandler($code, $header='', $reason='')
 * 1225:     function checkAndSetAlias()
 * 1240:     function idPartsAnalyze($str)
 * 1265:     function mergingWithGetVars($GET_VARS)
Kasper Skårhøj's avatar
Kasper Skårhøj committed
75
76
 *
 *              SECTION: Template and caching related functions.
77
78
79
80
81
82
83
 * 1313:     function makeCacheHash()
 * 1336:     function cHashParams($addQueryParams)
 * 1345:     function initTemplate()
 * 1357:     function getFromCache()
 * 1416:     function headerNoCache()
 * 1443:     function getHash()
 * 1463:     function getConfigArray()
Kasper Skårhøj's avatar
Kasper Skårhøj committed
84
85
 *
 *              SECTION: Further initialization and data processing
86
87
88
89
90
91
92
93
94
95
96
 * 1585:     function getCompressedTCarray()
 * 1639:     function includeTCA($TCAloaded=1)
 * 1666:     function settingLanguage()
 * 1756:     function settingLocale()
 * 1781:     function checkDataSubmission()
 * 1806:     function fe_tce()
 * 1820:     function locDataCheck($locationData)
 * 1836:     function sendFormmail()
 * 1879:     function checkJumpUrl()
 * 1961:     function jumpUrl()
 * 2004:     function setUrlIdToken()
Kasper Skårhøj's avatar
Kasper Skårhøj committed
97
98
 *
 *              SECTION: Page generation; cache handling
99
100
101
102
103
104
105
 * 2047:     function isGeneratePage()
 * 2057:     function tempPageCacheContent()
 * 2089:     function realPageCacheContent()
 * 2119:     function setPageCacheContent($c,$d,$t)
 * 2144:     function clearPageCacheContent()
 * 2154:     function clearPageCacheContent_pidList($pidList)
 * 2165:     function setSysLastChanged()
Kasper Skårhøj's avatar
Kasper Skårhøj committed
106
107
 *
 *              SECTION: Page generation; rendering and inclusion
108
109
110
111
112
113
114
115
 * 2201:     function generatePage_preProcessing()
 * 2223:     function generatePage_whichScript()
 * 2235:     function generatePage_postProcessing()
 * 2327:     function INTincScript()
 * 2387:     function INTincScript_loadJSCode()
 * 2428:     function isINTincScript()
 * 2437:     function doXHTML_cleaning()
 * 2446:     function doLocalAnchorFix()
Kasper Skårhøj's avatar
Kasper Skårhøj committed
116
117
 *
 *              SECTION: Finished off; outputting, storing session data, statistics...
118
119
120
121
122
123
124
125
126
127
128
129
 * 2477:     function isOutputting()
 * 2500:     function processOutput()
 * 2572:     function sendCacheHeaders()
 * 2633:     function isStaticCacheble()
 * 2648:     function contentStrReplace()
 * 2674:     function isEXTincScript()
 * 2683:     function storeSessionData()
 * 2693:     function setParseTime()
 * 2705:     function statistics()
 * 2804:     function previewInfo()
 * 2825:     function hook_eofe()
 * 2841:     function beLoginLinkIPList()
Kasper Skårhøj's avatar
Kasper Skårhøj committed
130
131
 *
 *              SECTION: Various internal API functions
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
 * 2896:     function makeSimulFileName($inTitle,$page,$type,$addParams='',$no_cache='')
 * 2939:     function simulateStaticDocuments_pEnc_onlyP_proc($linkVars)
 * 2968:     function getSimulFileName()
 * 2982:     function fileNameASCIIPrefix($inTitle,$titleChars,$mergeChar='.')
 * 3000:     function encryptEmail($string,$back=0)
 * 3019:     function codeString($string, $decode=FALSE)
 * 3045:     function roundTripCryptString($string)
 * 3065:     function checkFileInclude($incFile)
 * 3080:     function newCObj()
 * 3093:     function setAbsRefPrefix()
 * 3107:     function baseUrlWrap($url)
 * 3126:     function printError($label,$header='Error!')
 * 3137:     function updateMD5paramsRecord($hash)
 * 3148:     function tidyHTML($content)
 * 3174:     function prefixLocalAnchorsWithScript()
Kasper Skårhøj's avatar
Kasper Skårhøj committed
147
148
 *
 *              SECTION: Various external API functions - for use in plugins etc.
149
150
151
152
153
154
155
156
157
 * 3218:     function getStorageSiterootPids()
 * 3233:     function getPagesTSconfig()
 * 3266:     function setJS($key,$content='')
 * 3304:     function setCSS($key,$content)
 * 3319:     function make_seed()
 * 3332:     function uniqueHash($str='')
 * 3341:     function set_no_cache()
 * 3351:     function set_cache_timeout_default($seconds)
 * 3367:     function plainMailEncoded($email,$subject,$message,$headers='')
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
158
 *
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
159
 *              SECTION: Localization
160
161
162
163
164
165
166
 * 3408:     function sL($input)
 * 3437:     function readLLfile($fileRef)
 * 3452:     function getLLL($index,$LOCAL_LANG)
 * 3466:     function initLLvars()
 * 3500:     function csConv($str,$from='')
 * 3518:     function convOutputCharset($content,$label)
 * 3531:     function convPOSTCharset()
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
167
 *
168
 * TOTAL FUNCTIONS: 103
Kasper Skårhøj's avatar
Kasper Skårhøj committed
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
 * (This index is automatically created/updated by the extension "extdeveval")
 *
 */





















/**
 * Main frontend class, instantiated in the index_ts.php script as the global object TSFE
195
 *
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
196
 * @author	Kasper Skaarhoj <kasperYYYY@typo3.com>
197
198
 * @package TYPO3
 * @subpackage tslib
Kasper Skårhøj's avatar
Kasper Skårhøj committed
199
200
201
202
203
204
205
206
207
208
209
210
211
 */
 class tslib_fe	{

		// CURRENT PAGE:
	var $id='';							// The page id (int)
	var $type='';						// RO The type (int)
	var $idParts=array();				// Loaded with the id, exploded by ','
	var $cHash='';						// The submitted cHash
	var $no_cache=''; 					// Page will not be cached. Write only true. Never clear value (some other code might have reasons to set it true)
	var $rootLine='';					// The rootLine (all the way to tree root, not only the current site!) (array)
	var $page='';						// The pagerecord (array)
	var $contentPid=0;					// This will normally point to the same value as id, but can be changed to point to another page from which content will then be displayed instead.
	var $sys_page='';					// The object with pagefunctions (object)
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
212
	var $jumpurl='';
Kasper Skårhøj's avatar
Kasper Skårhøj committed
213
214
215
216
217
	var $pageNotFound=0;				// Is set to 1 if a pageNotFound handler could have been called.
	var $domainStartPage=0;				// Domain start page
	var $MP='';
	var $RDCT='';
	var $page_cache_reg1=0;				// This can be set from applications as a way to tag cached versions of a page and later perform some external cache management, like clearing only a part of the cache of a page...
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
218
	var $siteScript='';					// Contains the value of the current script path that activated the frontend. Typically "index.php" but by rewrite rules it could be something else! Used for Speaking Urls / Simulate Static Documents.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
219
220
221

		// USER
	var $fe_user='';					// The user (object)
222
	var $loginUser='';					// Global falg indicating that a front-end user is logged in. This is set only if a user really IS logged in. The group-list may show other groups (like added by IP filter or so) even though there is no user.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
223
224
	var $gr_list='';					// (RO=readonly) The group list, sorted numerically. Group '0,-1' is the default group, but other groups may be added by other means than a user being logged in though...
	var $beUserLogin='';				// Flag that indicates if a Backend user is logged in!
225
	var $loginAllowedInBranch = TRUE;	// Shows whether logins are allowed in branch
Kasper Skårhøj's avatar
Kasper Skårhøj committed
226
227
228
229
230
231

		// PREVIEW
	var $fePreview='';					// Flag indication that preview is active. This is based on the login of a backend user and whether the backend user has read access to the current page.
	var $showHiddenPage='';				// Flag indicating that hidden pages should be shown, selected and so on. This goes for almost all selection of pages!
	var $showHiddenRecords='';			// Flag indicating that hidden records should be shown. This includes sys_template, pages_language_overlay and even fe_groups in addition to all other regular content. So in effect, this includes everything except pages.
	var $simUserGroup='0';				// Value that contains the simulated usergroup if any
232
	var $versionPreviewMap=array();		// Versioning Preview record map (temporary, for sys_page)
Kasper Skårhøj's avatar
Kasper Skårhøj committed
233
234
235
236

		// CONFIGURATION
	var $TYPO3_CONF_VARS=array();		// The configuration array as set up in t3lib/config_default.php. Should be an EXACT copy of the global array.
	var $config='';						// 'CONFIG' object from TypoScript. Array generated based on the TypoScript configuration of the current page. Saved with the cached pages.
237
	var $TCAcachedExtras=array();		// Array of cached information from TCA. This is NOT TCA itself!
Kasper Skårhøj's avatar
Kasper Skårhøj committed
238
239
240
241
242

		// TEMPLATE / CACHE
	var $tmpl='';						// The TypoScript template object. Used to parse the TypoScript template
	var $cacheTimeOutDefault='';		// Is set to the time-to-live time of cached pages. If false, default is 60*60*24, which is 24 hours.
	var $cacheContentFlag='';			// Set internally if cached content is fetched from the database
243
244
	var $cacheExpires=0;				// Set to the expire time of cached content
	var $isClientCachable=FALSE;		// Set if cache headers allowing caching are sent.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
	var $all='';						// $all used by template fetching system. This array is an identification of the template. If $this->all is empty it's because the template-data is not cached, which it must be.
	var $sPre='';						// toplevel - objArrayName, eg 'page'
	var $pSetup='';						// TypoScript configuration of the page-object pointed to by sPre. $this->tmpl->setup[$this->sPre.'.']
	var $newHash='';					// This hash is unique to the template, the $this->id and $this->type vars and the gr_list (list of groups). Used to get and later store the cached data
	var $getMethodUrlIdToken='';		// If config.ftu (Frontend Track User) is set in TypoScript for the current page, the string value of this var is substituted in the rendered source-code with the string, '&ftu=[token...]' which enables GET-method usertracking as opposed to cookie based
	var $noCacheBeforePageGen='';		// This flag is set before inclusion of pagegen.php IF no_cache is set. If this flag is set after the inclusion of pagegen.php, no_cache is forced to be set. This is done in order to make sure that php-code from pagegen does not falsely clear the no_cache flag.
	var $tempContent='';				// This flag indicates if temporary content went into the cache during page-generation.
	var $forceTemplateParsing='';				// Boolean, passed to TypoScript template class and tells it to render the template forcibly
	var $cHash_array=array();			// The array which cHash_calc is based on, see ->makeCacheHash().
	var $hash_base='';					// Loaded with the serialized array that is used for generating a hashstring for the cache
	var $pagesTSconfig='';				// May be set to the pagesTSconfig
		// PAGE-GENERATION / cOBJ
	/*
		Eg. insert JS-functions in this array ($additionalHeaderData) to include them once. Use associative keys.
		Keys in use:
			JSFormValidate	:		<script type="text/javascript" src="'.$GLOBALS["TSFE"]->absRefPrefix.'t3lib/jsfunc.validateform.js"></script>
			JSincludeFormupdate :	<script type="text/javascript" src="t3lib/jsfunc.updateform.js"></script>
			JSMenuCode, JSMenuCode_menu :			JavaScript for the JavaScript menu
			JSCode : reserved
			JSImgCode : reserved
	*/
Kasper Skårhøj's avatar
Kasper Skårhøj committed
266
	var $defaultBodyTag='<body bgcolor="#FFFFFF">';		// Default bodytag, if nothing else is set. This can be overridden by applications like TemplaVoila.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
	var $additionalHeaderData=array();	// used to accumulate additional HTML-code for the header-section, <head>...</head>. Insert either associative keys (like additionalHeaderData['myStyleSheet'], see reserved keys above) or num-keys (like additionalHeaderData[] = '...')
	var $additionalJavaScript=array();	// used to accumulate additional JavaScript-code. Works like additionalHeaderData. Reserved keys at 'openPic' and 'mouseOver'
	var $additionalCSS=array();			// used to accumulate additional Style code. Works like additionalHeaderData.
	var $JSeventFuncCalls = array(		// you can add JavaScript functions to each entry in these arrays. Please see how this is done in the GMENU_LAYERS script. The point is that many applications on a page can set handlers for onload, onmouseover and onmouseup
		'onmousemove' => array(),
		'onmouseup' => array(),
		'onload' => array(),
	);
	var $JSCode='';						// Depreciated, use additionalJavaScript instead.
	var $JSImgCode='';					// Used to accumulate JavaScript loaded images (by menus)
	var $divSection='';					// Used to accumulate DHTML-layers.

		// RENDERING configuration, settings from TypoScript is loaded into these vars. See pagegen.php
	var $debug='';						// Debug flag, may output special debug html-code.
	var $intTarget='';					// Default internal target
	var $extTarget='';					// Default external target
	var $MP_defaults=array();			// Keys are page ids and values are default &MP (mount point) values to set when using the linking features...)
	var $spamProtectEmailAddresses=0;	// If set, typolink() function encrypts email addresses. Is set in pagegen-class.
	var $absRefPrefix='';				// Absolute Reference prefix
	var $absRefPrefix_force=0;			// Absolute Reference prefix force flag. This is set, if the type and id is retrieve from PATH_INFO and thus we NEED to prefix urls with at least '/'
	var $compensateFieldWidth='';		// Factor for form-field widths compensation
	var $lockFilePath='';				// Lock file path
	var $ATagParams='';					// <A>-tag parameters
	var $sWordRegEx='';					// Search word regex, calculated if there has been search-words send. This is used to mark up the found search words on a page when jumped to from a link in a search-result.
	var $sWordList='';					// Is set to the incoming array sword_list in case of a page-view jumped to from a search-result.
	var $linkVars='';					// A string prepared for insertion in all links on the page as url-parameters. Based on configuration in TypoScript where you defined which GET_VARS you would like to pass on.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
293
	var $excludeCHashVars='';			// A string set with a comma list of additional GET vars which should NOT be included in the cHash calculation. These vars should otherwise be detected and involved in caching, eg. through a condition in TypoScript.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
294
295
	var $displayEditIcons='';			// If set, edit icons are rendered aside content records. Must be set only if the ->beUserLogin flag is set and set_no_cache() must be called as well.
	var $displayFieldEditIcons='';		// If set, edit icons are rendered aside individual fields of content. Must be set only if the ->beUserLogin flag is set and set_no_cache() must be called as well.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
296
297
	var $sys_language_uid=0;			// Site language, 0 (zero) is default, int+ is uid pointing to a sys_language record. Should reflect which language it DOES actually display!
	var $sys_language_mode='';			// Site language mode
298
299
	var $sys_language_content=0;		// Site content selection uid
	var $sys_language_contentOL=0;		// Site content overlay flag; If set - and sys_language_content is > 0 - , records selected will try to look for a translation pointing to their uid. (If configured in [ctrl][languageField] / [ctrl][transOrigP...]
Kasper Skårhøj's avatar
Kasper Skårhøj committed
300
	var $sys_language_isocode = '';		// Is set to the iso code of the sys_language_content if that is properly defined by the sys_language record representing the sys_language_uid. (Requires the extension "static_info_tables")
Kasper Skårhøj's avatar
Kasper Skårhøj committed
301

302
		// RENDERING data
Kasper Skårhøj's avatar
Kasper Skårhøj committed
303
	var $applicationData=Array();		//	 'Global' Storage for various applications. Keys should be 'tx_'.extKey for extensions.
304
	var $register=Array();
Kasper Skårhøj's avatar
Kasper Skårhøj committed
305
306
307
308
309
310
311
312
313
314
315
316
	var $registerStack=Array();			// Stack used for storing array and retrieving register arrays (see LOAD_REGISTER and CLEAR_REGISTER)
	var $cObjectDepthCounter = 50;		// Checking that the function is not called eternally. This is done by interrupting at a depth of 50
	var $recordRegister = Array();		// used by cObj->RECORDS and cObj->CONTENT to ensure the a records is NOT rendered twice through it!
	var $currentRecord = '';			// This is set to the [table]:[uid] of the latest record rendered. Note that class tslib_cObj has an equal value, but that is pointing to the record delivered in the $data-array of the tslib_cObj instance, if the cObjects CONTENT or RECORD created that instance
	var $accessKey =array();			// Used by class tslib_menu to keep track of access-keys.
	var $imagesOnPage=array();			// Numerical array where image filenames are added if they are referenced in the rendered document. This includes only TYPO3 generated/inserted images.
	var $lastImageInfo=array();			// Is set in tslib_cObj->cImage() function to the info-array of the most recent rendered image. The information is used in tslib_cObj->IMGTEXT
	var $uniqueCounter=0;				// Used to generate page-unique keys. Point is that uniqid() functions is very slow, so a unikey key is made based on this, see function uniqueHash()
	var $uniqueString='';
	var $indexedDocTitle='';			// This value will be used as the title for the page in the indexer (if indexing happens)
	var $altPageTitle='';				// Alternative page title (normally the title of the page record). Can be set from applications you make.
	var $pEncAllowedParamNames=array();	// An array that holds parameter names (keys) of GET parameters which MAY be MD5/base64 encoded with simulate_static_documents method.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
317
	var $baseUrl='';					// The Base url set for the page header.
318
	var $anchorPrefix='';				// The proper anchor prefix needed when using speaking urls. (only set if baseUrl is set)
Kasper Skårhøj's avatar
Kasper Skårhøj committed
319
320
321

		// Page content render object
	var $cObj ='';						// is instantiated object of tslib_cObj
322

Kasper Skårhøj's avatar
Kasper Skårhøj committed
323
324
		// CONTENT accumulation
	var $content='';					// All page content is accumulated in this variable. See pagegen.php
325

Kasper Skårhøj's avatar
Kasper Skårhøj committed
326
		// GENERAL
Kasper Skårhøj's avatar
Kasper Skårhøj committed
327
	var $clientInfo='';					// Set to the browser: net / msie if 4+ browsers
Kasper Skårhøj's avatar
Kasper Skårhøj committed
328
	var $scriptParseTime=0;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
329
	var $TCAloaded = 0;					// Set ONLY if the full TCA is loaded
330

331
332
333
334
335
336
337
		// Character set (charset) conversion object:
	var $csConvObj;						// An instance of the "t3lib_cs" class. May be used by any application.
	var $defaultCharSet = 'iso-8859-1';	// The default charset used in the frontend if nothing else is set.
	var $renderCharset='';				// Internal charset of the frontend during rendering: Defaults to "forceCharset" and if that is not set, to ->defaultCharSet
	var $metaCharset='';				// Output charset of the websites content. This is the charset found in the header, meta tag etc. If different from $renderCharset a conversion happens before output to browser. Defaults to ->renderCharset if not set.
	var $localeCharset='';				// Assumed charset of locale strings.

Kasper Skårhøj's avatar
Kasper Skårhøj committed
338
		// LANG:
Kasper Skårhøj's avatar
Kasper Skårhøj committed
339
340
341
342
	var $lang='';						// Set to the system language key (used on the site)
	var $langSplitIndex=0;				// Set to the index number of the language key
	var $labelsCharset='';				// Charset of the labels from locallang (based on $this->lang)
	var $convCharsetToFrom='';			// Set to the charsets to convert from/to IF there are any difference. Otherwise this stays a string
Kasper Skårhøj's avatar
Kasper Skårhøj committed
343
344
	var $LL_labels_cache=array();
	var $LL_files_cache=array();
345
346


Kasper Skårhøj's avatar
Kasper Skårhøj committed
347
348
349
350
351
352
353
354



	/**
	 * Class constructor
	 * Takes a number of GET/POST input variable as arguments and stores them internally.
	 * The processing of these variables goes on later in this class.
	 * Also sets internal clientInfo array (browser information) and a unique string (->uniqueString) for this script instance; A md5 hash of the microtime()
355
	 *
Kasper Skårhøj's avatar
Kasper Skårhøj committed
356
	 * @param	array		The global $TYPO3_CONF_VARS array. Will be set internally in ->TYPO3_CONF_VARS
Kasper Skårhøj's avatar
Kasper Skårhøj committed
357
358
359
360
361
362
363
	 * @param	mixed		The value of t3lib_div::_GP('id')
	 * @param	integer		The value of t3lib_div::_GP('type')
	 * @param	boolean		The value of t3lib_div::_GP('no_cache'), evaluated to 1/0
	 * @param	string		The value of t3lib_div::_GP('cHash')
	 * @param	string		The value of t3lib_div::_GP('jumpurl')
	 * @param	string		The value of t3lib_div::_GP('MP')
	 * @param	string		The value of t3lib_div::_GP('RDCT')
364
	 * @return	void
Kasper Skårhøj's avatar
Kasper Skårhøj committed
365
366
367
	 * @see index_ts.php
	 */
	function tslib_fe($TYPO3_CONF_VARS, $id, $type, $no_cache='', $cHash='', $jumpurl='',$MP='',$RDCT='')	{
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
368

Kasper Skårhøj's avatar
Kasper Skårhøj committed
369
			// Setting some variables:
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
370
		$this->TYPO3_CONF_VARS = $TYPO3_CONF_VARS;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
371
372
373
374
375
		$this->id = $id;
		$this->type = $type;
		$this->no_cache = $no_cache ? 1 : 0;
		$this->cHash = $cHash;
		$this->jumpurl = $jumpurl;
376
		$this->MP = $this->TYPO3_CONF_VARS['FE']['enable_mount_pids'] ? (string)$MP : '';
Kasper Skårhøj's avatar
Kasper Skårhøj committed
377
378
379
		$this->RDCT = $RDCT;
		$this->clientInfo = t3lib_div::clientInfo();
		$this->uniqueString=md5(microtime());
380

Kasper Skårhøj's avatar
Kasper Skårhøj committed
381
		$this->csConvObj = t3lib_div::makeInstance('t3lib_cs');
382

Kasper Skårhøj's avatar
Kasper Skårhøj committed
383
			// Call post processing function for constructor:
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
384
		if (is_array($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['tslib_fe-PostProc']))	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
385
			$_params = array('pObj' => &$this);
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
386
			foreach($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['tslib_fe-PostProc'] as $_funcRef)	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
387
388
				t3lib_div::callUserFunction($_funcRef,$_params,$this);
			}
389
		}
Kasper Skårhøj's avatar
Kasper Skårhøj committed
390
391
392
	}

	/**
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
393
	 * Connect to MySQL database
Kasper Skårhøj's avatar
Kasper Skårhøj committed
394
	 * May exit after outputting an error message or some JavaScript redirecting to the install tool.
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
395
	 * Use connectToDB() instead!
396
397
	 *
	 * @return	void
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
398
	 * @deprecated
Kasper Skårhøj's avatar
Kasper Skårhøj committed
399
400
	 */
	function connectToMySQL()	{
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
401
402
403
404
405
406
407
408
409
410
	  $this->connectToDB();
	}

	/**
	 * Connect to SQL database
	 * May exit after outputting an error message or some JavaScript redirecting to the install tool.
	 *
	 * @return	void
	 */
	function connectToDB()	{
411
		if ($GLOBALS['TYPO3_DB']->sql_pconnect(TYPO3_db_host, TYPO3_db_username, TYPO3_db_password))	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
412
413
414
415
416
417
418
419
420
			if (!TYPO3_db)	{
				$this->printError('No database selected','Database Error');
					// Redirects to the Install Tool:
				echo '<script type="text/javascript">
						/*<![CDATA[*/
					document.location = "'.TYPO3_mainDir.'install/index.php?mode=123&step=1&password=joh316";
						/*]]>*/
					</script>';
				exit;
421
			} elseif (!$GLOBALS['TYPO3_DB']->sql_select_db(TYPO3_db))	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
				$this->printError('Cannot connect to the current database, "'.TYPO3_db.'"','Database Error');
				exit;
			}
		} else {
			if (!TYPO3_db)	{
					// Redirects to the Install Tool:
				echo '<script type="text/javascript">
						/*<![CDATA[*/
					document.location = "'.TYPO3_mainDir.'install/index.php?mode=123&step=1&password=joh316";
						/*]]>*/
					</script>';
				exit;
			}
			$this->printError('The current username, password or host was not accepted when the connection to the database was attempted to be established!','Database Error');
			exit;
		}
438
439
440
441
442
443
444
445
446


			// Call post processing function for DB connection:
		if (is_array($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['connectToDB']))	{
			$_params = array('pObj' => &$this);
			foreach($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['connectToDB'] as $_funcRef)	{
				t3lib_div::callUserFunction($_funcRef,$_params,$this);
			}
		}
Kasper Skårhøj's avatar
Kasper Skårhøj committed
447
448
449
450
451
	}

	/**
	 * Looks up the value of $this->RDCT in the database and if it is found to be associated with a redirect URL then the redirection is carried out with a 'Location:' header
	 * May exit after sending a location-header.
452
453
	 *
	 * @return	void
Kasper Skårhøj's avatar
Kasper Skårhøj committed
454
455
	 */
	function sendRedirect()	{
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
456
		$res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('params', 'cache_md5params', 'md5hash='.$GLOBALS['TYPO3_DB']->fullQuoteStr($this->RDCT, 'cache_md5params'));
457
		if ($row = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res))	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
			$this->updateMD5paramsRecord($this->RDCT);
			header('Location: '.$row['params']);
			exit;
		}
	}
















479

Kasper Skårhøj's avatar
Kasper Skårhøj committed
480
481
482
483
484
485
486
487
488
489

	/********************************************
	 *
	 * Initializing, resolving page id
	 *
	 ********************************************/


	/**
	 * Initializes the front-end login user.
490
491
	 *
	 * @return	void
Kasper Skårhøj's avatar
Kasper Skårhøj committed
492
493
494
	 */
	function initFEuser()	{
		$this->fe_user = t3lib_div::makeInstance('tslib_feUserAuth');
495
496

		$this->fe_user->lockIP = $this->TYPO3_CONF_VARS['FE']['lockIP'];
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
497
		$this->fe_user->lockHashKeyWords = $this->TYPO3_CONF_VARS['FE']['lockHashKeyWords'];
Kasper Skårhøj's avatar
Kasper Skårhøj committed
498
		$this->fe_user->checkPid = $this->TYPO3_CONF_VARS['FE']['checkFeUserPid'];
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
499
		$this->fe_user->lifetime = intval($this->TYPO3_CONF_VARS['FE']['lifetime']);
500
		$this->fe_user->checkPid_value = $GLOBALS['TYPO3_DB']->cleanIntList(t3lib_div::_GP('pid'));	// List of pid's acceptable
Kasper Skårhøj's avatar
Kasper Skårhøj committed
501
502

			// Check if a session is transferred:
Kasper Skårhøj's avatar
Kasper Skårhøj committed
503
504
		if (t3lib_div::_GP('FE_SESSION_KEY'))	{
			$fe_sParts = explode('-',t3lib_div::_GP('FE_SESSION_KEY'));
Kasper Skårhøj's avatar
Kasper Skårhøj committed
505
			if (!strcmp(md5($fe_sParts[0].'/'.$this->TYPO3_CONF_VARS['SYS']['encryptionKey']), $fe_sParts[1]))	{	// If the session key hash check is OK:
506
507
				$_COOKIE[$this->fe_user->name] = $fe_sParts[0];
				$this->fe_user->forceSetCookie = 1;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
508
509
			}
		}
510

Kasper Skårhøj's avatar
Kasper Skårhøj committed
511
512
513
		if ($this->TYPO3_CONF_VARS['FE']['dontSetCookie'])	{
			$this->fe_user->dontSetCookie=1;
		}
514

Kasper Skårhøj's avatar
Kasper Skårhøj committed
515
516
517
		$this->fe_user->start();
		$this->fe_user->unpack_uc('');
		$this->fe_user->fetchSessionData();	// Gets session data
Kasper Skårhøj's avatar
Kasper Skårhøj committed
518
		$recs = t3lib_div::_GP('recs');
Kasper Skårhøj's avatar
Kasper Skårhøj committed
519
520
521
522
		if (is_array($recs))	{	// If any record registration is submitted, register the record.
			$this->fe_user->record_registration($recs);
		}

523
524
525
526
527
528
529
530
			// Call hook for possible manipulation of frontend user object
		if (is_array($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['initFEuser']))	{
			$_params = array('pObj' => &$this);
			foreach($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['initFEuser'] as $_funcRef)	{
				t3lib_div::callUserFunction($_funcRef,$_params,$this);
			}
		}

Kasper Skårhøj's avatar
Kasper Skårhøj committed
531
			// For every 60 seconds the is_online timestamp is updated.
532
		if (is_array($this->fe_user->user) && $this->fe_user->user['uid'] && $this->fe_user->user['is_online']<($GLOBALS['EXEC_TIME']-60))	{
533
			$GLOBALS['TYPO3_DB']->exec_UPDATEquery('fe_users', 'uid='.intval($this->fe_user->user['uid']), array('is_online' => $GLOBALS['EXEC_TIME']));
Kasper Skårhøj's avatar
Kasper Skårhøj committed
534
535
		}
	}
536

537
538
	/**
	 * Initializes the front-end user groups.
539
	 * Sets ->loginUser and ->gr_list based on front-end user status.
540
541
	 *
	 * @return	void
542
	 */
543
	function initUserGroups() {
544

545
		$this->fe_user->showHiddenRecords = $this->showHiddenRecords;		// This affects the hidden-flag selecting the fe_groups for the user!
546
547
		$this->fe_user->fetchGroupData(); 	// no matter if we have an active user we try to fetch matching groups which can be set without an user (simulation for instance!)

548
549
550
551
552
553
554
555
556
557
		if (is_array($this->fe_user->user) && count($this->fe_user->groupData['uid']))	{
			$this->loginUser=1;	// global flag!
			$this->gr_list = '0,-2';	// group -2 is not an existing group, but denotes a 'default' group when a user IS logged in. This is used to let elements be shown for all logged in users!
			$gr_array = $this->fe_user->groupData['uid'];
		} else {
			$this->loginUser=0;
			$this->gr_list = '0,-1';	// group -1 is not an existing group, but denotes a 'default' group when not logged in. This is used to let elements be hidden, when a user is logged in!
			$gr_array = $this->fe_user->groupData['uid'];
		}
		// TYPO3_CONF_VARS']['FE']['IPmaskMountGroups']	moved to sysext/sv/class.tx_sv_auth.php service
Kasper Skårhøj's avatar
Kasper Skårhøj committed
558

559
560
561
562
563
			// Clean up.
		$gr_array = array_unique($gr_array);	// Make unique...
		sort($gr_array);	// sort
		if (count($gr_array))	{
			$this->gr_list.=','.implode(',',$gr_array);
564
565
		}

566
567
		if ($this->fe_user->writeDevLog) 	t3lib_div::devLog('Valid usergroups for TSFE: '.$this->gr_list, 'tslib_fe');
	}
568

Kasper Skårhøj's avatar
Kasper Skårhøj committed
569
570
	/**
	 * Provides ways to bypass the '?id=[xxx]&type=[xx]' format, using either PATH_INFO or virtual HTML-documents (using Apache mod_rewrite)
571
	 *
572
573
574
575
	 * Three options:
	 * 1) Apache mod_rewrite: Here a .htaccess file maps all .html-files to index.php and then we extract the id and type from the name of that HTML-file. (AKA "simulateStaticDocuments")
	 * 2) Use PATH_INFO (also Apache) to extract id and type from that var. Does not require any special modules compiled with apache. (less typical)
	 * 3) Using hook which enables features like those provided from "realurl" extension (AKA "Speaking URLs")
576
	 *
Kasper Skårhøj's avatar
Kasper Skårhøj committed
577
578
579
580
581
582
583
584
	 * Support for RewriteRule to generate   (simulateStaticDocuments)
	 * With the mod_rewrite compiled into apache, put these lines into a .htaccess in this directory:
	 * RewriteEngine On
	 * RewriteRule   ^[^/]*\.html$  index.php
	 * The url must end with '.html' and the format must comply with either of these:
	 * 1:      '[title].[id].[type].html'			- title is just for easy recognition in the logfile!; no practical use of the title for TYPO3.
	 * 2:      '[id].[type].html'					- above, but title is omitted; no practical use of the title for TYPO3.
	 * 3:      '[id].html'							- only id, type is set to the default, zero!
Kasper Skårhøj's avatar
Kasper Skårhøj committed
585
	 * NOTE: In all case 'id' may be the uid-number OR the page alias (if any)
586
587
	 *
	 * @return	void
Kasper Skårhøj's avatar
Kasper Skårhøj committed
588
589
590
	 * @link http://typo3.org/doc.0.html?&tx_extrepmgm_pi1[extUid]=270&cHash=4ad9d7acb4
	 */
	function checkAlternativeIdMethods()	{
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
591

Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
592
593
594
		$this->siteScript = t3lib_div::getIndpEnv('TYPO3_SITE_SCRIPT');

			// Resolving of "simulateStaticDocuments" URLs:
595
		if ($this->siteScript && substr($this->siteScript,0,9)!='index.php')	{		// If there has been a redirect (basically; we arrived here otherwise than via "index.php" in the URL) this can happend either due to a CGI-script or because of reWrite rule. Earlier we used $_SERVER['REDIRECT_URL'] to check but
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
596
			$uParts = parse_url($this->siteScript);	// Parse the path:
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
597
598
599
600
			$fI = t3lib_div::split_fileref($uParts['path']);

			if (!$fI['path'] && $fI['file'] && substr($fI['file'],-5)=='.html')	{
				$parts = explode('.',$fI['file']);
Kasper Skårhøj's avatar
Kasper Skårhøj committed
601
				$pCount = count($parts);
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
602
603
604
605
606
607
				if ($pCount>2)	{
					$this->type = intval($parts[$pCount-2]);
					$this->id = $parts[$pCount-3];
				} else {
					$this->type = 0;
					$this->id = $parts[0];
Kasper Skårhøj's avatar
Kasper Skårhøj committed
608
609
610
				}
			}
		}
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
611

Kasper Skårhøj's avatar
Kasper Skårhøj committed
612
613
			// If PATH_INFO
		if (t3lib_div::getIndpEnv('PATH_INFO'))	{		// If pathinfo contains stuff...
614
615
616
617
618
619
620
621
622
623
624
			$parts=t3lib_div::trimExplode('/',t3lib_div::getIndpEnv('PATH_INFO'),1);
			$parts[]='html';
			$pCount = count($parts);
			if ($pCount>2)	{
				$this->type = intval($parts[$pCount-2]);
				$this->id = $parts[$pCount-3];
			} else {
				$this->type = 0;
				$this->id = $parts[0];
			}
			$this->absRefPrefix_force=1;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
625
		}
626

Kasper Skårhøj's avatar
Kasper Skårhøj committed
627
			// Call post processing function for custom URL methods.
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
628
		if (is_array($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['checkAlternativeIdMethods-PostProc']))	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
629
			$_params = array('pObj' => &$this);
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
630
			foreach($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['checkAlternativeIdMethods-PostProc'] as $_funcRef)	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
631
632
				t3lib_div::callUserFunction($_funcRef,$_params,$this);
			}
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
633
		}
Kasper Skårhøj's avatar
Kasper Skårhøj committed
634
	}
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
635

Kasper Skårhøj's avatar
Kasper Skårhøj committed
636
637
638
	/**
	 * Clears the preview-flags, sets sim_exec_time to current time.
	 * Hidden pages must be hidden as default, $GLOBALS['SIM_EXEC_TIME'] is set to $GLOBALS['EXEC_TIME'] in t3lib/config_default.inc. Alter it by adding or subtracting seconds.
639
640
	 *
	 * @return	void
Kasper Skårhøj's avatar
Kasper Skårhøj committed
641
642
643
644
	 */
	function clear_preview()	{
		$this->showHiddenPage = 0;
		$this->showHiddenRecords = 0;
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
645
		$GLOBALS['SIM_EXEC_TIME'] = $GLOBALS['EXEC_TIME'];
Kasper Skårhøj's avatar
Kasper Skårhøj committed
646
647
648
649
650
651
		$this->fePreview = 0;
	}

	/**
	 * Determines the id and evaluates any preview settings
	 * Basically this function is about determining whether a backend user is logged in, if he has read access to the page and if he's previewing the page. That all determines which id to show and how to initialize the id.
652
653
	 *
	 * @return	void
Kasper Skårhøj's avatar
Kasper Skårhøj committed
654
655
	 */
	function determineId()	{
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
656

Kasper Skårhøj's avatar
Kasper Skårhøj committed
657
			// Getting ARG-v values if some
658
659
		$this->setIDfromArgV();

Kasper Skårhøj's avatar
Kasper Skårhøj committed
660
661
			// If there is a Backend login we are going to check for any preview settings:
		$GLOBALS['TT']->push('beUserLogin','');
662
		if ($this->beUserLogin)	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
663
664
665
666
667
668
669
670
671
672
673
674
675
676
			$this->fePreview = $GLOBALS['BE_USER']->extGetFeAdminValue('preview');

				// If admin panel preview is enabled...
			if ($this->fePreview)	{
				$fe_user_OLD_USERGROUP = $this->fe_user->user['usergroup'];

				$this->showHiddenPage = $GLOBALS['BE_USER']->extGetFeAdminValue('preview','showHiddenPages');
				$this->showHiddenRecords = $GLOBALS['BE_USER']->extGetFeAdminValue('preview','showHiddenRecords');
					// simulate date
				$simTime = $GLOBALS['BE_USER']->extGetFeAdminValue('preview','simulateDate');
				if ($simTime)	$GLOBALS['SIM_EXEC_TIME']=$simTime;
					// simulate user
				$simUserGroup = $GLOBALS['BE_USER']->extGetFeAdminValue('preview','simulateUserGroup');
				$this->simUserGroup = $simUserGroup;
677
				if ($simUserGroup)	$this->fe_user->user['usergroup']=$simUserGroup;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
678
679
680
681
682
683
684
685
				if (!$simUserGroup && !$simTime && !$this->showHiddenPage && !$this->showHiddenRecords)	{
					$this->fePreview=0;
				}
			}

				// Now it's investigated if the raw page-id points to a hidden page and if so, the flag is set.
				// This does not require the preview flag to be set in the admin panel
			if ($this->id)	{
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
686
687
				$idQ = t3lib_div::testInt($this->id) ? 'uid='.intval($this->id) : 'alias='.$GLOBALS['TYPO3_DB']->fullQuoteStr($this->id, 'pages').' AND pid>=0';	// pid>=0 added for the sake of versioning...
				$res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('hidden', 'pages', $idQ.' AND hidden!=0 AND deleted=0');
688
689
				if ($GLOBALS['TYPO3_DB']->sql_num_rows($res))	{
					$this->fePreview = 1;	// The preview flag is set only if the current page turns out to actually be hidden!
Kasper Skårhøj's avatar
Kasper Skårhøj committed
690
691
					$this->showHiddenPage = 1;
				}
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717

					// Check root line for proper connection to tree root (done because of possible preview of page / branch versions)
				if (!$this->fePreview)	{

						// Initialize the page-select functions to check rootline:
					$temp_sys_page = t3lib_div::makeInstance('t3lib_pageSelect');
					$temp_sys_page->init($this->showHiddenPage);

						// If root line contained NO records and ->error_getRootLine_failPid tells us that it was because of a pid=-1 (indicating a "version" record)...:
					if (!count($temp_sys_page->getRootLine($this->id,$this->MP)) && $temp_sys_page->error_getRootLine_failPid==-1)	{

							// Setting versioningPreview flag and try again:
						$temp_sys_page->versioningPreview = TRUE;
						if (count($temp_sys_page->getRootLine($this->id,$this->MP)))	{
								// Finally, we got a root line (meaning that it WAS due to versioning preview of a page somewhere) and we set the fePreview flag which in itself will allow sys_page class to display previews of versionized records.
							$this->fePreview = 1;
#debug('version in rootline...');
						}
					}
				}
			}

				// Checking for specific version preview of records:
			if (is_array(t3lib_div::_GP('ADMCMD_vPrev')))	{
				$this->fePreview = 1;
				$this->versionPreviewMap = t3lib_div::_GP('ADMCMD_vPrev');
Kasper Skårhøj's avatar
Kasper Skårhøj committed
718
719
720
721
722
723
724
725
726
727
728
729
			}

			if ($this->fePreview)	{	// If the front-end is showing a preview, caching MUST be disabled.
				$this->set_no_cache();
			}
		}
		$GLOBALS['TT']->pull();

			// Now, get the id, validate access etc:
		$this->fetch_the_id();

			// Check if backend user has read access to this page. If not, recalculate the id.
730
		if ($this->beUserLogin && $this->fePreview)	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
731
732
733
734
			if (!$GLOBALS['BE_USER']->doesUserHaveAccess($this->page,1))	{
					// Resetting
				$this->clear_preview();
				$this->fe_user->user['usergroup'] = $fe_user_OLD_USERGROUP;
735
736
737
738
739
740
741

					// Fetching the id again, now with the preview settings reset.
				$this->fetch_the_id();
			}
		}

			// Checks if user logins are blocked for a certain branch and if so, will unset user login and re-fetch ID.
742
743
744
		$this->loginAllowedInBranch = $this->checkIfLoginAllowedInBranch();
		if (!$this->loginAllowedInBranch)	{	// Logins are not allowed:
			if (is_array($this->fe_user->user))	{	// Only if there is a login will we run this...
745
				unset($this->fe_user->user);
Kasper Skårhøj's avatar
Kasper Skårhøj committed
746
747
					// Fetching the id again, now with the preview settings reset.
				$this->fetch_the_id();
748
749
			}
		}
750

Kasper Skårhøj's avatar
Kasper Skårhøj committed
751
			// Final cleaning.
752
753
		$this->id = $this->contentPid = intval($this->id);	// Make sure it's an integer
		$this->type = intval($this->type);	// Make sure it's an integer
Kasper Skårhøj's avatar
Kasper Skårhøj committed
754
755

			// Call post processing function for id determination:
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
756
		if (is_array($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['determineId-PostProc']))	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
757
			$_params = array('pObj' => &$this);
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
758
			foreach($this->TYPO3_CONF_VARS['SC_OPTIONS']['tslib/class.tslib_fe.php']['determineId-PostProc'] as $_funcRef)	{
Kasper Skårhøj's avatar
Kasper Skårhøj committed
759
760
				t3lib_div::callUserFunction($_funcRef,$_params,$this);
			}
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
761
		}
Kasper Skårhøj's avatar
Kasper Skårhøj committed
762
763
764
765
766
767
	}

	/**
	 * Get The Page ID
	 * This gets the id of the page, checks if the page is in the domain and if the page is accessible
	 * Sets variables such as $this->sys_page, $this->loginUser, $this->gr_list, $this->id, $this->type, $this->domainStartPage, $this->idParts
768
769
	 *
	 * @return	void
Kasper Skårhøj's avatar
Kasper Skårhøj committed
770
771
772
773
774
	 * @access private
	 */
	function fetch_the_id()	{
		$GLOBALS['TT']->push('fetch_the_id initialize/','');

775
			// Initialize the page-select functions.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
776
777
		$this->sys_page = t3lib_div::makeInstance('t3lib_pageSelect');
		$this->sys_page->init($this->showHiddenPage);
778
779
780
781
		$this->sys_page->versioningPreview = $this->fePreview ? TRUE : FALSE;
		if ($this->sys_page->versioningPreview)	{
			$this->sys_page->versionPreviewMap = $this->versionPreviewMap;
		}
Kasper Skårhøj's avatar
Kasper Skårhøj committed
782

783
784
			// Set the valid usergroups for FE
		$this->initUserGroups();
Kasper Skårhøj's avatar
Kasper Skårhøj committed
785
786

			// Sets sys_page where-clause
787
		$this->setSysPageWhereClause();
788

789
			// Splitting $this->id by a period (.). First part is 'id' and second part - if exists - will overrule the &type param if given
Kasper Skårhøj's avatar
Kasper Skårhøj committed
790
791
792
		$pParts = explode('.',$this->id);
		$this->id = $pParts[0];	// Set it.
		if (isset($pParts[1]))	{$this->type=$pParts[1];}
793
794

			// Splitting $this->id by a comma (,). First part is 'id' and other parts are just stored for use in scripts.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
795
796
797
798
799
800
		$this->idParts = explode(',',$this->id);

			// Splitting by a '+' sign - used for base64/md5 methods of parameter encryption for simulate static documents.
		list($pgID,$SSD_p)=explode('+',$this->idParts[0],2);
		if ($SSD_p)	{	$this->idPartsAnalyze($SSD_p);	}
		$this->id = $pgID;	// Set id
801

Kasper Skårhøj's avatar
Kasper Skårhøj committed
802
803
			// If $this->id is a string, it's an alias
		$this->checkAndSetAlias();
804

Kasper Skårhøj's avatar
Kasper Skårhøj committed
805
806
807
808
809
810
811
			// The id and type is set to the integer-value - just to be sure...
		$this->id = intval($this->id);
		$this->type = intval($this->type);
		$GLOBALS['TT']->pull();

			// We find the first page belonging to the current domain
		$GLOBALS['TT']->push('fetch_the_id domain/','');
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
812
		$this->domainStartPage = $this->findDomainRecord($this->TYPO3_CONF_VARS['SYS']['recursiveDomainSearch']);	// the page_id of the current domain
Kasper Skårhøj's avatar
Kasper Skårhøj committed
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
		if (!$this->id)	{
			if ($this->domainStartPage)	{
				$this->id = $this->domainStartPage;	// If the id was not previously set, set it to the id of the domain.
			} else {
				$theFirstPage = $this->sys_page->getFirstWebPage($this->id);	// Find the first 'visible' page in that domain
				if ($theFirstPage)	{
					$this->id = $theFirstPage['uid'];
				} else {
					$this->printError('No pages are found on the rootlevel!');
					exit;
				}
			}
		}
		$GLOBALS['TT']->pull();

		$GLOBALS['TT']->push('fetch_the_id rootLine/','');
		$requestedId = $this->id;		// We store the originally requested id
		$this->getPageAndRootlineWithDomain($this->domainStartPage);
		$GLOBALS['TT']->pull();

		if ($this->pageNotFound && $this->TYPO3_CONF_VARS['FE']['pageNotFound_handling'])	{
834
835
836
837
838
839
			$pNotFoundMsg = array(
				1 => 'ID was not an accessible page',
				2 => 'Subsection was found and not accessible',
				3 => 'ID was outside the domain',
			);
			$this->pageNotFoundAndExit($pNotFoundMsg[$this->pageNotFound]);
Kasper Skårhøj's avatar
Kasper Skårhøj committed
840
841
842
843
844
845
		}

			// set no_cache if set
		if ($this->page['no_cache'])	{
			$this->set_no_cache();
		}
846

Kasper Skårhøj's avatar
Kasper Skårhøj committed
847
848
			// Init SYS_LASTCHANGED
		$this->register['SYS_LASTCHANGED'] = intval($this->page['tstamp']);
849
850
851
		if ($this->register['SYS_LASTCHANGED'] < intval($this->page['SYS_LASTCHANGED']))	{
			$this->register['SYS_LASTCHANGED'] = intval($this->page['SYS_LASTCHANGED']);
		}
Kasper Skårhøj's avatar
Kasper Skårhøj committed
852
853
854
855
	}

	/**
	 * Gets the page and rootline arrays based on the id, $this->id
856
	 *
Kasper Skårhøj's avatar
Kasper Skårhøj committed
857
858
	 * If the id does not correspond to a proper page, the 'previous' valid page in the rootline is found
	 * If the page is a shortcut (doktype=4), the ->id is loaded with that id
859
	 *
Kasper Skårhøj's avatar
Kasper Skårhøj committed
860
	 * Whether or not the ->id is changed to the shortcut id or the previous id in rootline (eg if a page is hidden), the ->page-array and ->rootline is found and must also be valid.
861
	 *
Kasper Skårhøj's avatar
Kasper Skårhøj committed
862
	 * Sets or manipulates internal variables such as: $this->id, $this->page, $this->rootLine, $this->MP, $this->pageNotFound
863
864
	 *
	 * @return	void
Kasper Skårhøj's avatar
Kasper Skårhøj committed
865
866
867
868
869
	 * @access private
	 */
	function getPageAndRootline() {
		$this->page = $this->sys_page->getPage($this->id);
		if (!count($this->page))	{
870
				// If no page, we try to find the page before in the rootLine.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
871
872
873
874
875
876
877
878
879
880
881
			$this->pageNotFound=1;			// Page is 'not found' in case the id itself was not an accessible page. code 1
			$this->rootLine = $this->sys_page->getRootLine($this->id,$this->MP);
			if (count($this->rootLine))	{
				$c=count($this->rootLine)-1;
				while($c>0)	{
					$c--;
					$this->id=$this->rootLine[$c]['uid'];
					$this->page = $this->sys_page->getPage($this->id);
					if (count($this->page)){break;}
				}
			}
882
				// If still no page...
Kasper Skårhøj's avatar
Kasper Skårhøj committed
883
			if (!count($this->page))	{
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
884
				if ($this->TYPO3_CONF_VARS['FE']['pageNotFound_handling'])	{
885
					$this->pageNotFoundAndExit('The requested page does not exist!');
Kasper Skårhøj's avatar
   
Kasper Skårhøj committed
886
887
888
889
				} else {
					$this->printError('The requested page does not exist!');
					exit;
				}
Kasper Skårhøj's avatar
Kasper Skårhøj committed
890
891
			}
		}
892
			// Is the ID a link to another page??
Kasper Skårhøj's avatar
Kasper Skårhøj committed
893
		if ($this->page['doktype']==4)	{
894
			$this->MP = '';		// We need to clear MP if the page is a shortcut. Reason is if the short cut goes to another page, then we LEAVE the rootline which the MP expects.
Kasper Skårhøj's avatar
Kasper Skårhøj committed
895
896
897
			$this->page = $this->getPageShortcut($this->page['shortcut'],$this->page['shortcut_mode'],$this->page['uid']);
			$this->id = $this->page['uid'];
		}
898
			// Gets the rootLine
Kasper Skårhøj's avatar
Kasper Skårhøj committed
899
		$this->rootLine = $this->sys_page->getRootLine($this->id,$this->MP);
900
901

			// If not rootline we're off...
Kasper Skårhøj's avatar
Kasper Skårhøj committed
902
		if (!count($this->rootLine))	{
903
			$this->printError('The requested page didn\'t have a proper connection to the tree-root! <br /><br />('.$this->sys_page->error_getRootLine.')');
Kasper Skårhøj's avatar
Kasper Skårhøj committed
904
905
			exit;
		}
906
907

			// Checking for include section regarding the hidden/starttime/endtime/fe_user (that is access control of a whole subbranch!)
Kasper Skårhøj's avatar
Kasper Skårhøj committed
908
909
910
911
912
913
914
915
916
917
918
919
		if ($this->checkRootlineForIncludeSection())	{
			if (!count($this->rootLine))	{
				$this->printError('The requested page was not accessible!');
				exit;
			} else {
				$el = reset($this->rootLine);
				$this->id = $el['uid'];
				$this->page = $this->sys_page->getPage($this->id);
				$this->rootLine = $this->sys_page->getRootLine($this->id,$this->MP);
			}
		}
	}
920

Kasper Skårhøj's avatar
Kasper Skårhøj committed
921
	/**
922
	 * Get page shortcut; Finds the records pointed to by input value $SC (the shortcut value)
923
	 *
Kasper Skårhøj's avatar
Kasper Skårhøj committed
924
925
926
927
928
929
930
931
932
933
934
	 * @param	integer		The value of the "shortcut" field from the pages record
	 * @param	integer		The shortcut mode: 1 and 2 will select either first subpage or random subpage; the default is the page pointed to by $SC
	 * @param	integer		The current page UID of the page which is a shortcut
	 * @param	integer		Safety feature which makes sure that the function is calling itself recursively max 20 times (since this function can find shortcuts to other shortcuts to other shortcuts...)
	 * @param	array		An array filled with previous page uids tested by the function - new page uids are evaluated against this to avoid going in circles.
	 * @return	mixed		Returns the page record of the page that the shortcut pointed to.
	 * @access private
	 * @see getPageAndRootline()
	 */
	function getPageShortcut($SC,$mode,$thisUid,$itera=20,$pageLog=array())	{
		$idArray = t3lib_div::intExplode(',',$SC);
935
936

			// Find $page record depending on shortcut mode:
Kasper Skårhøj's avatar
Kasper Skårhøj committed
937
938
939
940
		switch($mode)	{
			case 1:
			case 2:
				$pageArray = $this->sys_page->getMenu($idArray[0]?$idArray[0]:$thisUid,'*','sorting','AND pages.doktype<199 AND pages.doktype!=6');
941
				$pO = 0;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
942
943
944
				if ($mode==2 && count($pageArray))	{	// random
					$this->make_seed();
					$randval = intval(rand(0,count($pageArray)-1));
945
					$pO = $randval;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
946
				}
947
				$c = 0;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
948
949
950
951
952
953
954
955
956
957
958
959
960
				reset($pageArray);
				while(list(,$pV)=each($pageArray))	{
					if ($c==$pO)	{
						$page = $pV;
						break;
					}
					$c++;
				}
			break;
			default:
				$page = $this->sys_page->getPage($idArray[0]);
			break;
		}
961
962

			// Check if short cut page was a shortcut itself, if so look up recursively:
Kasper Skårhøj's avatar
Kasper Skårhøj committed
963
964
965
966
967
968
969
970
971
972
		if ($page['doktype']==4)	{
			if (!in_array($page['uid'],$pageLog) && $itera>0)	{
				$pageLog[] = $page['uid'];
				$page = $this->getPageShortcut($page['shortcut'],$page['shortcut_mode'],$page['uid'],$itera-1,$pageLog);
			} else {
				$pageLog[] = $page['uid'];
				$this->printError('Page shortcuts were looping in uids '.implode(',',$pageLog).'...!');
				exit;
			}
		}
973
			// Return resulting page:
Kasper Skårhøj's avatar
Kasper Skårhøj committed
974
975
976
977
978
		return $page;
	}

	/**
	 * Checks the current rootline for defined sections.
979
980
	 *
	 * @return	boolean
Kasper Skårhøj's avatar
Kasper Skårhøj committed
981
982
983
984
	 * @access private
	 */
	function checkRootlineForIncludeSection()	{
		$c=count($this->rootLine);
985
		$removeTheRestFlag=0;
Kasper Skårhøj's avatar
Kasper Skårhøj committed
986
987
988
989
990
991
		for ($a=0;$a<$c;$a++)	{
			if (!$this->checkPagerecordForIncludeSection($this->rootLine[$a]))	{
				$removeTheRestFlag=1;
			}
			if ($this->rootLine[$a]['doktype']==6)	{
				if ($this->beUserLogin)	{	// If there is a backend user logged in, check if he has read access to the page:
992
993
					$res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('uid', 'pages', 'uid='.intval($this->id).' AND '.$GLOBALS['BE_USER']->getPagePermsClause(1));
					list($isPage) = $GLOBALS['TYPO3_DB']->sql_fetch_row($res);
Kasper Skårhøj's avatar
Kasper Skårhøj committed
994
995
996
997
998
999
1000
					if (!$isPage)	$removeTheRestFlag=1;	// If there was no page selected, the user apparently did not have read access to the current PAGE (not position in rootline) and we set the remove-flag...
				} else {	// Dont go here, if there is no backend user logged in.
					$removeTheRestFlag=1;
				}
			}
			if ($removeTheRestFlag)	{
				$this->pageNotFound=2;			// Page is 'not found' in case a subsection was found and not accessible, code 2
For faster browsing, not all history is shown. View entire blame