First working version
This commit is contained in:
		
							
								
								
									
										187
									
								
								Entity/LogEntry.php
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										187
									
								
								Entity/LogEntry.php
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,187 @@ | ||||
| <?php | ||||
|  | ||||
|  | ||||
| namespace App\Ardent\LoggerBundle\Entity; | ||||
|  | ||||
|  | ||||
| use DateTime; | ||||
| use Doctrine\ORM\Mapping as ORM; | ||||
|  | ||||
| /** | ||||
|  * @ORM\Entity | ||||
|  * @ORM\Table(name="logger_bundle_log_entries") | ||||
|  * @ORM\HasLifecycleCallbacks | ||||
|  */ | ||||
| class LogEntry | ||||
| { | ||||
|     /** | ||||
|      * @ORM\Id | ||||
|      * @ORM\GeneratedValue(strategy="AUTO") | ||||
|      * @ORM\Column(type="integer") | ||||
|      */ | ||||
|     private $id; | ||||
|  | ||||
|     /** | ||||
|      * @ORM\Column(type="string") | ||||
|      */ | ||||
|     private $message; | ||||
|  | ||||
|     /** | ||||
|      * @ORM\Column(type="array") | ||||
|      */ | ||||
|     private $context; | ||||
|  | ||||
|     /** | ||||
|      * @ORM\Column(type="integer") | ||||
|      */ | ||||
|     private $level; | ||||
|  | ||||
|     /** | ||||
|      * @ORM\Column(type="string") | ||||
|      */ | ||||
|     private $levelName; | ||||
|  | ||||
|     /** | ||||
|      * @ORM\Column(type="string", nullable=true) | ||||
|      */ | ||||
|     private $channel; | ||||
|  | ||||
|     /** | ||||
|      * @ORM\Column(type="datetime") | ||||
|      */ | ||||
|     private $createdAt; | ||||
|  | ||||
|     /** | ||||
|      * @ORM\PrePersist | ||||
|      */ | ||||
|     public function onPrePersist() | ||||
|     { | ||||
|         $this->createdAt = new DateTime(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getId() | ||||
|     { | ||||
|         return $this->id; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $id | ||||
|      * @return LogEntry | ||||
|      */ | ||||
|     public function setId($id) | ||||
|     { | ||||
|         $this->id = $id; | ||||
|         return $this; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getMessage() | ||||
|     { | ||||
|         return $this->message; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $message | ||||
|      * @return LogEntry | ||||
|      */ | ||||
|     public function setMessage($message) | ||||
|     { | ||||
|         $this->message = $message; | ||||
|         return $this; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getContext() | ||||
|     { | ||||
|         return $this->context; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $context | ||||
|      * @return LogEntry | ||||
|      */ | ||||
|     public function setContext($context) | ||||
|     { | ||||
|         $this->context = $context; | ||||
|         return $this; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getLevel() | ||||
|     { | ||||
|         return $this->level; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $level | ||||
|      * @return LogEntry | ||||
|      */ | ||||
|     public function setLevel($level) | ||||
|     { | ||||
|         $this->level = $level; | ||||
|         return $this; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getLevelName() | ||||
|     { | ||||
|         return $this->levelName; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $levelName | ||||
|      * @return LogEntry | ||||
|      */ | ||||
|     public function setLevelName($levelName) | ||||
|     { | ||||
|         $this->levelName = $levelName; | ||||
|         return $this; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getChannel() | ||||
|     { | ||||
|         return $this->channel; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $channel | ||||
|      * @return LogEntry | ||||
|      */ | ||||
|     public function setChannel($channel) | ||||
|     { | ||||
|         $this->channel = $channel; | ||||
|         return $this; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getCreatedAt() | ||||
|     { | ||||
|         return $this->createdAt; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $createdAt | ||||
|      * @return LogEntry | ||||
|      */ | ||||
|     public function setCreatedAt($createdAt) | ||||
|     { | ||||
|         $this->createdAt = $createdAt; | ||||
|         return $this; | ||||
|     } | ||||
| } | ||||
							
								
								
									
										219
									
								
								Service/LoggerService.php
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										219
									
								
								Service/LoggerService.php
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,219 @@ | ||||
| <?php | ||||
|  | ||||
|  | ||||
| namespace App\Ardent\LoggerBundle\Service; | ||||
|  | ||||
|  | ||||
| use App\Ardent\LoggerBundle\Entity\LogEntry; | ||||
| use DateTime; | ||||
| use Doctrine\ORM\EntityManagerInterface; | ||||
| use phpDocumentor\Reflection\Types\This; | ||||
| use Psr\Log\InvalidArgumentException; | ||||
|  | ||||
| class LoggerService | ||||
| { | ||||
|     /** | ||||
|      * Detailed debug information | ||||
|      */ | ||||
|     const DEBUG = 100; | ||||
|  | ||||
|     /** | ||||
|      * Interesting events | ||||
|      * | ||||
|      * Examples: User logs in, SQL logs. | ||||
|      */ | ||||
|     const INFO = 200; | ||||
|  | ||||
|     /** | ||||
|      * Uncommon events | ||||
|      */ | ||||
|     const NOTICE = 250; | ||||
|  | ||||
|     /** | ||||
|      * Exceptional occurrences that are not errors | ||||
|      * | ||||
|      * Examples: Use of deprecated APIs, poor use of an API, | ||||
|      * undesirable things that are not necessarily wrong. | ||||
|      */ | ||||
|     const WARNING = 300; | ||||
|  | ||||
|     /** | ||||
|      * Runtime errors | ||||
|      */ | ||||
|     const ERROR = 400; | ||||
|  | ||||
|     /** | ||||
|      * Critical conditions | ||||
|      * | ||||
|      * Example: Application component unavailable, unexpected exception. | ||||
|      */ | ||||
|     const CRITICAL = 500; | ||||
|  | ||||
|     /** | ||||
|      * Action must be taken immediately | ||||
|      * | ||||
|      * Example: Entire website down, database unavailable, etc. | ||||
|      * This should trigger the SMS alerts and wake you up. | ||||
|      */ | ||||
|     const ALERT = 550; | ||||
|  | ||||
|     /** | ||||
|      * Urgent alert. | ||||
|      */ | ||||
|     const EMERGENCY = 600; | ||||
|  | ||||
|     /** | ||||
|      * Logging levels from syslog protocol defined in RFC 5424 | ||||
|      * | ||||
|      * @var array $levels Logging levels | ||||
|      */ | ||||
|     protected static $levels = array( | ||||
|         self::DEBUG     => 'DEBUG', | ||||
|         self::INFO      => 'INFO', | ||||
|         self::NOTICE    => 'NOTICE', | ||||
|         self::WARNING   => 'WARNING', | ||||
|         self::ERROR     => 'ERROR', | ||||
|         self::CRITICAL  => 'CRITICAL', | ||||
|         self::ALERT     => 'ALERT', | ||||
|         self::EMERGENCY => 'EMERGENCY', | ||||
|     ); | ||||
|  | ||||
|     private $name; | ||||
|  | ||||
|     /** | ||||
|      * @var EntityManagerInterface | ||||
|      */ | ||||
|     private $em; | ||||
|  | ||||
|     /** | ||||
|      * LoggerService constructor. | ||||
|      * @param EntityManagerInterface $em | ||||
|      */ | ||||
|     public function __construct(EntityManagerInterface $em) | ||||
|     { | ||||
|         $this->name = ""; | ||||
|         $this->em = $em; | ||||
|     } | ||||
|  | ||||
|     public function addNotice($message, $context = []) | ||||
|     { | ||||
|         return $this->addRecord(self::NOTICE, $message, $context); | ||||
|     } | ||||
|  | ||||
|     public function addWarning($message, $context = []) | ||||
|     { | ||||
|         return $this->addRecord(self::WARNING, $message, $context); | ||||
|     } | ||||
|  | ||||
|     public function addError($message, $context = []) | ||||
|     { | ||||
|         return $this->addRecord(self::ERROR, $message, $context); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Adds a log record. | ||||
|      * | ||||
|      * @param  int     $level   The logging level | ||||
|      * @param  string  $message The log message | ||||
|      * @param  array   $context The log context | ||||
|      * | ||||
|      * @return bool Whether the record has been processed | ||||
|      */ | ||||
|     public function addRecord($level, $message, $context = []) | ||||
|     { | ||||
|         $levelName = static::getLevelName($level); | ||||
|  | ||||
|         if( $level > self::WARNING) { | ||||
|             $context += $this->automaticContext(); | ||||
|         } | ||||
|  | ||||
|         $logEntry = (new LogEntry()) | ||||
|             ->setMessage((string) $message) | ||||
|             ->setContext($context) | ||||
|             ->setLevel($level) | ||||
|             ->setLevelName($levelName) | ||||
|             ->setChannel($this->name) | ||||
|         ; | ||||
|  | ||||
|         $this->em->persist($logEntry); | ||||
|         $this->em->flush(); | ||||
|  | ||||
|         return true; | ||||
|     } | ||||
|  | ||||
|     private function automaticContext() | ||||
|     { | ||||
|         $classFilters = [ | ||||
|             'Ardent\LoggerBundle\Service\LoggerService', | ||||
|             'HttpKernel\Kernel', | ||||
|             'HttpKernel\HttpKernel', | ||||
|         ]; | ||||
|         $backtraces = debug_backtrace(); | ||||
|         $context = []; | ||||
|         $traces = 0; | ||||
|         foreach ($backtraces as $trace) { | ||||
|             $skip = false; | ||||
|             foreach ($classFilters as $class) { | ||||
|                 if(strpos($trace['class'], $class)) { | ||||
|                     $skip = true; | ||||
|                 } | ||||
|             } | ||||
|             if($skip) { | ||||
|                 continue; | ||||
|             } | ||||
|             $context[] = "function[$traces]: ".$trace['function']; | ||||
|             $context[] = "class[$traces]: ".$trace['class']; | ||||
|             ++$traces; | ||||
|         } | ||||
|         return $context; | ||||
|     } | ||||
|  | ||||
|     public function getLatest($level = self::DEBUG, $amount = 1) | ||||
|     { | ||||
|         $qb = $this->em->createQueryBuilder(); | ||||
|  | ||||
|         $qb | ||||
|             ->select('l') | ||||
|             ->from('ArdentLoggerBundle:LogEntry', 'l') | ||||
|             ->where($qb->expr()->gte('l.level', '?1')) | ||||
|             ->orderBy('l.createdAt', 'DESC') | ||||
|             ->setParameter(1, $level) | ||||
|             ->setMaxResults($amount); | ||||
|         ; | ||||
|  | ||||
|         return $qb->getQuery()->getResult(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Gets the name of the logging level. | ||||
|      * | ||||
|      * @param  int    $level | ||||
|      * @return string | ||||
|      */ | ||||
|     public static function getLevelName($level) | ||||
|     { | ||||
|         if (!isset(static::$levels[$level])) { | ||||
|             throw new InvalidArgumentException('Level "'.$level.'" is not defined, use one of: '.implode(', ', array_keys(static::$levels))); | ||||
|         } | ||||
|  | ||||
|         return static::$levels[$level]; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getName() | ||||
|     { | ||||
|         return $this->name; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $name | ||||
|      * @return LoggerService | ||||
|      */ | ||||
|     public function setName($name) | ||||
|     { | ||||
|         $this->name = $name; | ||||
|         return $this; | ||||
|     } | ||||
| } | ||||
		Reference in New Issue
	
	Block a user