| Uutiset | Koodikirjasto | Wiki | Keskustelut | FAQ | Info |
Loggerrainmikko 26.01.06 11:20 Helppokäytöinen logittaja vaikkapa debuggaamiseen. Yhdistin tähän myös Ezkun ErrorHandlerin (http://mureakuha.com/koodikirjasto/823) hanskaamaan virheilmotukset luettavampaan muotoon lokiin.
-- Logger.php -- <?php /** * Logger is easy and usefull logging tool. * * @author Mikko Rainio 2006 * @package Logger */ //////////////////// //Logger parameters /** * Defines debugmode */ define("LOG_DEBUG_ENABLED", true); /** * Absolute path to log directory. */ define("LOG_DIR_PATH","/path/to/logfolder"); /** * Log filename */ define("LOG_FILENAME","debug.log"); /** * Use custom error handler. Works in >= PHP 4.3.0 */ define("LOG_USE_CUSTOM_ERROR_HANDLER",true); /** * Set the maximum size that the output file is allowed to reach * before being rolled over to backup files. * * <p>You can specify the value with the suffixes "KB", "MB" or "GB" * so that the integer is interpreted being expressed respectively * in kilobytes, megabytes or gigabytes. For example, the value "10KB" * will be interpreted as 10240.</p> * <p>The default maximum file size is 5MB.</p> * * <p>Note that <var>LOG_MAX_FILE_SIZE</var> cannot exceed <b>2 GB</b>.</p> */ define("LOG_MAX_FILE_SIZE","5MB"); /** * Date format */ define("LOG_DATE_FORMAT","Y-m-d H:i:s"); // End: Logging parameters ////////////////////////// //verify log folder existence //if it does not exist, create it if(LOG_DIR_PATH != '' && !is_dir(LOG_DIR_PATH)){ if(mkdir(LOG_DIR_PATH)===FALSE){ die( "Could not create log dir: ".LOG_DIR_PATH ); } } // Use our own error handler? // Using class method in error handler works since PHP 4.3.0 if(LOG_USE_CUSTOM_ERROR_HANDLER && PHP_VERSION >= '4.3.0') set_error_handler(array(new Log(),'ErrorHandler')); /** * Class Log. Handles logging to logfile. All class methods can be used as * static method. * * <p>Usefull also for logging variables at debugtime.</p> * <p>For example: * <code> * $arr = array("one","two","three"); * Log::debug("Log array values",__FILE__,__LINE__); * Log::debug($arr); * </code></p> * <p>Output: * <pre> * 2006-01-25 16:21:21 DEBUG /path/to/filename.php(21): Log array values * 2006-01-25 16:21:21 DEBUG : Array ( [0] => one [1] => two [2] => three ) * </pre></p> * * @author Mikko Rainio 2006 * @version 1.1 * @package Logger * @static All methods can be used as static */ class Log { /** * Writes DEBUG-level message to log file. * For example:<code>Log::debug("Message",__FILE__,__LINE__);</code> * * @uses LOG_DEBUG_ENABLED * @param String $logMsg Log row * @param String $file Optional. Filename where something happens * @param String $line Optional. Line number */ function debug($logMsg,$file='',$line='') { if(LOG_DEBUG_ENABLED) { Log::logRow($logMsg,'DEBUG',$file,$line); } } /** * Writes WARNING-level message to log file. * For example:<code>Log::warn("Message",__FILE__,__LINE__);</code> * * @param String $logMsg Log row * @param String $file Optional. Filename where something happens * @param String $line Optional. Line number */ function warn($logMsg,$file='',$line='') { Log::logRow($logMsg,'WARNING',$file,$line); } /** * Writes ERROR-level message to log file. * For example:<code>Log::error("Message",__FILE__,__LINE__);</code> * * @param String $logMsg Log row * @param String $file Optional. Filename where something happens * @param String $line Optional. Line number */ function error($logMsg,$file='',$line='') { Log::logRow($logMsg,'ERROR',$file,$line); } /** * Writes INFO-level message to log file. * For example:<code>Log::info("Message",__FILE__,__LINE__);</code> * * @param String $logMsg Log row * @param String $file Optional. Filename where something happens * @param String $line Optional. Line number */ function info($logMsg,$file='',$line='') { Log::logRow($logMsg,'INFO',$file,$line); } /** * Return formatted actual date. * * @uses LOG_DATE_FORMAT * @param String $pattern Optional. Date pattern. Default is 'Y-m-d H:i:s' * @return String Actual date. */ function get_formatted_date($pattern = ''){ if($pattern == '') $pattern = LOG_DATE_FORMAT; return date($pattern); } /** * Converts $arg to string. Can handle objects, arrays, multidimensional * arrays etc... * * @access private * @param mixed $arg Convertable input * @return String Converted string */ function msgToString($arg) { $retMsg = ''; if(is_array($arg)) { $retMsg .= " Array ("; foreach($arg as $key => $value) { $retMsg .= " [".$key.'] => '.Log::msgToString($value)." "; } $retMsg .= ")"; } elseif( is_object($arg) ) { $retMsg .= get_class($arg)." Object ("; $vars = get_object_vars($arg); foreach($vars as $key => $value) { $retMsg .= " [".$key.'] => '.Log::msgToString($value)." "; } $retMsg .= ")"; } elseif( is_bool($arg) ) { $retMsg .= ($arg)? 'true': 'false'; } elseif( $arg == NULL ) { $retMsg .= 'NULL'; } else { $retMsg .= "$arg"; } return $retMsg; } /** * Error handler, providing rigorous backtrace information. * * @author Ezku * @link http://mureakuha.com/koodikirjasto/823 * @param int error type * @param string error message * @param string file name * @param string line number */ function ErrorHandler ($error_type, $error_message, $file, $line) { $strReturn = ""; static $error_types = array ( 1 => 'E_ERROR', 2 => 'E_WARNING', 4 => 'E_PARSE', 8 => 'E_NOTICE', 16 => 'E_CORE_ERROR', 32 => 'E_CORE_WARNING', 64 => 'E_COMPILE_ERROR', 128 => 'E_COMPILE_WARNING', 256 => 'E_USER_ERROR', 512 => 'E_USER_WARNING', 1024 => 'E_USER_NOTICE', 2047 => 'E_ALL', 2048 => 'E_STRICT' ); // Check error type against error reporting level. @ is always ignored. if (($error_type != 0) && ($error_type & ini_get('error_reporting'))){ $strReturn .= Log::get_formatted_date().' '.$error_types[$error_type]. ' '.$file.'('.$line.'): '.$error_message."\n"; $backtrace = debug_backtrace(); // First is always ErrorHandler, skip it array_shift($backtrace); $i = -1; foreach ($backtrace as $trace) { $args = array(); if (isset($trace['args'])) { foreach ($trace['args'] as $a) { switch (gettype($a)) { case 'integer': case 'double': $args[] = $a; break; case 'string': $args[] = "\"$a\""; break; case 'array': $args[] = 'Array('.count($a).')'; break; case 'object': $args[] = 'Object('.get_class($a).')'; break; case 'resource': $args[] = 'Resource('.strstr($a, '#').')'; break; case 'boolean': $args[] = $a ? 'True' : 'False'; break; case 'NULL': $args[] = 'NULL'; break; default: $args[] = 'UNKNOWN'; } } } if( true) { $strReturn .= "\t".'#'.++$i.' '.$trace['file'].'('.$trace['line'].'): '. (isset($trace['class']) ? $trace['class'].$trace['type'] : ''). $trace['function'].'('.implode(', ',$args).')'."\n"; } } Log::writeLog($strReturn); if($error_types[$error_type] == 'E_ERROR' || $error_types[$error_type] == 'E_USER_ERROR' || $error_types[$error_type] == 'E_USER_NOTICE') exit; } } /** * Empty constructor. Needed only in set_error_handler()-function above. * * @access private */ function Log(){} /** * Constructs the log row. * * @access private * @param String $logMsg Log row * @param String $level Message log-level ('INFO','DEBUG','WARNING','ERROR') * @param String $file Optional. Filename where something happens * @param String $line Optional. Line number */ function logRow($logMsg,$level,$file='',$line=''){ $logRow = Log::get_formatted_date().' '.$level.' '; if($file != '') { $logRow .= $file; if($line != '') $logRow .= '('.$line.')'; } $logRow .= ': '.Log::msgToString($logMsg)."\n"; Log::writeLog($logRow); }//end function /** * Recieves the string and writes it in to log file. * * @access private * @uses LOG_DIR_PATH * @uses LOG_FILENAME * @param String $logString Log row */ function writeLog($logString){ $logFile=(LOG_DIR_PATH != '')? LOG_DIR_PATH . "/" . LOG_FILENAME : LOG_FILENAME; //write to log file $fp=fopen($logFile,"a"); if(fwrite($fp,$logString)===FALSE){ die("Could not write to LOG file: ".$logFile); } fclose($fp); if(filesize($logFile) >= Log::getMaxFileSizeInBytes()) { $bakFile = ((LOG_DIR_PATH == '')? '': LOG_DIR_PATH.'/') . date("YmdHis") . ".log.bak"; rename( $logFile, $bakFile ); } }//end function /** * Converts property <var>LOG_MAX_FILE_SIZE</var> to bytes. * * @access private * @uses LOG_MAX_FILE_SIZE * @return integer LOG_MAX_FILE_SIZE in bytes */ function getMaxFileSizeInBytes() { $value = LOG_MAX_FILE_SIZE; $maxFileSize = null; $numpart = substr($value,0, strlen($value) -2); $suffix = strtoupper(substr($value, -2)); switch ($suffix) { case 'KB': $maxFileSize = (int)((int)$numpart * 1024); break; case 'MB': $maxFileSize = (int)((int)$numpart * 1024 * 1024); break; case 'GB': $maxFileSize = (int)((int)$numpart * 1024 * 1024 * 1024); break; default: if (is_numeric($value)) { $maxFileSize = (int)$value; } } if ($maxFileSize === null) { // if something fails, return default value (5242880 = 5MB) return 5242880; } else { return abs($maxFileSize); } } } ?> -- test.php -- <?php require_once('Logger.php'); Log::debug("debug-viesti",__FILE__,__LINE__); Log::info("info-viesti",__FILE__,__LINE__); Log::warn("warning-viesti",__FILE__,__LINE__); Log::error("error-viesti",__FILE__,__LINE__); $arr = array("one","two","three"); Log::debug("Laitetaan taulukko lokiin",__FILE__,__LINE__); Log::debug($arr); // Lokiin tulostuu: // 2006-01-25 16:21:21 DEBUG /path/to/filename.php(21): Laitetaan taulukko lokiin // 2006-01-25 16:21:21 DEBUG : Array ( [0] => one [1] => two [2] => three ) //Lähetetään virhe omalle virheenkäsittelijälle trigger_error("Nostetaan trigger_error() -functiolla E_USER_NOTICE -tasoinen virhe"); echo "Tätä ei pitäisi näkyä :)"; ?> rainmikko 11:24 26.1.06 Onko jotakin mitä en ole ottanut huomioon lokittajan toiminnassa? :) rainmikko 12:19 2.2.06 Pari bugikorjausta ja turhat vakiot pois. rainmikko 08:42 3.2.06 Eikö löydy kommentoitavaa? :) Veikko91 12:53 4.2.06 Virus 04:20 5.2.06 Muutappa pääte .php:ksi. |
![]() Haku
|