如何在Rails 3 ActiveRecord中进行OR查询。我找到的所有示例都只有AND查询。
Edit: OR方法从Rails 5开始可用。看到ActiveRecord:: QueryMethods
如何在Rails 3 ActiveRecord中进行OR查询。我找到的所有示例都只有AND查询。
Edit: OR方法从Rails 5开始可用。看到ActiveRecord:: QueryMethods
当前回答
rails + arel,一个更清晰的方式:
# Table name: messages
#
# sender_id: integer
# recipient_id: integer
# content: text
class Message < ActiveRecord::Base
scope :by_participant, ->(user_id) do
left = arel_table[:sender_id].eq(user_id)
right = arel_table[:recipient_id].eq(user_id)
where(Arel::Nodes::Or.new(left, right))
end
end
生产:
$ Message.by_participant(User.first.id).to_sql
=> SELECT `messages`.*
FROM `messages`
WHERE `messages`.`sender_id` = 1
OR `messages`.`recipient_id` = 1
其他回答
MetaWhere插件非常棒。
轻松混合OR's和and 's,任何关联的连接条件,甚至指定OUTER join 's!
Post.where({sharing_level: Post::Sharing[:everyone]} | ({sharing_level: Post::Sharing[:friends]} & {user: {followers: current_user} }).joins(:user.outer => :followers.outer}
rails + arel,一个更清晰的方式:
# Table name: messages
#
# sender_id: integer
# recipient_id: integer
# content: text
class Message < ActiveRecord::Base
scope :by_participant, ->(user_id) do
left = arel_table[:sender_id].eq(user_id)
right = arel_table[:recipient_id].eq(user_id)
where(Arel::Nodes::Or.new(left, right))
end
end
生产:
$ Message.by_participant(User.first.id).to_sql
=> SELECT `messages`.*
FROM `messages`
WHERE `messages`.`sender_id` = 1
OR `messages`.`recipient_id` = 1
如果你想使用数组作为参数,下面的代码在Rails 4中工作:
query = Order.where(uuid: uuids, id: ids)
Order.where(query.where_values.map(&:to_sql).join(" OR "))
#=> Order Load (0.7ms) SELECT "orders".* FROM "orders" WHERE ("orders"."uuid" IN ('5459eed8350e1b472bfee48375034103', '21313213jkads', '43ujrefdk2384us') OR "orders"."id" IN (2, 3, 4))
更多信息:在Rails 4中使用数组作为参数的OR查询。
Rails/ActiveRecord的更新版本可能原生支持此语法。它看起来类似于:
Foo.where(foo: 'bar').or.where(bar: 'bar')
如此拉请求https://github.com/rails/rails/pull/9052中所述
现在,只要坚持下面的方法就可以了:
Foo.where('foo= ? OR bar= ?', 'bar', 'bar')
更新:根据https://github.com/rails/rails/pull/16052, or特性将在Rails 5中可用
更新:特性已经合并到Rails 5分支
我想添加这是一个解决方案搜索一个ActiveRecord的多个属性。自
.where(A: param[:A], B: param[:B])
会搜索A和B。