Render HTML Elements Clientside Callback

I am using WebSockets with clientside callbacks.

How would I render this Python code client side so it would not require a post to the server?

        stock = data['stock']
        price = html.H1(data['price'])
        diff = html.H4(dbc.Badge(data['diff'], color="danger" if '-' in data[
            'diff'] else 'success', className="mr-1"))
        content = dbc.Row([dbc.Col([price]), dbc.Col([diff])])

If needed my imports are below

from dash_extensions import WebSocket
import dash
from dash.dependencies import ClientsideFunction, Input, Output
from dash import html
import dash_bootstrap_components as dbc
1 Like

For anyone who ever goes down this road… You are able to access the underlying js libraries directly; however, I did not find any documentation so spent a lot of time interrogating the different libraries. You can then use React to render the components. Here’s a sample of what I did to keep everything client side. Truly this is only very useful if you using WebSockets or very expensive DOM operations. The issue is my DOM was not expensive but to render this server-side would require a POST back with the data. My dashboard is receiving over 100 events a second and that wasn’t going to work.

    let stock = data.stock;
    let time = data.time;
    let price = window.dash_html_components.H1({"children": data.price});
    let color = "success"
    if (data.diff.includes("-")) {
        color = "danger";
    }
    let diff = window.dash_bootstrap_components.Badge({
        "children": data.diff,
        "color": color,
        "className": "mr-1"
    })
    let content = window.dash_bootstrap_components.Row({
        "children": [window.dash_bootstrap_components.Col({
            "key": "price",
            "children": price
        }), window.dash_bootstrap_components.Col({
            "key": "diff",
            "children": diff
        })]
    });
    ReactDOM.render(content, document.getElementById(stock));
1 Like

This is what i have been doing recently after the release of dash 2.0, trying to convert all my callbacks to the clientside_callbacks which dramatically increased my app’s performance.

Assuming you have a html.Div(id=‘stock’) as Ouput component and a dcc.Store(id=‘data’,data={ ‘stock’ : [ ], ‘price’ : [ ], ‘diff’: [ ] }) as Input this method makes the callback run on client side. For more info check this

app.clientside_callback(
'''
function update_div(data){
    let stock = data['stock']
    let price = {'props':
                    {'children':data['price']},
                'type':'H1',
                'namespace':'dash_html_components'}

    let color = "success"
    if (data.diff.includes("-")) {
        color = "danger";
    }
    let diff = {'props':{
                    'children': {
                        'props':{
                            'children':data['diff'],
                            'color':color,
                            'className':"mr-1"
                        },
                        'type':'Badge',
                        'namespace':'dash_bootstrap_components'
                    }

                },
                'type':'H4',
                'namespace':'dash_html_components'}
    let content = {'props':{
                        'children':[
                            {
                                'props':{
                                    'children':[price]
                                },
                                'type':'Col',
                                'namespace':'dash_bootstrap_components'
                            },

                            {
                                'props':{
                                    'children':[diff]
                                },
                                'type':'Col',
                                'namespace':'dash_bootstrap_components'
                            }
                        ]

                    },
                    'type':'Row',
                    'namespace':'dash_bootstrap_components'
                }
    
    return content
}
'''
Output('stock','children'),
Input('data','value'),
)
3 Likes

Thank you! This is even cleaner!

Agree 100% – love the client-side callbacks. I’m able to render hundreds of events a second, which is incredible.

1 Like