← 返回
未分类

Django Unfold

Expert guidance for building advanced Django admin interfaces with django-unfold (v0.56+). Use this skill whenever the user mentions django-unfold, unfold ad...
提供使用 django-unfold (v0.56+) 构建高级 Django 管理界面的专业指导。当用户提及 django-unfold、unfold admin 等内容时使用此技能。
ijmadalena ijmadalena 来源
未分类 clawhub v1.0.0 1 版本 100000 Key: 无需
★ 1
Stars
📥 304
下载
💾 0
安装
1
版本
#latest

概述

Django Unfold Skill

Django Unfold is a modern admin theme for Django built on Tailwind CSS. It is a **drop-in

enhancement** of django.contrib.admin — fully compatible with all native Django admin

patterns while adding UI, components, and developer-friendly features.

Current stable version: 0.90.x (Django 5.0+ required from v0.90; dropped Django 4.2)


⚠️ Critical Rules — Always Apply

Rule 1: Every ModelAdmin must inherit from unfold.admin.ModelAdmin

# ✅ CORRECT
from unfold.admin import ModelAdmin

@admin.register(MyModel)
class MyModelAdmin(ModelAdmin):
    pass

# ❌ WRONG — loses all styling and Unfold features
from django.contrib.admin import ModelAdmin  # never use this base

Rule 2: INSTALLED_APPS order — "unfold" must precede "django.contrib.admin"

INSTALLED_APPS = [
    "unfold",                           # REQUIRED FIRST
    "unfold.contrib.filters",           # optional: advanced filters
    "unfold.contrib.forms",             # optional: ArrayWidget, WysiwygWidget, crispy
    "unfold.contrib.inlines",           # optional: NonrelatedInline
    "unfold.contrib.import_export",     # optional: django-import-export
    "unfold.contrib.simple_history",    # optional: django-simple-history
    "unfold.contrib.guardian",          # optional: django-guardian
    "unfold.contrib.constance",         # optional: django-constance
    "unfold.contrib.location_field",    # optional: django-location-field
    "django.contrib.admin",             # AFTER unfold
]

Rule 3: Inlines also need Unfold base classes

from unfold.admin import StackedInline, TabularInline  # not django.contrib.admin

Rule 4: User & Group models need manual re-registration — see references/installation.md


Core ModelAdmin Options Reference

from unfold.admin import ModelAdmin
from unfold.contrib.forms.widgets import ArrayWidget, WysiwygWidget
from django.db import models

@admin.register(MyModel)
class MyModelAdmin(ModelAdmin):
    # ── Changelist layout ────────────────────────────────────────────
    list_fullwidth = False               # expand to full page width
    list_filter_sheet = True             # filters as bottom sheet (False = sidebar)
    list_filter_submit = False           # show Apply button in filter panel
    list_horizontal_scrollbar_top = False
    list_disable_select_all = False

    # ── Change form UX ────────────────────────────────────────────────
    compressed_fields = True             # compact field display
    warn_unsaved_form = True             # warn before leaving unsaved
    show_add_link = True                 # show Add button
    change_form_show_cancel_button = False

    # Custom template injection (HTML snippets, not full templates)
    change_form_before_template = "myapp/before_form.html"    # inside form, top
    change_form_after_template = "myapp/after_form.html"      # inside form, bottom
    change_form_outer_before_template = "myapp/outer_top.html"
    change_form_outer_after_template = "myapp/outer_bottom.html"

    # ── Readonly field post-processing ───────────────────────────────
    readonly_preprocess_fields = {
        "html_field": "html.unescape",
        "text_field": lambda content: content.strip(),
    }

    # ── Widget overrides ─────────────────────────────────────────────
    formfield_overrides = {
        models.TextField: {"widget": WysiwygWidget},
        # ArrayField: {"widget": ArrayWidget},  # for PostgreSQL ArrayField
    }

    # ── Actions (5 types) — see references/actions.md ────────────────
    actions_list = []        # above changelist (global)
    actions_row = []         # per-row in changelist table
    actions_detail = []      # top of change form header
    actions_submit_line = [] # near Save button in change form

    # ── Conditional fields — see references/forms-fields.md ──────────
    conditional_fields = {
        "field_name": "other_field == 'value'",  # Alpine.js expression
    }

    # ── Expandable row sections — see references/forms-fields.md ─────
    list_sections = []   # [SectionClass, ...]

    # ── Datasets on change form — see references/forms-fields.md ─────
    change_form_datasets = []  # [DatasetClass, ...]

