Commit 8d88a55247207f976f7f487cebc637b5fb181828

Authored by alex
1 parent d73c3e95

Add Google Recaptcha to site/contact

**** Нужно композером на сервере установить новую либу
common/config/main.php
@@ -26,6 +26,13 @@ @@ -26,6 +26,13 @@
26 ] 26 ]
27 ], 27 ],
28 'components' => [ 28 'components' => [
  29 +
  30 + 'reCaptcha' => [
  31 + 'name' => 'reCaptcha',
  32 + 'class' => 'sashsvamir\yii2\recaptcha\ReCaptcha',
  33 + 'siteKey' => '6LcZcmQUAAAAANF1TashIYAvYtTBCscpTlPe1q6T',
  34 + 'secret' => '6LcZcmQUAAAAAFH4Ru4S6QnmB3An3PJWglmV',
  35 + ],
29 'cache' => [ 36 'cache' => [
30 'class' => 'yii\caching\FileCache', 37 'class' => 'yii\caching\FileCache',
31 ], 38 ],
@@ -18,7 +18,8 @@ @@ -18,7 +18,8 @@
18 "minimum-stability": "RC", 18 "minimum-stability": "RC",
19 "require": { 19 "require": {
20 "php": ">=7.0", 20 "php": ">=7.0",
21 - "artweb/artbox-core" : ">0.0.10" 21 + "artweb/artbox-core": ">0.0.10",
  22 + "sashsvamir/yii2-recaptcha-widget": "dev-master"
22 }, 23 },
23 "require-dev": { 24 "require-dev": {
24 "yiisoft/yii2-debug": "~2.0.0", 25 "yiisoft/yii2-debug": "~2.0.0",
@@ -4,8 +4,8 @@ @@ -4,8 +4,8 @@
4 "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file", 4 "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file",
5 "This file is @generated automatically" 5 "This file is @generated automatically"
6 ], 6 ],
7 - "hash": "d1c4ebdcace0dbe46fef8e15f5de2d7f",  
8 - "content-hash": "20c2db805fdbbc718dc7c57c39800648", 7 + "hash": "9a6e92d2cba1e4da99f27abd0a2ae4f3",
  8 + "content-hash": "f335aaff8ec5703aad48c3b2fd89b0c1",
9 "packages": [ 9 "packages": [
10 { 10 {
11 "name": "2amigos/yii2-tinymce-widget", 11 "name": "2amigos/yii2-tinymce-widget",
@@ -226,7 +226,7 @@ @@ -226,7 +226,7 @@
226 "version": "1.4.0", 226 "version": "1.4.0",
227 "source": { 227 "source": {
228 "type": "git", 228 "type": "git",
229 - "url": "https://github.com/puikinsh/gentelella.git", 229 + "url": "git@github.com:puikinsh/gentelella.git",
230 "reference": "3448fdfdf16a41707d6e2a8154d592a88d85c41c" 230 "reference": "3448fdfdf16a41707d6e2a8154d592a88d85c41c"
231 }, 231 },
232 "dist": { 232 "dist": {
@@ -245,12 +245,12 @@ @@ -245,12 +245,12 @@
245 "version": "1.0.2", 245 "version": "1.0.2",
246 "source": { 246 "source": {
247 "type": "git", 247 "type": "git",
248 - "url": "https://github.com/fronteed/icheck.git", 248 + "url": "git@github.com:fronteed/iCheck.git",
249 "reference": "8a6eb37bd7dab1e843c1b630c91c6398ff409d05" 249 "reference": "8a6eb37bd7dab1e843c1b630c91c6398ff409d05"
250 }, 250 },
251 "dist": { 251 "dist": {
252 "type": "zip", 252 "type": "zip",
253 - "url": "https://api.github.com/repos/fronteed/icheck/zipball/8a6eb37bd7dab1e843c1b630c91c6398ff409d05", 253 + "url": "https://api.github.com/repos/fronteed/iCheck/zipball/8a6eb37bd7dab1e843c1b630c91c6398ff409d05",
254 "reference": "8a6eb37bd7dab1e843c1b630c91c6398ff409d05", 254 "reference": "8a6eb37bd7dab1e843c1b630c91c6398ff409d05",
255 "shasum": null 255 "shasum": null
256 }, 256 },
@@ -370,7 +370,7 @@ @@ -370,7 +370,7 @@
370 "version": "v1.3.2", 370 "version": "v1.3.2",
371 "source": { 371 "source": {
372 "type": "git", 372 "type": "git",
373 - "url": "https://github.com/bestiejs/punycode.js.git", 373 + "url": "git@github.com:bestiejs/punycode.js.git",
374 "reference": "38c8d3131a82567bfef18da09f7f4db68c84f8a3" 374 "reference": "38c8d3131a82567bfef18da09f7f4db68c84f8a3"
375 }, 375 },
376 "dist": { 376 "dist": {
@@ -2485,6 +2485,50 @@ @@ -2485,6 +2485,50 @@
2485 "time": "2017-01-11 14:05:47" 2485 "time": "2017-01-11 14:05:47"
2486 }, 2486 },
2487 { 2487 {
  2488 + "name": "sashsvamir/yii2-recaptcha-widget",
  2489 + "version": "dev-master",
  2490 + "source": {
  2491 + "type": "git",
  2492 + "url": "https://github.com/sashsvamir/yii2-recaptcha-widget.git",
  2493 + "reference": "3daa1b48d99839807c0bf520bb2660d43ed83446"
  2494 + },
  2495 + "dist": {
  2496 + "type": "zip",
  2497 + "url": "https://api.github.com/repos/sashsvamir/yii2-recaptcha-widget/zipball/3daa1b48d99839807c0bf520bb2660d43ed83446",
  2498 + "reference": "3daa1b48d99839807c0bf520bb2660d43ed83446",
  2499 + "shasum": ""
  2500 + },
  2501 + "require": {
  2502 + "himiklab/yii2-recaptcha-widget": "1.0.6",
  2503 + "yiisoft/yii2": "*"
  2504 + },
  2505 + "type": "yii2-extension",
  2506 + "autoload": {
  2507 + "psr-4": {
  2508 + "sashsvamir\\yii2\\recaptcha\\": ""
  2509 + }
  2510 + },
  2511 + "notification-url": "https://packagist.org/downloads/",
  2512 + "license": [
  2513 + "MIT"
  2514 + ],
  2515 + "authors": [
  2516 + {
  2517 + "name": "sashsvamir",
  2518 + "homepage": "https://github.com/sashsvamir/"
  2519 + }
  2520 + ],
  2521 + "description": "Yii2 Google reCAPTCHA widget",
  2522 + "keywords": [
  2523 + "captcha",
  2524 + "google",
  2525 + "recaptcha",
  2526 + "widget",
  2527 + "yii2"
  2528 + ],
  2529 + "time": "2018-01-24 10:27:21"
  2530 + },
  2531 + {
2488 "name": "skeeks/yii2-assets-auto-compress", 2532 "name": "skeeks/yii2-assets-auto-compress",
2489 "version": "1.4.0", 2533 "version": "1.4.0",
2490 "source": { 2534 "source": {
@@ -5899,7 +5943,9 @@ @@ -5899,7 +5943,9 @@
5899 ], 5943 ],
5900 "aliases": [], 5944 "aliases": [],
5901 "minimum-stability": "RC", 5945 "minimum-stability": "RC",
5902 - "stability-flags": [], 5946 + "stability-flags": {
  5947 + "sashsvamir/yii2-recaptcha-widget": 20
  5948 + },
5903 "prefer-stable": false, 5949 "prefer-stable": false,
5904 "prefer-lowest": false, 5950 "prefer-lowest": false,
5905 "platform": { 5951 "platform": {
frontend/config/main.php
@@ -137,7 +137,7 @@ @@ -137,7 +137,7 @@
137 }', 137 }',
138 ], 138 ],
139 'contact' => [ 139 'contact' => [
140 - 'class' => 'artbox\core\forms\Module', 140 + 'class' => 'frontend\views\forms\ContactModule',
141 'activeRecord' => "frontend\models\Feedback", 141 'activeRecord' => "frontend\models\Feedback",
142 'templateForm' => '<div class="row">{form}</div>', 142 'templateForm' => '<div class="row">{form}</div>',
143 'attributes' => [ 143 'attributes' => [
@@ -145,6 +145,7 @@ @@ -145,6 +145,7 @@
145 'email', 145 'email',
146 'phone', 146 'phone',
147 'message', 147 'message',
  148 +
148 ], 149 ],
149 'rules' => [ 150 'rules' => [
150 [ 151 [
@@ -158,7 +159,8 @@ @@ -158,7 +159,8 @@
158 'phone', 159 'phone',
159 ], 160 ],
160 'required', 161 'required',
161 - ] 162 + ],
  163 +
162 ], 164 ],
163 'labels' => [ 165 'labels' => [
164 'email' => \Yii::t('app','Email'), 166 'email' => \Yii::t('app','Email'),
frontend/controllers/SiteController.php
1 <?php 1 <?php
2 namespace frontend\controllers; 2 namespace frontend\controllers;
3 3
4 - use frontend\models\Feedback; 4 + use frontend\models\Feedback as F;
5 use common\models\blog\Article; 5 use common\models\blog\Article;
6 use common\models\Settings; 6 use common\models\Settings;
7 use common\models\slider\Slide; 7 use common\models\slider\Slide;
@@ -72,11 +72,11 @@ @@ -72,11 +72,11 @@
72 */ 72 */
73 public function actionContact() 73 public function actionContact()
74 { 74 {
75 - $contact = new Feedback(); 75 + $contact = new F(['scenario' => F::SCENARIO_DEFAULT]);
76 return $this->render( 76 return $this->render(
77 'contact', 77 'contact',
78 [ 78 [
79 - 'contact' => $contact, 79 + 'model' => $contact,
80 ] 80 ]
81 ); 81 );
82 } 82 }
frontend/models/Feedback.php
@@ -7,13 +7,18 @@ @@ -7,13 +7,18 @@
7 7
8 namespace frontend\models; 8 namespace frontend\models;
9 use artbox\core\models\Feedback as ArtboxCoreFeedback; 9 use artbox\core\models\Feedback as ArtboxCoreFeedback;
10 - 10 +use sashsvamir\yii2\recaptcha\ReCaptchaValidator;
11 11
12 class Feedback extends ArtboxCoreFeedback 12 class Feedback extends ArtboxCoreFeedback
13 { 13 {
  14 + public $reCaptcha;
  15 +
  16 +
14 public function rules() 17 public function rules()
15 { 18 {
16 - return [ 19 +
  20 +
  21 + return [
17 [ 22 [
18 [ 23 [
19 'name', 24 'name',
@@ -24,6 +29,14 @@ class Feedback extends ArtboxCoreFeedback @@ -24,6 +29,14 @@ class Feedback extends ArtboxCoreFeedback
24 'on' => self::SCENARIO_DEFAULT, 29 'on' => self::SCENARIO_DEFAULT,
25 'message' => \Yii::t('app', 'Empty field'), 30 'message' => \Yii::t('app', 'Empty field'),
26 ], 31 ],
  32 + ['reCaptcha', ReCaptchaValidator::className(), 'uncheckedMessage' => 'Please confirm that you are not a bot.',
  33 + // add follow lines to prevent checking recaptcha when from has errors
  34 + 'when' => function ($model) {
  35 + return !$model->hasErrors();
  36 + },
  37 + 'on' => self::SCENARIO_DEFAULT,
  38 +
  39 + ],
27 [ 40 [
28 [ 41 [
29 'name', 42 'name',
frontend/views/forms/ContactModule.php 0 → 100644
  1 +<?php
  2 +
  3 +namespace frontend\views\forms;
  4 +
  5 +
  6 +use yii\helpers\Html;
  7 +use yii\web\View;
  8 +use yii\widgets\ActiveForm;
  9 +use artbox\core\forms\Module as CoreModule;
  10 +
  11 +
  12 +/**
  13 + * Class ContactModule
  14 + * @package frontend\forms
  15 + *
  16 + *
  17 + * Класс, который немного видоизменяет вывод формы контактов для того, чтобы в ней появилась гугловая рекапча
  18 + *
  19 + */
  20 +class ContactModule extends CoreModule
  21 +{
  22 +
  23 +
  24 + public function renderForm(View $view)
  25 + {
  26 + if ($this->ajax) {
  27 + $js = <<<JS
  28 +$(document).on('submit', '#{$this->formId}', function(e) {
  29 + e.preventDefault();
  30 + e.stopImmediatePropagation();
  31 + $.post(
  32 + $(this).attr("action"), $(this).serialize(), {$this->successCallback}).fail({$this->errorCallback});
  33 +});
  34 +JS;
  35 +
  36 + $view->registerJs($js, View::POS_READY);
  37 + }
  38 + /**
  39 + * @var ActiveForm $form
  40 + */
  41 +
  42 + $form = ActiveForm::begin(
  43 + [
  44 + 'id' => $this->formId,
  45 + 'action' => ($this->ajax) ? '/' . $this->id . '/save/ajax' : '/' . $this->id . '/save/no-ajax',
  46 + 'class' => $this->classForm,
  47 + ]
  48 + );
  49 + $content = '';
  50 + foreach ($this->attributes as $field) {
  51 +
  52 + # если мы присвоили этому полю тип, то он его отрисовывает
  53 + if (isset($this->inputOptions[$field]['type'])) {
  54 + $function = $this->inputOptions[$field]['type'];
  55 + $formStr = $form->field($this->model, $field)
  56 + ->$function(
  57 + isset($this->inputOptions[$field]['options'])
  58 + ? $this->inputOptions[$field]['options'] : []
  59 + );
  60 + } # а если нет, то просто добавляет поле
  61 + else {
  62 + $formStr = $form->field($this->model, $field);
  63 + }
  64 + if (isset($this->labels[$field])) {
  65 + $formStr->label(\Yii::t($this->locale, $this->labels[$field]));
  66 + }
  67 + if (isset($this->inputOptions[$field]['template'])) {
  68 +
  69 + $formStr = str_replace('{input}', $formStr, $this->inputOptions[$field]['template']);
  70 + }
  71 + $content .= $formStr;
  72 +
  73 + }
  74 +
  75 + $content .= $form->field($this->model, 'reCaptcha')->widget(\sashsvamir\yii2\recaptcha\ReCaptcha::className())->label(false);
  76 +
  77 +
  78 + $content .= str_replace('{button}', Html::submitButton(\Yii::t($this->locale, $this->buttonContent), $this->buttonOptions), $this->buttonTemplate);
  79 + $content = str_replace('{form}', $content, $this->templateForm);
  80 + echo $content;
  81 + ActiveForm::end();
  82 + }
  83 +}
0 \ No newline at end of file 84 \ No newline at end of file
frontend/views/site/contact.php
@@ -11,6 +11,7 @@ @@ -11,6 +11,7 @@
11 use frontend\assets\MapAsset; 11 use frontend\assets\MapAsset;
12 use yii\helpers\Html; 12 use yii\helpers\Html;
13 use yii\web\View; 13 use yii\web\View;
  14 +use yii\widgets\ActiveForm;
14 15
15 MapAsset::register($this); 16 MapAsset::register($this);
16 $settings = Settings::getInstance(); 17 $settings = Settings::getInstance();
@@ -119,7 +120,9 @@ JS; @@ -119,7 +120,9 @@ JS;
119 </div> 120 </div>
120 121
121 <div class="col-md-8 col-md-offset-2"> 122 <div class="col-md-8 col-md-offset-2">
122 - <?=$module->renderForm($this)?> 123 +
  124 +
  125 + <?= $module->renderForm($this) ?>
123 126
124 </div> 127 </div>
125 </div> 128 </div>
frontend/web/css/site.css
@@ -133,3 +133,11 @@ a.desc:after { @@ -133,3 +133,11 @@ a.desc:after {
133 .background-white { 133 .background-white {
134 background-color: white; 134 background-color: white;
135 } 135 }
  136 +
  137 +/*
  138 +Класс для выравнивания по центру формы инпута google ReCaptcha
  139 +*/
  140 +.f_center {
  141 + margin-left: 80%;
  142 + transform: translateX(-50%);
  143 +}
136 \ No newline at end of file 144 \ No newline at end of file
frontend/web/js/script.js
@@ -67,6 +67,9 @@ $( @@ -67,6 +67,9 @@ $(
67 // } 67 // }
68 // ); 68 // );
69 69
  70 +
  71 + $('.field-feedback-recaptcha').addClass('col-sm-12').addClass('f_center')
  72 +
70 /** 73 /**
71 * Button UP code 74 * Button UP code
72 */ 75 */