隐形谷歌Recaptcha和ajax形式

Kuq*_*uqa 14 html javascript forms ajax recaptcha

我有一个ajax形式:

  <form id="my_form">
    <input type="text" id="field1" />
    <input type="submit" value="submit" />
  </form>
Run Code Online (Sandbox Code Playgroud)

和js代码:

document.getElementById("my_form").onsubmit = function(e) {
  e.preventDefault();

  var xhr = new XMLHttpRequest();
  //.............. send request to a server
Run Code Online (Sandbox Code Playgroud)

在文档中,它假定表单是普通表单,而不是ajax.我究竟应该如何将隐形reCaptcha整合到我的ajax表单中?例如:

  <form id="my_form">
    <input type="text" id="field1" />
    <div class="g-recaptcha" data-sitekey="12345" data-callback="????></div>
    <input type="submit" value="submit" />
  </form>
Run Code Online (Sandbox Code Playgroud)

而且,特别是,我应该为"数据回调"处理程序指定什么?同样,在文档中,数据回调提交了一个表单,但是一个普通表单,而我的是ajax.我需要"数据回调"吗?我不应该在我的处理程序中调用recaptcha吗?怎么样?

有"渲染","getResponse"和"执行".我应该使用哪一个?从文档中不清楚.

cod*_*eto 32

我同意"隐形"重新获取文件不够全面.在理解如何使用它之前,我不得不花一些时间挖掘代码示例和"可见"重新记录的文档.

先来谈谈recaptcha API:

grecaptcha.render(htmlEl, options, inherit)是在页面上呈现验证码HTML的JS API方法.默认情况下,recaptcha脚本将尝试查找任何元素class="g-recaptcha并尝试立即渲染,但可以通过将?render=explicit查询参数附加到recaptcha脚本src url 来覆盖此行为.当你的recaptcha .g-recaptcha元素在加载脚本之后的某个时刻附加到DOM时,你也可能希望使用这个api按需呈现recaptcha html .这个api返回一个可以传递给其他api方法的ID值,但如果没有传递,那些api的查找和引用首先在页面上重新调用.

grecaptcha.getResponse(optional_id)返回令牌.如果token是空字符串,则表示用户尚未验证,即用户尚未完成验证码质询.

grecaptcha.execute(optional_id)api以编程方式按需触发recaptcha挑战.这个api仅适用于"隐形"重新捕获.当用户单击recaptcha模块时会触发可见的recaptcha挑战.

grecaptcha.reset(optional_id) 将重置挑战,即每次服务器无法使用recaptcha api服务器验证令牌时都必须完成(因为令牌是一次性使用),但根据您的实现,您可能决定随时重置.

现在,让我们谈谈数据回调:

data-callback是一个属性,您可以在其中传递全局命名空间函数的名称,即一些可以作为window ['nameOfFunction']访问的函数.每次使用您最终将传递给服务器的令牌值成功验证用户时,都会调用此回调.这是由grecaptcha.getResponse()技术上返回的相同令牌,您根本不需要此功能.但它可以作为回调,让您知道用户已经通过验证,以防您需要更新UI或其他东西.

如果由于某种原因您不希望从窗口命名空间访问此回调,则可以在带有callback键的选项对象中传递此方法grecaptcha.render().注意:options.callback可以采用一个字符串值,该值等同于data-callback在HTML中传递属性,即必须是窗口命名空间中的函数.但options.callback也可以采取"功能"的价值.


现在一些示例代码:

HTML

<script src="https://www.google.com/recaptcha/api.js?render=explicit&onload=onScriptLoad" async defer></script>
Run Code Online (Sandbox Code Playgroud)

JS

window.onScriptLoad = function () {
    // this callback will be called by recaptcah/api.js once its loaded. If we used
   // render=explicit as param in script src, then we can explicitly render reCaptcha at this point

    // element to "render" invisible captcha in
    var htmlEl = document.querySelector('.g-recaptcha');

    // option to captcha
    var captchaOptions = {
      sitekey: '6Lck',
      size: 'invisible',
      // tell reCaptcha which callback to notify when user is successfully verified.
      // if this value is string, then it must be name of function accessible via window['nameOfFunc'], 
      // and passing string is equivalent to specifying data-callback='nameOfFunc', but it can be
      // reference to an actual function
      callback: window.onUserVerified
  };

    // Only for "invisible" type. if true, will read value from html-element's data-* attribute if its not passed via captchaOptions
    var inheritFromDataAttr = true;

    // now render
    recaptchaId = window.grecaptcha.render(htmlEl, captchaOptions, inheritFromDataAttr);
};

// this is assigned from "data-callback" or render()'s "options.callback"
window.onUserVerified = function (token) {
    alert('User Is verified');
    console.log('token=', token);
};


// click handler for form's submit button
function onSubmitBtnClick () {      
  var token =   window.grecaptcha.getResponse(recaptchaId);

  // if no token, mean user is not validated yet
  if (!token) {
     // trigger validation
     window.grecaptcha.execute(recaptchaId);
     return;
  }

  var xhrData = {
    'g-recaptcha-response': token
    // more ajax body/data here
  };

  // proceed with appending more ajax call data to xhrData and then rest of ajax call process
  // var xhr = new XMLHttpRequest();
  // ... ... .... ... ... 
}
Run Code Online (Sandbox Code Playgroud)

  • 这比官方文档解释得更好,他们在解释渲染与执行方面做得不好. (4认同)