Search code examples
pythondjangodst

Django DST Time change issue with django datetimefield


I am facing problem in my django app while working with DateTimeField.Its mainly because of DST time changes.

I have created an event on 30-oct-2015(DST last week). I created a copy of first event which will be on 06-Nov-2015(Non DST day)

I applied timedelta of 7 days , So it chaned days to 7+. But I did not aplly timedelta for hours.

Due to Day Light saving , its reduced by one hour. I dont need this. I just want to have same hours. How Can I do that.?

I tried with this , but did not help me.

DST timezone issue in django app

Please see this screenshot enter image description here

my models.py

from django.db import models
from datetime import timedelta

class Event(models.Model):

    name = models.CharField(max_length=100)

    created = models.DateTimeField(auto_now_add=True)

    start_date = models.DateTimeField()

    def __unicode__(self):
        return self.name


    def copy_event(self, add_days=timedelta(days=7)):

        start_date = self.start_date + add_days
        name = self.name +' (copy)'
        new_event = Event(name = name,created = self.created,start_date=start_date,)

        new_event.save()

        return new_event

Solution

  • Since USE_TZ=True you are always dealing with aware datetimes, which represent a precise moment in time. That moment in time will, in general, be displayed differently depending on the current time zone. Some time zones have DST and some don't, so in general there's no way you can store the datetime such that all users in all timezones will see the clock time you want (i.e. the same clock time as the event being copied).

    I can think of a couple workarounds:

    1. If it's the case that you're only serving one time zone (that is, the current time zone is always going to be the same), you can just do your arithmetic in that time zone.

      from django.utils.timezone import localtime
      new_start_date = localtime(self.start_date) + add_days
      

      The addition of add_days will always keep the clock time the same (that is, it doesn't take DST into account). The new_start_date will be converted to and stored in UTC, and then converted back to the desired local time for display.

    2. What you're really trying to represent is a particular clock time on a particular day, not an exact moment in time. So perhaps you don't want to be using aware datetimes at all. One option is to set USE_TZ=False, but that's a global, far-reaching change that you may not want to make. Another option is to use a different representation for this field. For example, you could use a DateField and a TimeField instead of a DateTimeField.