Por padrão, o captcha do Yii2 não vem com um link/botão “atualizar” que permita atualizar as imagens do captcha. Da mesma forma, ao recarregar a página da imagem do captcha, ela permanece a mesma. Isso pode ser frustrante porque muitas vezes as imagens de captcha são ilegíveis (até mesmo para humanos).
Neste tutorial, aprenderemos a criar um link/botão para “refresh” imagens de captcha e também atualizar as imagens de captcha sempre que a página for recarregada.
Outros artigos interessantes
1. Criar CaptchaRefreshable
A primeira etapa que precisamos fazer é criar uma CaptchaRefreshable classe no diretório models ou commons\models se você estiver usando o modelo avançado do yii2.
<?php namespace common\models; class CaptchaRefreshable extends \yii\captcha\Captcha { /** * Overrides the $template HTML */ public function init() { $refresh_a = \yii\helpers\Html::a('refresh', '#', [ 'id' => 'refresh-captcha', 'class' => 'text-small' // .text-small { font-size: 0.85em; } - include in your CSS ]); $this->template = ' <div id="verify-code" class="row"> <div class="large-3 columns">{image} ' . $refresh_a . '</div> <div class="large-6 columns">{input}</div> </div>'; parent::init(); } /** * Register the refresh JS */ public function registerClientScript() { $view = $this->getView(); $view->registerJs(" $('#refresh-captcha').on('click', function(e){ e.preventDefault(); $('#verify-code img').yiiCaptcha('refresh'); }) "); parent::registerClientScript(); } }
2. Criar a ação CaptchaRefreshable
Em seguida, criamos uma classe CaptchaRefreshableAction no diretório models ou commons\models se você estiver usando o modelo avançado do yii2.
<?php namespace common\models; use Yii; class CaptchaRefreshableAction extends \yii\captcha\CaptchaAction { public function validate($input, $caseSensitive) { // Skip validation on AJAX requests, as it expires the captcha. if (Yii::$app->request->isAjax) { return true; } return parent::validate($input, $caseSensitive); } }
3. Adicionar widgets ao views/site/login.php
............. ............. <div class="site-login"> ............. ............. <div class="row"> <div class="col-lg-5"> <?php $form = ActiveForm::begin(['id' => 'login-form']); ?> ............. ............. <?= $form->field($model, 'verifyCode')->widget(\common\models\CaptchaRefreshable::class) ?> ............. ............. <?php ActiveForm::end(); ?> </div> </div> </div>
4. Adicionar ação ao controlador/SiteController.php
............. ............. class SiteController extends Controller { ............. ............. public function actions() { return [ ............. ............. 'captcha' = > [ 'class' => 'common\models\CaptchaRefreshableAction', ], ............. ............. ]; } ............. ............. }
5. Adicionar ação para atualizar o captcha ao recarregar a página
Nas etapas 1 a 4 acima, criamos um botão/link para atualizar a imagem do captcha. O problema é que, ao recarregar a página, a imagem do captcha exibida não é alterada. Para que a imagem do captcha seja alterada a cada recarga de página, precisamos adicionar um script à função de login no controller/SiteController.php
............. ............. class SiteController extends Controller { ............. ............. public function actionLogin() { $this->createAction('captcha')->getVerifyCode(true); ............. ............. } ............. ............. }