@display Decorator

Always use unfold.decorators.display, not Django's built-in.

from unfold.decorators import display

class OrderAdmin(ModelAdmin):
    list_display = ["show_customer", "show_status", "show_priority"]

    # Two-line cell: main heading + subtitle
    @display(header=True)
    def show_customer(self, obj):
        return obj.full_name, obj.email   # tuple: (main, subtitle)

    # Colored status badge mapped from field values
    @display(
        description="Status",
        ordering="status",
        label={
            "PENDING":   "warning",   # orange
            "ACTIVE":    "info",      # blue
            "COMPLETED": "success",   # green
            "FAILED":    "danger",    # red
        },
    )
    def show_status(self, obj):
        return obj.status

    # Boolean label with default color
    @display(description="VIP", label=True)
    def show_priority(self, obj):
        return obj.is_vip

→ Full @display and @action decorator docs: references/decorators.md


Reference Files — When To Read Each

Read the relevant file before implementing any feature in that area.

Each reference file contains explicit pointers to related files.

Reference FileRead When You Need To...
------
references/installation.mdSet up from scratch, configure User/Group, run parallel admin
references/configuration.mdUnderstand any UNFOLD = {...} key: title, login, callbacks, favicons, env
references/theming.mdChange colors (OKLCH), sidebar nav, icons/badges, Tailwind custom CSS
references/actions.mdAdd list/row/detail/submitline/dropdown actions, permissions, form actions
references/filters.mdAdd text/date/dropdown/numeric/autocomplete/checkbox/radio/horizontal filters
references/tabs.mdAdd fieldset tabs, inline tabs, changelist tabs, changeform tabs, dynamic tabs
references/inlines.mdConfigure inlines: options, sortable, paginated, nested, nonrelated
references/dashboard-components.mdBuild dashboards, use components (card/chart/table/progress/tracker/cohort)
references/forms-fields.mdConditional fields, sections (expandable rows), datasets, crispy forms, JsonField
references/decorators.mdFull @display options (header, label, mapping) and @action decorator options
references/integrations.mdAll 10 third-party packages: celery-beat, import-export, guardian, constance, etc.
references/advanced.mdCustom pages, custom sites, sortable changelist, command palette, multi-language

Common Pitfalls

  • Styles missing in production → run collectstatic
  • Tailwind conflict on Unfold ≥ 0.56 → don't load a Tailwind 3 CSS file; use UNFOLD["COLORS"] or Tailwind 4
  • Custom pages not in sidebar → add manually to UNFOLD["SIDEBAR"]["navigation"]
  • Third-party admin unstyled (celery-beat, etc.) → unregister and re-register with unfold.admin.ModelAdmin
  • list_filter on Datasets → not supported; filter via get_queryset() instead
  • Django 4.2 → not supported from Unfold v0.90+

版本历史

共 1 个版本

  • v1.0.0 当前
    2026-05-07 23:43 安全 安全

安全检测

腾讯云安全 (Keen)

安全,无风险
查看报告

腾讯云安全 (Sanbu)

安全,无风险
查看报告

🔗 相关推荐

ai-agent

self-improving agent

pskoett
捕获经验教训、错误及修正内容,以实现持续改进。适用于以下场景:(1)命令或操作意外失败;(2)用户纠正Claude(如“不,那不对……”“实际上……”);(3)用户请求的功能不存在;(4)外部API或工具出现故障;(5)Claude发现自身
★ 4,082 📥 810,014
ai-agent

Self-Improving + Proactive Agent

ivangdavila
自我反思+自我批评+自我学习+自组织记忆。智能体评估自身工作、发现错误并持续改进。
★ 1,379 📥 320,415
dev-programming

Github

steipete
使用 `gh` CLI 与 GitHub 交互,通过 `gh issue`、`gh pr`、`gh run` 和 `gh api` 管理议题、PR、CI 运行及高级查询。
★ 676 📥 325,418