Skip to content

Getting Started with django-admin-deux

This tutorial will guide you through creating your first ModelAdmin and understanding the basics of django-admin-deux.

Prerequisites

  • Django project set up
  • django-admin-deux installed (see Installation Guide)
  • At least one Django model defined

Your First ModelAdmin

Let's create a simple admin interface for a Book model.

Step 1: Define Your Model

If you don't have a model yet, create one:

# myapp/models.py
from django.db import models

class Book(models.Model):
    title = models.CharField(max_length=200)
    author = models.CharField(max_length=100)
    isbn = models.CharField(max_length=13, unique=True)
    published_date = models.DateField()
    price = models.DecimalField(max_digits=6, decimal_places=2)
    in_stock = models.BooleanField(default=True)

    def __str__(self):
        return self.title

    class Meta:
        ordering = ['-published_date']

Run migrations:

python manage.py makemigrations
python manage.py migrate

Step 2: Create djadmin.py

Create a file named djadmin.py in your app directory:

# myapp/djadmin.py
from djadmin import ModelAdmin, register
from .models import Book

@register(Book)
class BookAdmin(ModelAdmin):
    list_display = ['title', 'author', 'published_date']

That's it! The @register() decorator registers your model with the default admin site.

Step 3: Access the Admin

Start your development server:

python manage.py runserver

Navigate to http://127.0.0.1:8000/djadmin/ in your browser.

You should see: - The project dashboard listing all apps - Your app name - The Book model with a link to its list view

Step 4: Explore the Interface

Click on "Books" to see: - A table showing your registered books - Columns for: Title, Author, Published Date - An "Add" button to create new books - "Edit" and "Delete" buttons for each row

Understanding list_display

The list_display attribute controls which columns appear in the list view.

Basic Field Names

class BookAdmin(ModelAdmin):
    list_display = ['title', 'author', 'published_date', 'price']

Custom Column Labels with Column Class

from djadmin import ModelAdmin, register, Column

@register(Book)
class BookAdmin(ModelAdmin):
    list_display = [
        'title',
        Column('author', label='Author Name'),
        Column('price', label='Price (USD)', classes='text-right'),
        'published_date',
    ]

Callable Methods

You can add custom columns using methods:

@register(Book)
class BookAdmin(ModelAdmin):
    list_display = ['title', 'author', 'availability_status']

    def availability_status(self, obj):
        return "Available" if obj.in_stock else "Out of Stock"

    availability_status.short_description = "Availability"

Adding Custom Actions

Actions define what operations users can perform. There are four types:

General Actions (Main Entry Points)

from djadmin.actions.list_view import ListAction

class BookAdmin(ModelAdmin):
    general_actions = [ListAction]  # Default

List Actions (No Record Selection)

from djadmin.plugins.core.actions import AddAction

class BookAdmin(ModelAdmin):
    list_actions = [AddAction]  # Default - appears in toolbar

Record Actions (Per-Record Operations)

from djadmin.plugins.core.actions import EditAction, DeleteAction

class BookAdmin(ModelAdmin):
    record_actions = [EditAction, DeleteAction]  # Defaults

Bulk Actions (Multiple Records)

from djadmin.plugins.core.actions import DeleteBulkAction

class BookAdmin(ModelAdmin):
    bulk_actions = [DeleteBulkAction]  # Default

Note: These are the defaults provided by the core plugin. You typically don't need to specify them unless you're adding custom actions.

Customizing Forms

Specifying Fields

Control which fields appear in create/edit forms:

class BookAdmin(ModelAdmin):
    fields = ['title', 'author', 'isbn', 'published_date', 'price', 'in_stock']

Different Fields for Create vs Update

class BookAdmin(ModelAdmin):
    # Default fields for both create and update
    fields = ['title', 'author', 'isbn', 'published_date', 'price', 'in_stock']

    # Simplified create form (only essential fields)
    create_fields = ['title', 'author', 'isbn', 'published_date']

    # Update form shows all fields (uses 'fields')

Custom Form Classes

from django import forms

class BookForm(forms.ModelForm):
    class Meta:
        model = Book
        fields = '__all__'
        widgets = {
            'published_date': forms.DateInput(attrs={'type': 'date'}),
        }

class BookAdmin(ModelAdmin):
    form_class = BookForm

Or different forms for create/update:

class BookCreateForm(forms.ModelForm):
    class Meta:
        model = Book
        fields = ['title', 'author', 'isbn']

class BookUpdateForm(forms.ModelForm):
    class Meta:
        model = Book
        fields = '__all__'

