我有一个案例需要为同一个对象的不同实例添加和删除自定义验证器。
例如......
class MyCustomValidator < ActiveModel::Validator
...
end
class Foo
include ActiveModel::Validations
validates_with MyCustomValidator
end
背景A:
Foo.new.valid? #=> This should use the custom validator
背景B:
f = Foo.new
f.class.clear_validators!
f.valid? #=> This should no longer call the custom validator
背景C:
f = Foo.new
f.class.clear_validators!
f.valid? #=> This should no longer call the custom validator
# This is where I need to do something to bring the validator back so I can run
f.valid? #=> This should use the custom validator
有没有办法实现这个目标?
答案 0 :(得分:0)
您可以执行以下操作:
class Foo
include ActiveModel::Validations
validates_with MyCustomValidator, if: :use_custom_validators?
def use_custom_validators?
!@custom_validator_disabled
end
def without_custom_validators(&block)
prev_disabled, @custom_validator_disabled = @custom_validator_disabled, true
@custom_validator_disabled = true
instance_eval(&block)
@custom_validator_disabled = prev_disabled
end
end
f = Foo.new
f.valid? # Custom validator used
f.without_custom_validators do
valid? # Custom validator not used
end
f.valid? # Custom validator used
答案 1 :(得分:0)
如果使用验证器的必要性由对象的某些状态定义,则可以使用state_machine
gem并明确定义状态标志。之后,您可以定义state-specific validations。
要使其工作,您需要定义两个状态,并在其中一个状态上定义额外的验证。然后,您需要创建一个从“干净”状态转换为“已验证”状态的事件(或任何您称之为的状态)。
示例:
class LockableSwitch < ActiveRecord::Base
state_machine initial: :off
state :off # It's probably redundant. I dunno.
# if you're not storing state as strings, you'd specify
# state :off, value: 0 # if `state` column was an integer
state :on do
# Can only be switched on if a key is inserted
validates :key, presence: true
end
event :switch do # An event that causes the apple to become ripe
transition :off => :on # `=>` justifies the use of that old syntax
transition :on => :off # The first matched transition is used
end
end
end
@l = LockableSwitch.new # :off by default
@l.switch! # fails, bang-method throws an error on failed transition
@l.key = "something"
@l.switch! # works
它是另一个库和额外的内存/复杂性(即使不是太多),但它使你的代码在“它的作用”中更加清晰。