我有一个导轨应用程序,并且有一个过滤功能。过滤标准之一是时间值,当我尝试按时间标准过滤时,它会显示出错误的结果。
**可变名称有一个错误,所以我编辑了
start_time = DateTime.new(2000, 1, 1, 6, 0, 0)
end_time = DateTime.new(2000, 1, 1, 9, 0, 0)
当我执行过滤功能时,结果是:
Item.where("(start_at >= ? AND start_at < ?) OR (end_at > ? AND end_at <= ?) OR (start_at < ? AND end_at > ?)", start_time, end_time, start_time, end_time, start_time, end_time)
=> Item id: 5931
但是,我执行了相同的句子,结果是:
(Item.find(5931).start_at >= start_time AND Item.find(5931).start_at < end_time)
=> false
(Item.find(5931).end_at > start_time AND Item.find(5931).end_at <= end_time)
=> false
(Item.find(5931).start_at < start_time AND Item.find(5931).end_at > end_time)
=> false
(Item.find(5931).start_at >= start_time AND Item.find(5931).start_at < end_time) or (Item.find(5931).end_at > start_time AND Item.find(5931).end_at <= end_time) or (Item.find(5931).start_at < start_time AND Item.find(5931).end_at > end_time)
=> false
有人找到这一点吗?如果我错过了任何需要的信息,请告诉我。
查询两次之间的数据,请使用SQL BETWEEN
关键字:
Item.where(start_at: start_time..end_time)
# => SELECT "items".* FROM "items" WHERE ("items"."start_at" BETWEEN $1 AND $2) [["start_at", 2000-01-01 06:00:00 UTC], ["start_at", 2000-01-01 09:00:00 UTC]]
start_time..end_time
中的 ..
是一种创建范围对象的特殊语法。
要添加一个或子句,您可以在Rails 5中使用.or
方法:
Item.where(start_at: start_time..end_time)
.or(Item.where(end_at: start_time..end_time))
在Rails 4中,您需要编写SQL字符串:
Item.where(
'(items.start_at BETWEEN :s AND :e) OR (items.end_at BETWEEN :s AND :e)',
s: start_time, e: end_time
)