如何检查数字是否在activerecord的范围内?

时间:2018-07-28 17:44:29

标签: ruby-on-rails postgresql activerecord

我有一个带有范围列的模型

#<JobRequirement id: 1, age: 18...30>

如何使用JobRequirement获得age: 20

类似

JobRequirement.where(age: 20)

1 个答案:

答案 0 :(得分:2)

我认为您需要在字符串中使用PostgreSQL range operators和一些SQL。特别是,您需要@>(包含元素)运算符:

JobRequirement.where('age @> ?', 20)

只要提供占位符值的范围:

JobRequirement.where('age <@ ?', 18..20)

您会发现AR对PostgreSQL范围类型的了解有些有限。当您提供一个范围作为占位符的值时,AR会想将范围扩展到以逗号分隔的列表,因为它假定您说的是where('col in (?)', 18..20)之类的东西,所以最终会像这样: >

where age <@ 18,19,20
在生成的SQL中

。您可以通过手动键入强制值来解决此问题。例如:

> ActiveRecord::Base.connection.type_cast(6..11)
 => "[6,11]" 
> ActiveRecord::Base.connection.type_cast(6...11)
 => "[6,11)" 

,然后将字符串发送到查询中,在该查询中PostgreSQL应该将其自动转换为PostgreSQL范围:

JobRequirement.where('age <@ ?', ActiveRecord::Base.connection.type_cast(18..20))

根据您在哪里进行操作,connection方法可能会适用于所有噪声:

JobRequirement.where('age <@ ?', connection.type_cast(18..20))

如果PostgreSQL没有自己选择<@运算符的正确版本,那么您可以通过更多类型转换来帮助它:

JobRequirement.where('age <@ ?::int4range', connection.type_cast(18..20))