· 

SalesforceでGoogle reCaptcha V3

SalesforceでGoogle reCaptcha V3を実装してみました。

Google reCaptcha V3がリリースされて、AIがボットかどうかを判定してくれるそうです。

それによって、とってもめんどくさかった画像の選択とかがなくなったそうなので実装してみました。

 

例によってPHPのサンプルとかしかなかったのでここに記載しておきます。

 

ちなみに、Google側の仕組みは全く分かっていないので、説明が雑ですが悪しからず。

 

始めにGoogleアカウントを作成してキーを取得してください。

 

まずはページ側からJavascriptでGoogleからトークンを取得します。

 

  1. <apex:page controller="reCaptcha_Ctrl" >
  2.     <script src="https://www.google.com/recaptcha/api.js?render=サイトキー"></script>
  3.     <script>
  4.          grecaptcha.ready(function() {
  5.              var form = document.getElementsByTagName('form')[0];
  6.              grecaptcha.execute('reCAPTCHAのキー',
  7.              action:'/apex/このVisualforcePage名'}).then(function(token) {
  8.                  var recaptchaResponse = document.getElementById('recaptchaResponse');
  9.                  recaptchaResponse.value = token;
  10.              });
  11.          });
  12.     </script>
  13.     <apex:form>
  14.         <apex:inputText value="{!hogehoge}"/>
  15.         <apex:commandButton action="{!save}" value="保存" id="Button"/>
  16.     </apex:form>
  17. </apex:page>

 

フォーム送信時にクラス側から、GoogleにAPIを送信して結果を取得します。

 

  1. public class reCaptcha_Ctrl{
  2.     // URL
  3.     private static String baseUrl = 'https://www.google.com/recaptcha/api/siteverify';
  4.     // シークレットキー
  5.     private static String secret = 'シークレットキー';
  6.     // tokenを取得
  7.     public String response { get { return ApexPages.currentPage().getParameters().get('recaptchaResponse');} }
  8.     //コンストラクタ
  9.     public reCaptcha_Ctrl(){
  10.     }
  11.     //処理
  12.     public PageReference save(){
  13.         // レスポンス
  14.         String responseBody = makeRequest(baseUrl,'secret=' + secret +'&response='+ response);
  15.          // レスポンスのsuccessの値を取得
  16.         String success = getValueFromJson(responseBody, 'success');
  17.         // レスポンスのスコア数を取得
  18.         Double inscore = double.valueOf(getValueFromJson(responseBody, 'score'));
  19.         // successがTrueの場合 かつ スコア数が0.5以上の場合
  20.         if(success.equalsIgnoreCase('true') && inscore >= 0.5){
  21.             // 成功の処理
  22.         }else{
  23.             // ボット対策の処理
  24.         }
  25.         return null;
  26.     }
  27.     //API投げるメソッド
  28.     private static String makeRequest(string url, string body) {
  29.         HttpResponse response = null;
  30.         HttpRequest req = new HttpRequest();
  31.         Http http = new Http();
  32.         req.setEndpoint(url);
  33.         req.setMethod('POST');
  34.         req.setBody (body);
  35.         response = http.send(req);
  36.         return response.getBody();
  37.     }
  38.     // Jsonの中身を返すメソッド
  39.     public static string getValueFromJson ( String strJson, String field ) {
  40.         JSONParser parser = JSON.createParser(strJson);
  41.         while (parser.nextToken() != null) {
  42.             // トークン全体を比較
  43.             if ((parser.getCurrentToken() == JSONToken.FIELD_NAME)) {
  44.                 // FIELD NAME を返す
  45.                 if(parser.getText() == field){
  46.                     // FIELD NAMEに対して値を返す
  47.                     parser.nextToken();
  48.                     // 次のトークンを返す
  49.                     return parser.getText();
  50.                 }
  51.             }
  52.         }
  53.         return parser.getText();
  54.     }
  55. }

 

ボットだとsuccessがfalseで帰ってきます。

手動だとscoreが返ってきますが、同じ動きを連続で実施すると点数がどんどん下がります。

 

Googleが何しているのかは謎。

その他のSalesforce記事


VisualforceでcommandButtonにrerender属性を設定して、 oncompleteにコールバック処理を記載したら動作してくれない。
Visualforceで生成したPDFが、Google Chromeで表示されない
項目履歴管理をデータローダで取得しようとしたらエラーが発生した。