src/EventSubscriber/Contest/ContestResultCreatedEventSubscriber.php line 33

Open in your IDE?
  1. <?php
  2. namespace App\EventSubscriber\Contest;
  3. use App\Entity\Contest;
  4. use App\Entity\Notification;
  5. use App\Entity\Transaction;
  6. use App\Event\Contest\ContestResultCreatedEvent;
  7. use App\Factory\TransactionFactory;
  8. use App\Helper\ContestHelper;
  9. use App\Helper\PlayerHelper;
  10. use App\Repository\BetConfigRepository;
  11. use App\Repository\NotificationRepository;
  12. use Doctrine\ORM\EntityManagerInterface;
  13. use Symfony\Component\EventDispatcher\EventSubscriberInterface;
  14. class ContestResultCreatedEventSubscriber implements EventSubscriberInterface
  15. {
  16.     public function __construct(
  17.         private EntityManagerInterface $entityManager, private BetConfigRepository $betConfigRepository,
  18.         private PlayerHelper $playerHelper, private NotificationRepository $notificationRepository,
  19.         private TransactionFactory $transactionFactory
  20.     ) {
  21.     }
  22.     public static function getSubscribedEvents(): array
  23.     {
  24.         return [
  25.             ContestResultCreatedEvent::class => 'onContestResultCreated',
  26.         ];
  27.     }
  28.     public function onContestResultCreated(ContestResultCreatedEvent $contestResultCreatedEvent): void
  29.     {
  30.         $contest $contestResultCreatedEvent->getContest();
  31.         $result $contestResultCreatedEvent->getResult();
  32.         $player $result->getPlayer();
  33.         $this->playerHelper->updateActivity($playerContestResultCreatedEvent::class);
  34.         // removes the bet PS from the player who just scored (we already removed for the contest creator earlier) and updates its activity
  35.         if ($player !== $contest->getCreatedBy()) {
  36.             $this->transactionFactory
  37.                 ->forPlayer($player)
  38.                 ->takePs($contest->getBet())
  39.                 ->because(Transaction::CONTEST_RESULT_CREATED_TYPE)
  40.                 ->save()
  41.             ;
  42.         }
  43.         // updates the player's xp
  44.         $player->setXp($player->getXp() + $result->getXp());
  45.         if (ContestHelper::hasAllPlayersScored($contest)) {
  46.             // updates all invite notifications for this Contest to "archived"
  47.             $this->notificationRepository->updateBy(
  48.                 ['archived' => true],
  49.                 [
  50.                     'contest' => $contest,
  51.                     'type'    => Notification::CONTEST_INVITATION_TYPE,
  52.                 ]
  53.             );
  54.             // gives back to all players their "bet" if the contest has even results
  55.             if (ContestHelper::hasEvenResults($contest)) {
  56.                 // notifies the players and refunds their bet
  57.                 foreach ($contest->getContestPlayers() as $contestPlayer) {
  58.                     $player $contestPlayer->getPlayer();
  59.                     $this->transactionFactory
  60.                         ->forPlayer($player)
  61.                         ->givePs($contest->getBet())
  62.                         ->because(Transaction::REFUNDED_PS_DUE_TO_CONTEST_EVEN_RESULTS_TYPE)
  63.                         ->save()
  64.                     ;
  65.                     $player
  66.                         ->addNotification(
  67.                             (new Notification())
  68.                                 ->setContest($contest)
  69.                                 ->setType(Notification::CONTEST_CLOSED_TYPE)
  70.                                 ->setMessage(
  71.                                     sprintf(
  72.                                         'Le match de %s s\'est terminé par un match nul et votre mise vous a été remboursée.',
  73.                                         $contest->getGame()->getName()
  74.                                     )
  75.                                 )
  76.                         )
  77.                     ;
  78.                 }
  79.             } else {
  80.                 $highestResult ContestHelper::findHighestResult($contest);
  81.                 $winner $highestResult->getPlayer();
  82.                 $betConfig $this->betConfigRepository->findOneBy([
  83.                     'initialValue' => $contest->getBet(),
  84.                 ]);
  85.                 $contest->setWinner($winner);
  86.                 $winner
  87.                     ->setXp($winner->getXp() + ContestHelper::getXpToEarn($contest$winner))
  88.                 ;
  89.                 $this->transactionFactory
  90.                     ->forPlayer($winner)
  91.                     ->givePs($betConfig->getWinningValue())
  92.                     ->because(Transaction::CONTEST_WINNER_TYPE)
  93.                     ->save()
  94.                 ;
  95.                 // notifies the players and updates their PS
  96.                 foreach ($contest->getContestPlayers() as $contestPlayer) {
  97.                     $player $contestPlayer->getPlayer();
  98.                     if ($player === $winner) {
  99.                         $message sprintf(
  100.                             'Vous avez gagné le match de %s et vous remportez %s PS.',
  101.                             $contest->getGame()->getName(),
  102.                             $betConfig->getWinningValue()
  103.                         );
  104.                     } else {
  105.                         $message sprintf(
  106.                             'Vous avez perdu le match de %s.',
  107.                             $contest->getGame()->getName()
  108.                         );
  109.                     }
  110.                     $player->addNotification(
  111.                         (new Notification())
  112.                             ->setContest($contest)
  113.                             ->setType(Notification::CONTEST_CLOSED_TYPE)
  114.                             ->setMessage($message)
  115.                     );
  116.                 }
  117.             }
  118.             // all players have scored so we close the contest
  119.             $contest->setStatus(Contest::CLOSED_STATUS);
  120.         } else {
  121.             $contest->setStatus(Contest::WAITING_SCORES_STATUS);
  122.             // creates notifications
  123.             foreach ($contest->getContestPlayers() as $contestPlayer) {
  124.                 $player $contestPlayer->getPlayer();
  125.                 // notifies all players except the creator
  126.                 if ($contest->getCreatedBy() === $player) {
  127.                     continue;
  128.                 }
  129.                 $message sprintf(
  130.                     'Le joueur %s vous a défié sur un %s',
  131.                     /* @phpstan-ignore-next-line */
  132.                     $contest->getCreatedBy()->getUser()->getUsername(),
  133.                     $contest->getGame()->getName()
  134.                 );
  135.                 $player->addNotification(
  136.                     (new Notification())
  137.                         ->setType(Notification::CONTEST_INVITATION_TYPE)
  138.                         ->setContest($contest)
  139.                         ->setMessage($message)
  140.                 );
  141.             }
  142.         }
  143.         $this->entityManager->flush();
  144.     }
  145. }