class User < ApplicationRecord
def self.query_from_tuples(array_of_tuples)
array_of_tuples.inject(nil) do |scope, (id, country)|
if scope
scope.or(where(id: id, country: country))
else
where(id: id, country: country) # this handles the initial iteration
end
end
end
end
结果查询是:
SELECT "users".* FROM "users"
WHERE (("users"."id" = $1 AND "users"."country" = $2 OR "users"."id" = $3 AND "users"."country" = $4) OR "users"."id" = $5 AND "users"."country" = $6)
LIMIT $7
您还可以通过以下方式调整 kamakazis WHERE (columns) IN (values) 查询:
class User < ApplicationRecord
def self.query_from_tuples_2(array_of_tuples)
# just a string of (?,?) SQL placeholders for the tuple values
placeholders = Array.new(array_of_tuples.length, '(?,?)').join(',')
# * is the splat operator and turns the tuples (flattened) into
# a list of arguments used to fill the placeholders
self.where("(id, country) IN (#{placeholders})", *array_of_tuples.flatten)
end
end
这会导致以下查询不那么冗长:
SELECT "users".* FROM "users"
WHERE ((id, country) IN ((1,'us'),(2,'mexico'),(3,'us'))) LIMIT $1
如果您在 [id, country] 上有一个复合索引,也可以表现得更好。