remote: true form avoids js field validation

2019-09-02 04:02发布

问题:

This is my form:

<%= form_for [@company,@company_branch], :html => { :onsubmit => "return validateName();" }, remote: true do |f| %>
    <%= f.text_field :name %>
    ...

The "validateName" validation works fine when i don't use a remote call. But if do it remote, the form still gets submitted, even if my validation returns false.

This is the .js for validation:

function validateName() {
    var name = document.getElementById('name');
    if( name.value == "" ) {
        highlightError(name, "Please provide a name");
        return false;
    }

    return ( true );

}

回答1:

I have collided with the same. I have not found an explanation at the moment, but in according my experiments, the remote do post of the form independently of return value of onsubmit function. I've used form validation on server side and send back a js for validation errors processing.

Updated. "In Rails 2? and at least 3, form_form, :remote => true overrides the :onsubmit => ‘func();’ method to do the actual form submission. If you want to bind something to your form before it gets submitted (or during or after!), bind the form using jQuery.bind() and then observe the AJAX callback functions to do what you need.

<script type="text/javascript>
  function get_address_information() {
    // check jquery for all the possible callbacks. there is also success and error. compete get calls after both success and error
    var pars = 'param1=x&amp;param2=y&amp;param3=z';
    $.ajax({ type: "POST",
      url: "/get_invite_address",
      data: pars, dataType: 'script',
      beforeSend: function() {
        // do your before send checking here
      },
      complete: function(data, status) {
        // do some post processing ehre
      }
    });
  }
</script>"

Form the source



回答2:

The variant working solution is to bind a validation to ajax:beforeSend event, the function beforeOneClick returns false or true:

$('form')
 .bind('ajax:success', function(evt, data, status, xhr) {
  console.log('success: ' + xhr + '/' + status + '/' + data);
 })
 .bind("ajax:beforeSend", function(evt, xhr, settings){
  return beforeOneClick();
 })
 .bind('ajax:complete', function(evt, xhr, status){
  console.log('complete');
 })
 .bind("ajax:error", function(evt, xhr, status, error){
  console.log('error:' + xhr + '/' + status + '/' + error);
 });