Я пытаюсь использовать обратные вызовы для обновления источника данных в графике боке, запущенном на сервере боке, встроенном в приложение Flask. Я получаю сообщение об ошибке, когда пытаюсь изменить период с помощью виджета выбора периода. Моя ошибка:
ERROR:bokeh.server.protocol_handler:error handling message
message: Message 'PATCH-DOC' content: {'events': [{'kind': 'ModelChanged', 'model': {'id': '1166'},
'attr': 'value', 'new': '2y'}], 'references': []}
error: UnboundLocalError("local variable 'current_feature' referenced before assignment")
Traceback (most recent call last):
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\server\protocol_handler.py", line 90, in handle
work = await handler(message, connection)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\server\session.py", line 67, in _needs_document_lock_wrapper
result = func(self, *args, **kwargs)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\server\session.py", line 261, in _handle_patch
message.apply_to_document(self.document, self)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\protocol\messages\patch_doc.py", line 100, in apply_to_document
doc._with_self_as_curdoc(lambda: doc.apply_json_patch(self.content, setter))
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\document\document.py", line 1150, in _with_self_as_curdoc
return f()
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\protocol\messages\patch_doc.py", line 100, in <lambda>
doc._with_self_as_curdoc(lambda: doc.apply_json_patch(self.content, setter))
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\document\document.py", line 411, in apply_json_patch
patched_obj.set_from_json(attr, value, models=references, setter=setter)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\core\has_props.py", line 341, in set_from_json
descriptor.set_from_json(self, json, models, setter)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\core\property\descriptors.py", line 612, in set_from_json
models, setter)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\core\property\descriptors.py", line 321, in set_from_json
self._internal_set(obj, json, setter=setter)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\core\property\descriptors.py", line 763, in _internal_set
self._real_set(obj, old, value, hint=hint, setter=setter)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\core\property\descriptors.py", line 832, in _real_set
self._trigger(obj, old, value, hint=hint, setter=setter)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\core\property\descriptors.py", line 909, in _trigger
obj.trigger(self.name, old, value, hint, setter)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\model.py", line 661, in trigger
super().trigger(attr, old, new, hint=hint, setter=setter)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\util\callback_manager.py", line 157, in trigger
self._document._notify_change(self, attr, old, new, hint, setter, invoke)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\document\document.py", line 1042, in _notify_change
self._trigger_on_change(event)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\document\document.py", line 1132, in _trigger_on_change
self._with_self_as_curdoc(event.callback_invoker)
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\document\document.py", line 1150, in _with_self_as_curdoc
return f()
File "c:\users\grego\onedrive\projects\python projects\ey\eyflask_virtualenv\eyvenv\lib\site-packages\bokeh\util\callback_manager.py", line 155, in invoke
callback(attr, old, new)
File "C:\Users\grego\Documents\GitHub\EY-DashboardV2\EYvenv\app\routes.py", line 120, in update_plot
'y' : new_data[current_feature]
UnboundLocalError: local variable 'current_feature' referenced before assignment
Кажется, что-то с переменными областями действия. Я просто не понимаю, как я могу ссылаться на переменную current_feature до того, как инициализирую ее? Любая помощь приветствуется.
Код вопроса:
def create_stocks_graph(doc):
feature_names = ['Open', 'High', 'Low', 'Close']
periods = ['1d','5d','1mo','3mo','6mo','1y','2y','5y','10y','ytd','max']
default_period = 'ytd'
default_feature = 'Close'
current_feature = default_feature # keep this
data = companyObject.getHistoricalPricesDf(period=default_period)
source = ColumnDataSource(data={
'x' : data.index,
'y' : data['Close']
})
p = figure(title=f"Stocks at {default_feature} for past {default_period}",
x_axis_label='Date',
y_axis_label=default_feature,
tools="pan,wheel_zoom,reset",
plot_width=600,
plot_height=600,
x_axis_type="datetime")
# x ticks
data.index = pd.to_datetime(data.index)
data.index.name = 'Date'
data.sort_index(inplace=True)
x_ticks = [d.strftime("%m/%d/%Y)")[:-1] for d in data.index.date]
# make graph
p.line('x', 'y', legend_label="Stock Price", line_width=2, source=source)
def update_plot(attr, old, new):
if new in feature_names:
print('updating feature')
print('old:', old)
print('new:', new)
current_feature = new
source.data['y'] = data[new]
else:
# get new data and update x ticks
print('updating period')
print('old:', old)
print('new:', new)
new_data = companyObject.getHistoricalPricesDf(period=new)
new_data.index = pd.to_datetime(new_data.index)
new_data.index.name = 'Date'
new_data.sort_index(inplace=True)
x_ticks = [d.strftime("%m/%d/%Y)")[:-1] for d in new_data.index.date]
source.data = {
'x' : new_data.index,
'y' : new_data[current_feature]
}
# add selects
period_select = Select(title="Period", value=default_period, options=periods)
feature_select = Select(title="Feature", value=default_feature, options=feature_names)
period_select.on_change("value", update_plot) # update period
feature_select.on_change("value", update_plot) # update feature
doc.add_root(layout(
[feature_select, period_select],
[p]))