A scalable real-time customer support chat platform built with Django, Django Ninja, Django Channels, React, and TypeScript. This project provides a complete live chat infrastructure between visitors and support administrators using REST APIs and WebSocket communication. The system supports real-time messaging, typing indicators, admin notifications, chat session management, temporary WebSocket authentication, and persistent message storage. Because apparently modern users expect instant communication instead of patiently waiting three business days like it’s 2004. Humanity really looked at HTTP and said: “What if requests never ended?” and thus WebSockets were born. Somehow, against all odds, this architecture is actually clean and scalable. So credit where it’s due.
This project implements a real-time customer support chat platform using:
- Django
- Django Ninja
- Django Channels
- In-memory caching layer (Redis-compatible design)
- WebSocket communication
- JWT-based administrator authentication
- Persistent chat storage using SQLite
- React
- TypeScript
- React Router
- Tailwind CSS
- Framer Motion
- Axios
- Native WebSocket API
- LocalStorage-based session persistence
- Component-based UI architecture
- Debounced client-side search and filtering
The architecture is divided into two communication layers:
| Layer | Purpose |
|---|---|
| REST API | Session initialization and management |
| WebSocket | Real-time bi-directional messaging |
- Real-time visitor-to-admin communication
- WebSocket-based messaging
- Typing indicators
- Admin live notifications
- JWT-secured admin channels
- Temporary visitor access tokens
- Persistent chat sessions
- Session restore capability
- Chat room lifecycle management
- Soft delete and recovery system
- Online admin monitoring
- Multi-room support
- Group-based broadcasting architecture
Visitor Client (React + TypeScript)
│
▼
REST API (Django Ninja)
│
├── SQLite Database
├── Cache Layer
│
▼
WebSocket Layer (Django Channels)
│
├── Visitor Chat Rooms
├── Admin Chat Rooms
├── Notification Channels
│
▼
Support Dashboard
ScreenCapture_26-05-26_13.52.30.mp4
The visitor creates a chat session through a REST API endpoint.
POST /sessions- Generate visitor token
- Generate temporary WebSocket access token
- Create chat session record
- Store temporary authentication data in cache
The frontend establishes a WebSocket connection using the temporary access token.
/ws/chat/visitor/<access_token>/
/ws/chat/admin/<room_id>/<jwt_token>/
/ws/chat/notification/<jwt_token>/
Once connected:
- Messages are broadcast to room groups
- Messages are persisted in the database
- Admin dashboards receive notifications
- Typing events are synchronized in real time
Handles authentication and temporary access management.
- Visitor token generation
- Temporary WebSocket token generation
- Cache-based access validation
- JWT validation for admins
- Room session initialization
- Temporary WebSocket access tokens
- Cache-based session authorization
- JWT-protected admin access
- Role-based validation
Implements all WebSocket consumers using Django Channels.
| Consumer | Purpose |
|---|---|
VisitorChatConsumer |
Visitor chat communication |
AdminChatConsumer |
Admin room communication |
AdminNotificationConsumer |
Live dashboard notifications |
BaseChatConsumer |
Shared WebSocket logic |
- Group-based broadcasting
- Typing indicators
- Real-time notifications
- Session state updates
- Async message handling
- Automatic room activation
Defines database models for chat sessions and messages.
Stores:
- visitor identity
- session state
- assigned admin
- metadata
- timestamps
Stores:
- sender information
- message content
- delivery state
- timestamps
Defines ASGI WebSocket routes.
ws/chat/visitor/<access_token>/
ws/chat/admin/<room_id>/<access_token>/
ws/chat/notification/<access_token>/REST API layer implemented using Django Ninja.
| Endpoint | Purpose |
|---|---|
POST /sessions |
Create chat session |
GET /get-sessions |
Retrieve sessions |
GET /get-sessions/{id} |
Retrieve messages |
POST /chat-sessions/{id}/close |
Close session |
DELETE /chat-session/delete |
Soft delete session |
PATCH /chat-session/recovery |
Restore session |
GET /get-online-users |
Online admin statistics |
The frontend is built with React and TypeScript and provides two real-time interfaces:
- A visitor-facing chat widget
- An administrative support dashboard
It is responsible for session initialization, REST communication, WebSocket lifecycle management, live message rendering, typing state synchronization, local session persistence, and interactive dashboard operations.
- Anonymous chat session initialization
- Temporary token-based WebSocket connection
- Real-time message sending and receiving
- Typing indicator support
- Automatic reconnect handling
- Session restore after refresh
- Responsive chat widget UI
- Tab-based session filtering (
waiting,active,closed) - Live session list updates
- Real-time room selection and conversation rendering
- Real-time admin-to-visitor messaging
- Typing indicator visibility
- Unread / new message indicators
- Session close workflow
- Soft delete and recovery support
- Search across chat sessions
- Debounced client-side filtering
- Highlighted search matches in the session list
- Incremental list rendering / infinite scroll behavior
- Create visitor chat sessions
- Fetch chat session lists
- Fetch conversation history
- Close sessions
- Delete or restore sessions
- Retrieve online admin statistics
- Connect visitors to temporary session channels
- Connect admins to room-specific chat channels
- Connect admins to live notification channels
- Receive and render real-time messages instantly
- Synchronize typing events between participants
- Update UI state on incoming events without page reload
The frontend maintains lightweight client-side persistence using localStorage for items such as:
- active chat session identifiers
- last received messages
- API key / access token references (development flow)
- session continuity after refresh
This helps preserve dashboard state and improve continuity during reconnect or refresh scenarios.
The admin dashboard includes a client-side search system designed to improve session navigation.
- Search by visitor name
- Search by visitor email
- Search by visitor IP
- Search by site
- Search by latest message preview
- Debounced input handling
- Status-based filtering before search
- Highlighted matches in the session list
- Efficient rendering for larger chat lists
ScreenCapture_26-05-26_13.57.19.mp4
Visitors use temporary WebSocket access tokens generated during session creation.
300 seconds (5 minutes)
- Prevent direct room access
- Reduce replay attack risks
- Secure WebSocket initialization
Admins authenticate using JWT tokens.
- JWT signature verification
- Staff/superuser validation
- Permission checks
| State | Description |
|---|---|
waiting |
Waiting for admin response |
active |
Active conversation |
closed |
Conversation closed |
{
"type": "typing",
"is_typing": true
}Whenever a visitor sends a message:
- Admin dashboards receive instant alerts
- Notification previews are generated
- Room IDs are synchronized
Current implementation:
- SQLite database
- In-memory cache
- Single-node ASGI setup
Recommended production upgrades:
| Current | Recommended |
|---|---|
| SQLite | PostgreSQL |
| Local Cache | Redis |
| Single ASGI Worker | Daphne/Uvicorn Cluster |
| Local Channels Layer | Redis Channel Layer |
- Temporary visitor WebSocket tokens
- JWT-protected admin channels
- Role-based admin authorization
- Cache-backed access validation
- Session isolation per room
- Environment-based secret management
cd frontend
npm install
npm run devCreate a .env file in the frontend directory and configure the required variables: VITE_API_BASE_URL=http://127.0.0.1:8001 VITE_SOCKET_BASE_URL=ws://127.0.0.1:8001/ws
VITE_API_BASE_URL is used for REST API requests VITE_SOCKET_BASE_URL is used for WebSocket connections Local development assumes the Django server is running locally
To run the project locally, start by creating and activating a Python virtual environment, because installing packages globally is how small problems grow up to become therapy sessions.
After activating the virtual environment, install the required dependencies:
pip install -r requirements.txtNext, run the Django migrations to create the local SQLite database:
python manage.py migrateThe project also requires a Django SECRET_KEY, which should be stored inside a .env file instead of being hardcoded directly into the settings module. Hardcoding secrets is generally frowned upon, mostly because future-you deserves fewer reasons to question past-you’s life choices.
You can generate a secure Django secret key using the built-in utility:
from django.core.management.utils import get_random_secret_key
print(get_random_secret_key())Once everything is ready and the database has been properly convinced to exist, start the development server:
python manage.py runserverFor accessing the admin dashboard in local development, use the following credentials:
Username: admin
Password: adminadmin123!
1. Visitor creates session
2. Backend generates temporary token
3. Visitor opens WebSocket connection
4. Token validated through cache
5. Visitor joins room
6. Visitor sends message
7. Message saved to database
8. Notification broadcast to admins
9. Admin joins room
10. Real-time communication begins
11. Admin closes session
12. WebSocket disconnect event triggered
The platform architecture is designed with scalability and extensibility in mind, allowing future integration of advanced real-time communication features and distributed infrastructure components. Planned enhancements include Redis integration for shared state management and channel layers, horizontal scaling support for handling increased concurrent connections, message delivery acknowledgements, user presence tracking, read receipts, secure file attachments, end-to-end message encryption, and AI-assisted support automation.
These improvements aim to increase system reliability, scalability, and user experience while preparing the platform for production-grade workloads and enterprise-level support operations. The long-term objective is to transform the system from a basic real-time chat service into a fully distributed customer communication platform capable of intelligent automation and high-availability deployment scenarios. Because no chat platform remains “just a chat platform” for long. Eventually someone in a meeting says, “Can we add AI support?” and three weeks later the team is debugging why the assistant confidently invented refund policies at 3 AM. A remarkably stable pattern in software engineering history.
This project is intended for educational, internal, and scalable real-time communication systems.