← Back to Python

All Topics

Advertisement

Learn/Python/Django

Django Templates - Jinja2, Template Inheritance, Filters

Topic: Django Templates

Advertisement

Introduction

Django templates use Jinja2 syntax with Django-specific extensions. Templates enable dynamic HTML generation with inheritance, filters, and template tags.

Template Configuration

# settings.py
TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.jinja2.Jinja2',
        'DIRS': [os.path.join(BASE_DIR, 'templates')],
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.contrib.messages.context_processors.messages',
            ],
            'extensions': [
                'jinja2.ext.i18n',
            ],
        },
    },
]

# Use Django templates instead
TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': [BASE_DIR / 'templates'],
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [...],
        },
    },
]

Template Inheritance

<!-- templates/base.html -->
<!DOCTYPE html>
<html>
<head>
    <title>{% block title %}My Site{% endblock %}</title>
    {% block extra_css %}{% endblock %}
</head>
<body>
    <nav>
        <a href="{% url 'home' %}">Home</a>
        <a href="{% url 'about' %}">About</a>
    </nav>
    
    <main>
        {% block content %}{% endblock %}
    </main>
    
    <footer>
        {% block footer %}&copy; 2024{% endblock %}
    </footer>
    
    {% block extra_js %}{% endblock %}
</body>
</html>

<!-- templates/blog/post_list.html -->
{% extends 'base.html' %}

{% block title %}Blog - {{ block.super }}{% endblock %}

{% block content %}
<h1>Blog Posts</h1>
{% for post in posts %}
    <article>
        <h2>{{ post.title }}</h2>
        <p>{{ post.content|truncatewords:50 }}</p>
        <a href="{% url 'post_detail' post.slug %}">Read more</a>
    </article>
{% empty %}
    <p>No posts available.</p>
{% endfor %}

{% if is_paginated %}
    {% include 'pagination.html' %}
{% endif %}
{% endblock %}

Custom Filters

# app/templatetags/custom_filters.py
from django import template

register = template.Library()

@register.filter
def truncate_words(value, arg):
    """Truncate value to arg number of words."""
    words = value.split()
    if len(words) > arg:
        return ' '.join(words[:arg]) + '...'
    return value

@register.filter
def currency(value):
    """Format value as currency."""
    return f'${value:,.2f}'

@register.simple_tag
def get_greeting(name):
    """Return a greeting message."""
    return f'Hello, {name}!'

@register.inclusion_tag('weather.html')
def show_weather(location):
    """Include weather template with context."""
    weather_data = get_weather_data(location)
    return {'weather': weather_data}

Template Tags

# app/templatetags/form_tags.py
from django import template

register = template.Library()

@register.simple_tag
def url_replace(request, field, value):
    """Replace query parameter in URL."""
    dict_ = request.GET.copy()
    dict_[field] = value
    return dict_.urlencode()

@register.inclusion_tag('blog/post_list.html')
def recent_posts(count=5):
    """Show recent blog posts."""
    from blog.models import Post
    posts = Post.objects.filter(status='published')[:count]
    return {'posts': posts}

Practice Problems

  1. Create a base template with navigation, main content area, and footer
  2. Implement a custom filter that formats dates in a specific locale
  3. Build a template tag that displays related posts based on tags
  4. Create a multi-level inheritance structure (base, base_blog, post_detail)
  5. Implement a template tag that handles pagination URL generation

Advertisement

Advertisement

Need More Practice?

Get personalized Python help from ChatWhole's AI-powered platform.

Get Expert Help →