Single input not updating multiple outputs

Hi.
I’m new here and this is my first post.

I’m trying to write an app where I can upload a file and, as a consequence, the options in a dropdown menu are updated. From the guide I had understood that writing two callback functions would make it, but there is something I’m not getting.

#!/usr/bin/env python

import dash
import dash_core_components as dcc
import dash_html_components as html
from dash.dependencies import Input, Output, State

app = dash.Dash()

app.layout = html.Div([
        # Upload area
        dcc.Upload(
            id='upload-data',
            children=html.Div([ 'Drag and Drop or ', html.A('Select File')]),
            multiple=False
        ),
        html.Div(id='output-data-upload'),
        html.Div([
            html.Label('Column names', style={'textAlign': 'center'}),
            dcc.Dropdown(id='col-names')
            ])
    ])


@app.callback(Output('output-data-upload', 'children'),
              [Input('upload-data', 'contents'),
               Input('upload-data', 'filename')])
def update_upload_data(content, filename):
    if content is not None:
        return html.Div([
            html.H5(filename)
        ])


@app.callback(Output('col-names', 'options'),
              [Input('upload-data', 'contents'),
               Input('upload-data', 'filename')])
def update_pred_target(content, filename):
    if content is not None:
        options = [{'label': 'a', 'value': 'A'}, {'label': 'b', 'value': 'B'}]
        return options


if __name__ == '__main__':
    app.run_server(debug=True)

When I run the code above, something strange happens. At first, when I select the file to upload, dropdown is not updated. Rather, an undo button appears on the bottom left. If I click it, a redo button appears. I click it, and then the filename is displayed and the dropdown is updated.

Any idea?

Try this instead:

@app.callback(Output('col-names', 'options'),
              [Input('upload-data', 'contents'),
               Input('upload-data', 'filename')])
def update_pred_target(content, filename):
    if content is not None:
        options = [{'label': 'a', 'value': 'A'}, {'label': 'b', 'value': 'B'}]
        return options
    return []

without the return [], the dropdown’s options is getting updated to None, which I believe might through an error

Great!

Interesting that the error thrown is completely silent.

Many thanks for the support you gave, and for all the support I’ve seen you give on this forum.

In [WIP] Dash dev tools by rmarren1 · Pull Request #64 · plotly/dash-renderer · GitHub, we’re actually exposing the error in the fron end (an error isn’t actually slient, it’s just getting printed in the javascript console. That PR will display javascript errors to the user.)

and in https://github.com/plotly/dash/pull/340, we’re adding backend validation to the properties, so we’ll raise an error if options isn’t a list.

1 Like