Quickstart

This quickstart assumes you have a Django and React application, and on Django side you already have a serializer.

Install RxDjango

Start by installing RxDjango

pip install rxdjango

RxDjango depends on daphne and channels. Add all these to INSTALLED_APPS, make sure rxdjango comes before daphne, and both come before django.contrib.staticfiles.

INSTALLED_APPS = [
    # rxdjango must come before daphne, and both before contrib.staticfiles

    'rxdjango',
    'daphne',
    'django.contrib.staticfiles',

    # these can come anywhere
    'channels',
]

Configure ASGI and Redis

Set the ASGI_APPLICATION variable

ASGI_APPLICATION = 'your_project.asgi.application'

RxDjango depends on Redis for messaging. Configure REDIS_URL.

REDIS_URL = f'redis://127.0.0.1:6379/0'

Configure MongoDB for Caching

RxDjango comes with a native cache system using MongoDB.

MONGO_URL = 'mongodb://localhost:27017/'
MONGO_STATE_DB = 'hot_state'

Configure Frontend Code Generation

RxDjango automatically generates Typescript interfaces and classes for the frontend based on the backend classes. You need to configure a directory in your frontend code and the websocket url of your application.

RX_FRONTEND_DIR = os.path.join(BASE_DIR, '../frontend/src/app/modules')
RX_WEBSOCKET_URL = "http://localhost:8000/ws"

Create a ContextChannel

This quickstart assumes you already have models and serializers.ModelSerializer class, most likely a nested serializer.

Create a channels.py file, and create a rxdjango.channels.ContextChannels subclass.

from rxdjango.channels import ContextChannel
from myapp.serializers import MyNestedSerializer


class MyContextChannel(ContextChannel):

    class Meta:
        state = MyNestedSerializer()

    @staticmethod
    def has_permission(self, user, instance):
        # check if user has permission on instance
        return True

Set Up WebSocket Routing

Create a route for this channel in asgi.py:

from myapp.channels import MyContextChannel

websocket_urlpatterns = [
    path('ws/myapp/<str:mymodel_id>/', MyContextChannel.as_asgi()),
]

application = ProtocolTypeRouter({
    "http": app,
    "websocket": URLRouter(
        websocket_urlpatterns
    ),
})

Generate Frontend Files

Run the makefrontend command to generate interfaces matching your serializer and a MyContextChannel class in the frontend.

python manage.py makefrontend

Alternatively, you can pass –makefrontend option to runserver command during development, so frontend files are automatically generated on changes.

python manage.py runserver --makefrontend

Check the files generated inside your modules app. There are interfaces matching your serializer, and a MyContextChannel class on the frontend which provides an API to access the backend ContextChannel.

Install RxDjango on the Frontend

RxDjango provides the @rxdjango/react library for frontend integration. Install it using or your preferred package manager, this example uses yarn:

yarn add @rxdjango/react

Connect the Frontend State

On your frontend code, link the state of your page with MyContextChannel. The token variable is the token from rest_framework.authtoken.models.Token, the only supported authentication method for now.

import { MyContextChannel } from 'app/modules/myapp.channels';
import { useChannelState } from '@rxdjango/react';

const channel = new MyContextChannel(mymodelId, token);
const state = useChannelState(channel);

That’s it! Now:

  • The state variable in the frontend automatically updates when the database changes.

  • Data is serialized and cached as flat dictionaries.

  • Signals broadcast updates to connected clients and MongoDB cache.

  • The nested instance is reconstructed on the frontend.

For the signals to work, make sure you use instance.save(), live updates won’t work if you use YourModel.objects.update().