Verbinden von Google reCAPTCHA mit Vue und Überprüfen der Antwort auf dem Server


In diesem Artikel werde ich zeigen, wie Captcha von Google (reCAPTCHA) mit Vue JS verbunden und die Antwort auf dem Server validiert wird (ich verwende das Backend auf Laravel / Lumen als Beispiel, aber das Prinzip der Validierung ist für alle Technologien gleich).


Vorwort


Wir werden Invisible reCAPTCHA verwenden .
Dies ist ein unsichtbares * Captcha, das erst übergeben werden muss, wenn das System dies für erforderlich hält. Der Site-Administrator kann einen Schwellenwert (Sicherheitseinstellungen) festlegen, bei dem das System vom Benutzer eine zusätzliche Überprüfung verlangt.


* - Das reCAPTCHA-Symbol sollte weiterhin auf der Seite vorhanden sein.



Unsichtbares Captcha auf der Website.


Frage Antwort


Bevor ich mit der Arbeit beginne, möchte ich die Fragen beantworten, die sich bei der Arbeit mit Google reCAPTCHA stellten.


F: Wie viel kostet reCAPTCHA?
A: ReCAPTCHA von Google ist ein kostenloses Tool.


F: Warum muss ich die Antwort des Benutzers im Backend erneut überprüfen, wenn er das Captcha auf der Site bereits bestanden hat?
A: Wenn Sie eine Anfrage an den Server stellen, senden Sie Folgendes:


