Rails 3 - how to skip validation rule?

北城以北 提交于 2020-01-02 03:53:08

问题


I have for the registration form this validation rule:

  validates :email, 
    :presence => {:message => 'cannot be blank.'}, 
    :allow_blank => true, 
    :format => {
      :with => /\A[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]+\z/, 
      :message => 'address is not valid. Please, fix it.'
    }, 
    :uniqueness => true

This rule check, if a user fill into the registration form email address (+ its correct format).

Now I am trying to add the opportunity to log in with using Twitter. Twitter doesn't provide user's email address.

How to skip in this case the validation rule above?


回答1:


You can skip validation while saving the user in your code. Instead of using user.save!, use user.save(:validate => false). Learnt this trick from Railscasts episode on Omniauth




回答2:


I'm not sure whether my answer is correct, just trying to help.

I think you can take help from this question. If i modify the accepted answer for your question, it will be like (DISCLAIMER: I could not test the following codes as env is not ready in the computer i'm working now)

validates :email, 
  :presence => {:message => 'cannot be blank.', :if => :email_required? },
  :allow_blank => true, 
  :format => {
    :with => /\A[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]+\z/, 
    :message => 'address is not valid. Please, fix it.'
  },
  :uniqueness => true

def email_required?
  #logic here
end

Now, you update the email_required? method to determine whether it is from twitter or not! If from twitter, return false otherwise true.

I believe, you need use same :if for the :uniqueness validator too. otherwise it will. Though, i'm not sure too :(. Sorry




回答3:


You seem to be doing two separate validations here:

  • If a user provides an email address, validate it's format and uniqueness
  • Validate the presence of an email address, unless it's a twitter signup

I would do this as two separate validations:

validates :email, 
  :presence => {:message => "..."}, 
  :if => Proc.new {|user| user.email.blank? && !user.is_twitter_signup?}

validates :email, 
  :email => true, # You could use your :format argument here
  :uniqueness => { :case_sensitive => false }
  :unless => Proc.new {|user| user.email.blank?}

Additional info: validate email format only if not blank Rails 3




回答4:


The best way would be:

It would validate the email when the user is not signed in from twitter as well as skip email validation when signed from twitter.

  validates :email, 
    :presence => {:message => 'cannot be blank.'}, 
    :allow_blank => true, 
    :format => {
      :with => /\A[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]+\z/, 
      :message => 'address is not valid. Please, fix it.'
    }, 
    :uniqueness => true
    unless: Proc.new {|user| user.is_twitter_signup?}



回答5:


Skipping Individual Validations Skipping individual validations requires a bit more work. We need to create a property on our model called something like skip_activation_price_validation:

class Product < ActiveRecord::Base
  attr_accessor :skip_activation_price_validation
  validates_numericality_of :activation_price, :greater_than => 0.0, unless: :skip_activation_price_validation
end

Next we will set the property to true any time we want to skip validations. For example:

def create
   @product = Product.new(product_params)
   @product.skip_name_validation = true
   if @product.save
    redirect_to products_path, notice: "#{@product.name} has been created."
  else
    render 'new'
  end
end

def update
  @product = Product.find(params[:id])
  @product.attributes = product_params

  @product.skip_price_validation = true

  if @product.save
    redirect_to products_path, notice: "The product \"#{@product.name}\" has been updated. "
  else
    render 'edit'
  end
end


来源:https://stackoverflow.com/questions/12661413/rails-3-how-to-skip-validation-rule

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!