我正在开发一个用于记录潜水的 Django 应用程序,每次潜水都有日期时间和时区。我正在使用 django-timezone-field 应用程序作为时区。
class Dive(models.Model):
...
date_time_in = models.DateTimeField(default=timezone.now)
timezone = TimeZoneField(default=timezone.get_current_timezone_name())
因此,用户可以输入日期时间字符串("2016-07-11 14:00")并选择时区("亚洲/曼谷" - UTC+0700),然后将日期时间的时区设置为我视图中给出的时区,如下所示:
def log_dive(request):
if request.method == 'POST':
form = DiveForm(request.POST)
if form.is_valid():
dive = form.save(commit=False)
date = dive.date_time_in
date = date.replace(tzinfo=None)
dive.date_time_in = dive.timezone.localize(date)
dive.save()
然后,数据库将日期时间存储为 UTC 在数据库中(SELECT 语句以我的本地时区给出):
# SELECT date_time_in, timezone FROM divelog_dive ORDER BY number DESC;
date_time_in | timezone
------------------------+------------------
2014-07-11 17:00:00+10 | Asia/Bangkok
现在有两件事我正在努力:
1)我想显示给定时区的日期,但是我似乎无法阻止它默认为TIME_ZONE设置。
2) 如果用户编辑记录,则编辑字段中显示的时间应为他们最初输入的时间 (14:00) 显示,而是以当前时区 (17:00) 显示。
在settings.py
中检查您的时区设置
你的设置文件中有 USE_TZ = true 吗?如果你使用 djangoadmin-startproject 命令创建了你的应用,它是默认设置的。
此外,我在上一份工作中为时区而苦苦挣扎,但发现使用 pytz 确实有帮助。你试过那个包吗?
编辑:好吧,伙计,我可能离得很远,但由于没有其他人回答并且我感到时区挣扎,这是我注意到的......
您要将日期对象替换为 tz_info=None,但您是否不想将其替换为数据库中的时区?所以你会得到那个时区并使用有效格式(tzinfo=blah...)进行替换?就像我说的,我可能离得很远,但如果有帮助,你就会去。
抱歉,我认为我没有很好地解释我的问题。我终于想通了,所以我会回答我自己的问题。
1)结果很简单,Django有一个模板标签来显示给定区域中的时间:
{{ dive.date_time_in|timezone:dive.timezone|date:"Y-m-d H:i e" }}
对于 2),我遇到了 [1],它导致我找到这个解决方案:在视图中,从数据库获取对象后,我使用 astimezone(...) 将日期值(数据库存储为 UTC)转换为给定时区。然后我使用 replace(tzinfo=None) 让它变得幼稚,然后它在我的表单上正确显示。
def edit_dive(request, dive_id=None):
dive = None
if dive_id != None:
dive = get_object_or_404(Dive, pk=dive_id)
local_date = dive.date_time_in.astimezone(timezone(str(dive.timezone)))
dive.date_time_in = local_date.replace(tzinfo=None)
[1] http://www.saltycrane.com/blog/2009/05/converting-time-zones-datetime-objects-python/