2013-04-25 2 views
0

У меня есть эти модели:Джанго и Часовые пояса: как сделать осведомленный DateTime как наивный один в шаблоне (с pytz)

class TimeZone(models.Model): 
    name = models.CharField(max_length = 40, unique = True, editable = False) 
    def tz(self): 
     return pytz.timezone(str(self.name)) 

class Place(models.Model): 
    name = models.CharField(max_length=200) 
    timezone = models.ForeignKey(TimeZone) 

class PlaceAction(models.Model): 
    action_time = models.DateTimeField(blank=True, null=True) 
    place = models.ForeignKey(Place, related_name='Stop place') 

    def save(self, *args, **kwargs): 
     place_tz = self.place.timezone.tz() 
     if self.action_time: 
      self.action_time = place_tz.localize(self.action_time) 
     return super(PlaceAction, self).save(*args, **kwargs) 

Моих пользователи вводят место и наивное DateTime в форме. У меня есть часовой пояс места в БД, так что я не требую часового пояса от моих пользователей. Я конвертирую и сохраняю это datetime как известное время в DB (я использую Postgres). Данные корректно сохраняются с правильным смещением.

Когда я хочу отображать данные (например, в форме обновления), Django преобразует его обратно в наивное datetime, но использует часовой пояс settings.py по умолчанию (TIME_ZONE = 'UTC'). Я хотел бы знать, как наилучшим образом преобразовать значение datetime в наивное, используя правильный часовой пояс (объект Place). Я предпочел бы преобразование на уровне модели вместо уровня шаблона (я использую JQueryUI для выбора даты и времени, а так как первое преобразование выполняется там, я предпочел бы обратное преобразование в одном и том же месте).

Некоторые из моих идей: В модели PlaceAction init()? С пользовательским менеджером?

Я не смог найти оптимальную практику в документах для обратного преобразования в другой часовой пояс, чем по умолчанию. Есть ли это?

ответ

0

Вы можете добавить метод к PlaceAction, который преобразует в наивность, а затем использует его в вашем шаблоне.

class PlaceAction(models.Model): 
    action_time = models.DateTimeField(blank=True, null=True) 
    place = models.ForeignKey(Place, related_name='Stop place') 

    def naive_action_time (self): 
     """action_time but without the timezone :-) 

     """ 
     # Updated from Renaud Milon's comment 
     return self.action_time.astimezone(place_tz).replace(tzinfo=None) 

.

{% place_action.naive_action_time %} 
+0

По-видимому, в процессе разработки существует метод запроса. [здесь] (https://docs.djangoproject.com/en/dev/ref/models/querysets/#datetimes) –

+0

И чтобы получить правильное время в исходном часовом поясе: 'self.action_time.astimezone (place_tz) .replace (tzinfo = None) ' –

+0

Ах да, конечно,' astimezone' должен закрывать DLS. Вы можете быть заинтересованы в https://github.com/mfogel/django-timezone-field для вашего поля часового пояса. Он проверяет на ptyz и возвращает объект ptyz.Timezone(). – rockingskier

0

Наивное datetime - это дата, которое не знает о часовых поясах. Чтобы визуализировать время и время в часовом поясе, как если бы оно было наивным, вы просто не показываете часовой пояс.

«Я хотел бы знать, лучший способ, чтобы преобразовать обратно осведомленный DateTime к наивным один, используя правильный часовой пояс»

Это предложение просто не имеет никакого смысла. С наивным временем, нет правильного часового пояса. Я подозреваю, что вы хотите преобразовать дату в конкретный часовой пояс, начиная с UTC, датой, которую дает вам база данных.

И правильное место для этого в представлении. Всегда сохраняйте UTC внутри и конвертируйте только для отображения. Это просто.

+0

Да, но КАК вы его конвертируете для отображения? – Bobort

+0

datetime.strftime() обычно. –