This set of files allow to
- add a unique log ID to all logs for one request, or one AMQP message
- but allow to be overrided if a specific header is present
- forward this id to messenger message to keep the whole trace
<?php | |
namespace App\Middleware; | |
use App\Middleware\Stamp\LogStamp; | |
use App\Monolog\Processor\UuidProcessor; | |
use Symfony\Component\Messenger\Envelope; | |
use Symfony\Component\Messenger\Middleware\MiddlewareInterface; | |
use Symfony\Component\Messenger\Middleware\StackInterface; | |
final readonly class LogMiddleware implements MiddlewareInterface | |
{ | |
public function __construct( | |
private UuidProcessor $uidProcessor, | |
) { | |
} | |
public function handle(Envelope $envelope, StackInterface $stack): Envelope | |
{ | |
$stamp = $envelope->last(LogStamp::class); | |
if ($stamp) { | |
$this->uidProcessor->setUuid($stamp->logUuid); | |
} else { | |
$envelope = $envelope->with(new LogStamp($this->uidProcessor->getUuid())); | |
} | |
return $stack->next()->handle($envelope, $stack); | |
} | |
} |
<?php | |
namespace App\Middleware\Stamp; | |
use Symfony\Component\Messenger\Stamp\StampInterface; | |
final readonly class LogStamp implements StampInterface | |
{ | |
public function __construct( | |
public string $logUuid, | |
) { | |
} | |
} |
framework: | |
messenger: | |
buses: | |
messenger.bus.default: | |
middleware: | |
- App\Middleware\LogMiddleware |
<?php | |
namespace App\Monolog\Processor; | |
use Monolog\LogRecord; | |
use Monolog\Processor\ProcessorInterface; | |
use Symfony\Component\HttpFoundation\RequestStack; | |
use Symfony\Contracts\Service\ResetInterface; | |
final class UuidProcessor implements ProcessorInterface, ResetInterface | |
{ | |
private string $uuid; | |
public function __construct( | |
private readonly RequestStack $requestStack | |
) { | |
} | |
public function getUuid(): string | |
{ | |
$this->initUuid(); | |
return $this->uuid; | |
} | |
public function setUuid(string $uuid): void | |
{ | |
$this->uuid = $uuid; | |
} | |
public function __invoke(LogRecord $record): LogRecord | |
{ | |
$this->initUuid(); | |
$record->extra['log_uuid'] = $this->uuid; | |
return $record; | |
} | |
public function reset() | |
{ | |
unset($this->uuid); | |
} | |
private function initUuid(): void | |
{ | |
if (isset($this->uuid)) { | |
return; | |
} | |
$request = $this->requestStack->getMainRequest(); | |
if (!$request) { | |
$this->uuid = uuid_create(); | |
return; | |
} | |
$uuid = $request->headers->get('X-Request-Id', ''); | |
if (!uuid_is_valid($uuid)) { | |
$this->uuid = uuid_create(); | |
return; | |
} | |
$this->uuid = $uuid; | |
} | |
} |