"TYPO3 4.0.1: typo3_src-4.0.1/t3lib/class.t3lib_timetrack.php Source File", "datetime" => "Sat Dec 2 19:22:19 2006", "date" => "2 Dec 2006", "doxygenversion" => "1.4.6", "projectname" => "TYPO3 4.0.1", "projectnumber" => "4.0.1" ); get_header($doxygen_vars); ?>

class.t3lib_timetrack.php

00001 <?php
00002 /***************************************************************
00003 *  Copyright notice
00004 *
00005 *  (c) 1999-2006 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 ***************************************************************/
00088 class t3lib_timeTrack {
00089         var $starttime = 0;             // Is loaded with the millisecond time when this object is created
00090 
00091         var $LR = 1;                    // Log Rendering flag. If set, ->push() and ->pull() is called from the cObj->cObjGetSingle(). This determines whether or not the TypoScript parsing activity is logged. But it also slows down the rendering
00092         var $printConf=array(
00093                 'showParentKeys' => 1,
00094                 'contentLength' => 10000,       // Determines max lenght of displayed content before it gets cropped.
00095                 'contentLength_FILE' => 400,    // Determines max lenght of displayed content FROM FILE cObjects before it gets cropped. Reason is that most FILE cObjects are huge and often used as template-code.
00096                 'flag_tree' => 1,
00097                 'flag_messages' => 1,
00098                 'flag_queries' => 0,
00099                 'flag_content' => 0,
00100                 'allTime' => 0,
00101                 'keyLgd' => 40,
00102                 'factor' => 10,
00103                 'col' => '#D9D5C9'
00104         );
00105 
00106         var $wrapError =array(
00107                 0 => array('',''),
00108                 1 => array('<b>','</b>'),
00109                 2 => array('<b><font color="#ff6600">','</font></b>'),
00110                 3 => array('<b><font color="#ff0000">','</font></b>')
00111         );
00112         var $wrapIcon =array(
00113                 0 => '',
00114                 1 => '<img src="typo3/gfx/icon_note.gif" width="18" height="16" align="absmiddle" alt="" />',
00115                 2 => '<img src="typo3/gfx/icon_warning.gif" width="18" height="16" align="absmiddle" alt="" />',
00116                 3 => '<img src="typo3/gfx/icon_fatalerror.gif" width="18" height="16" align="absmiddle" alt="" />'
00117         );
00118 
00119         var $uniqueCounter=0;
00120         var $tsStack = array(array());
00121         var $tsStackLevel = 0;
00122         var $tsStackLevelMax=array();
00123         var $tsStackLog = array();
00124         var $tsStackPointer=0;
00125         var $currentHashPointer=array();
00126 
00127 
00128 
00129 
00130 
00131 
00132         /*******************************************
00133         *
00134         * Logging parsing times in the scripts
00135         *
00136         *******************************************/
00137 
00144         function start()    {
00145                 $this->wrapIcon =array(
00146                         0 => '',
00147                         1 => '<img src="'.TYPO3_mainDir.'gfx/icon_note.gif" width="18" height="16" align="absmiddle" alt="" />',
00148                         2 => '<img src="'.TYPO3_mainDir.'gfx/icon_warning.gif" width="18" height="16" align="absmiddle" alt="" />',
00149                         3 => '<img src="'.TYPO3_mainDir.'gfx/icon_fatalerror.gif" width="18" height="16" align="absmiddle" alt="" />'
00150                 );
00151 
00152                 $this->starttime=0;
00153                 $this->starttime=$this->mtime();
00154         }
00155 
00164         function push($tslabel, $value='')  {
00165                 array_push($this->tsStack[$this->tsStackPointer], $tslabel);
00166                 array_push($this->currentHashPointer, 'timetracker_'.$this->uniqueCounter++);
00167 
00168                 $this->tsStackLevel++;
00169                 $this->tsStackLevelMax[] = $this->tsStackLevel;
00170 
00171                         // setTSlog
00172                 $k = end($this->currentHashPointer);
00173                 $this->tsStackLog[$k] = array(
00174                         'level' => $this->tsStackLevel,
00175                         'tsStack' => $this->tsStack,
00176                         'value' => $value,
00177                         'starttime' => microtime(),
00178                         'stackPointer' => $this->tsStackPointer
00179                 );
00180         }
00181 
00189         function pull($content='')  {
00190                 $k = end($this->currentHashPointer);
00191                 $this->tsStackLog[$k]['endtime'] =  microtime();
00192                 $this->tsStackLog[$k]['content'] = $content;
00193 
00194                 $this->tsStackLevel--;
00195                 array_pop($this->tsStack[$this->tsStackPointer]);
00196                 array_pop($this->currentHashPointer);
00197         }
00198 
00207         function setTSlogMessage($content,$num=0)   {
00208                 end($this->currentHashPointer);
00209                 $k = current($this->currentHashPointer);
00210 
00211                 $this->tsStackLog[$k]['message'][] = $this->wrapIcon[$num].$this->wrapError[$num][0].htmlspecialchars($content).$this->wrapError[$num][1];
00212         }
00213 
00221         function setTSselectQuery($query,$msg)  {
00222                 end($this->currentHashPointer);
00223                 $k = current($this->currentHashPointer);
00224 
00225                 $this->tsStackLog[$k]['selectQuery'][] = array('query'=>$query,'msg'=>$msg);
00226         }
00227 
00234         function incStackPointer()  {
00235                 $this->tsStackPointer++;
00236                 $this->tsStack[$this->tsStackPointer]=array();
00237         }
00238 
00245         function decStackPointer()  {
00246                 unset($this->tsStack[$this->tsStackPointer]);
00247                 $this->tsStackPointer--;
00248         }
00249 
00255         function mtime()    {
00256                 return $this->convertMicrotime(microtime())-$this->starttime;
00257         }
00258 
00265         function convertMicrotime($microtime)   {
00266                 $parts = explode(' ',$microtime);
00267                 return round(($parts[0]+$parts[1])*1000);
00268         }
00269 
00270 
00271 
00272 
00273 
00274 
00275 
00276 
00277 
00278 
00279 
00280 
00281 
00282 
00283 
00284 
00285 
00286         /*******************************************
00287         *
00288         * Printing the parsing time information (for Admin Panel)
00289         *
00290         *******************************************/
00291 
00298         function printTSlog()   {
00299                         // Calculate times and keys for the tsStackLog
00300                 $preEndtime=0;
00301                 foreach($this->tsStackLog as $uniqueId=>$data)  {
00302                         $this->tsStackLog[$uniqueId]['endtime'] = $this->convertMicrotime($this->tsStackLog[$uniqueId]['endtime'])-$this->starttime;
00303                         $this->tsStackLog[$uniqueId]['starttime'] = $this->convertMicrotime($this->tsStackLog[$uniqueId]['starttime'])-$this->starttime;
00304                         $this->tsStackLog[$uniqueId]['deltatime'] = $this->tsStackLog[$uniqueId]['endtime']-$this->tsStackLog[$uniqueId]['starttime'];
00305                         $this->tsStackLog[$uniqueId]['key'] = implode($this->tsStackLog[$uniqueId]['stackPointer']?'.':'/', end($data['tsStack']));
00306                         $preEndtime = $this->tsStackLog[$uniqueId]['endtime'];
00307                 }
00308 
00309                         // Create hierarchical array of keys pointing to the stack
00310                 $arr = array();
00311                 reset($this->tsStackLog);
00312                 while(list($uniqueId,$data)=each($this->tsStackLog))    {
00313                         $this->createHierarchyArray($arr,$data['level'], $uniqueId);
00314                 }
00315                         // Parsing the registeret content and create icon-html for the tree
00316                 $this->tsStackLog[$arr['0.'][0]]['content'] = $this->fixContent($arr['0.']['0.'], $this->tsStackLog[$arr['0.'][0]]['content'], '', 0, $arr['0.'][0]);
00317 
00318                         // Displaying the tree:
00319                 reset($this->tsStackLog);
00320                 $out='<tr>
00321                         <td bgcolor="#ABBBB4" align="center"><b>'.$this->fw('TypoScript Key').'</b></td>
00322                         <td bgcolor="#ABBBB4" align="center"><b>'.$this->fw('Value').'</b></td>';
00323                 if ($this->printConf['allTime'])    {
00324                         $out.='
00325                         <td bgcolor="#ABBBB4" align="center"><b>'.$this->fw('Time').'</b></td>
00326                         <td bgcolor="#ABBBB4" align="center"><b>'.$this->fw('Own').'</b></td>
00327                         <td bgcolor="#ABBBB4" align="center"><b>'.$this->fw('Sub').'</b></td>
00328                         <td bgcolor="#ABBBB4" align="center"><b>'.$this->fw('Total').'</b></td>';
00329                 } else {
00330                         $out.='
00331                         <td bgcolor="#ABBBB4" align="center"><b>'.$this->fw('Own').'</b></td>';
00332                 }
00333 
00334                 $out.='
00335                         <td bgcolor="#ABBBB4" align="center"><b>'.$this->fw('Details').'</b></td>
00336                         </tr>';
00337 
00338 
00339 
00340                 $flag_tree=$this->printConf['flag_tree'];
00341                 $flag_messages=$this->printConf['flag_messages'];
00342                 $flag_content=$this->printConf['flag_content'];
00343                 $flag_queries=$this->printConf['flag_queries'];
00344                 $keyLgd=$this->printConf['keyLgd'];
00345                 $factor=$this->printConf['factor'];
00346                 $col=$this->printConf['col'];
00347 
00348                 $c=0;
00349                 while(list($uniqueId,$data)=each($this->tsStackLog))    {
00350                         $bgColor = ' bgcolor="'.($c%2 ? t3lib_div::modifyHTMLColor($col,$factor,$factor,$factor) : $col).'"';
00351                         $item='';
00352                         if (!$c)    {   // If first...
00353                                 $data['icons']='';
00354                                 $data['key']= 'Script Start';
00355                                 $data['value'] = '';
00356                         }
00357 
00358 
00359                                 // key label:
00360                         $keyLabel='';
00361                         if (!$flag_tree && $data['stackPointer'])   {
00362                                 $temp=array();
00363                                 reset($data['tsStack']);
00364                                 while(list($k,$v)=each($data['tsStack']))   {
00365                                         $temp[]=t3lib_div::fixed_lgd_pre(implode($v,$k?'.':'/'),$keyLgd);
00366                                 }
00367                                 array_pop($temp);
00368                                 $temp = array_reverse($temp);
00369                                 array_pop($temp);
00370                                 if (count($temp))   {
00371                                         $keyLabel='<br /><font color="#999999">'.implode($temp,'<br />').'</font>';
00372                                 }
00373                         }
00374                         if ($flag_tree) {
00375                                 $tmp = t3lib_div::trimExplode('.',$data['key'],1);
00376                                 $theLabel = end($tmp);
00377                         } else {
00378                                 $theLabel = $data['key'];
00379                         }
00380                         $theLabel = t3lib_div::fixed_lgd_pre($theLabel, $keyLgd);
00381                         $theLabel = $data['stackPointer'] ? '<font color="maroon">'.$theLabel.'</font>' : $theLabel;
00382                         $keyLabel=$theLabel.$keyLabel;
00383                         $item.='<td valign="top" nowrap="nowrap"'.$bgColor.'>'.($flag_tree?$data['icons']:'').$this->fw($keyLabel).'</td>';
00384 
00385                                 // key value:
00386                         $keyValue=$data['value'];
00387                         $item.='<td valign="top" nowrap="nowrap"'.$bgColor.'>'.$this->fw(htmlspecialchars($keyValue)).'</td>';
00388 
00389                         if ($this->printConf['allTime'])    {
00390                                         // deltatime:
00391                                 $item.='<td valign="top" align="right" nowrap="nowrap"'.$bgColor.'>'.$this->fw($data['starttime']).'</td>';
00392                                 $item.='<td valign="top" align="right" nowrap="nowrap"'.$bgColor.'>'.$this->fw($data['owntime']).'</td>';
00393                                 $item.='<td valign="top" align="right" nowrap="nowrap"'.$bgColor.'>'.$this->fw($data['subtime'] ? '+'.$data['subtime'] : '').'</td>';
00394                                 $item.='<td valign="top" align="right" nowrap="nowrap"'.$bgColor.'>'.$this->fw($data['subtime'] ? '='.$data['deltatime'] : '').'</td>';
00395                         } else {
00396                                         // deltatime:
00397                                 $item.='<td valign="top" align="right" nowrap="nowrap"'.$bgColor.'>'.$this->fw($data['owntime']).'</td>';
00398                         }
00399 
00400 
00401                                 // messages:
00402                         $msgArr=array();
00403                         $msg='';
00404                         if ($flag_messages && is_array($data['message']))   {
00405                                 reset($data['message']);
00406                                 while(list(,$v)=each($data['message'])) {
00407                                         $msgArr[]=nl2br($v);
00408                                 }
00409                         }
00410                         if ($flag_queries && is_array($data['selectQuery']))    {
00411                                 reset($data['selectQuery']);
00412                                 while(list(,$v)=each($data['selectQuery'])) {
00413                                         $res = $GLOBALS['TYPO3_DB']->sql_query('EXPLAIN '.$v['query']);
00414                                         $v['mysql_error'] = $GLOBALS['TYPO3_DB']->sql_error();
00415                                         if (!$GLOBALS['TYPO3_DB']->sql_error()) {
00416                                                 while($row = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($res))   {
00417                                                         $v['explain'][]=$row;
00418                                                 }
00419                                         }
00420                                         $msgArr[]=t3lib_div::view_array($v);
00421                                 }
00422                         }
00423                         if ($flag_content && strcmp($data['content'],''))   {
00424                                 $msgArr[]='<font color="#000066">'.nl2br($data['content']).'</font>';
00425                         }
00426                         if (count($msgArr)) {
00427                                 $msg=implode($msgArr,'<hr />');
00428                         }
00429                         $item.='<td valign="top"'.$bgColor.'>'.$this->fw($msg).'</td>';
00430                         $out.='<tr>'.$item.'</tr>';
00431                         $c++;
00432                 }
00433                 $out='<table border="0" cellpadding="0" cellspacing="0">'.$out.'</table>';
00434                 return $out;
00435         }
00436 
00447         function fixContent(&$arr, $content, $depthData='', $first=0, $vKey='') {
00448                 $ac=0;
00449                 $c=0;
00450                         // First, find number of entries
00451                 reset($arr);
00452                 while(list($k,$v)=each($arr))   {
00453                         if (t3lib_div::testInt($k)) {
00454                                 $ac++;
00455                         }
00456                 }
00457                         // Traverse through entries
00458                 $subtime=0;
00459                 reset($arr);
00460                 while(list($k,$v)=each($arr))   {
00461                         if (t3lib_div::testInt($k)) {
00462                                 $c++;
00463 
00464                                 $deeper = is_array($arr[$k.'.']) ? 1 : 0;
00465                                 $PM = 'join';
00466                                 $LN = ($ac==$c)?'blank':'line';
00467                                 $BTM = ($ac==$c)?'bottom':'';
00468                                 $PM = is_array($arr[$k.'.']) ? ($deeper ? 'minus':'plus') : 'join';
00469                                 $this->tsStackLog[$v]['icons']=$depthData.($first?'':'<img src="'.TYPO3_mainDir.'gfx/ol/'.$PM.$BTM.'.gif" width="18" height="16" align="top" border="0" alt="" />');
00470 
00471                                 if (strlen($this->tsStackLog[$v]['content']))   {
00472                                         $content = str_replace($this->tsStackLog[$v]['content'],$v, $content);
00473                                 }
00474                                 if (is_array($arr[$k.'.'])) {
00475                                         $this->tsStackLog[$v]['content'] = $this->fixContent($arr[$k.'.'], $this->tsStackLog[$v]['content'], $depthData.($first?'':'<img src="'.TYPO3_mainDir.'gfx/ol/'.$LN.'.gif" width="18" height="16" align="top" border="0" alt="" />'), 0, $v);
00476                                 } else {
00477                                         $this->tsStackLog[$v]['content'] = $this->fixCLen($this->tsStackLog[$v]['content'], $this->tsStackLog[$v]['value']);
00478                                         $this->tsStackLog[$v]['subtime']='';
00479                                         $this->tsStackLog[$v]['owntime']=$this->tsStackLog[$v]['deltatime'];
00480                                 }
00481                                 $subtime+=$this->tsStackLog[$v]['deltatime'];
00482                         }
00483                 }
00484                         // Set content with special chars
00485                 if (isset($this->tsStackLog[$vKey]))    {
00486                         $this->tsStackLog[$vKey]['subtime']=$subtime;
00487                         $this->tsStackLog[$vKey]['owntime']=$this->tsStackLog[$vKey]['deltatime']-$subtime;
00488                 }
00489                 $content=$this->fixCLen($content, $this->tsStackLog[$vKey]['value']);
00490 
00491                         // Traverse array again, this time substitute the unique hash with the red key
00492                 reset($arr);
00493                 while(list($k,$v)=each($arr))   {
00494                         if (t3lib_div::testInt($k)) {
00495                                 if (strlen($this->tsStackLog[$v]['content']))   {
00496                                         $content = str_replace($v, '<font color="red"><b>['.$this->tsStackLog[$v]['key'].']</b></font>', $content);
00497                                 }
00498                         }
00499                 }
00500                         // return the content
00501                 return $content;
00502         }
00503 
00511         function fixCLen($c,$v) {
00512                 $len = $v=='FILE'?$this->printConf['contentLength_FILE']:$this->printConf['contentLength'];
00513                 if (strlen($c)>$len)    {
00514                         $c='<font color="green">'.htmlspecialchars(t3lib_div::fixed_lgd($c,$len)).'</font>';
00515                 } else {
00516                         $c=htmlspecialchars($c);
00517                 }
00518                 return $c;
00519         }
00520 
00527         function fw($str)   {
00528                 return '<font face="verdana" color="black" size="1" style="color:black;">'.$str.'&nbsp;</font>';
00529         }
00530 
00541         function createHierarchyArray(&$arr,$pointer,$uniqueId) {
00542                 if (!is_array($arr))    $arr=array();
00543                 if ($pointer>0) {
00544                         end($arr);
00545                         $k=key($arr);
00546                         $this->createHierarchyArray($arr[intval($k).'.'],$pointer-1,$uniqueId);
00547                 } else {
00548                         $arr[] = $uniqueId;
00549                 }
00550         }
00551 
00561         function debug_typo3PrintError($header,$text,$js,$baseUrl='')   {
00562                 if ($js)    {
00563                         echo"alert('".t3lib_div::slashJS($header."\n".$text)."');";
00564                 } else {
00565                         echo '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
00566                                         "http://www.w3.org/TR/xhtml1/DTD/xhtml11.dtd">
00567                                 <?xml version="1.0" encoding="utf-8"?>
00568                                 <html>
00569                                         <head>
00570                                                 '.($baseUrl ? '<base href="'.htmlspecialchars($baseUrl).'" />' : '').'
00571                                                 <title>Error!</title>
00572                                                 <style type="text/css"><!--/*--><![CDATA[/*><!--*/
00573                                                         body { font-family: verdana,arial,helvetica; font-size: 90%; text-align: center; background-color: #ffffff; }
00574                                                         h1 { font-size: 1.2em; margin: 0 0 1em 0; }
00575                                                         p { margin: 0; text-align: left; }
00576                                                         img { border: 0; margin: 10px 0; }
00577                                                         div.center div { margin: 0 auto; }
00578                                                         .errorBox { width: 400px; padding: 0.5em; border: 1px solid black; background-color: #F4F0E8; }
00579                                                 /*]]>*/--></style>
00580                                         </head>
00581                                         <body>
00582                                                 <div class="center">
00583                                                         <img src="'.TYPO3_mainDir.'gfx/typo3logo.gif" width="123" height="34" alt="" />
00584                                                         <div class="errorBox">
00585                                                                 <h1>'.$header.'</h1>
00586                                                                 <p>'.$text.'</p>
00587                                                         </div>
00588                                                 </div>
00589                                         </body>
00590                                 </html>';
00591                 }
00592         }
00593 }
00594 ?>