Unhandled exception in application causes all later sessions to fail
See original GitHub issueThe problem
In a “bokeh serve” application, if there is an unhandled exception in the main code, all new sessions after the exception do not work.
Background: https://groups.google.com/a/continuum.io/forum/#!topic/bokeh/BZpiJJ4TO2M
Expected behaviour
The preferred behaviour would be that an unhandled exception would only affect the session that caused the exception, and sessions started later would continue to work. Other frameworks typically isolate exceptions so that if a request causes an exception, only that request is affected.
Versions
Bokeh: 0.13.0 Python: 3.5.2
Example application
The below example application is copied from https://bokeh.pydata.org/en/latest/docs/user_guide/server.html#single-module-format, except it raises an exception in 33% of new sessions.
To duplicate the issue, do:
- Run “bokeh serve myapp.py”
- Open a browser to http://localhost:5006/boom. If you don’t see “Exception: boom!” in the console, you can click the “Press Me” button to see numbers appear.
- Refresh the page until you see “Exception: boom!” in the console. The Bokeh app won’t appear in the browser.
- Refresh the page again. The app still doesn’t appear. This demonstrates that later sessions are affected.
- Restart the server and refresh the page. If the exception isn’t raised, the app will load. It will work until a new session triggers the exception.
# myapp.py
from random import random
from bokeh.layouts import column
from bokeh.models import Button
from bokeh.palettes import RdYlBu3
from bokeh.plotting import figure, curdoc
# create a plot and style its properties
p = figure(x_range=(0, 100), y_range=(0, 100), toolbar_location=None)
p.border_fill_color = 'black'
p.background_fill_color = 'black'
p.outline_line_color = None
p.grid.grid_line_color = None
# add a text renderer to our plot (no data yet)
r = p.text(x=[], y=[], text=[], text_color=[], text_font_size="20pt",
text_baseline="middle", text_align="center")
i = 0
ds = r.data_source
# create a callback that will add a number in a random location
def callback():
global i
# BEST PRACTICE --- update .data in one step with a new dict
new_data = dict()
new_data['x'] = ds.data['x'] + [random()*70 + 15]
new_data['y'] = ds.data['y'] + [random()*70 + 15]
new_data['text_color'] = ds.data['text_color'] + [RdYlBu3[i%3]]
new_data['text'] = ds.data['text'] + [str(i)]
ds.data = new_data
i = i + 1
# add a button widget and configure with the call back
button = Button(label="Press Me")
button.on_click(callback)
boom = random()
print(boom)
if boom < 0.3333:
raise Exception('boom!')
# put the button and plot in a layout and add to the document
curdoc().add_root(column(button, p))
Example console output:
(venv) $ bokeh serve myapp.py
2018-06-27 12:59:45,343 Starting Bokeh server version 0.13.0 (running on Tornado 5.0.1)
2018-06-27 12:59:45,345 Bokeh app running at: http://localhost:5006/myapp
2018-06-27 12:59:45,345 Starting Bokeh server with process id: 13979
0.5604607908584933
2018-06-27 13:00:06,274 200 GET /myapp (::1) 96.25ms
2018-06-27 13:00:06,437 101 GET /myapp/ws?bokeh-protocol-version=1.0&bokeh-session-id=OxhSy81ZBM8URWfk6wp7OTH7bTictF12u6pI8o7fkIUs (::1) 0.64ms
2018-06-27 13:00:06,437 WebSocket connection opened
2018-06-27 13:00:06,438 ServerConnection created
0.6452850662545722
0.2762922805351794
2018-06-27 13:00:11,120 Error running application handler <bokeh.application.handlers.script.ScriptHandler object at 0x7feae4861a58>: boom!
File "myapp.py", line 46, in <module>:
raise Exception('boom!') Traceback (most recent call last):
File "/home/matt/Clients/QEye/venv/lib/python3.5/site-packages/bokeh/application/handlers/code_runner.py", line 163, in run
exec(self._code, module.__dict__)
File "/home/matt/Clients/QEye/isolate/myapp.py", line 46, in <module>
raise Exception('boom!')
Exception: boom!
2018-06-27 13:00:11,125 200 GET /myapp (::1) 25.45ms
2018-06-27 13:00:11,132 WebSocket connection closed: code=1001, reason=None
2018-06-27 13:00:11,207 101 GET /myapp/ws?bokeh-protocol-version=1.0&bokeh-session-id=Y5IlTpoIxVs42drth0tKZonyuwGnUNM3zKK6OAG5eg6n (::1) 0.60ms
2018-06-27 13:00:11,208 WebSocket connection opened
2018-06-27 13:00:11,208 ServerConnection created
Issue Analytics
- State:
- Created 5 years ago
- Comments:12 (11 by maintainers)
Top GitHub Comments
sorry - I meant main.py it’s getting a bit late here, so I’m no longer fully operational 😉
For me, it definitely remains dead after the first exception this time.
Anyhow, this simply means I will need to upgrade to bokeh 1.2.0 (I just have some coffescript extension I need to migrate …) Thanks for the help!
@ltalirz I am not sure why that works at all. Directory style apps are required to have a
main.py
(that is what the sever looks for). If that works at all withmyapp.py
I think it is unintentional/accidental👍