【问题标题】:Query for events in different timezones that start on a particular day查询从特定日期开始的不同时区的事件
【发布时间】:2014-06-25 15:19:50
【问题描述】:

我正在尝试编写一个处理事件计时的 django 网站。我想要一个日历视图,我可以在其中显示与每一天相关的事件。

我的初步研究表明,最佳实践是以 UTC 格式存储所有时间,包括它们在数据库中的偏移量。我的麻烦是,如果我有两个事件:

  1. 事件 A 开始于 2014-05-05 00:20:00+00:00(在零偏移时区的星期一午夜之后。)
  2. 事件B 开始于2014-05-05 00:20:00+01:00(就在星期一午夜之后,在一小时偏移时区中,因此就在午夜之前,在像UTC 这样的零偏移时区中。)

我想查询从2014-05-05 开始的所有事件,然后我执行如下查询:

monday_start = make_aware(datetime(2014, 5, 5), utc)
monday_end = make_aware(datetime(2014, 5, 6), utc)

events = EventInstance.objects.filter(
        start_datetime__gte=monday_start,
        start_datetime__lt=monday_end,
        )

而且我只得到一个事件。理想情况下,我会得到两者,因为它们都在各自时区的星期一。

如果我提供天真的日期时间对象,即。日期时间没有时区,对于查询,我从 Django 收到警告,但仍然只得到一个结果。

问题:处理这种情况的最佳方法是什么?

我觉得最好存储没有偏移的所有时间,然后将事件的时区存储在单独的字段中,以便可以针对原始时间进行查询,然后在必要时使用时区显示给用户.但这可能有我无法预见的陷阱。

【问题讨论】:

  • 这可能更像是programmers.stackexchange.com 的问题吗?

标签: python django timezone


【解决方案1】:

问题在于您将 UTC 作为时区分配给 monday_start 和 monday_end 的定义。尽管事件 B 从它自己的角度来看是在星期一开始的,但它不是从 UTC 的角度来看的,这是您的过滤器正在检查的内容。

为什么不用天真的日期(没有时区信息)查询?

monday_start = datetime.combine(datetime(2014, 5, 5), datetime.min.time())
monday_end = datetime.combine(datetime(2014, 5, 5), datetime.max.time())

events = EventInstance.objects.filter(
    start_datetime__gte=monday_start,
    start_datetime__lt=monday_end,
)

【讨论】:

  • 感谢您的回复。恐怕使用天真的日期也只会返回一个结果。不是都。您是否认为使用天真的日期应该强制进行时区独立比较?我觉得他们可能被认为是 UTC 或内部的东西。此外,如果您在比较哪个感知对象时使用幼稚的日期时间对象,Python/Django 会发出警告。
  • 怎么样:d = datetime.date(2014, 5, 5) EventInstance.objects.filter(start_datetime__gte=d, start_datetime__lte=d) 我认为您当前存储信息的方式是很好,您只需要能够在忽略时区的情况下对其进行过滤。 Django 1.7 引入了具有更复杂查询的功能,这可以让您像 start_datetime.day == monday_start.day、year == year 和 month == month 这样进行过滤。但我想我们可以得到我们想要的功能,而无需等待。
  • 感谢您再次回复。恐怕仍然会引发有关天真的日期时间对象的警告(我认为日期可能会转换为日期时间以进行比较)并且它只返回 1 个结果。 Django 1.7 的东西听起来很有希望,但你是对的,我认为这在 Django 1.6 堆栈之前会遇到过。再次感谢。
  • 奇怪的是,您看到的是幼稚的日期时间警告。我以前见过它们,但是在使用数据库中的时间戳测试我在此处发布的示例代码时,我从来没有得到任何东西。不过,我使用的是所有存储为 UTC 的数据。令人惊讶的是它仍然返回一个结果,因为天真的日期比较正是您想要发生的。
  • 感谢您仔细检查所有内容。这可能与我目前在我的设置中使用 Sqlite 有关吗?其他数据库可能做得更好吗?我同意天真的日期比较是理想的,但我没有运气。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-03-21
  • 2012-05-30
  • 2014-10-11
  • 2015-04-09
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多