src/AppBundle/Controller/Customer/PasswordResetController.php line 27

Open in your IDE?
  1. <?php
  2. namespace AppBundle\Controller\Customer;
  3. use AppBundle\Email\ResetConfirmMail;
  4. use AppBundle\Email\ResetMail;
  5. use AppBundle\Form\Customer\ResetConfirmType;
  6. use AppBundle\Form\Customer\ResetType;
  7. use AppBundle\Repository\CustomerRepository;
  8. use Doctrine\ORM\EntityManagerInterface;
  9. use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
  10. use Symfony\Component\HttpFoundation\RedirectResponse;
  11. use Symfony\Component\HttpFoundation\Request;
  12. use Symfony\Component\PasswordHasher\Hasher\UserPasswordHasherInterface;
  13. use Symfony\Component\Routing\Annotation\Route;
  14. class PasswordResetController extends AbstractController
  15. {
  16.     public function __construct(
  17.         private string $passwordResetTokenTimespan,
  18.         private EntityManagerInterface $entityManager,
  19.         private CustomerRepository $customerRepository
  20.     ) {
  21.     }
  22.     #[Route(path'/password/reset'name'reset')]
  23.     public function editAction(Request $requestResetMail $resetMail)
  24.     {
  25.         $form $this->createForm(ResetType::class);
  26.         $form->handleRequest($request);
  27.         if ($form->isSubmitted() && $form->isValid()) {
  28.             $customer $this->customerRepository->findOneBy(['email' => $form->get('email')->getData()]);
  29.             if ($customer) {
  30.                 // reset token if invalid
  31.                 if (
  32.                     null != $customer->getPasswordResetTokenValidDate() &&
  33.                     (new \DateTime(date('Y-m-d H:i:s')))->format('Y-m-d H:i:s') > $customer->getPasswordResetTokenValidDate()->format('Y-m-d H:i:s')) {
  34.                     $customer->setPasswordResetToken(null);
  35.                     $customer->setPasswordResetTokenValidDate(null);
  36.                 }
  37.                 // send reset mail if no valid token is set
  38.                 if (
  39.                     null == $customer->getPasswordResetToken() &&
  40.                     null == $customer->getPasswordResetTokenValidDate()
  41.                 ) {
  42.                     // token is only 30 minutes valid
  43.                     $customer->setPasswordResetToken(bin2hex(random_bytes(20)));
  44.                     $customer->setPasswordResetTokenValidDate(
  45.                         (new \DateTime(date('Y-m-d H:i:s')))
  46.                             ->add(\DateInterval::createFromDateString('+'.$this->passwordResetTokenTimespan.' minutes'))
  47.                     );
  48.                     // dont update the timestamps
  49.                     // these changes are only technical and not explicitlly done by the user
  50.                     $customer->disableUpdateTimestamps();
  51.                     // save user
  52.                     $this->entityManager->persist($customer);
  53.                     $this->entityManager->flush();
  54.                     // send reset mail
  55.                     $resetMail
  56.                         ->setTo([$customer->getEmail() => $customer->getEmail()])
  57.                         ->addMessage(
  58.                             'Gericke Buchungsassistent - Passwort ändern / zurücksetzen',
  59.                             ['customer' => $customer]
  60.                         )
  61.                         ->send();
  62.                 }
  63.             }
  64.             // show the success page, always
  65.             // we don't want the customer to know which email addresses exist at this point
  66.             $this->addFlash('info''security.password.reset_send');
  67.             return new RedirectResponse($this->generateUrl('login'));
  68.         }
  69.         return $this->render('Customer/reset.html.twig', [
  70.             'form' => $form->createView(),
  71.         ]);
  72.     }
  73.     #[Route(path'/password/reset/confirm'name'reset.confirm')]
  74.     public function saveAction(
  75.         Request $request,
  76.         ResetConfirmMail $resetConfirmMail,
  77.         UserPasswordHasherInterface $userPasswordEncoder
  78.     ) {
  79.         $customer null;
  80.         if (
  81.             $this->isGranted('IS_AUTHENTICATED_FULLY') ||
  82.             $this->isGranted('ROLE_USER')
  83.         ) {
  84.             $customer $this->getUser();
  85.         } else {
  86.             // if a customer submits a valid token -> use this user
  87.             if ($request->query->has('token')) {
  88.                 $customer $this->customerRepository->findOneBy(['passwordResetToken' => $request->query->get('token')]);
  89.                 if ($customer) {
  90.                     if (
  91.                         null != $customer->getPasswordResetTokenValidDate() &&
  92.                         (new \DateTime(date('Y-m-d H:i:s')))->format('Y-m-d H:i:s') > $customer->getPasswordResetTokenValidDate()->format('Y-m-d H:i:s')
  93.                     ) {
  94.                         $customer->setPasswordResetToken(null);
  95.                         $customer->setPasswordResetTokenValidDate(null);
  96.                         $this->entityManager->persist($customer);
  97.                         $this->entityManager->flush();
  98.                         $customer null;
  99.                     }
  100.                 } else {
  101.                     $customer null;
  102.                 }
  103.             }
  104.         }
  105.         // customer could be found
  106.         if ($customer) {
  107.             $form $this->createForm(ResetConfirmType::class, $customer);
  108.             $form->handleRequest($request);
  109.             if ($form->isSubmitted() && $form->isValid()) {
  110.                 // change password
  111.                 $password $userPasswordEncoder
  112.                     ->hashPassword(
  113.                         $customer,
  114.                         $form->get('plainPassword')->getData()
  115.                     );
  116.                 $customer->setPassword($password);
  117.                 // reset password_reset
  118.                 $customer->setPasswordResetToken(null);
  119.                 $customer->setPasswordResetTokenValidDate(null);
  120.                 // save customer
  121.                 $this->entityManager->persist($customer);
  122.                 $this->entityManager->flush();
  123.                 // send confirm mail
  124.                 $resetConfirmMail
  125.                     ->setTo([$customer->getEmail() => $customer->getEmail()])
  126.                     ->addMessage(
  127.                         'Gericke Buchungsassistenten - Passwort erfolgreich geändert',
  128.                         ['customer' => $customer]
  129.                     )
  130.                     ->send();
  131.                 $this->addFlash('success''security.password.reset_success');
  132.                 if (
  133.                     $this->isGranted('IS_AUTHENTICATED_FULLY') ||
  134.                     $this->isGranted('ROLE_USER')
  135.                 ) {
  136.                     return new RedirectResponse($this->generateUrl('dashboard'));
  137.                 }
  138.                 return new RedirectResponse($this->generateUrl('login'));
  139.             }
  140.             return $this->render('Customer/resetConfirm.html.twig', [
  141.                 'form' => $form->createView(),
  142.             ]);
  143.         }
  144.         // show error page
  145.         $this->addFlash('error''Es ist ein Fehler aufgetreten.');
  146.         return new RedirectResponse($this->generateUrl('dashboard'));
  147.     }
  148. }