Skip to content

Django — greenfield or existing project

Use hedron-django for Django-native apps. Requires Django >=5.2,<6. Scaffold with the hedron CLI (hedron new --django); runtime is hedron-django + hedron-core (no FastAPI in the app process). The adapter mounts /hedron-static so PAGE responses can inject bundled HTMX.

Install: pip install "hedron-django>=1.0.0" (or uv add "hedron-django>=1.0.0"). Requires Python 3.11–3.14. See Installation.

Django supports AppConfig, forms, and QuerySet DataSource. Progressive FastAPI facades (@app.view, @app.action, and related symbols) are FastAPI-only — see the host matrix on What’s ready.

Golden path (scaffold + Refresh)

Same success criteria as FastAPI: open the app, see Hello, click Refresh, watch the status region update without a full page reload. The scaffold uses Django views and raw hx-* attributes, not FastAPI status.refresh_button(...).

# Need uv? https://docs.astral.sh/uv/getting-started/installation/
uvx --from "hedron>=1.0.0" hedron new my-django-app --django
cd my-django-app && uv sync
uv run waitress-serve --listen=127.0.0.1:8000 wsgi:application

Open http://127.0.0.1:8000 — you should see Hello from hedron new --django. Click Refresh; the panel timestamp updates via HTMX into the declared #panel region.

The scaffold includes page + fragment regions and security headers middleware. Set HEDRON_SESSION_SECRET before production.

refresh_button vs raw hx-*

FastAPI scaffolds use status.refresh_button(...). Django getting-started samples may show raw hx-get / hx-target attributes — both are valid across adapters.

Try without local setup

Open the monorepo in Codespaces / Dev Container, then scaffold with hedron new my-app --django or run the reference slice below.

Alternate: clone the reference

git clone https://github.com/eddiethedean/hedron.git
cd hedron
uv sync
cd examples/django-reference
uv run waitress-serve --listen=127.0.0.1:8000 wsgi:application

Open http://127.0.0.1:8000/. Source: examples/django-reference. ASGI: uv run uvicorn asgi:application --host 127.0.0.1 --port 8000.

Existing Django project (add a Refresh page)

  pip install "hedron-django>=1.0.0" "django>=5.2,<6"

Add hedron_django to INSTALLED_APPS when you need forms/QuerySet helpers. Keep SessionMiddleware and CsrfViewMiddleware for production Django CSRF.

Minimal Refresh-capable view:

# demo/views.py
from datetime import datetime, timezone

from django.http import HttpRequest
from django.urls import path

from hedron_core import FragmentRegion, InteractionResult, Page, Text, html
from hedron_core.interaction import InteractionPolicy
from hedron_django import page, view

PANEL = FragmentRegion(id="panel", selector="#panel")


def panel_body() -> object:
    stamp = datetime.now(timezone.utc).strftime("%H:%M:%S UTC")
    return html.div(Text(f"Django status · {stamp}"), id="panel")


@page
def home(request: HttpRequest):
    return Page(
        html.div(
            Text("Hello Django"),
            panel_body(),
            html.button(
                Text("Refresh"),
                **{
                    "hx-get": "/status",
                    "hx-target": "#panel",
                    "hx-swap": "outerHTML",
                },
            ),
        ),
        title="Home",
    )


@view(fragment_regions=(PANEL,))
def status(request: HttpRequest):
    return InteractionResult(
        content=panel_body(),
        region_id="panel",
        policy=InteractionPolicy(declared_regions=(PANEL,)),
    )


urlpatterns = [
    path("", home, name="home"),
    path("status", status, name="status"),
]

Wire urlpatterns into your ROOT_URLCONF, then python manage.py runserver.

Portable CSRF header

HedronDjango.validate_csrf accepts both Django's X-CSRFToken and Hedron's portable X-CSRF-Token. For stock Django middleware alone, HTMX clients that send only the portable header should set::

CSRF_HEADER_NAME = "HTTP_X_CSRF_TOKEN"

in Django settings (as the reference app does). Stock Django's X-CSRFToken remains valid if you keep the default. Form posts must use csrfmiddlewaretoken. Django's CsrfViewMiddleware does not accept Hedron's portable csrf_token field name.

Next

Stay on Django: extend the canonical @page / @view decorators and POST with csrfmiddlewaretoken. Prefer polling for job status.

FastAPI-only continuation

HTMX interactions and Minimal form assume Hedron() / CsrfField() (csrf_token). Use them after you switch hosts.

  • Security · Ship a Hedron app
  • Forms: hedron_django.forms.form_to_nodes / validation_interaction
  • QuerySets: hedron_data.DjangoQuerySetDataSource with an already-authorized base QS