. */ namespace vierbergenlars\AuthserverStatsBundle\EventListener; use Symfony\Component\EventDispatcher\EventSubscriberInterface; use vierbergenlars\AuthserverStatsBundle\Event\StatsEvent; use Symfony\Bridge\Doctrine\RegistryInterface; use Symfony\Component\Security\Core\AuthenticationEvents; use Symfony\Component\Security\Core\Event\AuthenticationEvent; use vierbergenlars\AuthserverStatsBundle\Entity\AuthenticationEntry; use Symfony\Component\HttpFoundation\RequestStack; use Symfony\Component\Security\Core\Event\AuthenticationFailureEvent; use Symfony\Component\Security\Core\Authentication\Token\AnonymousToken; class AuthenticationStatsListener implements EventSubscriberInterface { /** * * @var RegistryInterface */ private $registry; /** * * @var RequestStack */ private $requestStack; public static function getSubscribedEvents() { return [ StatsEvent::class => [ [ 'getAuthStats', -1 ] ], AuthenticationEvents::AUTHENTICATION_SUCCESS => [ 'onAuthSuccess' ], AuthenticationEvents::AUTHENTICATION_FAILURE => [ 'onAuthFailure' ] ]; } public function __construct(RegistryInterface $registry, RequestStack $requestStack) { $this->registry = $registry; $this->requestStack = $requestStack; } public function onAuthSuccess(AuthenticationEvent $event) { if ($event->getAuthenticationToken() instanceof AnonymousToken) return; $authSuccess = new AuthenticationEntry($this->requestStack->getMasterRequest()->getClientIp(), true); $em = $this->registry->getManagerForClass(AuthenticationEntry::class); $em->persist($authSuccess); $em->flush($authSuccess); } public function onAuthFailure(AuthenticationFailureEvent $event) { $authFailure = new AuthenticationEntry($this->requestStack->getMasterRequest()->getClientIp(), false); $em = $this->registry->getManagerForClass(AuthenticationEntry::class); $em->persist($authFailure); $em->flush($authFailure); } public function getAuthStats(StatsEvent $event) { if (!$event->isEnabled('login')) return; $event->setMuninConfig('login', $event->getMuninConfig('login') + [ 'auth_succ.label' => 'Authentication passes', 'auth_succ.type' => 'COUNTER', 'auth_fail.label' => 'Authentication failures', 'auth_fail.type' => 'COUNTER' ]); $queryBuilder = $this->registry->getRepository(AuthenticationEntry::class)->createQueryBuilder('e'); /* @var $queryBuilder \Doctrine\ORM\QueryBuilder */ $queryBuilder->select('count(e)', 'e.success')->groupBy('e.success'); $rawStats = $queryBuilder->getQuery()->getArrayResult(); $stats = [ 'login.auth_succ' => 0, 'login.auth_fail' => 0 ]; foreach ($rawStats as $rawStat) { if ($rawStat['success']) { $stats['login.auth_succ'] += $rawStat['1']; } else { $stats['login.auth_fail'] += $rawStat['1']; } } $event->addStatistics($stats); } }