It seems like multiple outputs don’t work when the input component is defined in another file.
A MWE is below. The index’s layout contains a hidden div that stores a list of city names. This list is used in app1.py to populate two dropdowns. The case of having two callbacks in app1.py, each updating its dropdown, works. The case of having a single callback that updates two dropdowns does not.
Is it a bug?
app.py:
import dash
app = dash.Dash(__name__)
app.config.suppress_callback_exceptions = True
index.py:
import dash_core_components as dcc
import dash_html_components as html
from dash.dependencies import Input, Output
from app import app
import app1
cities = ["Toronto", "Montreal", "Vancouver", "New York", "Austin", "Los Angeles"]
app.layout = html.Div([
dcc.Location(id='url', refresh=False),
html.Div(id='cities_div', style={'display': 'none'}, children=cities),
html.Div(id='page-content'),
])
@app.callback(Output('page-content', 'children'),
[Input('url', 'pathname')])
def display_page(pathname):
if pathname == '/':
return app1.layout
else:
return '404'
if __name__ == '__main__':
app.run_server(debug=True)
app1.py:
import dash_core_components as dcc
import dash_html_components as html
from dash.dependencies import Input, Output
from app import app
layout = html.Div([
dcc.Dropdown(
id='ca_city_dropdown',
options=[],
value=None,
),
dcc.Dropdown(
id='us_city_dropdown',
options=[],
value=None,
),
])
# ------------- Single callback with multiple outputs does not work -------------
# @app.callback(
# [Output('ca_city_dropdown', 'options'),
# Output('us_city_dropdown', 'options')],
# [Input('cities_div', 'children')]) # this Div is in index.py
# def display_cities(cities):
# ca_cities = [{'label': i, 'value': i} for i in cities[:3]]
# us_cities = [{'label': i, 'value': i} for i in cities[3:]]
# return [ca_cities, us_cities]
# ------------- Separate callbacks work -------------
@app.callback(
Output('ca_city_dropdown', 'options'),
[Input('cities_div', 'children')]) # this Div is in index.py
def display_ca_cities(cities):
return [{'label': i, 'value': i} for i in cities[:3]]
@app.callback(
Output('us_city_dropdown', 'options'),
[Input('cities_div', 'children')]) # this Div is in index.py
def display_us_cities(cities):
return [{'label': i, 'value': i} for i in cities[3:]]