Django Enterprise Structure: How Large Django Codebases Are Organized
Organizing and properly separating business concerns in large, enterprise-scale applications.
As Django projects grow from a small application into a serious business platform, the default flat structure starts to break down.
What works for a small prototype:
project/
settings.py
urls.py
users/
products/
orders/
often becomes harder to manage when you have: - multiple teams - dozens of apps - hundreds of models - large test suites - CI/CD pipelines - shared internal tooling - years of continuous development
This is where an enterprise Django structure becomes valuable.
What Is an Enterprise Django Structure?
It usually means organizing your Django codebase into a dedicated application package, commonly called:
apps/
or:
src/
Example:
project/
manage.py
config/
settings/
urls.py
wsgi.py
asgi.py
apps/
users/
products/
billing/
orders/
analytics/
support/
This creates clear separation between: - project configuration - business applications - infrastructure code
Why Large Teams Prefer This Enterprise Approach:
1. Clear Separation of Concerns
Without structure:
project/
users/
orders/
settings.py
urls.py
utils.py
celery.py
Everything mixes together.
With enterprise structure:
- config/ -> Django runtime config
- apps/ -> business domains
- common/ -> shared libraries
Much easier to navigate.
Typical Enterprise Layout
project/ │ ├── manage.py │ ├── config/ │ ├── settings/ │ │ ├── base.py │ │ ├── dev.py │ │ ├── prod.py │ │ └── test.py │ ├── urls.py │ ├── asgi.py │ └── wsgi.py │ ├── apps/ │ ├── users/ │ ├── products/ │ ├── inventory/ │ ├── checkout/ │ ├── billing/ │ ├── shipping/ │ ├── analytics/ │ └── support/ │ ├── common/ │ ├── logging/ │ ├── permissions/ │ ├── middleware/ │ └── utils/ │ ├── requirements/ ├── scripts/ └── docs/
config/
This is the Django runtime package.
Contains: - settings - root URLs - WSGI - ASGI - startup config
Why split settings?
Because production, development, tests, staging all differ.
apps/
This contains your business domains.
Examples:
⧉
1 2 3 4 | |
Each app should represent a real business capability.
Good examples: - users - payments - subscriptions - inventory - messaging
Bad examples: - helpers - misc - sharedstuff
Article eplaining apps and when to separate business logic: Django Apps Explained A guide on how to organize your apps inside a dedecated apps-directory: Organize Django Apps
common/
This contains reusable internal libraries.
Examples: - common/auth/ - common/logging/ - common/exceptions/ - common/middleware/
These are not business domains. They support all apps.
Why Not Put Everything in apps/?
Because not everything is an app.
Example: - JWT helper - logging formatter - S3 storage adapter - custom middleware - base model mixins
These belong in infrastructure/shared code.
INSTALLED_APPS in Enterprise Projects
⧉
1 2 3 4 5 6 7 8 9 | |
Internal Structure of Each App
Example:
apps/orders/
migrations/
admin.py
apps.py
urls.py
models/
views/
tasks.py
tests/
This avoids giant models.py and views.py.
Why This Scales Better
Team Ownership
Different teams can own apps:
Billing team → apps/billing Growth team → apps/users Ops team → apps/support
Ownership becomes obvious.
Easier Navigation
Need refund logic?
Go to: apps/billing/
Need order fulfillment?
Go to: apps/orders/
Well-designed apps communicate through: - services - selectors - APIs - events/signals
instead of random imports everywhere.
Settings Structure in Enterprise Teams
Instead of one giant settings file: settings.py # 1200 lines
Split the settings file into separate concerns:
config/settings/
base.py
local.py
staging.py
prod.py
test.py
base.py
Shared defaults.
local.py
Debug toolbar, sqlite, local email.
prod.py
Security, PostgreSQL, Redis, S3, sentry.
Example Import Pattern inside dev.py and prod.py:
⧉
1 | |
Then override environment-specific values.
A full article on how to split your settings can be found here: Split Django's settings.py
Common Mistakes in Large Django Projects
1. Giant core app
core/
Contains 80% of business logic.
Eventually becomes unmaintainable.
2. Everything in utils.py
Avoid dumping grounds.
3. Technical Instead of Domain Apps
Bad:
api/ forms/ models/ views/
These are layers, not domains.
4. Circular Imports Between Apps
Use lazy model refs:
models.ForeignKey("orders.Order")
Use services instead of model cross-calls.
Naming Conventions
Prefer:
⧉
1 2 3 | |
Avoid:
⧉
1 2 | |
Keep names short and business-oriented.
Best Practices
Use enterprise structure when: - project is serious - multiple engineers involved - expected multi-year lifespan - multiple business domains exist - Keep apps domain-driven - Keep config isolated - Keep shared code separate - Prefer services over cross-app chaos
The enterprise Django structure does not add complexity - it is about creating order before chaos appears.
This pattern:
⧉
1 2 3 | |
lets Django monoliths scale to surprisingly large systems without losing maintainability.
If your project may exceed 3–5 apps or 2+ engineers, start with enterprise structure early on. Refactoring later is far more expensive.
Join the Newsletter
Practical insights on Django, backend systems, deployment, architecture, and real-world development — delivered without noise.
Get updates when new guides, learning paths, cheat sheets, and field notes are published.
No spam. Unsubscribe anytime.
There is no third-party involved so don't worry - we won't share your details with anyone.