POST /register 1.1 HTTP Host: www.example.com { "email:"user@gmail.com", "password": "supersecret", "recaptcha-token":"01ASJASJFZ_AASD3115..." } 

Wenn Sie das Captcha-Token im Backend nicht überprüfen, können Bots einfach Spam mit Anfragen OHNE dieses Token senden oder es durch ein Dummy-Token ersetzen.


F: Ich habe eine Reaktion. Was soll ich tun?
A: JS zu reagieren ist eine großartige Sache. Wenn Sie es für die Website-Entwicklung verwenden, empfehle ich Ihnen, auf https://github.com/appleboy/react-recaptcha zu achten. Das Funktionsprinzip ist dem Beispiel mit Vue sehr ähnlich.


An die Arbeit gehen


Bevor wir mit dem Kochen beginnen, benötigen wir eine Liste mit Zutaten:



Schritt 1: Holen Sie sich die Schlüssel, um reCAPTCHA auf Ihrer Site zu verwenden


Wir benötigen den Site-Schlüssel und den geheimen Schlüssel auf der Google-Website: https://www.google.com/recaptcha/admin#list



Sie können alles in das Beschriftungsfeld schreiben.


Wählen Sie als Nächstes den Typ - Invisible reCAPTCHA badge .


Sie können mehrere Domänen angeben, für die Sie Captcha verwenden möchten.
Als Beispiel habe ich yourawesomedomain.com und localhost angegeben .


Wir akzeptieren die Nutzungsbedingungen und fahren fort.



Sie haben zwei Schlüssel erhalten, bewahren Sie diese an einem sicheren Ort auf. Wir werden später darauf zurückkommen.


Schritt 2: Frontend. Captcha installieren und mit unseren Formularen verbinden


Um zu beginnen, müssen wir diesen Code zum Kopfabschnitt hinzufügen:


 <script src="https://www.google.com/recaptcha/api.js?onload=vueRecaptchaApiLoaded&render=explicit" async defer></script> 

Die Eigenschaft onload teilt unserer Komponente mit, dass das Captcha einsatzbereit ist.


Als nächstes werde ich die fertige Komponente zeigen und sie in Teilen analysieren:


 <template> <div id="app"> <div class="container my-4"> <div class="row justify-content-center"> <div class="col-md-8"> <h2 class="text-center mb-4"> Sign Up Form with Google reCAPTCHA </h2> <form method="post" @submit.prevent="validate"> <div class="form-group"> <input type="email" name="email" class="form-control" placeholder="Enter your e-mail address" required /> </div> <div class="form-group"> <input type="password" name="password" class="form-control" placeholder="Enter your password" required /> </div> <div class="form-group"> <vue-recaptcha ref="recaptcha" size="invisible" :sitekey="sitekey" @verify="register" @expired="onCaptchaExpired" /> <button type="submit" class="btn btn-primary btn-block"> Sign Up </button> </div> </form> </div> </div> </div> </div> </template> <script> import VueRecaptcha from 'vue-recaptcha' export default { name: 'Register', components: { VueRecaptcha }, data () { return { email: null, password: null, sitekey: ' SITE KEY' } }, methods: { register (recaptchaToken) { axios.post('https://yourserverurl.com/register', { email: this.email, password: this.password, recaptchaToken: recaptchaToken }) }, validate () { //       // ,   vee validate //       ,   this.$refs.recaptcha.execute() }, onCaptchaExpired () { this.$refs.recaptcha.reset() } } } </script> 

Beispielkomponente mit VeeValidate zum Überprüfen von Feldern
 <template> <div id="app"> <div class="container my-4"> <div class="row justify-content-center"> <div class="col-md-8"> <h2 class="text-center mb-4"> Sign Up Form with Google reCAPTCHA </h2> <form method="post" @submit.prevent="validate"> <div class="form-group"> <input type="email" name="email" class="form-control" placeholder="Enter your e-mail address" v-validate.disable="'required|email'" required /> <div v-show="errors.has('email')" class="invalid-feedback d-block" > {{ errors.first('email') }} </div> </div> <div class="form-group"> <input type="password" name="password" class="form-control" placeholder="Enter your password" v-validate.disable="'required|min:6|max:32'" required /> <div v-show="errors.has('password')" class="invalid-feedback d-block" > {{ errors.first('password') }} </div> </div> <div class="form-group"> <vue-recaptcha ref="recaptcha" size="invisible" :sitekey="sitekey" @verify="register" @expired="onCaptchaExpired" /> <button type="submit" class="btn btn-primary btn-block"> Sign Up </button> </div> </form> </div> </div> </div> </div> </template> <script> import VueRecaptcha from 'vue-recaptcha' export default { name: 'Register', components: { VueRecaptcha }, data () { return { email: null, password: null, sitekey: ' SITE KEY' } }, methods: { register (recaptchaToken) { axios.post('https://yourserverurl.com/register', { email: this.email, password: this.password, recaptchaToken: recaptchaToken }) }, validate () { const self = this self.$validator.validateAll().then((result) => { if (result) { self.$refs.recaptcha.execute() } }) }, onCaptchaExpired () { this.$refs.recaptcha.reset() } } } </script> 

Zunächst haben wir Vue-Recaptcha in unsere Komponente importiert:


 import VueRecaptcha from 'vue-recaptcha' ... components: { VueRecaptcha }, 

Als Nächstes haben wir die sitekey-Eigenschaft in der data () -Komponente deklariert:


 data () { return { ... sitekey: ' SITE KEY' } }, 

Fügen Sie die Vue-Recaptcha-Komponente zu unserem Formular hinzu:


 <vue-recaptcha ref="recaptcha" size="invisible" :sitekey="sitekey" @verify="register" @expired="onCaptchaExpired" /> 

Die Registermethode wird nach erfolgreichem Abschluss des Captchas aufgerufen, während abgelaufen nach Ablauf des Captchas aufgerufen wird.


Die onCaptchaExpired- Methode startet das Captcha neu:


 onCaptchaExpired () { this.$refs.recaptcha.reset() } 

Auf dem Formular selbst fügen wir das Ereignis @ submit.prevent = "validate" hinzu , das die Validierungsmethode auslöst, wenn das Formular gesendet wird.


 validate () { this.$refs.recaptcha.execute() } 

Der Prozess kann wie folgt beschrieben werden:


  1. Der Benutzer hat die Daten eingegeben und auf die Schaltfläche Anmelden geklickt. Die Funktion validate () wird aufgerufen.
  2. Die validate () -Funktion startet captcha. Wenn der Benutzer es erfolgreich übergibt, wird die Registrierungsmethode aufgerufen.

Bei der Registrierungsmethode erhalten wir ein recaptchaToken , das wir zusammen mit den vom Benutzer eingegebenen Daten an den Server senden müssen:


 register (recaptchaToken) { axios.post('https://yourserverurl.com/register', { email: this.email, password: this.password, recaptchaToken: recaptchaToken }) } 

Damit ist unsere Arbeit mit dem Frontend abgeschlossen. ReCAPTCHA erfolgreich installiert und ausgeführt.


PS Wenn Sie Captcha in mehreren Komponenten verwenden möchten, platzieren Sie den Sitekey am besten in der ENV- Datei und rufen Sie ihn mit process.env ab :


 data () { return { ... sitekey: process.env.VUE_APP_RECAPTCHA_TOKEN } }, 

Schritt 3: Backend-Validierung. Validierungsbeispiel für Laravel und Lumen


Die Überprüfung der Antwort auf dem Server ist sehr einfach. Beginnen wir mit dem Laravel-Beispiel.


1) Erstellen Sie im Konfigurationsordner eine recaptcha.php- Datei mit folgendem Inhalt:


 <?php return [ 'enabled' => env('RECAPTCHA_ENABLED', true), 'key' => env('RECAPTCHA_SITE_KEY'), 'secret' => env('RECAPTCHA_SECRET_KEY'), ]; 

2) Fügen Sie danach die Variablen zur .env- Datei hinzu:


 RECAPTCHA_ENABLED=FALSE RECAPTCHA_SITE_KEY=_SITE_KEY RECAPTCHA_SECRET_KEY=_SECRET_KEY 

3) Installieren Sie GuzzleHttp , um Google API-Anfragen senden zu können:


 composer require guzzlehttp/guzzle 

4) Fügen Sie im Controller die checkRecaptcha- Methode hinzu:


 protected function checkRecaptcha($token, $ip) { $response = (new Client)->post('https://www.google.com/recaptcha/api/siteverify', [ 'form_params' => [ 'secret' => config('recaptcha.secret'), 'response' => $token, 'remoteip' => $ip, ], ]); $response = json_decode((string)$response->getBody(), true); return $response['success']; } 

