Как добавить в PHP-форму reCAPTCHA v3 и отправлять данные с помощью Ajax
В этом руководстве мы добавим в PHP-форму Google reCAPTCHA v3 и отправим ее данные без перезагрузки веб-страницы, используя Ajax.
Почему Google reCAPTCHA v3?
У многих пользователей раньше возникали проблемы при прохождении капчи.

К счастью, сейчас многие сайты используют Google reCAPTCHA v2, которая просто отображает флажок «Я не робот».

В 2018 году Google выпустила reCAPTCHA v3, которая вообще не требует взаимодействия с пользователем. Ее можно использовать в формах, чтобы предотвратить отправку спама.
Теперь узнаем, как добавить Google reCAPTCHA v3 в простую форму.
Регистрация ключей reCAPTCHA v3
Сначала необходимо зарегистрировать свой сайт и получить ключи здесь. Затем добавьте метку, выберите reCAPTCHA v3, введите доменное имя сайта и отправьте данные.

После этого будет сгенерирован site key и secret key. Скопируйте и сохраните их.
HTML-форма
В качестве примера используем простую форму с полями «Полное имя», «Электронная почта» и «Сообщение».

HTML
Ниже представлен HTML-код формы. Ее CSS-код доступен в архиве с исходниками.
<form id="contact-form" method="post">
<p class="label">Full Name *</p>
<input type="text" name="name" placeholder="Full Name" required>
<p class="label">Email *</p>
<input type="email" name="email" placeholder="Email" required>
<p class="label">Message *</p>
<textarea name="message" rows="6" placeholder="Type your message here" required></textarea>
<!-- Скрытый div “alert” ниже для отображения сообщения, возвращаемого с сервера после отправки данных формы-->
<div id="alert"></div>
<button id="submit-button" type="submit">Send Message</button>
</form>
Отправка данных формы с помощью Ajax
Доработаем процесс отправки формы с помощью Ajax, Для этого потребуется библиотека jQuery. Загрузите ее, используя CDN. Вставьте приведенную ниже строку кода перед закрывающимся тегом body.
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
Теперь выполнить Ajax-запрос на отправку данных формы.
<script>
$('#contact-form').submit(function(event) {
event.preventDefault(); // Предотвращаем прямую отправку данных формы
$('#alert').text('Processing...').fadeIn(0); // Выводим "Processing...", чтобы сообщить пользователю, что данные формы отправлены
$.ajax({
url: 'contact.php',
type: 'post',
data: $('#contact-form').serialize(),
dataType: 'json',
success: function( _response ){
// Запрос Ajax выполнен успешно. _response - это объект JSON object
var error = _response.error;
var success = _response.success;
if(error != "") {
// В случае ошибки выводим пользователю это сообщение
$('#alert').html(error);
}
else {
// В случае успешного выполнения, выводим пользователю это сообщение и удаляем кнопку отправки
$('#alert').html(success);
$('#submit-button').remove();
}
},
error: function(jqXhr, json, errorThrown){
// В случае ошибки Ajax, выводим пользователю результат для демонстрационных целей
var error = jqXhr.responseText;
$('#alert').html(error);
}
});
});
</script>
Сейчас если вы нажмете кнопку отправки формы, то получите сообщение об ошибке 404. Так как файл contact.php еще не существует.
PHP
Создайте файл contact.php. На стороне сервера необходимо проверить полученные данные и отправить ответ JSON.
<?php
// Валидация на стороне сервера
function isValid() {
// Простейшая валидация для демонстрационных целей. Замените ее на валидацию на стороне сервера
if($_POST['name'] != "" && $_POST['email'] != "" && $_POST['message'] != "") {
return true;
} else {
return false;
}
}
$error_output = '';
$success_output = '';
if(isValid()) {
$success_output = "Your message sent successfully";
} else {
// Валидация на стороне сервера не прошла
$error_output = "Please fill all the required fields";
}
$output = array(
'error' => $error_output,
'success' => $success_output
);
// Вывод должен быть в формате JSON
echo json_encode($output);
?>
Теперь пришло время интегрировать reCAPTCHA v3.
Интеграция на стороне клиента
Загрузите API JavaScript с site key. Вставьте приведенный ниже код под ссылкой на CDN JQuery.
<script async src="https://www.google.com/recaptcha/api.js?render=YOUR_SITE_KEY_HERE"></script>
Важно: замените YOUR_SITE_KEY_HERE значением, которое вы сохранили ранее.
В документации к reCAPTCHA v3 сказано, что необходимо вызывать grecaptcha.execute
для каждого пользовательского действия, которое нужно защитить (отправка данных формы). Этот вызов генерирует токен, который необходимо отправить вместе с данными формы для проверки на стороне сервера. Для этого нужно добавить в форму скрытое поле ввода и динамически присвоить ему значение токена:
<input type="hidden" name="recaptcha_response" id="recaptchaResponse">
Вызовите эту функцию ниже Ajax-запроса и присвойте скрытому полю ввода значение токена.
grecaptcha.ready(function () {
grecaptcha.execute('YOUR_SITE_KEY_HERE', { action: 'contact' }).then(function (token) {
var recaptchaResponse = document.getElementById('recaptchaResponse');
recaptchaResponse.value = token;
// Выполняем здесь вызов Ajax
});
});
Значение 'action' является специфичным для действия отправки данных формы. Различные действия помогут анализировать данные по всему сайту, если добавить reCAPTCHA сразу в нескольких местах.
Примечание: срок действия токенов reCAPTCHA истекает через две минуты. Поэтому необходимо сгенерировать этот токен только после того, как пользователь нажмет кнопку отправки и перед выполнением Ajax- запрос.
Интеграция на стороне сервера
После проверки введенных пользователем данных на стороне сервера, нужно получить оценку от Google, чтобы убедиться в том, что имеем дело с реальным человеком. Внутри блока if(isvalid()){ } добавьте приведенный ниже код, чтобы выполнить API-запрос для получения оценки.
// Составляем POST-запрос, чтобы получить от Google оценку reCAPTCHA v3
$recaptcha_url = 'https://www.google.com/recaptcha/api/siteverify';
$recaptcha_secret = 'YOUR_SECRET_KEY_HERE'; // Insert your secret key here
$recaptcha_response = $_POST['recaptcha_response'];
// Выполняем POST-запрос
$recaptcha = file_get_contents($recaptcha_url . '?secret=' . $recaptcha_secret . '&response=' . $recaptcha_response);
Важно: замените YOUR_SECRET_KEY_HERE значением, которое вы скопировали ранее. Secret key предназначен только для серверной части.
Полученный ответ является объектом JSON.
{
"success": true|false, // является ли этот запрос валидным токеном reCAPTCHA для вашего сайта
"score": number // оценка для этого запроса (0.0 – 1.0)
"action": string // имя действия для этого запроса (важно для верификации)
"challenge_ts": timestamp, // временная метка для загрузки задачи (форма ISO yyyy-MM-dd’T’HH:mm:ssZZ)
"hostname": string, // имя хоста сайта, на котором обрабатывается reCAPTCHA
"error-codes": […] // необязательно
}
Расшифруем объект JSON $recaptcha и проверим success, score и action. Оценка имеет значение от 0,0 до 1,0. По умолчанию можно использовать порог 0,5.
$recaptcha = json_decode($recaptcha);
// Принимаем действие на основе возвращаемой оценки
if ($recaptcha->success == true && $recaptcha->score >= 0.5 && $recaptcha->action == 'contact') {
// Это человек. Вставляем сообщение в базу данных или отправляем на электронную почту
$success_output = "Your message sent successfully";
} else {
// Оценка меньше 0.5 означает подозрительную активность. Возвращаем ошибку
$error_output = "Something went wrong. Please try again later";
}
Все готово! Нажмите кнопку отправки, и если вы все правильно настроили, то получите ответ your message was sent successfully.

Бонусный совет:
Добавив JavaScript API, мы получили раздражающий значок reCAPTCHA в правом нижнем углу веб-страницы.

Но этот значок можно скрыть, если добавить следующий текст в поток пользователя:
This site is protected by reCAPTCHA and the Google
<a href="https://policies.google.com/privacy">Privacy Policy</a> and
<a href="https://policies.google.com/terms">Terms of Service</a> apply.
Поэтому добавьте это в элемент <p > под кнопкой отправки.

Теперь, чтобы скрыть значок, просто добавьте приведенный ниже код в CSS.
.grecaptcha-badge {
visibility: hidden;
}
Мы успешно настроили Google reCAPTCHA v3 для формы. Теперь вы будете получать сообщения только от реальных людей.
СКАЧАТЬ ИСХОДНЫЙ КОД