简体   繁体   English

仅在属性存在时如何验证?

[英]How to validate an attribute only if it exists?

I have a lot of models with many different attributes that are shared between them, and so I have to validate them all and thats where I am having a problem. 我有很多模型,它们之间共享着许多不同的属性,因此我必须验证所有模型,这就是我遇到问题的地方。 If I group all attributes that are always used together and put their validations in a separated module, I end up with like 20 modules, which just doesnt seem right... Also I thought about putting attrs validations in only like 2-3 modules grouping them logically, like one module for location attrs, other is for options and etc and additing to all of them the IF condition the following way: 如果我将所有总是一起使用的属性归为一组,然后将其验证放在一个单独的模块中,则最终会得到20个模块,这看起来似乎不正确。此外,我还考虑将attrs验证仅放在2-3个模块中进行分组从逻辑上讲,它们就像一个用于位置属性的模块,另一个是用于选项等的模块,并通过以下方式向它们添加IF条件:

validates :city,
presence: true,
length: {minimum: 5},
if: Proc.new {|p| p.respond_to?(:city)}

and it looks like it works but repeating this condition to every validation method is just even more wrong than having a bunch of modules, so the question is, how do I do it right? 看起来很有效,但对每个验证方法重复此条件比拥有一堆模块甚至更错,所以问题是,我该怎么做?

Edit: Example: Imagine you have 3 models: Car, Truck and Bicycle and their attrs are: 编辑:示例:假设您有3个模型:汽车,卡车和自行车,它们的属性为:

Car -> attr_1, attr_3 汽车-> attr_1,attr_3

Truck -> attr_2, attr_3 卡车-> attr_2,attr_3

Bicycle -> attr_1, attr_2 自行车-> attr_1,attr_2

and so u can put validation of every attr to its module and include it to the clases that have this attribute, so u dont have to repeat it... ( thats where I end up with 20 modules) or u can create only one module with 3 validations like the following: 因此,您可以将每个属性的验证都添加到其模块中,并将其包括在具有此属性的分类中,这样您就不必重复它了……(也就是说,我最终得到20个模块),或者您只能创建一个模块经过3次验证,如下所示:

validates :attr_1, length: {minimum: 2}, if: Proc.new {|p| p.respond_to?(:attr_1)}
validates :attr_2, presence: true, if: Proc.new {|p| p.respond_to?(:attr_2)}
validates :attr_3, inclusion: {in: 1..5}, if: Proc.new {|p| p.respond_to?(:attr_3)}

which seems to be more ugly ... So I need to find some compromise here ... 这似乎更难看...所以我需要在这里找到一些折衷...

Ok... so you have multiple models with a set of related attribute (and validations) on them> 好的...所以您有多个带有一组相关属性(和验证)的模型>

some options are: 一些选项是:

  1. use a module that is included in each of the models 使用每个模型中包含的模块
  2. extract the attributes out into a model of its own (with its own attributes and validations) and is polymorphically associated to each of the related models 将属性提取到自己的模型中(具有自己的属性和验证),并与每个相关模型进行多态关联
  3. if you are using the latest version of rails, have a look at concerns - which is a better way of doing (1) 如果您使用的是最新版本的Rails,请查看相关问题-这是一种更好的方法(1)

if there really are 20 different groups of things... then create 20. But if groups of these things are always together in every model that uses them... you can put them into one spot together (and use code like Max's suggestion to make it shorter to read) 如果确实有20种不同的事物组...则创建20种。但是如果在使用它们的每个模型中这些事物组总是在一起的...则可以将它们放在一起(并使用Max的建议之类的代码使阅读更短)

Remember you're just using ruby code here, there's nothing magical going on. 记住,您只是在这里使用ruby代码,没有神奇的事情发生。 So you can do a loop: 所以你可以做一个循环:

[:attr1, :attr2, :attr3].each do |att|
  validates att, presence: true, length: {minimum: 5}, if: Proc.new {|p| p.respond_to?(att)}
end

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Rails验证attribute_a存在或attribute_b存在 - Rails validate that attribute_a exists OR attribute_b exists Rails如何仅在属性存在于更新时调用自定义验证方法 - Rails how to only call custom validate method if attribute is present on update 仅在使用ElasticSearch和Tire的情况下,如何按属性过滤搜索? - How to filter search by attribute only if it exists using ElasticSearch and Tire? 如何使RABL仅在对象中存在属性时才呈现它? - How can I make RABL render an attribute only if it exists in the object? 仅在属性存在时验证属性(仅当用户填写时) - Validate attribute only if it present (only if user fill in it) 仅当Rails和Carrierwave中存在属性时才进行验证 - Only validate when an attribute is present with Rails and Carrierwave 仅在virt_attribute为false时验证字段 - Validate fields only if virt_attribute is false 如何在Rails中验证虚拟属性? - How to validate virtual attribute in Rails? Rails:如何仅在一对多关系中验证属性的唯一性 - Rails: How to validate uniqueness of an attribute only within a one-to-many relationship 如何访问仅存在于1个属性中的哈希值? - How do I access a hash value that only exists in 1 attribute out of many?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM