Rails将Time.current与数据库输入,Postgres与MySQL进行比较

时间:2015-11-11 16:42:33

标签: ruby-on-rails ruby database postgresql rails-activerecord

我使用Rails的PostgreSQL存在问题。我有一个日期时间为“from”和“to”的表。在我的控制器中,我得到了以下内容:

@running = Model.where("'to' > ?", Time.now)
@finished = Model.where("'to' < ?", Time.now)

我已经知道我必须逃避“to”,因为它是一个SQL语句。现在的问题是,使用MySQL和SQLite,我可以用`来逃避它,所以在我的开发环境(sqlite)中,它正在使用:

.where("`to` > ?", Time.now) 

它实际上在应用程序中正常工作。

但是我的制作环境是Postgres,而且Postgres不支持``,而且''显然不起作用,因为无论是什么叫“to”,它总是显示@running一个,尽管它应该是@finished。

怎么了?

谢谢!

1 个答案:

答案 0 :(得分:1)

这是SQL中的字符串文字:

'to'

这是(标准)SQL中的引用标识符:

"to"

这是MySQL中的引用标识符:

`to`

出于兼容性原因,SQLite还支持特定于MySQL的语法。为了完整起见,这是SQL Server中引用的标识符:

[to]

PostgreSQL遵循标准。

所以当你这样说时:

Model.where("'to' > ?", Time.now)

您正在尝试将常量字符串与格式化为字符串的时间戳进行比较。在Ruby中就是这样:

'to' > '2015-11-11 09:27:11'

所以当然它没有按预期工作。

您有多种选择:

  1. 重命名列,以便您不必担心引用它。
  2. 在开发,测试和生产环境中使用相同的数据库,这样您就不必担心标识符引用差异。无论如何,这是一个非常好的主意,ActiveRecord无法帮助您的数据库之间存在许多差异。
  3. 尝试让ActiveRecord为您编写SQL。这对于非=比较来说效果不佳,除非你想要与AREL混淆不清。
  4. 我会从 2 开始,因为正如我所说,数据库之间存在许多差异(标识符引用,保留字,区分大小写,日期/时间操作函数,SQL功能,列类型,GROUP BY行为,......)ActiveRecord无法帮助你。在一个数据库之上开发和测试,但在另一个数据库上进行部署只是在寻找麻烦。