django中navie time 和 aware time的使用和转换

Posted gaoshiguo

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了django中navie time 和 aware time的使用和转换相关的知识,希望对你有一定的参考价值。

在django中有关时间被分为navie time 和 aware time两种,前者指的是不带时区标记的时间格式,后者被认为是带有时区标记的时间格式。在django框架的setting.py文件中

LANGUAGE_CODE = en-us
#TIME_ZONE 代表你所处的时区,刚创建时默认为‘UTC’即东0区(或西0区)
TIME_ZONE = Asia/shanghai

USE_I18N = True

USE_L10N = True
#USE_TZ 为true代表使用带时区标记的aware时间格式
USE_TZ = True

在python中,默认将aware的时间设为UTC即东0区,

例如我们创建数据如下:

from django.shortcuts import render,reverse,redirect
from .models import Book
from django.utils.timezone import now,localtime

def add_book(request):
    if request.method==GET:
        return render(request,add_books.html)
    else:
        title = request.POST.get("book_title")
        author = request.POST.get("book_author")
        price = request.POST.get("book_price")
        book=Book(title=title,author=author,price=price,create_time=now())
        book.save()
        return redirect(reverse(index))

在数据库中存储的时间为:

技术图片

可以看到其实真实的时间要比这个时间晚八个小时,这是因为我们处在东八区,而django会把时间设置成东0区,为什么会变成东0区呢?

我们需要看一看

django.utils.timezone.now

这个函数

def now():
    """
    Return an aware or naive datetime.datetime, depending on settings.USE_TZ.
    """
    if settings.USE_TZ:
        # timeit shows that datetime.now(tz=utc) is 24% slower
        return datetime.utcnow().replace(tzinfo=utc)
    else:
        return datetime.now()

可以看到,通过django.utils.timezone.now函数,虽然我们调用了now函数,但这个函数实质上,先判断

USE_TZ值是否为true,如果为true就将date.now中的datetime转化成utc时区的时间,如果为false,就直接使用datetime这个时间,所以有两种解决办法:1、将
USE_TZ的值设置为false,2、先设置本地时区,然后通过localtime将东0区的时间转换成本地时区的时间。
我们推荐第二种做法,这是因为,第一种做法在不部署服务器时是可行的,在部署到服务器上使用linux操作系统时不可行的。
第二种的做法如下:
1.设置本地时区,在setting.py文件中设置本地时区为Asia/shanghai
TIME_ZONE = Asia/shanghai

 

然后,在模板渲染时导入tz模块,使用tz模块中的localtime方法转化:
{% extends base.html %}
{% load tz %}
{% block title %}
首页
{% endblock %}
{% block main %}

    <table>
    <thead>
    <tr>
        <th>序号</th>
        <th>书名</th>
        <th>作者</th>
        <th>价格(美元)</th>
        <th>上架时间</th>
    </tr>

    </thead>
    <tbody>
    {% for book in books %}
        <tr>
        <td>{{ book.title }}</td>
        <td>{{ book.author }}</td>
        <td>{{ book.price }}$</td>
        <td>{{ book.create_time|localtime }}</td>
        </tr>
    {% endfor %}

    </tbody>
    </table>



{% endblock %}

 

最后在前端页面上展示的时间就是我们的东京时间了:
技术图片

 

以上是关于django中navie time 和 aware time的使用和转换的主要内容,如果未能解决你的问题,请参考以下文章

050:navie时间和aware时间详解

pytz库处理时区转换

django 1.4 - 无法比较 offset-naive 和 offset-aware 日期时间

从 Django 的 make_aware 中解决 AmbiguousTimeError

django-celery-beat时区问题

067:Django数据库ORM查询条件详解-range