class BookAdmin(ModelAdmin):
    create_form_class = BookCreateForm
    update_form_class = BookUpdateForm

Pagination

Control how many items appear per page:

class BookAdmin(ModelAdmin):
    paginate_by = 50  # Default is 100

Multiple ModelAdmins for One Model

You can register multiple ModelAdmin classes for the same model:

# Simple view for quick access
@register(Book)
class SimpleBookAdmin(ModelAdmin):
    list_display = ['title', 'author']

# Detailed view with all fields
@register(Book)
class DetailedBookAdmin(ModelAdmin):
    list_display = ['title', 'author', 'isbn', 'published_date', 'price', 'in_stock']
    fields = '__all__'

Both will appear in the dashboard with separate URLs: - /djadmin/myapp/book/0/ → SimpleBookAdmin - /djadmin/myapp/book/1/ → DetailedBookAdmin

Complete Example

Here's a complete, real-world example:

# myapp/djadmin.py
from djadmin import ModelAdmin, register, Column
from djadmin.plugins.core.actions import (
    AddAction, EditAction, DeleteAction, DeleteBulkAction
)
from .models import Book

@register(Book)
class BookAdmin(ModelAdmin):
    # List view configuration
    list_display = [
        Column('title', label='Book Title'),
        'author',
        Column('price', label='Price (USD)', classes='text-right'),
        Column('published_date', label='Published'),
        'stock_status',
    ]

    # Pagination
    paginate_by = 25

    # Actions (these are defaults, shown for clarity)
    general_actions = [ListAction]
    list_actions = [AddAction]
    record_actions = [EditAction, DeleteAction]
    bulk_actions = [DeleteBulkAction]

    # Form configuration
    create_fields = ['title', 'author', 'isbn', 'published_date', 'price']
    fields = '__all__'  # Update form shows all fields

    # Custom column
    def stock_status(self, obj):
        if obj.in_stock:
            return "✓ In Stock"
        return "✗ Out of Stock"

    stock_status.short_description = "Status"

Working with Dashboards

Project Dashboard

Navigate to /djadmin/ to see all registered apps and models.

App Dashboard

Navigate to /djadmin/myapp/ to see all models in a specific app.

The dashboard shows: - App name - List of models in the app - Available actions for each model (from general_actions and list_actions)

Next Steps

Now that you have a basic ModelAdmin working:

  1. Basic Usage Guide - Learn more ModelAdmin configuration options
  2. CRUD Operations - Understand how create, update, and delete work
  3. Action System - Deep dive into the action system
  4. Customization Guide - Advanced customization techniques

Common Patterns

Read-Only Admin

@register(Book)
class ReadOnlyBookAdmin(ModelAdmin):
    list_display = ['title', 'author', 'published_date']
    list_actions = []        # No add button
    record_actions = []      # No edit/delete buttons
    bulk_actions = []        # No bulk operations

Minimal Admin (List Only)

@register(Book)
class MinimalBookAdmin(ModelAdmin):
    list_display = ['title']
    list_actions = []
    record_actions = []
from djadmin.plugins.core.actions import (
    AddAction, EditAction, DeleteAction, DeleteBulkAction
)

@register(Book)
class FullBookAdmin(ModelAdmin):
    list_display = ['title', 'author', 'isbn', 'published_date', 'price', 'in_stock']
    list_actions = [AddAction]
    record_actions = [EditAction, DeleteAction]
    bulk_actions = [DeleteBulkAction]
    fields = '__all__'
    paginate_by = 50

Tips and Best Practices

  1. Start Simple: Begin with basic list_display, add complexity as needed
  2. Use Column Class: For better control over column display and styling
  3. Separate Create/Update: Use create_fields for simplified creation forms
  4. Custom Methods: Add computed columns with methods
  5. Multiple Admins: Create different views for different use cases
  6. Test Early: Create some test data to see your admin in action

Troubleshooting

ModelAdmin not showing in dashboard

Solution: Ensure: - You've created djadmin.py in your app directory - Your app is in INSTALLED_APPS - You've used the @register() decorator - You've restarted the development server

Columns not displaying correctly

Solution: Check that field names in list_display match your model fields.

Actions not appearing

Solution: Default actions are provided by the core plugin. If you're using djadmin_apps() (recommended), it's automatically included. If configuring manually, ensure djadmin.plugins.core is in INSTALLED_APPS.

Summary

You've learned: - ✅ How to create a basic ModelAdmin - ✅ How to configure list_display - ✅ How to customize forms - ✅ How to work with actions - ✅ How to register multiple ModelAdmins

Continue learning with the User Guide!