我有一个包含Event
,name
和start_time
字段的end_time
模型的修改视图。我的观点是一个大致如下的形式:
# ...
# form with:
# - event name
# - datetime_select for event start_time (in business's local time zone)
# - datetime_select for event end_time (in business's local time zone)
现在,问题出现了:start_time
和end_time
附加了一个时区,但是当我们渲染视图时,时间会丢失,因为datetime_select不包含时区。结果是我们有一个“UTC时间”,实际上是剥离其时区的本地时间。
总结一下,当我们在视图中渲染表单时,情况看起来像这样,然后立即提交它而不做任何更改:
db time: 2011-05-15 @ 1100 UTC
converted to local time: 2011-05-15 @ 0600 CDT
time stored in view: 2011-05-15 @ 0600 UTC (time zone info lost)
time posted back to db: 2011-05-15 @ 0600 UTC
请注意,最初存储的时间是1100 UTC,但现在是0600 UTC,即使我们没有进行任何更改。这是一个严重的错误。
我们可以采取多种方法。在发布到视图时避免丢失时区的最明智的方法是什么? (请注意,模型可能会以不同于发布表单的方式进行更新 - 例如,通过API。)
答案 0 :(得分:0)
它从来没有感觉非常令人满意,但我通常通过为虚拟属性创建一些名为local_time或time_formatted或类似的东西来处理这个问题,这些方法来自存储在db中的UTC时间来回转换
在此示例中,db字段为“deadline”,虚拟属性为“deadline_formatted”:
def deadline_formatted
self.deadline
end
def deadline_formatted= s
self.deadline = s
end
然后,在表格中,
<%= f.label :deadline_formatted, "Deadline" %>
<%= f.text_field :deadline_formatted %>
通过一些魔法,我仍然不太明白*,这就足够了 - 它看起来应该不起作用,但确实如此。至少它对我有用。
*我不理解的部分是在表单中设置截止日期字段将继续使用文本字段中的值调用deadline =方法。相反,我调用deadline_formatted =方法,它只是将结果传递给deadline =,所以你认为结果是相同的。但是,不知何故,时间从UTC(数据库)转换为本地时间(表格)。
答案 1 :(得分:0)
您可以尝试使用delocalize gem:https://github.com/clemens/delocalize