You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
		
			
		
			
				
					
					
						
							419 lines
						
					
					
						
							18 KiB
						
					
					
				
			
		
		
		
			
			
			
				
					
				
				
					
				
			
		
		
	
	
							419 lines
						
					
					
						
							18 KiB
						
					
					
				| <?php | |
| /** | |
|  * log4php is a PHP port of the log4j java logging package. | |
|  *  | |
|  * <p>This framework is based on log4j (see {@link http://jakarta.apache.org/log4j log4j} for details).</p> | |
|  * <p>Design, strategies and part of the methods documentation are developed by log4j team  | |
|  * (Ceki Gülcü as log4j project founder and  | |
|  * {@link http://jakarta.apache.org/log4j/docs/contributors.html contributors}).</p> | |
|  * | |
|  * <p>PHP port, extensions and modifications by VxR. All rights reserved.<br> | |
|  * For more information, please see {@link http://www.vxr.it/log4php/}.</p> | |
|  * | |
|  * <p>This software is published under the terms of the LGPL License | |
|  * a copy of which has been included with this distribution in the LICENSE file.</p> | |
|  *  | |
|  * @package log4php | |
|  * @subpackage helpers | |
|  */ | |
| 
 | |
| /** | |
|  * @ignore  | |
|  */ | |
| if (!defined('LOG4PHP_DIR')) define('LOG4PHP_DIR', dirname(__FILE__) . '/..'); | |
| 
 | |
| if (!defined('LOG4PHP_LINE_SEP')) { | |
|     if (substr(php_uname(), 0, 7) == "Windows") { | |
|         /** | |
|          * @ignore | |
|          */ | |
|         define('LOG4PHP_LINE_SEP', "\r\n"); | |
|     } else { | |
|         /** | |
|          * @ignore | |
|          */ | |
|         define('LOG4PHP_LINE_SEP', "\n"); | |
|     } | |
| } | |
|   | |
| /** | |
|  */ | |
| require_once(LOG4PHP_DIR . '/helpers/LoggerFormattingInfo.php'); | |
| require_once(LOG4PHP_DIR . '/helpers/LoggerPatternConverter.php'); | |
| require_once(LOG4PHP_DIR . '/LoggerLog.php'); | |
| 
 | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_ESCAPE_CHAR',         '%'); | |
| 
 | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_LITERAL_STATE',       0); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_CONVERTER_STATE',     1); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_MINUS_STATE',         2); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_DOT_STATE',           3); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_MIN_STATE',           4); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_MAX_STATE',           5); | |
| 
 | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_FULL_LOCATION_CONVERTER',         1000); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_METHOD_LOCATION_CONVERTER',       1001); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_CLASS_LOCATION_CONVERTER',        1002); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_FILE_LOCATION_CONVERTER',         1003); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_LINE_LOCATION_CONVERTER',         1004); | |
| 
 | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_RELATIVE_TIME_CONVERTER',         2000); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_THREAD_CONVERTER',                2001); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_LEVEL_CONVERTER',                 2002); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_NDC_CONVERTER',                   2003); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_MESSAGE_CONVERTER',               2004); | |
| 
 | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_DATE_FORMAT_ISO8601',    'Y-m-d H:i:s,u');  | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_DATE_FORMAT_ABSOLUTE',   'H:i:s'); | |
| define('LOG4PHP_LOGGER_PATTERN_PARSER_DATE_FORMAT_DATE',       'd M Y H:i:s,u'); | |
| 
 | |
