1 <?php
declare(strict_types
=1);
4 * This file is part of the Rapsys PackBundle package.
6 * (c) Raphaël Gertz <symfony@rapsys.eu>
8 * For the full copyright and license information, please view the LICENSE
9 * file that was distributed with this source code.
12 namespace Rapsys\PackBundle\Form
;
14 use Rapsys\PackBundle\Util\ImageUtil
;
15 use Rapsys\PackBundle\Util\SluggerUtil
;
17 use Symfony\Contracts\Translation\TranslatorInterface
;
18 use Symfony\Component\Form\AbstractType
;
19 use Symfony\Component\Form\Extension\Core\Type\HiddenType
;
20 use Symfony\Component\Form\Extension\Core\Type\IntegerType
;
21 use Symfony\Component\Form\FormBuilderInterface
;
22 use Symfony\Component\Form\FormEvents
;
23 use Symfony\Component\Form\FormEvent
;
24 use Symfony\Component\Form\FormError
;
27 * Captcha Type class definition
29 * @see https://symfony.com/doc/current/form/create_custom_field_type.html
31 class CaptchaType
extends AbstractType
{
33 * @var ImageUtil $image
38 * @var SluggerUtil $slugger
43 * @var Translator instance
50 * @param ImageUtil $image
51 * @param SluggerUtil $slugger
52 * @param TranslatorInterface $translator The translator instance
54 public function __construct(ImageUtil
$image, SluggerUtil
$slugger, TranslatorInterface
$translator) {
56 $this->image
= $image;
59 $this->slugger
= $slugger;
62 $this->translator
= $translator;
70 public function buildForm(FormBuilderInterface
$builder, array $options) {
72 $captcha = $this->image
->getCaptcha((new \
DateTime('-1 year'))->getTimestamp());
75 $builder->add('_captcha_token', HiddenType
::class, ['data' => $captcha['token'], 'empty_data' => $captcha['token']]);
78 $builder->add('captcha', IntegerType
::class, ['label_attr' => ['class' => 'captcha'], 'label' => '<img src="'.htmlentities($captcha['src']).'" alt="'.htmlentities($captcha['equation']).'" />', 'label_html' => true, 'translation_domain' => false]);
80 //Add event listener on captcha
81 $builder->addEventListener(FormEvents
::PRE_SUBMIT
, [$this, 'validateCaptcha']);
87 * @param FormEvent $event The form event
89 public function validateCaptcha(FormEvent
$event): void {
91 $form = $event->getForm();
94 $data = $event->getData();
97 $token = $form->get('_captcha_token')->getConfig()->getData();
100 if (empty($data['captcha'])) {
101 //Add error on captcha
102 $form->addError(new FormError($this->translator
->trans('Captcha is empty')));
104 //Reset captcha token
105 $data['_captcha_token'] = $token;
108 $event->setData($data);
109 //With invalid captcha
110 } elseif ($this->slugger
->hash($data['captcha']) !== $data['_captcha_token']) {
111 //Add error on captcha
112 $form->addError(new FormError($this->translator
->trans('Captcha is invalid')));
114 //Reset captcha token
115 $data['_captcha_token'] = $token;
118 $event->setData($data);