Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to display validation errors inline instead of at the top of page

I am trying to get my user model validation errors to display inline with its corresponding form field. I am using bootstrap and devise. I have client side validations so it wont let you submit the signup form until most of the validations are met. The problem is when a user signs up with facebook via omniauth. Omniauth will take the fields that facebook gives me and use those for the user, but the fields that facebook does not offer will then raise an ugly looking error on the top of the page. I have been trying to find a way to get those to display inline.

This is my user Model:

class User < ActiveRecord::Base

    has_many :bills, :dependent => :destroy

    validates :cell_phone, presence: true
    validates :cell_phone, length: { is: 10 }
    validates :cell_phone, :numericality => {:only_integer => true}
    validates :first_name, presence: true
    validates :last_name, presence: true
    validates :terms, presence: true

    geocoded_by :last_sign_in_ip
    after_validation :geocode


    # Include default devise modules. Others available are:
    # :confirmable, :lockable, :timeoutable and :omniauthable
    devise :database_authenticatable, :registerable, :omniauthable,
    :recoverable, :rememberable, :trackable, :validatable



    def ability
    @ability ||= Ability.new(self)
    end

    delegate :can?, :cannot?, :to => :ability



    def self.from_omniauth(auth)
        where(auth.slice(:sprovider, :uid)).first_or_create do |user|
            user.sprovider = auth.provider
            user.uid = auth.uid
            user.first_name = auth.info.first_name
            user.last_name = auth.info.last_name
            user.email = auth.info.email
            user.cell_phone = auth.info.cell_phone
            user.avatar = auth.info.image
        end
    end

This is the devise signup form that i would like the inline errors to appear on:

<div class="row sign_in">
  <div class="col-md-6 col-md-offset-3 col-lg-4 col-lg-offset-4">


    <%= form_for(resource, as: resource_name, url: registration_path(resource_name)) do |f| %>
    <%= devise_error_messages! %>


  <div class="row">
    <div class="form-group">
      <div class="col-md-6">  
        <%= f.text_field :first_name, autofocus: true , class:'form-control',placeholder:'First Name *' , :required => true %>
      </div>

      <div class="col-md-6">
        <%= f.text_field :last_name, class:'form-control',placeholder:'Last Name*' , :required => true %>
      </div>
    <div class="row">
    </div>
  </div>
</div>
  <div class="form-group">
      <%= f.phone_field :cell_phone, class:'form-control',placeholder:'Mobile Number*(Solely for notification purposes)', :required => true, :maximum => 10, :minimum => 10 %>
  </div>

   <div class="form-group">
      <%= f.email_field :email, class:'form-control',placeholder:'Email*', :required => true %>
  </div>

  <% if f.object.password_required? %>
    <div class="form-group">
      <% if @validatable %><i></i><% end %>
      <%= f.password_field :password, autocomplete: "off", class:'form-control',placeholder:'Password* (8 characters minimum)', id:"myPassword", :required => true %>
    </div>

    <div class="form-group">
      <%= f.password_field :password_confirmation, autocomplete: "off", class:'form-control',placeholder:'Password Confirmation*', :required => true %>
    </div>
  <% end %>
  <div class="form-group">
    <%= f.check_box :terms%>
    I have read and agreed the User

<a href="#" data-toggle="modal" data-target=".bs-example-modal-sm">Terms and Conditions</a>
         <div class="modal fade bs-example-modal-sm" tabindex="-1" role="dialog" aria-labelledby="mySmallModalLabel" aria-hidden="true">
          <div class="modal-dialog modal-md">
            <div class="modal-content">
              <p>
  Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec pretium libero eget posuere ornare. Donec rutrum augue eu erat fringilla posuere. Aenean tempus dui a erat facilisis posuere. Pellentesque eget nulla et turpis mollis egestas. Donec molestie consequat ultricies. Vivamus in feugiat risus. Ut a quam id sapien fringilla efficitur eget in justo. Suspendisse tincidunt libero metus. Sed ultrices auctor diam mattis pretium. Integer in aliquam dui. Praesent pulvinar ante non urna consectetur, eget porta lorem porta. Etiam ac orci pretium, faucibus neque vel, egestas velit. Nullam condimentum ultrices imperdiet. Maecenas vel nisi commodo, bibendum purus dapibus, porttitor felis.

Nullam nec porta lectus. Vivamus porta lobortis justo, sed cursus arcu tincidunt et. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Pellentesque a rhoncus tellus. Ut mollis orci quis lacus consequat, quis varius nunc auctor. Ut elit ligula, bibendum quis mauris a, ornare elementum dui. Phasellus commodo ipsum eu augue consequat porta.</p>
            </div>
          </div>
        </div>
        </div>

  <div><i class="icon-heart"></i></div>
    <%= f.submit 'Sign up', class:'btn btn-primary btn-block' %> 

      <% end %>

  </div>
</div>
</body>
</html>

This is the sign in with facebook button:

<div><i class="icon-heart"></i></div>
    <%= f.submit 'Sign in', class:'btn btn-primary btn-block' %> 
    <%= link_to "Sign in with facebook", user_omniauth_authorize_path(:facebook), class:'btn btn-primary btn-block' %>
    <br>
    <div align="center"> 
</div>

Any help on how to go about displaying these validation errors are much appreciated. Thanks

like image 886
Joel Avatar asked Sep 20 '14 14:09

Joel


People also ask

How do your inline validation forms work?

Our inline validation forms worked differently: they gave real-time feedback as people filled in answers, using lightweight and direct success messages (green checkmarks) and error messages (red triangles and text) next to the form input fields. You can see the difference in Video 2 below. Video 2.

Is it possible to display all validation errors in HTML5 forms?

While browser support is getting to be quite good for HTML5 forms the implementations themselves are still a bit buggy. Nevertheless, this approach will work for displaying all validation errors to the end user.

How does inline validation affect eye-tracking?

Eye-tracking also showed that they “fixated” on the forms with inline validation less frequently and for less time, which shows that they found these forms easier to process visually than the forms without inline validation.

What is real-time inline validation and why is it important?

Real-time inline validation can help people complete web forms more quickly and with less effort, fewer errors, and (surprise!) more satisfaction. Inline validation gives people several types of real-time feedback: It can confirm an appropriate answer, suggest valid answers, and provide regular updates to help people stay within necessary limits.


1 Answers

You can try to add conditions to validations, i.e. not validate some of the attributes when the facebook id is present (meaning user is signing up form facebook)

validates :first_name, presence: true, if: Proc.new {|u| u.facebookid.nil? }

Regarding the errors in your form, you can get rid of the top section that displays all the errors, and use

<%= user.errors[:first_name] %> 

close to your field instead. You can always get access to attribute (form field) errors by doing

object.errors[:attributename]
like image 60
Marcelo Ribeiro Avatar answered Sep 23 '22 03:09

Marcelo Ribeiro