(我的问题与described in this question几乎相同,只有答案在我的情况下不起作用。)
我在一个带有Postgres数据库的Rails应用程序中使用jQuery UI Datepicker。默认实现使用 mm / dd / yy 日期格式来显示所选日期,这正是我想要的。但是,在将记录保存到数据库后,月份和日期相反 - 然后显示为 yy-dd-mm 。所以选择3/11/2012会尝试保存为11月3日而不是3月11日,并且根本不保存像2012年3月31日这样的日期,因为它不存在。
到目前为止,我已经尝试了三种不同的途径来解决这个问题:
1)首次尝试重新格式化文本字段,以便显示我的想法:
<%= f.text_field :foo, :value => (@model.foo.blank? ? '' : @model.foo.strftime('%m/%d/%Y')), class: "datepicker" %>
最初正确显示03/31/2012,但在保存时仍然相反。
2)接下来我尝试更改存储日期的默认方式,认为可以解决问题。正如this question的答案中所述,我在 config / locales / en.yml 中添加了以下内容:
# config/locales/en.yml
en:
date:
formats:
default: "%m/%d/%Y"
这根本没有任何区别。接下来我找到this question并尝试使用以下行创建 config / initializers / date_formats.rb :
Date::DATE_FORMATS[:default]="%m/%d/%Y"
Time::DATE_FORMATS[:default]="%m/%d/%Y %H:%M"
与上述相同,没有区别。
3)在玩了很多组合之后,我发现DID工作的一件事是在我调用datepicker插件时指定yyyy-mm-dd格式 - 它与我想要的相反,但至少是日期可以成功保存。所以datepicker调用如下所示:
$( ".datepicker" ).datepicker({ dateFormat: 'yy-mm-dd' });
从日历中选择3月31日将使用2012-03-31填充该字段,并在保存后仍显示为2012-03-31。
但是我怎样才能让日期选择器以mm / dd / yy格式工作?我无法想象这是一件困难的事情,但我错过了什么?我是否必须对Postgres中的日期存储方式做些什么? (它们被指定为日期,而不是日期时间。)
答案 0 :(得分:3)
这取决于您在数据库中存储数据的方式。
如果您碰巧使用 RAW sql查询,则可以在插入查询中使用to_date('31 Mar 2012', 'DD Mon YYYY')
。
Postgres'to_date
reference
现在,在您的客户端,您可以使用
在jquery日期选择器中$.datepicker.formatDate('dd-M-yy', Yourdate);
我使用了DD Mon YYYY,因为它看起来更清晰。您可以根据需要使用mm/dd/yy
格式或其他格式。在这些情况下,请在postgre的to_date
函数中使用必需的 格式
请注意,我还没有测试过上面的代码。如果有任何问题或您遇到任何麻烦,请留下评论。
编辑:
您可以在rails视图中使用Date.parse('2011-06-18')
,然后再将数据插入数据库,并在datepicker中将formatDate
设置为'yy-mm-dd'
。
答案 1 :(得分:0)
如果要全局更改数据库群集的默认日期格式,还可以在postgresql.conf
中设置DateStyle GUC并重新加载:
datestyle = 'iso, mdy'
(无论如何,这应该是默认值。)
请注意,这不会影响日期在应用中的显示方式。 PostgreSQL如何解释Postgres的模糊输入和一些输出选项。
如果您在(显然)不同的连接中检查psql中的datestyle
设置,则不能证明任何内容。您的应用可能正在设置与本地设置相关的其他datestyle
。您必须检查实际连接内的设置(而不是psql)。
如果您的日期风格设置为'iso, mdy'
,那么它应该按照您的意愿运行:日期文字被解释为一个月前的。考虑一下这个演示(使用PostgreSQL 9.1):
db=# set datestyle = 'ISO, MDY'; SET db=# select '1.12.2012'::date; date ------------ 2012-01-12 (1 row) db=# set datestyle = 'ISO, DMY'; SET db=# select '1.12.2012'::date; date ------------ 2012-12-01 (1 row)
强调我的。
要了解您的应用实际设置了哪些选项,您可以设置
log_statement = all
在postgresql.conf
并重新加载。然后启动您的应用并保存日期。将记录每个命令。不要忘记之后重置和重新加载(或者您的日志文件可能会变得很大):
log_statement = none
然后检查您的数据库日志文件您的应用实际发送到数据库的内容。
您可能还对to_date()
命令感兴趣,该命令可让您以任何您喜欢的格式输入日期文字。但你不应该那样。
答案 2 :(得分:0)
我遇到了与原始海报相同的问题。由于我必须相互比较日期/时间,所以我不想将数据库字段更改为字符串,因为这将需要额外的代码和转换。
我最终在我的模型中使用了before_save和attr_accessor,如下所示:
before_save :format_date
attr_accessor :unformatted_date
def format_date
self.inquiry_date = Date.strptime(self.unformatted_date, "%m/%d/%Y").to_time(:utc)
end
我视图中的这一行如下所示:
f.text_field :unformatted_date, :value => (@foo.inquiry_date.blank? ? '' : @foo.inquiry_date.strftime('%m/%d/%Y)), :id => 'datepicker'