担当アプリのお問い合わせページが中国からのスパム投稿を行われるようになってしまったので、急遽IP制限を追加して一時的に凌ぐことにしたのですが、完全な対策ではないのでreCAPTCHAを導入することにしました。
reCAPTCHAとは?
reCAPTCHAは、Googleが提供している「人間かロボットか」を判断する仕組みです。最近よく見かけるようになったと思いますが、「私はロボットではありません」というチェックボックスにチェックを入れるだけでいいというやつです。
人間かロボットかの判断をGoogle側に依存するようになるのですが、まぁ問題ないかと思います。
Railsアプリでの導入について
RailsアプリでのreCAPTCHAの導入は簡単です。recaptchaというgemがあります。
reCAPTCHAのキーの発行
まずは以下のリンクからGet reCAPTCHAボタンを押して、reCAPTCHAのキーを取得します。
次に、
- ラベルにわかりやすいものを設定します。(ドメイン名、何のページか等)
- reCAPTCHAのタイプを選択します。今回はreCAPTCHGA v2。
- ドメインを設定します。サブドメインも設定することと、開発環境で試す場合はlocalhostや127.0.0.1なども登録しておいたほうがいいでしょう。
- 利用規約に同意して登録します。
キーが発行されるので、それをRailsアプリに登録していきます。
Railsアプリでの設定
recaptchaのサイトに導入の仕方は書いてありますが、一応書きます。
gem recaptchaのインストール
Gemfileに以下を追加します。
gem 'recaptcha', require: "recaptcha/rails"
そして、bundle install
を実行します。
環境変数の設定
環境変数にreCAPTCHAで発行されたキー類を登録しておきます。 開発環境でdotenvを使っている場合は、以下のようにしましょう。
RECAPTCHA_SITE_KEY = '発行されたサイトキーをここに設定' RECAPTCHA_SECRET_KEY = '発行されたシークレットキーをここに設定'
ViewにreCAPTCHAを表示する
あとは、Viewのformタグの内側にreCAPTCHA用のタグを出力します。人として認証されたらJavaScriptのコールバック関数を呼ぶことができますので、それが成立したら送信ボタンを有効にする、なども可能です。コードはslimで書いていますのであしからず。
= form_for @foo do |f| # 他のタグ = recaptcha_tags callback: 'successRecaptchaVerified' # 他のタグ
Controller側でreCAPTCHAのチェック
最後に、Controllerでチェックします。
def create @foo = Foo.new(foo_params) if verify_recaptcha(model: @foo) && @foo.save redirect_to @foo else render 'new' end end
これで完了です。が、みなさんテストを書いていますよね?その場合は追加が必要です。
テストでreCAPTCHAの認証をパスする
gem recaptchaはテストの際はverify_recaptcha
の結果を常にtrueを返すようになっていますので、引数に環境を渡す必要があります。env: Rails.env
を追加してください。
def create @foo = Foo.new(foo_params) if verify_recaptcha(model: @foo, env: Rails.env) && @foo.save redirect_to @foo else render 'new' end end
これでOKです。
まとめ
reCAPTCHAの導入は比較的簡単で助かりました。ただ、ローカルで何度も実験しようとすると、すぐにロボット扱いされてしまって困りました。ブラウザを変えるなどして凌いだのですが、いい方法はないものか…。どなたかご存知であれば教えてください。