Improving the New Django Developer Experience
At DjangoCon 2024, I gave a lightning talk about improving the experience for new Django developers. While Django is an incredibly powerful framework, there’s one aspect of the initial developer experience that I believe we can significantly enhance. Let’s explore the current onboarding experience and how we might make it more intuitive for newcomers.
The Current Django Project Setup
If you look at the official Django documentation, the tutorial instructs you to create a new project like this:
$ mkdir djangotutorial
$ django-admin startproject mysite djangotutorial
This creates the following directory structure:
.
├── manage.py
└── mysite
├── __init__.py
├── asgi.py
├── settings.py
├── urls.py
└── wsgi.py
As someone who’s both learned and taught Django, I’ve noticed this structure raises several questions for newcomers:
- Why create a
djangotutorial
directory only to have another directory calledmysite
inside it? - What should the
mysite
directory be named in a real-world project? - Why are configuration files housed in a project-named directory?
- How does this impact project maintainability, especially when version control and project renaming come into play?
Learning from Other Frameworks
To provide context, let’s look at how other modern web frameworks handle project initialization. Laravel, for instance, offers a notably streamlined experience:
Laravel places all configuration files in a dedicated config
directory:
.
...
├── config
│ ├── app.php
│ ├── auth.php
│ ├── cache.php
│ ├── database.php
│ ├── filesystems.php
│ ├── logging.php
│ ├── mail.php
│ ├── queue.php
│ ├── services.php
│ └── session.php
...
Compare this to the current Django experience:
The Django CLI experience has some rough edges - error messages aren’t consistently formatted, and simple issues like hyphens in project names result in errors rather than automatic conversion to underscores. The resulting structure still uses the project name for configuration files:
.
├── example_project
│ ├── __init__.py
│ ├── asgi.py
│ ├── settings.py
│ ├── urls.py
│ └── wsgi.py
└── manage.py
A Path Forward: DJ Beat Drop
While changing Django’s core project templates might be challenging (as evidenced by this PR that’s been open for two years), we can take a more pragmatic approach. I’ve created dj-beat-drop, a modern Django project initializer that brings the best practices from other frameworks to the Django ecosystem.
DJ Beat Drop offers:
- A more intuitive project structure
- It uses the official Django project template, but puts all configuration files in a
config
directory - Built-in support for environment variables via
.env
files - Integration with modern Python tooling like
uv
- A smoother, more user-friendly CLI experience
Here’s what creating a new Django project with DJ Beat Drop looks like:
With the defaults the resulting structure looks like this:
.
├── README.md
├── config
│ ├── __init__.py
│ ├── asgi.py
│ ├── settings.py
│ ├── urls.py
│ └── wsgi.py
├── db.sqlite3
├── manage.py
├── pyproject.toml
└── uv.lock
If you say no to the defaults, then the resulting structure looks like this:
.
├── config
│ ├── __init__.py
│ ├── asgi.py
│ ├── settings.py
│ ├── urls.py
│ └── wsgi.py
└── manage.py
Join the Movement
If you’re interested in improving the Django developer experience, I invite you to try DJ Beat Drop and share your feedback. With community support, this could become the recommended way to start new Django projects, making the framework even more accessible to newcomers while maintaining the power and flexibility that Django developers love.
Want to help? Star the repository on GitHub and share it with your fellow Djangonauts. Together, we can make the Django ecosystem even better for the next generation of developers.