Search code examples
pythonbootstrap-4plotlyplotly-dash

how to resolve this Duplicate callback outputs error in Dash ploty


In the callback for output(s): page-content.children Output 0 (page-content.children) is already in use. Any given output can only have one callback that sets it. To resolve this situation, try combining these into one callback function, distinguishing the trigger by using dash.callback_context if necessary.

I am getting the above error when I run the Dash app can anyone help me out with this.

This my layout part

   html.Div([
        dbc.Row(
            [
                dbc.Col(dbc.NavbarBrand(dcc.Link(
                    html.Button(children='HOME',
                                style={
                                    'marginLeft': '100px',
                                    'marginRight': 'auto',
                                    'display': 'inline-block',
                                    'align': 'center', 'color': 'white'}, ),

                    href='/', refresh=True))),
                dbc.Col(dbc.NavbarBrand(dcc.Link(
                    html.Button(children='OVERVIEW',
                                style={'margin-left': '100px',
                                       'margin-right': 'auto', 'color': 'white', 'align': 'center'
                                       }),
                    href='/apps/overview', refresh=True))),
                dbc.Col(dbc.NavbarBrand(dcc.Link(
                    html.Button(children='GRAPH',
                                style={'marginLeft': '100px',
                                       'marginRight': 'auto', 'color': 'white', 'align': 'center'
                                       }),
                    href='/apps/graph_page', refresh=True))),
                dbc.Col(dbc.NavbarBrand(dcc.Link(
                    html.Button(children='CONSOLE',
                                style={'marginLeft': '100px',
                                       'marginRight': 'auto', 'color': 'white', 'align': 'center'
                                       }),
                    href='/log_stream', refresh=True))),
            ],
            style={
                'height': 'auto',
                'width': 'auto',
                'background-color': '#101820',
                'align-items': 'center',
                'diplay': 'flex',
            },
            align="center",
            no_gutters=True,
        ),
        dcc.Location(id='url', refresh=False),
        html.Div(id='page-content', children=[])
    ]),
    html.Div([
                dcc.Dropdown(
                    id='demo-dropdown',
                    options=[
                        {'label': 'Dummy', 'value': 0},
                        {'label': 'CAN', 'value': 1},
                    ],
                    placeholder="Select a Mode",
                    searchable=False
                ),
                html.Div(id='dd-output-container')
            ])
])

These are my callbacks

@app.callback(
    Output('dd-output-container', 'children'),
    Input('demo-dropdown', 'value'))
def update_output(value):
    return 'You have selected "{}"'.format(value)


@app.callback(Output(component_id='page-content', component_property='children'),
              (Input(component_id='url', component_property='pathname')))
def display_page(pathname):
    if pathname == '/apps/graph_page':
        return graph_page.layout
    elif pathname == '/apps/overview':
        return overview.layout


Thank you in advance.


Solution

  • It is no longer necessary to eliminate duplicate callback outputs. From Dash 2.9, they are supported with the following modifications:

    • set allow_duplicate = True in your Output
    • set prevent_initial_call = True in your callbacks
    • set prevent_initial_callbacks = True in your app instantiation

    Final code:

    @app.callback(
      Output(component_id = 'page-content', component_property = 'children', allow_duplicate = True),
      (Input(component_id = 'url', component_property = 'pathname')),
      prevent_initial_call = True
    )
    

    And in your entry point file:

    app = Dash(
      __name__,
      prevent_initial_callbacks = True
    )
    

    See this article for more info: https://dash.plotly.com/duplicate-callback-outputs.