Time zone issues with Django deployed in Docker container

Time zone issues with Django deployed in Docker container

Now container deployment is very mature. Many of our services will use container deployment, and update and recovery are very convenient. However, there is a more troublesome problem, which is time zone processing. Usually, it is solved by injecting TZ environment variables, but this processing method does not work in Django.

Time zone configuration in Django

In Django's configuration file settings.py, there are two configuration parameters related to time and time zone, namely TIME_ZONE and USE_TZ. We expect that after configuring in settings.py, Django will be able to correctly obtain the local time, but in fact it is contrary to our expectations. Let's see what these two settings do.

USE_TZ=True

If USE_TZ is set to True, Django will use the system default time zone. At this time, the TIME_ZONE setting is basically invalid, that is, it has no effect regardless of whether it is set or not.

USE_TZ=False

If USE_TZ is set to False

  1. TIME_ZONE is set to None
  2. Django will still use the default time zone
  3. If TIME_ZONE is set to another time zone

If you are using Windows, the TIME_ZONE setting is useless and Django will use the local time. If you are using other systems, it will use the UTC time in that time zone.

For example, if you set USE_TZ = False, TIME_ZONE = 'Asia/Shanghai', the UTC time of Shanghai will be used.

At this point, you may think that the time is good, but in fact it is not. We also need to pay attention to the system time zone settings.

Setting the time zone in Linux containers

My local time is now: 16:15, and the settings in Django are: USE_TZ = False, TIME_ZONE = 'Asia/Shanghai'

Do not inject TZ=Asia/Shanghai environment variable to enter the container to view the container time and time zone

The system time is displayed in the UTC time zone, the time is: 08:15, exactly 8 hours difference

Enter the Django environment to view the time and time zone

python manage.py shell 
 
from datetime import datetime 
datetime.now() 
# Output datetime.datetime(2021, 10, 8, 8, 24, 8, 289230) 
 
from django.utils import timezone 
timezone.get_current_timezone_name() 
# Output 'Asia/Shanghai'

Inject environment variable TZ=Asia/Shanghai
Enter the container to view the time and time zone

The system time is displayed in the Asia time zone, but the time is still UTC time, not the real local time.

Enter the Django environment to view the time and time zone

python manage.py shell 
 
from datetime import datetime 
datetime.now() 
# Output datetime.datetime(2021, 10, 8, 8, 24, 8, 289230) 
 
from django.utils import timezone 
timezone.get_current_timezone_name() 
# Output 'Asia/Shanghai' 

As you can see, although the time zone has changed, the time is still UTC time, both in the container itself and in Django

By searching online, we know that to change the Linux system time zone, we need to modify the /etc/localtime file.

Modify the Linux container time zone

The usual practice is to copy the host's /etc/localtime file to the container's /etc/localtime file. However, we found through query that the /etc/localtime file is actually just a soft link. The actual file is: /usr/share/zoneinfo/Asia/Shanghai

docker cp /usr/share/zoneinfo/Asia/Shanghai test:/etc/localtime
Without injecting the TZ=Asia/Shanghai environment variable into the container, we log in to the container and find that the system time of the container has correctly obtained the local time and time zone.

If the TZ=Asia/Shanghai environment variable is injected, even if the /etc/localtime file is replaced, only the time zone is changed, and the time is still UTC time

Enter the Django environment to view the time

python manage.py shell 
 
from datetime import datetime 
datetime.now() 
# Output datetime.datetime(2021, 10, 8, 8, 43, 43, 754698) 

The Linux system time is normal, but the time in the Django environment is still incorrect and is still UTC time. At this time, many people are a little crazy, and may think that there is a problem with the USE_TZ and TIME_ZONE settings in settings.py. In fact, the problem is not here. The reason is that the datetime library will look for the Asia/Shanghai file in the /usr/share/zoneinfo/ directory, but our image does not contain this directory, so Django still uses the UTC time zone. The solution is very simple: create a directory /usr/share/zoneinfo/Asia and copy the files to this directory.

# In the container (if this directory does not exist) 
mkdir -p /usr/share/zoneinfo/Asia 
 
# Outside the container docker cp /usr/share/zoneinfo/Asia/Shanghai test:/usr/share/zoneinfo/Asia/Shanghai

Then log in to the container and enter the Django environment to check the time

python manage.py shell 
 
from datetime import datetime 
datetime.now() 
# Output datetime.datetime(2021, 10, 8, 16, 49, 32, 57) 

This time the timing was exactly right.

Summarize

For the container time zone issue, it is recommended to install and set /etc/localtime during the container creation phase. For example, add the following statement in the Dockerfile

ADD /usr/share/zoneinfo/Asia/Shanghai /usr/share/zoneinfo/Asia/Shanghai 
 
RUN ln -s /usr/share/zoneinfo/Asia/Shanghai /etc/localtime 

In this way, we don't need to pay attention to the time zone issue when starting our container. If the container has been made, mount the time zone file when starting it

docker run -d -v /etc/localtime:/etc/localtime -v /usr/share/zoneinfo/Asia/Shanghai:/usr/share/zoneinfo/Asia/Shanghai imageName 

This method is more troublesome. Another situation is what we are facing now. The service is already online, and we find that there is a time problem. We manually copy the two files to the container and then restart the container.

docker cp /usr/share/zoneinfo/Asia/Shanghai test:/etc/localtime 
docker cp /usr/share/zoneinfo/Asia/Shanghai test:/usr/share/zoneinfo/Asia/Shanghai 
docker restart test 

This is the end of this article about the time zone issue of deploying Django in a Docker container. For more information about Docker deployment of Django time zone, please search for previous articles on 123WORDPRESS.COM or continue to browse the following related articles. I hope everyone will support 123WORDPRESS.COM in the future!

You may also be interested in:
  • Example of deploying Django application with Docker
  • How to use docker to deploy Django technology stack project
  • Example of how to deploy a Django project using Docker
  • Django Docker container deployment Django-Docker local deployment
  • How to Dockerize a Python Django Application
  • How to use Docker-compose to deploy Django applications offline
  • Detailed explanation of how to use Docker to deploy Django+MySQL8 development environment

<<:  CSS makes the footer automatically stick to the bottom when the content height is not enough

>>:  Nodejs global variables and global objects knowledge points and usage details

Recommend

Docker Gitlab+Jenkins+Harbor builds a persistent platform operation

CI/CD Overview CI workflow design Git code versio...

Html+CSS floating advertisement strip implementation

1.html part Copy code The code is as follows: <...

How to implement multiple parameters in el-dropdown in ElementUI

Recently, due to the increase in buttons in the b...

Classes in TypeScript

Table of contents 1. Overview 2. Define a simple ...

How to set static IP in centOS7 NET mode

Preface NAT forwarding: Simply put, NAT is the us...

How to display percentage and the first few percent in MySQL

Table of contents Require Implementation Code dat...

How to change $ to # in Linux

In this system, the # sign represents the root us...

Detailed explanation of using echarts map in angular

Table of contents Initialization of echart app-ba...

Solution to elementui's el-popover style modification not taking effect

When using element-ui, there is a commonly used c...

Vue3 navigation bar component encapsulation implementation method

Encapsulate a navigation bar component in Vue3, a...

Design of pop-up windows and floating layers in web design

In the trend of gradual transition from tradition...

How to install Nginx and configure multiple domain names

Nginx Installation CentOS 6.x yum does not have n...

HTML uses marquee to achieve text scrolling left and right

Copy code The code is as follows: <BODY> //...

Detailed explanation of Linux CPU load and CPU utilization

CPU Load and CPU Utilization Both of these can re...