Running Multiple Django Sites in a Single WSGI Process via Dynamic Host Routing
When operating a multi-brand SaaS platform or white-label web portfolio, spinning up separate Gunicorn/uWSGI worker pools for every domain wastes RAM. Instead, a single Django WSGI process can serve multiple distinct domains and URL configurations dynamically based on the incoming Host header.
1. Custom Host-Routing Middleware in Django
In Django, setting request.urlconf inside a middleware class before URL resolution overrides settings.ROOT_URLCONF for that specific request thread/coroutine:
class MultiHostUrlConfMiddleware:
HOST_URLCONF_MAP = {
"www.aldianfazrihady.com": "afcom.urls",
"cello.aldianfazrihady.com": "cello.urls",
"payflow-hosted-page.aldianfazrihady.com": "payflow_hosted_page.urls",
}
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
host = request.get_host().split(":")[0].lower()
urlconf = self.HOST_URLCONF_MAP.get(host)
if urlconf:
request.urlconf = urlconf
return self.get_response(request)
2. Cache Key Isolation & CSRF Trusted Origins
- Cache Key Prefixing: Always include the current
request.get_host()in your customKEY_FUNCTIONso Django's per-site or view cache never serves HTML rendered for Domain A to a visitor on Domain B. - Allowed Hosts & CSRF: List all white-label domains in
ALLOWED_HOSTSandCSRF_TRUSTED_ORIGINS, and scope session cookies appropriately.