Module 3: Advanced Django Features

Learn advanced Django features including admin interface, forms, authentication, permissions, and REST API development for web development.

Back to Course|5 hours|Intermediate

Advanced Django Features

Learn advanced Django features including admin interface, forms, authentication, permissions, and REST API development for web development.

Progress: 0/4 topics completed0%

Select Topics Overview

Django Admin Interface

Master Django's built-in admin interface for managing your application's data and users.

Content by: Manali Trivedi

Python Django Developer

Connect

Django Admin Overview

Django's admin interface is a powerful, automatically generated web interface for managing your application's data. It's highly customizable and provides a user-friendly way to interact with your models.

Admin Configuration

Code Example
# admin.py
from django.contrib import admin
from django.utils.html import format_html
from .models import Post, Category, Tag, Comment

@admin.register(Post)
class PostAdmin(admin.ModelAdmin):
    list_display = ['title', 'author', 'category', 'status', 'created_date', 'published_date']
    list_filter = ['status', 'created_date', 'category', 'author']
    search_fields = ['title', 'content']
    prepopulated_fields = {'slug': ('title',)}
    date_hierarchy = 'created_date'
    ordering = ['-created_date']
    
    fieldsets = (
        ('Content', {
            'fields': ('title', 'slug', 'content', 'excerpt')
        }),
        ('Metadata', {
            'fields': ('author', 'category', 'tags', 'status')
        }),
        ('Publishing', {
            'fields': ('published_date',),
            'classes': ('collapse',)
        }),
    )
    
    def get_queryset(self, request):
        return super().get_queryset(request).select_related('author', 'category')
    
    def save_model(self, request, obj, form, change):
        if not change:  # New object
            obj.author = request.user
        super().save_model(request, obj, form, change)

@admin.register(Category)
class CategoryAdmin(admin.ModelAdmin):
    list_display = ['name', 'slug', 'post_count']
    prepopulated_fields = {'slug': ('name',)}
    
    def post_count(self, obj):
        return obj.post_set.count()
    post_count.short_description = 'Number of Posts'

@admin.register(Tag)
class TagAdmin(admin.ModelAdmin):
    list_display = ['name', 'color_display', 'post_count']
    search_fields = ['name']
    
    def color_display(self, obj):
        if obj.color:
            return format_html(
                '<span style="color: {};">{}</span>',
                obj.color,
                obj.color
            )
        return '-'
    color_display.short_description = 'Color'
    
    def post_count(self, obj):
        return obj.post_set.count()
    post_count.short_description = 'Number of Posts'

# Custom admin actions
@admin.action(description='Mark selected posts as published')
def make_published(modeladmin, request, queryset):
    from django.utils import timezone
    updated = queryset.update(status='published', published_date=timezone.now())
    modeladmin.message_user(request, f'{updated} posts were successfully marked as published.')

@admin.action(description='Mark selected posts as draft')
def make_draft(modeladmin, request, queryset):
    updated = queryset.update(status='draft', published_date=None)
    modeladmin.message_user(request, f'{updated} posts were successfully marked as draft.')

# Add actions to PostAdmin
PostAdmin.actions = [make_published, make_draft]
Swipe to see more code

Practice Exercise: Custom Admin Dashboard

Code Example
# Custom Admin Dashboard
from django.contrib import admin
from django.contrib.admin import AdminSite
from django.utils.html import format_html
from django.urls import path
from django.shortcuts import render
from django.db.models import Count, Sum
from django.utils import timezone
from datetime import timedelta

class CustomAdminSite(AdminSite):
    site_header = "My Django Site Administration"
    site_title = "My Django Site Admin Portal"
    index_title = "Welcome to My Django Site Administration"
    
    def get_urls(self):
        urls = super().get_urls()
        custom_urls = [
            path('dashboard/', self.admin_view(self.dashboard_view), name='dashboard'),
            path('analytics/', self.admin_view(self.analytics_view), name='analytics'),
        ]
        return custom_urls + urls
    
    def dashboard_view(self, request):
        """Custom dashboard view"""
        from .models import Post, User, Comment
        
        # Get statistics
        total_posts = Post.objects.count()
        published_posts = Post.objects.filter(status='published').count()
        total_users = User.objects.count()
        total_comments = Comment.objects.count()
        
        # Recent activity
        recent_posts = Post.objects.order_by('-created_date')[:5]
        recent_comments = Comment.objects.order_by('-created_date')[:5]
        
        # Chart data
        last_30_days = timezone.now() - timedelta(days=30)
        daily_posts = Post.objects.filter(
            created_date__gte=last_30_days
        ).extra(
            select={'day': 'date(created_date)'}
        ).values('day').annotate(count=Count('id')).order_by('day')
        
        context = {
            'total_posts': total_posts,
            'published_posts': published_posts,
            'total_users': total_users,
            'total_comments': total_comments,
            'recent_posts': recent_posts,
            'recent_comments': recent_comments,
            'daily_posts': list(daily_posts),
        }
        
        return render(request, 'admin/dashboard.html', context)
    
    def analytics_view(self, request):
        """Analytics view"""
        from .models import Post, User
        
        # User engagement metrics
        user_engagement = User.objects.annotate(
            post_count=Count('post'),
            comment_count=Count('comment')
        ).order_by('-post_count')[:10]
        
        # Category popularity
        category_popularity = Post.objects.values('category__name').annotate(
            post_count=Count('id')
        ).order_by('-post_count')
        
        context = {
            'user_engagement': user_engagement,
            'category_popularity': category_popularity,
        }
        
        return render(request, 'admin/analytics.html', context)

# Register the custom admin site
admin_site = CustomAdminSite(name='custom_admin')

# Register models with custom admin site
admin_site.register(Post, PostAdmin)
admin_site.register(Category, CategoryAdmin)
admin_site.register(Tag, TagAdmin)

# Usage in urls.py:
# from .admin import admin_site
# urlpatterns = [
#     path('admin/', admin_site.urls),
# ]
Swipe to see more code

🎯 Practice Exercise

Test your understanding of this topic:

Additional Resources

📚 Recommended Reading

  • Django Admin Documentation
  • Django Forms Documentation
  • Django REST Framework Documentation
  • Django Authentication Documentation

🌐 Online Resources

  • Django Admin Tutorial
  • Django Forms Examples
  • DRF Tutorial
  • Django Security Best Practices

Ready for the Next Module?

Continue your learning journey and master the next set of concepts.

Continue to Module 4