| /** | |
|  * Most of the work of the {@link LoggerPatternLayout} class  | |
|  * is delegated to the {@link LoggerPatternParser} class. | |
|  *  | |
|  * <p>It is this class that parses conversion patterns and creates | |
|  * a chained list of {@link LoggerPatternConverter} converters.</p> | |
|  *  | |
|  * @author VxR <vxr@vxr.it> | |
|  * @version $Revision: 1.1 $  | |
|  * @package log4php | |
|  * @subpackage helpers | |
|  * | |
|  * @since 0.3 | |
|  */ | |
| class LoggerPatternParser { | |
| 
 | |
|     var $state; | |
|     var $currentLiteral; | |
|     var $patternLength; | |
|     var $i; | |
|      | |
|     /** | |
|      * @var LoggerPatternConverter | |
|      */ | |
|     var $head = null; | |
|       | |
|     /** | |
|      * @var LoggerPatternConverter | |
|      */ | |
|     var $tail = null; | |
|      | |
|     /** | |
|      * @var LoggerFormattingInfo | |
|      */ | |
|     var $formattingInfo; | |
|      | |
|     /** | |
|      * @var string pattern to parse | |
|      */ | |
|     var $pattern; | |
| 
 | |
|     /** | |
|      * Constructor  | |
|      * | |
|      * @param string $pattern | |
|      */ | |
|     function LoggerPatternParser($pattern) | |
|     { | |
|         LoggerLog::debug("LoggerPatternParser::LoggerPatternParser() pattern='$pattern'"); | |
|      | |
|         $this->pattern = $pattern; | |
|         $this->patternLength =  strlen($pattern); | |
|         $this->formattingInfo = new LoggerFormattingInfo(); | |
|         $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_LITERAL_STATE; | |
|     } | |
| 
 | |
|     /** | |
|      * @param LoggerPatternConverter $pc | |
|      */ | |
|     function addToList($pc) | |
|     { | |
|         // LoggerLog::debug("LoggerPatternParser::addToList()"); | |
|      | |
|         if($this->head == null) { | |
|             $this->head = $pc; | |
|             $this->tail =& $this->head; | |
|         } else { | |
|             $this->tail->next = $pc; | |
|             $this->tail =& $this->tail->next; | |
|         } | |
|     } | |
| 
 | |
|     /** | |
|      * @return string | |
|      */ | |
|     function extractOption() | |
|     { | |
|         if(($this->i < $this->patternLength) and ($this->pattern{$this->i} == '{')) { | |
|             $end = strpos($this->pattern, '}' , $this->i); | |
|             if ($end !== false) { | |
|                 $r = substr($this->pattern, ($this->i + 1), ($end - $this->i - 1)); | |
| 	            $this->i= $end + 1; | |
|         	    return $r; | |
|             } | |
|         } | |
|         return null; | |
|     } | |
| 
 | |
|     /** | |
|      * The option is expected to be in decimal and positive. In case of | |
|      * error, zero is returned.   | |
|      */ | |
|     function extractPrecisionOption() | |
|     { | |
|         $opt = $this->extractOption(); | |
|         $r = 0; | |
|         if ($opt !== null) { | |
|             if (is_numeric($opt)) { | |
|     	        $r = (int)$opt; | |
|             	if($r <= 0) { | |
|             	    LoggerLog::warn("Precision option ({$opt}) isn't a positive integer."); | |
|             	    $r = 0; | |
|             	} | |
|             } else { | |
|                 LoggerLog::warn("Category option \"{$opt}\" not a decimal integer."); | |
|             } | |
|         } | |
|         return $r; | |
|     } | |
| 
 | |
|     function parse() | |
|     { | |
|         LoggerLog::debug("LoggerPatternParser::parse()"); | |
|      | |
|         $c = ''; | |
|         $this->i = 0; | |
|         $this->currentLiteral = ''; | |
|         while ($this->i < $this->patternLength) { | |
|             $c = $this->pattern{$this->i++}; | |
| //            LoggerLog::debug("LoggerPatternParser::parse() char is now '$c' and currentLiteral is '{$this->currentLiteral}'");             | |
|             switch($this->state) { | |
|                 case LOG4PHP_LOGGER_PATTERN_PARSER_LITERAL_STATE: | |
|                     // LoggerLog::debug("LoggerPatternParser::parse() state is 'LOG4PHP_LOGGER_PATTERN_PARSER_LITERAL_STATE'"); | |
|                     // In literal state, the last char is always a literal. | |
|                     if($this->i == $this->patternLength) { | |
|                         $this->currentLiteral .= $c; | |
|                         continue; | |
|                     } | |
|                     if($c == LOG4PHP_LOGGER_PATTERN_PARSER_ESCAPE_CHAR) { | |
|                         // LoggerLog::debug("LoggerPatternParser::parse() char is an escape char");                     | |
|                         // peek at the next char. | |
|                         switch($this->pattern{$this->i}) { | |
|                             case LOG4PHP_LOGGER_PATTERN_PARSER_ESCAPE_CHAR: | |
|                                 // LoggerLog::debug("LoggerPatternParser::parse() next char is an escape char");                     | |
|                                 $this->currentLiteral .= $c; | |
|                                 $this->i++; // move pointer | |
|                                 break; | |
|                             case 'n': | |
|                                 // LoggerLog::debug("LoggerPatternParser::parse() next char is 'n'");                             | |
|                                 $this->currentLiteral .= LOG4PHP_LINE_SEP; | |
|                                 $this->i++; // move pointer | |
|                                 break; | |
|                             default: | |
|                                 if(strlen($this->currentLiteral) != 0) { | |
|                                     $this->addToList(new LoggerLiteralPatternConverter($this->currentLiteral)); | |
|                                     LoggerLog::debug("LoggerPatternParser::parse() Parsed LITERAL converter: \"{$this->currentLiteral}\"."); | |
|                                 } | |
|                                 $this->currentLiteral = $c; | |
|                                 $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_CONVERTER_STATE; | |
|                                 $this->formattingInfo->reset(); | |
|                         } | |
|                     } else { | |
|                         $this->currentLiteral .= $c; | |
|                     } | |
|                     break; | |
|               case LOG4PHP_LOGGER_PATTERN_PARSER_CONVERTER_STATE: | |
|                     // LoggerLog::debug("LoggerPatternParser::parse() state is 'LOG4PHP_LOGGER_PATTERN_PARSER_CONVERTER_STATE'");               | |
|                 	$this->currentLiteral .= $c; | |
|                 	switch($c) { | |
|                     	case '-': | |
|                             $this->formattingInfo->leftAlign = true; | |
|                             break; | |
|                     	case '.': | |
|                             $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_DOT_STATE; | |
| 	                        break; | |
|                     	default: | |
|                             if(ord($c) >= ord('0') and ord($c) <= ord('9')) { | |
|                         	    $this->formattingInfo->min = ord($c) - ord('0'); | |
|                         	    $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_MIN_STATE; | |
|                             } else { | |
|                                 $this->finalizeConverter($c); | |
|                             } | |
|                   	} // switch | |
|                     break; | |
|               case LOG4PHP_LOGGER_PATTERN_PARSER_MIN_STATE: | |
|                     // LoggerLog::debug("LoggerPatternParser::parse() state is 'LOG4PHP_LOGGER_PATTERN_PARSER_MIN_STATE'");               | |
| 	                $this->currentLiteral .= $c; | |
|                     if(ord($c) >= ord('0') and ord($c) <= ord('9')) { | |
|                         $this->formattingInfo->min = ($this->formattingInfo->min * 10) + (ord(c) - ord('0')); | |
|                 	} elseif ($c == '.') { | |
|                         $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_DOT_STATE; | |
|                     } else { | |
|                     	$this->finalizeConverter($c); | |
|                 	} | |
|                 	break; | |
|               case LOG4PHP_LOGGER_PATTERN_PARSER_DOT_STATE: | |
|                     // LoggerLog::debug("LoggerPatternParser::parse() state is 'LOG4PHP_LOGGER_PATTERN_PARSER_DOT_STATE'");               | |
|                 	$this->currentLiteral .= $c; | |
|                     if(ord($c) >= ord('0') and ord($c) <= ord('9')) { | |
|                         $this->formattingInfo->max = ord($c) - ord('0'); | |
| 	                    $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_MAX_STATE; | |
|                     } else { | |
|                 	  LoggerLog::warn("LoggerPatternParser::parse() Error occured in position {$this->i}. Was expecting digit, instead got char \"{$c}\"."); | |
| 	                  $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_LITERAL_STATE; | |
|                     } | |
|                 	break; | |
|               case LOG4PHP_LOGGER_PATTERN_PARSER_MAX_STATE: | |
|                     // LoggerLog::debug("LoggerPatternParser::parse() state is 'LOG4PHP_LOGGER_PATTERN_PARSER_MAX_STATE'");               | |
|                 	$this->currentLiteral .= $c; | |
|                     if(ord($c) >= ord('0') and ord($c) <= ord('9')) { | |
|                         $this->formattingInfo->max = ($this->formattingInfo->max * 10) + (ord($c) - ord('0')); | |
| 	                } else { | |
|                 	  $this->finalizeConverter($c); | |
|                       $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_LITERAL_STATE; | |
| 	                } | |
|                 	break; | |
|             } // switch | |
|         } // while | |
|         if(strlen($this->currentLiteral) != 0) { | |
|             $this->addToList(new LoggerLiteralPatternConverter($this->currentLiteral)); | |
|             // LoggerLog::debug("LoggerPatternParser::parse() Parsed LITERAL converter: \"{$this->currentLiteral}\"."); | |
|         } | |
|         return $this->head; | |
|     } | |
| 
 | |
|     function finalizeConverter($c) | |
|     { | |
|         LoggerLog::debug("LoggerPatternParser::finalizeConverter() with char '$c'");     | |
| 
 | |
|         $pc = null; | |
|         switch($c) { | |
|             case 'c': | |
|                 $pc = new LoggerCategoryPatternConverter($this->formattingInfo, $this->extractPrecisionOption()); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() CATEGORY converter."); | |
|                 // $this->formattingInfo->dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'C': | |
|                 $pc = new LoggerClassNamePatternConverter($this->formattingInfo, $this->extractPrecisionOption()); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() CLASSNAME converter."); | |
|                 //$this->formattingInfo->dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'd': | |
|                 $dateFormatStr = LOG4PHP_LOGGER_PATTERN_PARSER_DATE_FORMAT_ISO8601; // ISO8601_DATE_FORMAT; | |
|                 $dOpt = $this->extractOption(); | |
| 
 | |
|                 if($dOpt !== null) | |
| 	                $dateFormatStr = $dOpt; | |
|                      | |
|                 if ($dateFormatStr == 'ISO8601') { | |
|                     $df = LOG4PHP_LOGGER_PATTERN_PARSER_DATE_FORMAT_ISO8601; | |
|                 } elseif($dateFormatStr == 'ABSOLUTE') { | |
|                     $df = LOG4PHP_LOGGER_PATTERN_PARSER_DATE_FORMAT_ABSOLUTE; | |
|                 } elseif($dateFormatStr == 'DATE') { | |
|                     $df = LOG4PHP_LOGGER_PATTERN_PARSER_DATE_FORMAT_DATE; | |
|                 } else { | |
|                     $df = $dateFormatStr; | |
|                     if ($df == null) { | |
|                         $df = LOG4PHP_LOGGER_PATTERN_PARSER_DATE_FORMAT_ISO8601; | |
|                     } | |
| 	            } | |
|                 $pc = new LoggerDatePatternConverter($this->formattingInfo, $df); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'F': | |
|                 $pc = new LoggerLocationPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_FILE_LOCATION_CONVERTER); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() File name converter."); | |
|                 //formattingInfo.dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'l': | |
|                 $pc = new LoggerLocationPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_FULL_LOCATION_CONVERTER); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() Location converter."); | |
|                 //formattingInfo.dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'L': | |
|                 $pc = new LoggerLocationPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_LINE_LOCATION_CONVERTER); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() LINE NUMBER converter."); | |
|                 //formattingInfo.dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'm': | |
|                 $pc = new LoggerBasicPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_MESSAGE_CONVERTER); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() MESSAGE converter."); | |
|                 //formattingInfo.dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'M': | |
|                 $pc = new LoggerLocationPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_METHOD_LOCATION_CONVERTER); | |
|                 //LogLog.debug("METHOD converter."); | |
|                 //formattingInfo.dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'p': | |
|                 $pc = new LoggerBasicPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_LEVEL_CONVERTER); | |
|                 //LogLog.debug("LEVEL converter."); | |
|                 //formattingInfo.dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'r': | |
|                 $pc = new LoggerBasicPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_RELATIVE_TIME_CONVERTER); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() RELATIVE TIME converter."); | |
|                 //formattingInfo.dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 't': | |
|                 $pc = new LoggerBasicPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_THREAD_CONVERTER); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() THREAD converter."); | |
|                 //formattingInfo.dump(); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             case 'u': | |
|                 if($this->i < $this->patternLength) { | |
| 	                $cNext = $this->pattern{$this->i}; | |
|                     if(ord($cNext) >= ord('0') and ord($cNext) <= ord('9')) { | |
| 	                    $pc = new LoggerUserFieldPatternConverter($this->formattingInfo, (string)(ord($cNext) - ord('0'))); | |
|                         LoggerLog::debug("LoggerPatternParser::finalizeConverter() USER converter [{$cNext}]."); | |
| 	                    // formattingInfo.dump(); | |
|                         $this->currentLiteral = ''; | |
| 	                    $this->i++; | |
| 	                } else { | |
|                         LoggerLog::warn("LoggerPatternParser::finalizeConverter() Unexpected char '{$cNext}' at position {$this->i}."); | |
|                     } | |
|                 } | |
|                 break; | |
|             case 'x': | |
|                 $pc = new LoggerBasicPatternConverter($this->formattingInfo, LOG4PHP_LOGGER_PATTERN_PARSER_NDC_CONVERTER); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() NDC converter."); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
| 
 | |
|             case 'X': | |
|                 $xOpt = $this->extractOption(); | |
|                 $pc = new LoggerMDCPatternConverter($this->formattingInfo, $xOpt); | |
|                 LoggerLog::debug("LoggerPatternParser::finalizeConverter() MDC converter."); | |
|                 $this->currentLiteral = ''; | |
|                 break; | |
|             default: | |
|                 LoggerLog::warn("LoggerPatternParser::finalizeConverter() Unexpected char [$c] at position {$this->i} in conversion pattern."); | |
|                 $pc = new LoggerLiteralPatternConverter($this->currentLiteral); | |
|                 $this->currentLiteral = ''; | |
|         } | |
|         $this->addConverter($pc); | |
|     } | |
| 
 | |
|     function addConverter($pc) | |
|     { | |
|         $this->currentLiteral = ''; | |
|         // Add the pattern converter to the list. | |
|         $this->addToList($pc); | |
|         // Next pattern is assumed to be a literal. | |
|         $this->state = LOG4PHP_LOGGER_PATTERN_PARSER_LITERAL_STATE; | |
|         // Reset formatting info | |
|         $this->formattingInfo->reset(); | |
|     } | |
| } | |
| 
 | |
| ?>
 |