Bei dieser Methode senden wir unser Token (das wir vom Frontend erhalten haben) mithilfe der POST-Methode an https://www.google.com/recaptcha/api/siteverify


5) Fügen Sie in der Registrierungsmethode (in Ihrem Fall kann der Name abweichen, dies ist die Methode, an die Sie die POST-Anforderung vom Frontend gesendet haben) den folgenden Code hinzu:


 if (config('recaptcha.enabled') && !$this->checkRecaptcha($request->recaptcha_token, $request->ip())) { return return response()->json([ 'error' => 'Captcha is invalid.', ], Response::HTTP_BAD_REQUEST); } 

Alles ist gebrauchsfertig!


  • Beim Zugriff auf die Registrierungsmethode erhalten wir E-Mail, Passwort und recaptcha_token.
  • Wenn recaptcha aktiviert ist (in der .env-Datei ist der Wert RECAPTCHA_ENABLED TRUE),
    Laravel sendet eine Google API-Anfrage.
  • Wenn die Antwort Nein lautet, geben wir einen Fehler mit dem Text zurück: Captcha ist ungültig.
  • Wenn positiv, setzen Sie die Benutzerregistrierung fort.


Token Travel Visuelle Präsentation.


Der vollständige Controller-Code sieht folgendermaßen aus:


 <?php namespace App\Http\Controllers\Users; use App\Http\Controllers\Controller; use Illuminate\Http\Request; use Illuminate\Http\Response; use GuzzleHttp\Client; class UserController extends Controller { protected function checkRecaptcha($token, $ip) { $response = (new Client)->post('https://www.google.com/recaptcha/api/siteverify', [ 'form_params' => [ 'secret' => config('recaptcha.secret'), 'response' => $token, 'remoteip' => $ip, ], ]); $response = json_decode((string)$response->getBody(), true); return $response['success']; } public function register(Request $request) { $request->validate([ 'email' => 'required|string|email|unique:users|max:255', 'password' => 'required|string|max:32|min:6', 'recaptcha_token' => 'string' ]); if (config('recaptcha.enabled') && !$this->checkRecaptcha($request->recaptcha_token, $request->ip())) { return response()->json([ 'error' => 'Captcha is invalid.', ], Response::HTTP_BAD_REQUEST); } //  .  ... } } 

Validierung der Antwort auf Lumen


Auf Lumen machen wir alles auf die gleiche Weise wie im Beispiel mit Laravel, außer dass wir unsere Konfiguration ( recaptcha.php ) in bootstrap / app.php registrieren müssen :


 $app->configure('recaptcha'); 

Fazit


In diesem Artikel haben Sie gelernt, wie Sie Google reCAPTCHA in Ihrem Vue-Projekt verwenden.


ReCAPTCHA ist ein großartiges kostenloses Tool, um Ihre Ressource vor Bots zu schützen.
Mit unsichtbarem Captcha können Sie Besucher überprüfen, ohne dass sie Maßnahmen ergreifen müssen.


Beispielanwendung aus einem Artikel über Codepen


Verwendete Quellen:


  1. https://github.com/DanSnow/vue-recaptcha
  2. https://developers.google.com/recaptcha/docs/invisible
  3. https://developers.google.com/recaptcha/docs/verify
  4. https://security.stackexchange.com/questions/78807/how-does-googles-no-captcha-recaptcha-work

Source: https://habr.com/ru/post/de443370/


All Articles