Laravel - 驗證碼

GucciLee發表於2019-01-29

驗證碼

驗證碼 是防止惡意破解密碼、刷票、論壇灌水、刷頁的手段。驗證碼有 多種型別。 本專案中我們將使用圖片驗證碼,其原理是讓使用者輸入一個扭曲變形的圖片上所顯示的文字或數字,扭曲變形是為了避免被光學字元識別軟體(OCR)自動辨識。由於計算機無法識別驗證碼的圖片,所以回答出問題的使用者就可以被認為是人類。

接下來我們將使用驗證碼來防衛的使用者註冊功能。

安裝擴充套件包

我們將以第三方擴充套件包 mews/captcha 作為基礎來實現 Laravel 中的驗證碼功能。

使用 Composer 安裝:

$ composer require "mews/captcha:~2.0"

執行以下命令生成配置檔案 config/captcha.php:

$  php artisan vendor:publish --provider='Mews\Captcha\CaptchaServiceProvider' 

我們可以開啟配置檔案,檢視其內容:

config/captcha.php

<?php

return [

    'characters' => '2346789abcdefghjmnpqrtuxyzABCDEFGHJMNPQRTUXYZ',

    'default'   => [
        'length'    => 5,
        'width'     => 120,
        'height'    => 36,
        'quality'   => 90,
    ],

    'flat'   => [
        'length'    => 6,
        'width'     => 160,
        'height'    => 46,
        'quality'   => 90,
        'lines'     => 6,
        'bgImage'   => false,
        'bgColor'   => '#ecf2f4',
        'fontColors'=> ['#2c3e50', '#c0392b', '#16a085', '#c0392b', '#8e44ad', '#303f9f', '#f57c00', '#795548'],
        'contrast'  => -5,
    ],

    'mini'   => [
        'length'    => 3,
        'width'     => 60,
        'height'    => 32,
    ],

    'inverse'   => [
        'length'    => 5,
        'width'     => 120,
        'height'    => 36,
        'quality'   => 90,
        'sensitive' => true,
        'angle'     => 12,
        'sharpen'   => 10,
        'blur'      => 2,
        'invert'    => true,
        'contrast'  => -5,
    ]

];

可以看到這些配置選項都非常通俗易懂,characters 選項是用來顯示給使用者的所有字串,default, flat, mini, inverse 分別是定義的四種驗證碼型別,你可以在此修改對應選項自定義驗證碼的長度、背景顏色、文字顏色等屬性,在此不做過多敘述。

頁面嵌入

此擴充套件包的使用分為兩步:

  1. 前端展示 —— 生成驗證碼給使用者展示,並收集使用者輸入的答案;
  2. 後端驗證 —— 接收答案,檢測使用者輸入的驗證碼是否正確。

1. 前端展示

接下來我們請將註冊頁面模板 register.blade.php 內容替換為以下:

resources/views/auth/register.blade.php

<div class="form-group row">
  <label for="captcha" class="col-md-4 col-form-label text-md-right">驗證碼</label>

  <div class="col-md-6">
    <input id="captcha" class="form-control{{ $errors->has('captcha') ? ' is-invalid' : '' }}" name="captcha" required>

    <img class="thumbnail captcha mt-3 mb-2" src="{{ captcha_src('flat') }}" onclick="this.src='/captcha/flat?'+Math.random()" title="點選圖片重新獲取驗證碼">

    @if ($errors->has('captcha'))
      <span class="invalid-feedback" role="alert">
        <strong>{{ $errors->first('captcha') }}</strong>
      </span>
    @endif
  </div>
</div>

程式碼講解:

  1. 我們首先將此檔案裡的英文翻譯為中文;
  2. 在『確認密碼』區塊程式碼下,我們增加了『驗證碼』區塊程式碼;
  3. captcha_src() 方法是 mews/captcha 提供的輔助方法,用於生成驗證碼圖片連結;
  4. 『驗證碼』區塊中 onclick() 是 JavaScript 程式碼,實現了點選圖片重新獲取驗證碼的功能,允許使用者在驗證碼太難識別的情況下換一張圖片試試。

因涉及到樣式程式碼編譯,請確保虛擬機器裡的 $ npm run watch-poll 命令處於執行中。

2. 後端驗證

mews/captcha 是專門為 Laravel 量身定製的擴充套件包,能很好的相容 Laravel 生成的註冊邏輯。我們只需要在註冊的時候,新增上表單驗證規則即可:

app/Http/Controllers/Auth/RegisterController.php

<?php
.
.
.

class RegisterController extends Controller
{
    .
    .
    .

    /**
     * Get a validator for an incoming registration request.
     *
     * @param  array  $data
     * @return \Illuminate\Contracts\Validation\Validator
     */
    protected function validator(array $data)
    {
        return Validator::make($data, [
            'name' => ['required', 'string', 'max:255'],
            'email' => ['required', 'string', 'email', 'max:255', 'unique:users'],
            'password' => ['required', 'string', 'min:6', 'confirmed'],
            'captcha' => ['required', 'captcha'],
        ], [
            'captcha.required' => '驗證碼不能為空',
            'captcha.captcha' => '請輸入正確的驗證碼',
        ]);
    }
    .
    .
    .
}

我們新增了驗證規則:

'captcha' => ['required', 'captcha'],

表示式裡的第二個 captchamews/captcha 自定義的表單驗證規則。擴充套件包非常巧妙地利用了 Laravel 表單驗證器提供的 自定義表單驗證規則 功能。令我們在開發驗證碼時非常方便。

Validator 表單驗證的 make() 方法第三個引數是自定義錯誤提示,這裡我們對驗證碼的錯誤提示進行自定義。

相關文章