Overview

Django 1.4, released on March 23, 2012, brings native timezone support and the bulk_create method for mass inserts. It is also the first Django version to receive long-term support (LTS), guaranteeing security fixes for at least three years.

Key Features

Timezone support

With USE_TZ = True, Django stores all dates in UTC in the database and automatically converts them to the user's time zone for display. This eliminates an entire class of timezone-related bugs.

python
# settings.py
USE_TZ = True
TIME_ZONE = 'Europe/Paris'

# Always use timezone.now() instead of datetime.now()
from django.utils import timezone

class Event(models.Model):
    title = models.CharField(max_length=200)
    start = models.DateTimeField()
    end = models.DateTimeField()

# Creating with UTC date
event = Event.objects.create(
    title="Python Conference",
    start=timezone.now(),
    end=timezone.now() + timezone.timedelta(hours=2),
)

# In a template, dates are automatically converted
# {% load tz %}
# {% timezone "Europe/Paris" %}
#     {{ event.start }}
# {% endtimezone %}

bulk_create for mass inserts

The bulk_create method allows inserting many objects in a single SQL query, which is considerably faster than creating objects one by one.

python
import random

# Before bulk_create: one INSERT query per object (slow)
# for i in range(1000):
#     Measurement.objects.create(value=random.uniform(0, 100))

# With bulk_create: a single INSERT query (fast)
measurements = [
    Measurement(value=random.uniform(0, 100), sensor_id=1)
    for _ in range(1000)
]
Measurement.objects.bulk_create(measurements)

# For very large volumes, use batch_size
large_batch = [
    Measurement(value=random.uniform(0, 100), sensor_id=2)
    for _ in range(50000)
]
Measurement.objects.bulk_create(large_batch, batch_size=5000)

New project layout

Django 1.4 reorganizes the default project structure created by startproject. The manage.py file is now at the project root, and configuration files are grouped in a subdirectory named after the project.

python
# Old layout (Django < 1.4)
# myproject/
#     __init__.py
#     manage.py
#     settings.py
#     urls.py

# New layout (Django >= 1.4)
# myproject/
#     manage.py
#     myproject/
#         __init__.py
#         settings.py
#         urls.py
#         wsgi.py

Sources