diff --git a/README.md b/README.md index c0a9cc5f..ba4a3184 100644 --- a/README.md +++ b/README.md @@ -346,6 +346,23 @@ Symbiote\QueuedJobs\Services\QueuedJobService\QueuedJobsService: ALTER TABLE `QueuedJobDescriptor` ADD INDEX ( `JobStatus` , `JobType` ) ``` +## Job error logging + +The logger can be attached to a helper which is executed within a job like below: + +```php +// Within job class +public function process(): void +{ + $logger = new Logger(); + $logger->setJob($this); + + Helper::create() + ->setLogger($logger) + ->run(); +} +``` + ## Unit tests Writing units tests for queued jobs can be tricky as it's quite a complex system. Still, it can be done. diff --git a/src/Util/Logger.php b/src/Util/Logger.php new file mode 100644 index 00000000..7d4fef3b --- /dev/null +++ b/src/Util/Logger.php @@ -0,0 +1,90 @@ +job = $job; + return $this; + } + + public function getJob(): ?QueuedJob + { + return $this->job; + } + + public function debug($message, array $context = []): void + { + $this->logJobMessage($message, LogLevel::DEBUG); + } + + public function critical($message, array $context = []): void + { + $this->logJobMessage($message, LogLevel::CRITICAL); + } + + public function alert($message, array $context = []): void + { + $this->logJobMessage($message, LogLevel::ALERT); + } + + public function emergency($message, array $context = []): void + { + $this->logJobMessage($message, LogLevel::EMERGENCY); + } + + public function warning($message, array $context = []): void + { + $this->logJobMessage($message, LogLevel::WARNING); + } + + public function error($message, array $context = []): void + { + $this->logJobMessage($message, LogLevel::ERROR); + } + + public function notice($message, array $context = []): void + { + $this->logJobMessage($message, LogLevel::NOTICE); + } + + public function info($message, array $context = []): void + { + $this->logJobMessage($message, LogLevel::INFO); + } + + public function log($level, $message, array $context = []): void + { + $this->logJobMessage($message, $level, $context); + } + + private function logJobMessage(string $message, string $level, array $context = []): void + { + $job = $this->job; + + if (!$job instanceof QueuedJob) { + return; + } + + $job->addMessage($message, $level); + } +} diff --git a/tests/Util/LoggerTest.php b/tests/Util/LoggerTest.php new file mode 100644 index 00000000..ddc986e9 --- /dev/null +++ b/tests/Util/LoggerTest.php @@ -0,0 +1,202 @@ +getService(); + + // Create a job and add it to the queue + $job = new TestQueuedJob(); + $service->queueJob($job); + + // Create a logger and set it for the created job + $logger = new Logger(); + return $logger->setJob($job); + } + + /** + * @group logger + */ + public function testSetLogger() + { + $logger = $this->getLogger(); + $this->assertNotNull($logger); + } + + /** + * @group logger + */ + public function testDebug() + { + $logger = $this->getLogger(); + + $message = 'This is debug message'; + $logger->debug($message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper(LogLevel::DEBUG), $jobData); + } + + /** + * @group logger + */ + public function testCritical() + { + $logger = $this->getLogger(); + + $message = 'This is critical message'; + $logger->critical($message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper(LogLevel::CRITICAL), $jobData); + } + + /** + * @group logger + */ + public function testAlert() + { + $logger = $this->getLogger(); + + $message = 'This is alert message'; + $logger->alert($message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper(LogLevel::ALERT), $jobData); + } + + /** + * @group logger + */ + public function testEmergency() + { + $logger = $this->getLogger(); + + $message = 'This is emergency message'; + $logger->emergency($message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper(LogLevel::EMERGENCY), $jobData); + } + + /** + * @group logger + */ + public function testWarning() + { + $logger = $this->getLogger(); + + $message = 'This is warning message'; + $logger->warning($message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper(LogLevel::WARNING), $jobData); + } + + /** + * @group logger + */ + public function testError() + { + $logger = $this->getLogger(); + + $message = 'This is error message'; + $logger->error($message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper(LogLevel::ERROR), $jobData); + } + + /** + * @group logger + */ + public function testNotice() + { + $logger = $this->getLogger(); + + $message = 'This is notice message'; + $logger->notice($message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper(LogLevel::NOTICE), $jobData); + } + + /** + * @group logger + */ + public function testInfo() + { + $logger = $this->getLogger(); + + $message = 'This is info message'; + $logger->info($message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper(LogLevel::INFO), $jobData); + } + + /** + * @dataProvider loggerProvider + * @param $logLevel + * @group logger + */ + public function testLog($logLevel) + { + $logger = $this->getLogger(); + + $message = 'This is info message'; + $logger->log($logLevel, $message); + + $jobData = $logger->getJob()->getJobData()->messages[0]; + $this->assertContains($message, $jobData); + $this->assertContains(strtoupper($logLevel), $jobData); + } + + /** + * @return array + */ + public function loggerProvider() + { + return [ + [LogLevel::WARNING], + [LogLevel::EMERGENCY], + [LogLevel::ALERT], + [LogLevel::CRITICAL], + [LogLevel::ERROR], + [LogLevel::NOTICE], + [LogLevel::INFO], + [LogLevel::DEBUG], + ]; + } +}