validates_timeliness icon indicating copy to clipboard operation
validates_timeliness copied to clipboard

Can't test the validation with allow_blank: true

Open v-tsvid opened this issue 8 years ago • 5 comments

Hi! I have the Order model with :completed_date attribute. And I would like to validate :completed_date in the following way

class Order < ActiveRecord::Base
  #...
  validates_date :completed_date, allow_blank: true
  #...
end

But my spec for this validation doesn't work

it "is invalid when completed_date is invalid" do
  order.completed_date = "incorrect date"
  expect{ order.valid? }.to change{ order.errors.messages[:completed_date] }
end

I believe it's because any incorrect date value sets to nil and nil is valid value since I have allow_blank: true in my validation

When I remove allow_blank: true from my validation, the spec above works perfectly but I really need to permit blank :completed_date for my orders.

So I wonder if I do something wrong or if there is any way to test such validation?

P.S. I have tried all of the following constructions and all of them didn't work validates_date :completed_date, allow_blank: true validates :completed_date, timeliness: { type: :date }, allow_blank: true validates :completed_date, timeliness: { type: :date, allow_blank: true }

v-tsvid avatar Mar 29 '16 11:03 v-tsvid

Do you have the plugin parser enabled in the initializer?

adzap avatar Mar 30 '16 07:03 adzap

I didn't have it but I do have now and the spec above still don't want to pass.

If it will help or if it will turn out as a new issue: when I uncomment the following line config.enable_multiparameter_extension! I get the error

...gems/activesupport-4.2.2/lib/active_support/core_ext/module/aliasing.rb:32:in `alias_method': undefined method `instantiate_time_object' for class `ActiveRecord::Base' (NameError)

v-tsvid avatar Mar 30 '16 08:03 v-tsvid

Using datetime type for column in pgsql + ActiveRecord, following does not work

validates_datetime :published_at, allow_blank: true

Allow blank values, any string values become allowed.

I tried enabling plugin parser, but it did not resolve this issue.

also, enabling multiparameter extension results in error.

dachinat avatar Feb 02 '18 00:02 dachinat

According to one of the answers here the problem is that recent versions of Rails do a type cast on values before validation is called and that changes the stored value to nil if it's invalid for the type. With allow_blank that value is then accepted.

The gem needs to detect a case where:

if record.public_send("#{attribute}_before_type_cast").present? && value.blank?

and treat it as an invalid datetime having been entered. Or just validate against record.public_send("#{attribute}_before_type_cast") and ignore what value has become after typecast?

JamesFerguson avatar Jun 12 '19 21:06 JamesFerguson

Also, fwiw, it's probably preferable to use record.read_attribute_before_type_cast(attribute) rather than send.

JamesFerguson avatar Jun 12 '19 21:06 JamesFerguson