通过ajax成功提交表单时如何验证真实性令牌?

时间:2018-12-17 12:23:07

标签: ruby-on-rails ruby

我有一个条件,首先触发ajax请求以获取相应的主机URL。如果返回的条件为true,我想提交rails表单。表单已正确提交,但我收到无法验证真实性令牌的错误。

$(document).ready(function() {
      var url, email;
      $("form#new_user").submit(function(e){
        e.preventDefault();
        email = document.getElementById("user_email").value;
        $.ajax("/return_host", {
          type: "GET",
          data: {
            email: email
          },
          beforeSend: function(xhr) {
            xhr.setRequestHeader('X-CSRF-Token', $('meta[name="csrf-token"]').attr('content'));
          },
          success: function(data) {
            if(data['goto'] == true){
              host = data["host"];
              url = host + "/users/sign_in";
              $("form").attr("action", url);
              $("form").trigger('submit.rails');
            } else {
              location.reload();
            }
          }
        });
      });
    });

通过Ajax成功触发Rails表单时如何发送真实性令牌?

2 个答案:

答案 0 :(得分:0)

请检查您的表单是否具有名为authenticity_token的隐藏输入字段,对于使用rails helper生成的表单,默认情况下会包含此字段。

否则,这就是导致错误的原因,因为Rails在发布表单时期望一个名为authenticity_token的参数。

您可以在成功回调中即时添加它,如下所示:

     success: function(data) {
        if(data['goto'] == true){
          host = data["host"];
          url = host + "/users/sign_in";
          var form = $("form");
          var authenticityToken = document.createElement("input");
          authenticityToken.setAttribute("type", "hidden");
          authenticityToken.setAttribute("name", "authenticity_token");
          authenticityToken.setAttribute("value", $('meta[name="csrf-token"]').attr('content'));
          form.append(authenticityToken);
          form.attr("action", url);
          form.trigger('submit.rails');
        } else {
          location.reload();
        }
      }

希望有帮助!

答案 1 :(得分:0)

如果您使用的是Rails 5.1+,我建议使用form_with帮助程序来处理ajax请求[https://api.rubyonrails.org/v5.2.1/classes/ActionView/Helpers/FormHelper.html#method-i-form_with]

您仍然可以使用我在下面共享的代码来插入成功和错误回调。

```

let form = document.getElementById('my_form')

form.addEventListener('ajax:error', (event) => {
  let form                  = event.target
  let [errors, status, xhr] = event.detail

  // DO SOMETHING
})

form.addEventListener('ajax:success', (event) => {
  let form = event.target

  // DO SOMETHING
})

form.addEventListener('ajax:before', (event) => {
  let form = event.target

  // DO SOMETHING
})

```

通过这种方式,rails会处理真实性令牌/ csrf,但您仍然可以使用Ajax-选项data: { remote: true }以确保不重新加载页面。

希望这会有所帮助。