Hello,
Upon clicking a link using (dcc.link) in my app, I get the below error and then immediately get taken back to the page I was on previously. In order to get to this certain page, I have to actually type in the page URL in the address bar of my browser. Here is the code of the error:
Cannot read properties of undefined (reading 'getRef')
TypeError: Cannot read properties of undefined (reading 'getRef')
at n.value (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash_design_kit/dash_design_kit.v1_6_7m1677006696.min.js:17:6158888)
at https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash_design_kit/dash_design_kit.v1_6_7m1677006696.min.js:17:6159129
at updateContextConsumer (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash/deps/react-dom@16.v2_8_0m1677006696.14.0.js:18439:21)
at beginWork (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash/deps/react-dom@16.v2_8_0m1677006696.14.0.js:18796:16)
at HTMLUnknownElement.callCallback (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash/deps/react-dom@16.v2_8_0m1677006696.14.0.js:182:16)
at Object.invokeGuardedCallbackDev (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash/deps/react-dom@16.v2_8_0m1677006696.14.0.js:231:18)
at invokeGuardedCallback (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash/deps/react-dom@16.v2_8_0m1677006696.14.0.js:286:33)
at beginWork$1 (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash/deps/react-dom@16.v2_8_0m1677006696.14.0.js:23338:9)
at performUnitOfWork (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash/deps/react-dom@16.v2_8_0m1677006696.14.0.js:22292:14)
at workLoopSync (https://dash.dsa.corp.amway.net/Workspaces/view/demand-forecast-stats-models/_dash-component-suites/dash/deps/react-dom@16.v2_8_0m1677006696.14.0.js:22265:24)
Here is the code to that specific page of the app:
dash.register_page(__name__,
path = '/pages/hierarchy_walk')
os.environ["GOOGLE_APPLICATION_CREDENTIALS"]="/workspace/service_key.json"
plotly_template = pio.templates["plotly_dark"]
##################################################################################################################################
#Pull The Data
##################################################################################################################################
months = {1:'Jan', 2:'Feb', 3:'Mar', 4:'Apr', 5:'May', 6:'Jun', 7:'Jul', 8:'Aug', 9:'Sep', 10:'Oct', 11:'Nov', 12:'Dec'}
query = """SELECT a.*,
b.* EXCEPT (ord_base7, dmand_yr_mo, snapshot, location_type, oper_cntry_id, ord_qty, sales_dollars, residual, ts_preds, preds),
b.preds as promo_regression_preds
FROM `gcp-sc-demand-plan-analytics.Modeling_Output.monthly_best_ts_predictions` a
left join `gcp-sc-demand-plan-analytics.Modeling_Output.promo_bayesian_regression` b
on a.ord_base7 = b.ord_base7
and a.dmand_yr_mo = b.dmand_yr_mo
and a.location_type = b.location_type
and a.snapshot = b.snapshot
"""
client = bigquery.Client(project="gcp-sc-demand-plan-analytics")
query_job = client.query(
query,
# Location must match that of the dataset(s) referenced in the query.
location="US",
) # API request - starts the query
df = query_job.to_dataframe()
df['dmand_month'] = pd.to_datetime(df['dmand_yr_mo']).dt.month
df['months'] = df['dmand_month'].map(months)
df.loc[:, 'price'] = df.loc[:, 'sales_dollars']/df.loc[:, 'ord_qty']
df.loc[:, 'predicted_sales'] = np.round(df.loc[:, 'ts_preds']*df.loc[:, 'price'])
df.loc[:, 'diff'] = np.round(np.abs(np.round(df.loc[:, 'predicted_sales'] - df.loc[:, 'sales_dollars'],2)))
df.loc[:, 'snapshot'] = df.loc[:, 'snapshot'].dt.strftime('%Y-%m-%d')
df.loc[:, 'model'] = 'base_model'
query_job = client.query(
query,
# Location must match that of the dataset(s) referenced in the query.
location="US",
) # API request - starts the query
df1 = query_job.to_dataframe()
df1['dmand_month'] = pd.to_datetime(df1['dmand_yr_mo']).dt.month
df1['months'] = df1['dmand_month'].map(months)
df1.loc[:, 'price'] = df1.loc[:, 'sales_dollars']/df1.loc[:, 'ord_qty']
df1.loc[:, 'predicted_sales'] = np.round(((df1.loc[:, 'ts_preds']+df1.loc[:, 'promo_regression_preds'])*df1.loc[:, 'price']))
df1.loc[:, 'diff'] = np.round(np.abs(np.round(df1.loc[:, 'predicted_sales'] - df1.loc[:, 'sales_dollars'],2)))
df1.loc[:, 'snapshot'] = df1.loc[:, 'snapshot'].dt.strftime('%Y-%m-%d')
df1.loc[:, 'model'] = 'bayesian_promo_regression'
print(df1.head())
df_final = pd.concat([df, df1])
snapshot = list(df_final['snapshot'].unique())
location = list(df_final['location_type'].unique())
model = list(df_final['model'].unique())
##################################################################################################################################
#Start the Layout
#Documents: https://dash.dsa.corp.amway.net/Docs/dash-design-kit/migrating
##################################################################################################################################
money = dash_table.FormatTemplate.money(0)
money_cols = ['sales_dollars']
percentage = dash_table.FormatTemplate.percentage(0)
percentage_cols = ['MAPE', 'MAPE_CONTRIBUTION', 'BIAS', 'sales_pct']
# app = dash.Dash(__name__)
layout = ddk.App(show_editor=True, children = [
ddk.Block(
#width = 99,
children=[
ddk.ControlCard(
[ddk.CardHeader(title="Location Type/Model Choice"),
ddk.ControlItem(children=[
dcc.Dropdown(
options = [{'label':i, 'value':i}
for i in ['home_delivery', 'shop_sales']
],
multi=False,
value = 'home_delivery',
id='location_dropdown',
),
dcc.Dropdown(
options = [{'label':i, 'value':i}
for i in model
],
multi=False,
value = 'base_model',
id='model_dropdown'
)
],
)]
),
ddk.Card(children =[
ddk.Graph(
id='Business_Line'
)
]),
]
),
ddk.Block(
width = 100,
children=[
ddk.CardHeader(title="Forecast Data Tables"),
ddk.Card(
width=100,
children=[ddk.DataTable(id="bl_table",
columns=[],
data=[],
filter_action = 'native',
sort_action = 'native')
]
),
ddk.Card(
width=100,
children=[
ddk.DataTable(id='cat_table',
columns = [],
data = [],
filter_action = 'native',
sort_action = 'native',)
]
),
ddk.Card(
width=100,
children=[
ddk.DataTable(id='subcat_table',
columns = [],
data = [],
filter_action = 'native',
sort_action = 'native',
),
]
),
ddk.Card(
width=100,
children=[
ddk.DataTable(id='item_table',
columns = [],
data = [],
filter_action = 'native',
sort_action = 'native',
),
]
)
]
)
]
)
#CONTROL THE BUSINESS LINE GRAPH
@callback(
dash.dependencies.Output('Business_Line', 'figure'),
dash.dependencies.Input('model_dropdown', 'value'),
dash.dependencies.Input('location_dropdown', 'value'),
)
def update_bl(model, location):
df1 = df_final[(df_final['location_type'] == location) & (df_final['model'] == model)]
bl = df1.groupby(['glbl_bus_ln_desc']).agg({'ord_qty':'sum',
'predictions':'sum',
'sales_dollars':'sum',
'predicted_sales':'sum',
'diff':'sum'}).reset_index()
bl.replace([np.inf, -np.inf], np.nan, inplace=True)
bl['sales_dollars'] = np.round(bl['sales_dollars'])
bl['predictions'] = np.round(bl['predictions'])
bl.dropna(inplace = True)
bl.loc[:, 'MAPE'] = np.round(bl.loc[:, 'diff']/ bl.loc[:, 'sales_dollars'], 4) * 100
bl.loc[:, 'BIAS'] = np.round((bl.loc[:,'predicted_sales']- bl.loc[:, 'sales_dollars'])/ bl.loc[:, 'sales_dollars'], 4) * 100
fig1 = go.Figure(data=[
go.Bar( name='MAPE', x=bl['glbl_bus_ln_desc'], y=bl['MAPE']),
go.Bar(name='BIAS', x=bl['glbl_bus_ln_desc'], y=bl['BIAS'])
])
fig1.update_layout(barmode='group', plot_bgcolor='rgb(0,0,0)',
title=go.layout.Title(
text=f"{location} MAPE AND BIAS",
font=dict(
family="Courier New, monospace",
size=22,
color="#111111"
)))
return fig1
#CONTROL THE BL TABLE
@callback(
Output('bl_table', 'data'),
Output('bl_table', 'columns'),
Input('location_dropdown', 'value'),
#look up ignore initial
#look up design kit
)
def filter_table_bl(location):
if location == 'home_delivery':
df1 = df[df['location_type']=='home_delivery'].copy()
else:
df1 = df[df['location_type']=='shop_sales'].copy()
bl = df1.groupby(['location_type', 'glbl_bus_ln_desc']).agg({'ord_qty':'sum',
'predictions':'sum',
'sales_dollars':'sum',
'predicted_sales':'sum',
'diff':'sum'}).reset_index()
bl.replace([np.inf, -np.inf], np.nan, inplace=True)
bl['sales_dollars'] = np.round(bl['sales_dollars'])
bl.loc[:, 'sales_pct'] = bl['sales_dollars']/bl['sales_dollars'].sum()
bl['predictions'] = np.round(bl['predictions'])
bl.dropna(inplace = True)
bl.loc[:, 'MAPE'] = bl.loc[:, 'diff']/ bl.loc[:, 'sales_dollars']
bl.loc[:, 'MAPE_CONTRIBUTION'] = bl.loc[:, 'sales_pct']*bl.loc[:, 'MAPE']/(bl.loc[:, 'sales_pct']*bl.loc[:, 'MAPE']).sum()
bl.loc[:, 'BIAS'] = np.round((bl.loc[:,'predicted_sales']- bl.loc[:, 'sales_dollars'])/ bl.loc[:, 'sales_dollars'], 4)
bl = bl[['location_type','glbl_bus_ln_desc', 'sales_dollars', 'sales_pct', 'MAPE', 'MAPE_CONTRIBUTION', 'BIAS']]
return bl.to_dict('records'), [{'id':c, 'name':c, 'type':'numeric', 'format': money} if c in money_cols else {'id':c, 'name':c, 'type':'numeric', 'format':percentage} if c in percentage_cols
else {'id':c, 'name':c} for c in bl.columns ]
@callback(
Output('cat_table', 'data'),
Output('cat_table', 'columns'),
Input('location_dropdown', 'value'),
Input('bl_table', 'active_cell'),
State('bl_table', 'data')
#look up ignore initial
#look up design kit
)
def filter_table_cat(location, active_cell, state_):
state_ = pd.DataFrame(state_)
print(state_)
cat = df.groupby(['location_type', 'glbl_bus_ln_desc', 'glbl_ctgry_desc']).agg({'ord_qty':'sum',
'predictions':'sum',
'sales_dollars':'sum',
'predicted_sales':'sum',
'diff':'sum'}).reset_index()
if ctx.triggered_id == 'location_dropdown':
filtered_df = cat[cat['location_type'] == location]
elif ctx.triggered_id == 'bl_table':
filtered_df = cat[(cat['glbl_bus_ln_desc'] == state_.iloc[active_cell['row'], active_cell['column']]) &
(cat['location_type'] == location)]
print(active_cell)
else:
filtered_df = cat
filtered_df.replace([np.inf, -np.inf], np.nan, inplace=True)
filtered_df['sales_dollars'] = np.round(filtered_df['sales_dollars'])
filtered_df['sales_pct'] = filtered_df.loc[:, 'sales_dollars']/filtered_df['sales_dollars'].sum()
filtered_df.loc[:, 'MAPE'] = np.round(filtered_df.loc[:, 'diff']/ filtered_df.loc[:, 'sales_dollars'],4)
filtered_df.loc[:, 'MAPE_CONTRIBUTION'] = filtered_df['sales_pct']*filtered_df.loc[:, 'MAPE']/(filtered_df['sales_pct']*filtered_df.loc[:, 'MAPE']).sum()
filtered_df.loc[:, 'BIAS'] = np.round((filtered_df.loc[:,'predicted_sales']- filtered_df.loc[:, 'sales_dollars'])/ filtered_df.loc[:, 'sales_dollars'], 4)
bl_category_table = filtered_df[['location_type','glbl_bus_ln_desc','glbl_ctgry_desc', 'sales_dollars', 'sales_pct', 'MAPE', 'MAPE_CONTRIBUTION', 'BIAS']]
data = filtered_df.to_dict('records')
return data, [{'id':c, 'name':c, 'type':'numeric', 'format': money} if c in money_cols else {'id':c, 'name':c, 'type':'numeric', 'format':percentage} if c in percentage_cols
else {'id':c, 'name':c} for c in bl_category_table.columns ]
@callback(
Output('subcat_table', 'data'),
Output('subcat_table', 'columns'),
Input('location_dropdown', 'value'),
Input('cat_table', 'active_cell'),
State('cat_table', 'data')
#look up ignore initial
#look up design kit
)
def filter_table_subcat(location, active_cell, state_):
state_ = pd.DataFrame(state_)
subcat = df.groupby(['location_type', 'glbl_bus_ln_desc', 'glbl_ctgry_desc', 'glbl_sub_ctgry_desc']).agg({'ord_qty':'sum',
'predictions':'sum',
'sales_dollars':'sum',
'predicted_sales':'sum',
'diff':'sum'}).reset_index()
if ctx.triggered_id == 'location_dropdown':
filtered_df = subcat[subcat['location_type'] == location]
elif ctx.triggered_id == 'cat_table':
filtered_df = subcat[(subcat['glbl_ctgry_desc'] == state_.iloc[active_cell['row'], active_cell['column']]) &
(subcat['location_type'] == location)]
print(active_cell)
print(subcat[subcat['glbl_ctgry_desc'] == state_.iloc[active_cell['row'], active_cell['column']]])
else:
filtered_df = subcat
filtered_df.replace([np.inf, -np.inf], np.nan, inplace=True)
filtered_df['sales_pct'] = filtered_df['sales_dollars']/filtered_df['sales_dollars'].sum()
filtered_df.loc[:, 'MAPE'] = np.round(filtered_df.loc[:, 'diff']/ filtered_df.loc[:, 'sales_dollars'],4)
filtered_df.loc[:, 'MAPE_CONTRIBUTION'] = filtered_df['sales_pct']*filtered_df.loc[:, 'MAPE']
filtered_df.loc[:, 'BIAS'] = np.round((filtered_df.loc[:,'predicted_sales']- filtered_df.loc[:, 'sales_dollars'])/ filtered_df.loc[:, 'sales_dollars'], 4)
filtered_df.loc[:, 'MAPE_CONTRIBUTION'] = filtered_df['sales_pct']*filtered_df.loc[:, 'MAPE']/(filtered_df['sales_pct']*filtered_df.loc[:, 'MAPE']).sum()
bl_subcategory_table = filtered_df[['location_type','glbl_bus_ln_desc', 'glbl_ctgry_desc', 'glbl_sub_ctgry_desc', 'sales_dollars', 'sales_pct', 'MAPE', 'MAPE_CONTRIBUTION', 'BIAS']]
data = filtered_df.to_dict('records')
return data, [{'id':c, 'name':c, 'type':'numeric', 'format': money} if c in money_cols else {'id':c, 'name':c, 'type':'numeric', 'format':percentage} if c in percentage_cols
else {'id':c, 'name':c} for c in bl_subcategory_table.columns ]
@callback(
Output('item_table', 'data'),
Output('item_table', 'columns'),
Input('location_dropdown', 'value'),
Input('subcat_table', 'active_cell'),
State('subcat_table', 'data')
#look up ignore initial
#look up design kit
)
def filter_table_item(location, active_cell, state_):
state_ = pd.DataFrame(state_)
item = df.groupby(['location_type', 'glbl_bus_ln_desc', 'glbl_ctgry_desc', 'glbl_sub_ctgry_desc', 'item_desc', 'ord_base7']).agg({'ord_qty':'sum',
'predictions':'sum',
'sales_dollars':'sum',
'predicted_sales':'sum',
'diff':'sum'}).reset_index()
if ctx.triggered_id == 'location_dropdown':
filtered_df = item[item['location_type'] == location]
elif ctx.triggered_id == 'subcat_table':
filtered_df = item[(item['glbl_sub_ctgry_desc'] == state_.iloc[active_cell['row'], active_cell['column']]) &
(item['location_type'] == location)]
print(active_cell)
print(item[item['glbl_ctgry_desc'] == state_.iloc[active_cell['row'], active_cell['column']]])
else:
filtered_df = item
filtered_df.replace([np.inf, -np.inf], np.nan, inplace=True)
filtered_df['sales_dollars'] = np.round(filtered_df['sales_dollars'])
filtered_df['sales_pct'] = filtered_df['sales_dollars']/filtered_df['sales_dollars'].sum()
filtered_df.loc[:, 'MAPE'] = np.round(filtered_df.loc[:, 'diff']/ filtered_df.loc[:, 'sales_dollars'],4)
filtered_df.loc[:, 'MAPE_CONTRIBUTION'] = filtered_df['sales_pct']*filtered_df.loc[:, 'MAPE']/(filtered_df['sales_pct']*filtered_df.loc[:, 'MAPE']).sum()
filtered_df.loc[:, 'BIAS'] = np.round((filtered_df.loc[:,'predicted_sales']- filtered_df.loc[:, 'sales_dollars'])/ filtered_df.loc[:, 'sales_dollars'], 4)
bl_item_table = filtered_df[['location_type','glbl_bus_ln_desc', 'glbl_ctgry_desc', 'glbl_sub_ctgry_desc', 'item_desc', 'ord_base7', 'sales_dollars', 'sales_pct',
'MAPE', 'MAPE_CONTRIBUTION', 'BIAS']]
data = filtered_df.to_dict('records')
return data, [{'id':c, 'name':c, 'type':'numeric', 'format': money} if c in money_cols else {'id':c, 'name':c, 'type':'numeric', 'format':percentage} if c in percentage_cols
else {'id':c, 'name':c} for c in bl_item_table.columns ]