示例#1
0
文件: __init__.py 项目: rbtr/bokeh
    def build_applications(self, args):
        if args.files:
            files = args.files
        else:
            files = []

        applications = {}

        for file in files:
            file = os.path.abspath(file)
            if os.path.isdir(file):
                handler = DirectoryHandler(filename=file)
            else:
                handler = ScriptHandler(filename=file)

            application = Application()
            application.add(handler)

            route = handler.url_path()
            if not route:
                if '/' in applications:
                    die("Don't know the URL path to use for %s" % (file))
                route = '/'
            applications[route] = application

        if len(applications) == 0:
            # create an empty application by default, used with output_server typically
            applications['/'] = Application()

        return applications
示例#2
0
    def test_pull_document(self):
        application = Application()
        def add_roots(doc):
            doc.add_root(AnotherModelInTestClientServer(bar=43))
            doc.add_root(SomeModelInTestClientServer(foo=42))
        handler = FunctionHandler(add_roots)
        application.add(handler)

        with ManagedServerLoop(application) as server:
            client_session = pull_session(session_id='test_pull_document',
                                          url=server.ws_url,
                                          io_loop=server.io_loop)
            assert len(client_session.document.roots) == 2

            server_session = server.get_session('/', client_session.id)
            assert len(server_session.document.roots) == 2

            results = {}
            for r in server_session.document.roots:
                if hasattr(r, 'foo'):
                    results['foo'] = r.foo
                if hasattr(r, 'bar'):
                    results['bar'] = r.bar
            assert results['foo'] == 42
            assert results['bar'] == 43

            client_session.close()
            client_session.loop_until_closed()
            assert not client_session.connected
示例#3
0
def test_application_doesnt_validate_document_due_to_env_var(check_integrity, monkeypatch):
    monkeypatch.setenv("BOKEH_VALIDATE_DOC", "false")
    a = Application()
    d = Document()
    d.add_root(figure())
    a.initialize_document(d)
    assert not check_integrity.called
示例#4
0
 def test_one_handler(self):
     a = Application()
     def add_roots(doc):
         doc.add_root(AnotherModelInTestApplication())
         doc.add_root(SomeModelInTestApplication())
     handler = FunctionHandler(add_roots)
     a.add(handler)
     doc = a.create_document()
     assert len(doc.roots) == 2
示例#5
0
def test_no_static_path():
    a = Application()
    def add_roots(doc):
        doc.add_root(AnotherModelInTestApplication())
        doc.add_root(SomeModelInTestApplication())
    def add_one_root(doc):
        doc.add_root(AnotherModelInTestApplication())
    handler = FunctionHandler(add_roots)
    a.add(handler)
    handler2 = FunctionHandler(add_one_root)
    a.add(handler2)
    assert a.static_path == None
示例#6
0
def test_excess_static_path():
    a = Application()
    def add_roots(doc):
        doc.add_root(AnotherModelInTestApplication())
        doc.add_root(SomeModelInTestApplication())
    def add_one_root(doc):
        doc.add_root(AnotherModelInTestApplication())
    handler = FunctionHandler(add_roots)
    handler._static = "foo"
    a.add(handler)
    handler2 = FunctionHandler(add_one_root)
    handler2._static = "bar"
    with pytest.raises(RuntimeError):
        a.add(handler2)
示例#7
0
    def test_lots_of_concurrent_messages(self, ManagedServerLoop) -> None:
        application = Application()
        def setup_stuff(doc):
            m1 = AnotherModelInTestClientServer(bar=43, name='m1')
            m2 = SomeModelInTestClientServer(foo=42, name='m2')
            m3 = SomeModelInTestClientServer(foo=68, name='m3')
            doc.add_root(m1)
            doc.add_root(m2)
            doc.add_root(m3)
            def timeout1():
                m1.bar += 1
            timeout1_cb_id = doc.add_timeout_callback(timeout1, 1)
            def timeout2():
                m2.foo +=1
            timeout2_cb_id = doc.add_timeout_callback(timeout2, 3)
            def periodic1():
                m1.bar += 1
                doc.remove_timeout_callback(timeout1_cb_id)
                doc.add_timeout_callback(timeout1, m1.bar % 7)
            doc.add_periodic_callback(periodic1, 3)
            def periodic2():
                m2.foo += 1
                doc.remove_timeout_callback(timeout2_cb_id)
                doc.add_timeout_callback(timeout2, m2.foo % 7)
            doc.add_periodic_callback(periodic2, 1)

            def server_on_change(event):
                if isinstance(event, ModelChangedEvent) and event.model is m3:
                    return
                m3.foo += 1

            doc.on_change(server_on_change)

        handler = FunctionHandler(setup_stuff)
        application.add(handler)

        # keep_alive_milliseconds=1 sends pings as fast as the OS will let us
        with ManagedServerLoop(application, keep_alive_milliseconds=1) as server:
            session = pull_session(session_id='test_lots_of_concurrent_messages',
                                   url=url(server),
                                   io_loop=server.io_loop)
            assert session.connected

            server_session = server.get_session('/', session.id)

            def client_timeout():
                m = session.document.roots[0]
                m.name = m.name[::-1]
            cb_id = session.document.add_timeout_callback(client_timeout, 3)

            def client_periodic():
                m = session.document.roots[1]
                m.name = m.name[::-1]
                session.document.remove_timeout_callback(cb_id)
                session.document.add_timeout_callback(client_timeout, 3)

            session.document.add_periodic_callback(client_periodic, 1)

            result = {}
            def end_test():
                result['connected'] = session.connected
                result['server_connection_count'] = server_session.connection_count
                result['server_close_code'] = next(iter(server._tornado._clients))._socket.close_code
                result['doc'] = session.document.to_json()
                session.close()

            # making this longer is more likely to trigger bugs, but it also
            # makes the test take however much time you put here
            session.document.add_timeout_callback(end_test, 250)

            def client_on_change(event):
                if not isinstance(event, TitleChangedEvent):
                    session.document.title = session.document.title[::-1]

            session.document.on_change(client_on_change)

            session._loop_until_closed()

            assert not session.connected

            # we should have still been connected at the end,
            # if we didn't have any crazy protocol errors
            assert 'connected' in result
            assert result['connected']

            # server should also still have been connected
            assert result['server_connection_count'] == 1
            assert result['server_close_code'] is None
示例#8
0
def test__lifecycle_hooks():
    application = Application()
    handler = HookTestHandler()
    application.add(handler)
    with ManagedServerLoop(application, check_unused_sessions_milliseconds=30) as server:
        # wait for server callbacks to run before we mix in the
        # session, this keeps the test deterministic
        def check_done():
            if len(handler.hooks) == 4:
                server.io_loop.stop()
        server_load_checker = PeriodicCallback(check_done, 1)
        server_load_checker.start()
        server.io_loop.start()
        server_load_checker.stop()

        # now we create a session
        client_session = pull_session(session_id='test__lifecycle_hooks',
                                      url=url(server),
                                      io_loop=server.io_loop)
        client_doc = client_session.document
        assert len(client_doc.roots) == 1

        server_session = server.get_session('/', client_session.id)
        server_doc = server_session.document
        assert len(server_doc.roots) == 1

        # we have to capture these here for examination later, since after
        # the session is closed, doc.roots will be emptied
        client_hook_list = client_doc.roots[0]
        server_hook_list = server_doc.roots[0]

        client_session.close()
        # expire the session quickly rather than after the
        # usual timeout
        server_session.request_expiration()

        def on_done():
            server.io_loop.stop()

        server.io_loop.call_later(0.1, on_done)

        server.io_loop.start()

    assert handler.hooks == ["server_loaded",
                             "next_tick_server",
                             "timeout_server",
                             "periodic_server",
                             "session_created",
                             "next_tick_session",
                             "modify",
                             "timeout_session",
                             "periodic_session",
                             "session_destroyed",
                             "server_unloaded"]

    assert handler.load_count == 1
    assert handler.unload_count == 1
    # this is 3 instead of 6 because locked callbacks on destroyed sessions
    # are turned into no-ops
    assert handler.session_creation_async_value == 3
    assert client_doc.title == "Modified"
    assert server_doc.title == "Modified"
    # only the handler sees the event that adds "session_destroyed" since
    # the session is shut down at that point.
    assert client_hook_list.hooks == ["session_created", "modify"]
    assert server_hook_list.hooks == ["session_created", "modify"]
示例#9
0
def test__existing_ioloop_with_multiple_processes_exception(ManagedServerLoop, event_loop) -> None:
    application = Application()
    loop = IOLoop.current()
    with pytest.raises(RuntimeError):
        with ManagedServerLoop(application, io_loop=loop, num_procs=3):
            pass
示例#10
0
    def invoke(self, args: argparse.Namespace) -> None:
        '''

        '''
        basicConfig(format=args.log_format, filename=args.log_file)

        # This is a bit of a fudge. We want the default log level for non-server
        # cases to be None, i.e. we don't set a log level. But for the server we
        # do want to set the log level to INFO if nothing else overrides that.
        log_level = settings.py_log_level(args.log_level)
        if log_level is None:
            log_level = logging.INFO
        logging.getLogger('bokeh').setLevel(log_level)

        if args.use_config is not None:
            log.info(f"Using override config file: {args.use_config}")
            settings.load_config(args.use_config)

        # protect this import inside a function so that "bokeh info" can work
        # even if Tornado is not installed
        from bokeh.server.server import Server

        files: List[str] = []
        for f in args.files:
            if args.glob:
                files.extend(glob(f))
            else:
                files.append(f)

        argvs = {f: args.args for f in files}
        applications = build_single_handler_applications(files, argvs)

        if len(applications) == 0:
            # create an empty application by default
            applications['/'] = Application()

        # rename args to be compatible with Server
        if args.keep_alive is not None:
            args.keep_alive_milliseconds = args.keep_alive

        if args.check_unused_sessions is not None:
            args.check_unused_sessions_milliseconds = args.check_unused_sessions

        if args.unused_session_lifetime is not None:
            args.unused_session_lifetime_milliseconds = args.unused_session_lifetime

        if args.stats_log_frequency is not None:
            args.stats_log_frequency_milliseconds = args.stats_log_frequency

        if args.mem_log_frequency is not None:
            args.mem_log_frequency_milliseconds = args.mem_log_frequency

        server_kwargs = {
            key: getattr(args, key)
            for key in [
                'port',
                'address',
                'unix_socket',
                'allow_websocket_origin',
                'num_procs',
                'prefix',
                'index',
                'keep_alive_milliseconds',
                'check_unused_sessions_milliseconds',
                'unused_session_lifetime_milliseconds',
                'stats_log_frequency_milliseconds',
                'mem_log_frequency_milliseconds',
                'use_xheaders',
                'websocket_max_message_size',
                'websocket_compression_level',
                'websocket_compression_mem_level',
                'include_cookies',
                'include_headers',
                'exclude_cookies',
                'exclude_headers',
                'session_token_expiration',
            ] if getattr(args, key, None) is not None
        }

        server_kwargs['sign_sessions'] = settings.sign_sessions()
        server_kwargs['secret_key'] = settings.secret_key_bytes()
        server_kwargs['ssl_certfile'] = settings.ssl_certfile(
            getattr(args, 'ssl_certfile', None))
        server_kwargs['ssl_keyfile'] = settings.ssl_keyfile(
            getattr(args, 'ssl_keyfile', None))
        server_kwargs['ssl_password'] = settings.ssl_password()
        server_kwargs['generate_session_ids'] = True
        if args.session_ids is None:
            # no --session-ids means use the env vars
            pass
        elif args.session_ids == 'unsigned':
            server_kwargs['sign_sessions'] = False
        elif args.session_ids == 'signed':
            server_kwargs['sign_sessions'] = True
        elif args.session_ids == 'external-signed':
            server_kwargs['sign_sessions'] = True
            server_kwargs['generate_session_ids'] = False
        else:
            raise RuntimeError(
                "argparse should have filtered out --session-ids mode " +
                args.session_ids)

        if server_kwargs['sign_sessions'] and not server_kwargs['secret_key']:
            die("To sign sessions, the BOKEH_SECRET_KEY environment variable must be set; "
                +
                "the `bokeh secret` command can be used to generate a new key."
                )

        if 'unix_socket' in server_kwargs:
            if server_kwargs['port'] != DEFAULT_SERVER_PORT:
                die("--port arg is not supported with a unix socket")
            invalid_args = [
                'address', 'allow_websocket_origin', 'ssl_certfile',
                'ssl_keyfile'
            ]

            if any(server_kwargs.get(x) for x in invalid_args):
                die(f"{invalid_args + ['port']} args are not supported with a unix socket"
                    )

        auth_module_path = settings.auth_module(
            getattr(args, 'auth_module', None))
        if auth_module_path:
            server_kwargs['auth_provider'] = AuthModule(auth_module_path)
        else:
            server_kwargs['auth_provider'] = NullAuth()

        server_kwargs['xsrf_cookies'] = settings.xsrf_cookies(
            getattr(args, 'enable_xsrf_cookies', False))
        server_kwargs['cookie_secret'] = settings.cookie_secret(
            getattr(args, 'cookie_secret', None))
        server_kwargs['use_index'] = not args.disable_index
        server_kwargs['redirect_root'] = not args.disable_index_redirect
        server_kwargs['autoreload'] = args.dev is not None
        server_kwargs['ico_path'] = settings.ico_path(
            getattr(args, 'ico_path', None))

        def find_autoreload_targets(app_path: str) -> None:
            path = os.path.abspath(app_path)
            if not os.path.isdir(path):
                return

            for path, _, files in os.walk(path):
                for name in files:
                    if (fnmatch(name, '*.html') or fnmatch(name, '*.css')
                            or fnmatch(name, '*.yaml')):
                        log.info("Watching: " + os.path.join(path, name))
                        watch(os.path.join(path, name))

        def add_optional_autoreload_files(file_list: List[str]) -> None:
            for filen in file_list:
                if os.path.isdir(filen):
                    log.warning("Cannot watch directory " + filen)
                    continue
                log.info("Watching: " + filen)
                watch(filen)

        if server_kwargs['autoreload']:
            if len(applications.keys()) != 1:
                die("--dev can only support a single app.")
            if server_kwargs['num_procs'] != 1:
                log.info("Running in --dev mode. --num-procs is limited to 1.")
                server_kwargs['num_procs'] = 1

            find_autoreload_targets(args.files[0])
            add_optional_autoreload_files(args.dev)

        applications = self.customize_applications(args, applications)
        server_kwargs = self.customize_kwargs(args, server_kwargs)

        with report_server_init_errors(**server_kwargs):
            server = Server(applications, **server_kwargs)

            if args.show:

                # we have to defer opening in browser until we start up the server
                def show_callback() -> None:
                    for route in applications.keys():
                        server.show(route)

                server.io_loop.add_callback(show_callback)

            # Server may not have a port when bound to a unix socket
            if server.port:
                address_string = 'localhost'
                if server.address is not None and server.address != '':
                    address_string = server.address

                if server_kwargs['ssl_certfile'] and (
                        server_kwargs['ssl_certfile'].endswith('.pem')
                        or server_kwargs['ssl_keyfile']):
                    protocol = 'https'
                else:
                    protocol = 'http'

                for route in sorted(applications.keys()):
                    url = f"{protocol}://{address_string}:{server.port}{server.prefix}{route}"
                    log.info("Bokeh app running at: %s" % url)

                log.info("Starting Bokeh server with process id: %d" %
                         os.getpid())
            server.run_until_shutdown()
示例#11
0
def run_server(filename, path='/', port=5000):
    apps = {path: Application(FunctionHandler(make_makedoc(filename)))}

    server = Server(apps, port=port, allow_websocket_origin=['*'])
    server.run_until_shutdown()
示例#12
0
def test_use_xheaders(ManagedServerLoop) -> None:
    application = Application()
    with ManagedServerLoop(application, use_xheaders=True) as server:
        assert server._http.xheaders == True
示例#13
0
 def test_address(self):
     loop = IOLoop()
     loop.make_current()
     server = Server(Application(), address='0.0.0.0')
     assert server.address == '0.0.0.0'
示例#14
0
文件: bokeh.py 项目: smcndiaye/dsl
                      y='Lon',
                      text='code',
                      level='glyph',
                      x_offset=5,
                      y_offset=5,
                      source=flight_source,
                      render_mode='canvas',
                      background_fill_color='red',
                      text_font_size="8pt")
    p.add_tile(STAMEN_TONER)
    p.circle('y',
             'x',
             source=flight_source,
             fill_color={
                 'field': 'country',
                 'transform': color_mapper
             },
             hover_color='yellow',
             size=10,
             fill_alpha=0.8,
             line_width=0.5)
    p.add_tools(my_hover)
    p.add_layout(labels)
    doc.title = 'REAL TIME FLIGHT TRACKING WITH PANDAS AND BOKEH'
    doc.add_root(p)


# SERVER CODE
apps = {'/': Application(FunctionHandler(flight_track))}
server = Server(apps, port=5000)  #define an unused port
server.start()
示例#15
0
文件: serve.py 项目: qwshy/bokeh
    def invoke(self, args):
        argvs = {f: args.args for f in args.files}
        applications = build_single_handler_applications(args.files, argvs)

        log_level = getattr(logging, args.log_level.upper())
        logging.basicConfig(level=log_level, format=args.log_format)

        if len(applications) == 0:
            # create an empty application by default, typically used with output_server
            applications['/'] = Application()

        if args.keep_alive is not None:
            if args.keep_alive == 0:
                log.info("Keep-alive ping disabled")
            else:
                log.info("Keep-alive ping configured every %d milliseconds",
                         args.keep_alive)
            # rename to be compatible with Server
            args.keep_alive_milliseconds = args.keep_alive

        if args.check_unused_sessions is not None:
            log.info("Check for unused sessions every %d milliseconds",
                     args.check_unused_sessions)
            # rename to be compatible with Server
            args.check_unused_sessions_milliseconds = args.check_unused_sessions

        if args.unused_session_lifetime is not None:
            log.info("Unused sessions last for %d milliseconds",
                     args.unused_session_lifetime)
            # rename to be compatible with Server
            args.unused_session_lifetime_milliseconds = args.unused_session_lifetime

        if args.stats_log_frequency is not None:
            log.info("Log statistics every %d milliseconds",
                     args.stats_log_frequency)
            # rename to be compatible with Server
            args.stats_log_frequency_milliseconds = args.stats_log_frequency

        server_kwargs = {
            key: getattr(args, key)
            for key in [
                'port',
                'address',
                'allow_websocket_origin',
                'host',
                'prefix',
                'develop',
                'keep_alive_milliseconds',
                'check_unused_sessions_milliseconds',
                'unused_session_lifetime_milliseconds',
                'stats_log_frequency_milliseconds',
                'use_xheaders',
            ] if getattr(args, key, None) is not None
        }

        server_kwargs['sign_sessions'] = settings.sign_sessions()
        server_kwargs['secret_key'] = settings.secret_key_bytes()
        server_kwargs['generate_session_ids'] = True
        if args.session_ids is None:
            # no --session-ids means use the env vars
            pass
        elif args.session_ids == 'unsigned':
            server_kwargs['sign_sessions'] = False
        elif args.session_ids == 'signed':
            server_kwargs['sign_sessions'] = True
        elif args.session_ids == 'external-signed':
            server_kwargs['sign_sessions'] = True
            server_kwargs['generate_session_ids'] = False
        else:
            raise RuntimeError(
                "argparse should have filtered out --session-ids mode " +
                args.session_ids)

        if server_kwargs['sign_sessions'] and not server_kwargs['secret_key']:
            die("To sign sessions, the BOKEH_SECRET_KEY environment variable must be set; "
                +
                "the `bokeh secret` command can be used to generate a new key."
                )

        server = Server(applications, **server_kwargs)

        if args.show:
            # we have to defer opening in browser until we start up the server
            def show_callback():
                for route in applications.keys():
                    server.show(route)

            server.io_loop.add_callback(show_callback)

        if args.develop:
            log.info(
                "Using develop mode (do not enable --develop in production)")

        address_string = ''
        if server.address is not None and server.address != '':
            address_string = ' address ' + server.address

        log.info(
            "Starting Bokeh server on port %d%s with applications at paths %r",
            server.port, address_string, sorted(applications.keys()))

        log.info("Staring Bokeh server with process id: %d" % getpid())

        server.start()
示例#16
0
 def test_port(self):
     loop = IOLoop()
     loop.make_current()
     server = Server(Application(), port=1234)
     assert server.port == 1234
def disss(abc):

    handler = FunctionHandler(modify_doc)
    app = Application(handler)
    show(app)
    make_plot(abc)
    initial_crimes = option_selection

    # Put controls in a single element
    controls = WidgetBox(option_selection)

    # Create a row layout
    layout = row(controls)

    # Make a tab with the layout
    doc.add_root(layout)


# Set up an application
handler = FunctionHandler(modify_doc)
app = Application(handler)
show(app)

# In[22]:

from IPython.display import HTML
HTML('''<script>
code_show=true; 
function code_toggle() {
 if (code_show){
 $('div.input').hide();
 } else {
 $('div.input').show();
 }
 code_show = !code_show
} 
示例#19
0
def test__existing_ioloop_with_multiple_processes_exception():
    application = Application()
    ioloop_instance = IOLoop.instance() ; ioloop_instance # silence flake8
    with pytest.raises(RuntimeError):
        with ManagedServerLoop(application, num_procs=3):
            pass
示例#20
0
    # Put all the tabs into one application
    tabs = Tabs(tabs=[tab1])
    doc.title = "World Development Indicator"
    doc.add_root(tabs)


'''
def form_menu_group(list):
    return [(x,x) for x in list]

def country_change_handler(attr, old, new):
    print (country_selection.value)

def indicator_change_handler(attr, old, new):
    print(indicator_selection.value)

form_menu_group(available_countries)

'''
# show(layout)

# curdoc().add_root(layout)
# curdoc().title="World Development Indicator"

# if __init__='__main__':

apps = {'/': Application(FunctionHandler(modify_doc))}

server = Server(apps, port=5000)
server.start()
示例#21
0
    action='append',
    type=str,
    metavar='HOST[:PORT]',
    help="""Public hostnames which may connect to the Bokeh websocket""",
    default=None)

args = parser.parse_args()

# This should remain here until --host is removed entirely
_fixup_deprecated_host_args(args)

applications = {}
main_path = os.path.join(os.path.dirname(os.path.realpath(__file__)),
                         'plot_app')
handler = DirectoryHandler(filename=main_path)
applications['/plot_app'] = Application(handler)

server_kwargs = {}
if args.port != None: server_kwargs['port'] = args.port
if args.use_xheaders: server_kwargs['use_xheaders'] = args.use_xheaders
server_kwargs['num_procs'] = args.numprocs
if args.address != None: server_kwargs['address'] = args.address
if args.host != None: server_kwargs['host'] = args.host
if args.allow_websocket_origin != None:
    server_kwargs['allow_websocket_origin'] = args.allow_websocket_origin

# increase the maximum upload size (default is 100MB)
server_kwargs['http_server_kwargs'] = {'max_buffer_size': 300 * 1024 * 1024}

show_ulog_file = False
show_3d_page = False
示例#22
0
# other stuff
if (not isdir(server.config['UPLOAD_FOLDER'])):
    mkdir(server.config['UPLOAD_FOLDER'])

# start Bokeh server
if "gunicorn" in environ.get("SERVER_SOFTWARE", ""):
    forcedPort = getpid()
    sockets, port = bind_sockets("localhost", forcedPort)
    server.config['PORT'] = port + 20
    server.logger.info("STARTED LISTENING INTERNALLY ON %d AND EXTERNALLY ON %d" % (port, server.config['PORT']))
else:
    sockets, port = bind_sockets("localhost", 0)
    server.config['PORT'] = port

from graphion.visualise import modify_doc
bkapp = Application(FunctionHandler(modify_doc))

def bk_worker():
    set_event_loop(new_event_loop())

    bokeh_tornado = BokehTornado({'/bkapp': bkapp}, extra_websocket_origins=["localhost:5000", "graphion.uddi.ng:*"])
    bokeh_http = HTTPServer(bokeh_tornado)
    bokeh_http.add_sockets(sockets)

    server = BaseServer(IOLoop.current(), bokeh_tornado, bokeh_http)
    server.start()
    server.io_loop.start()

from threading import Thread
Thread(target=bk_worker).start()
示例#23
0
def test__lifecycle_hooks():
    application = Application()
    handler = HookTestHandler()
    application.add(handler)
    with ManagedServerLoop(application,
                           check_unused_sessions_milliseconds=30) as server:
        # wait for server callbacks to run before we mix in the
        # session, this keeps the test deterministic
        def check_done():
            if len(handler.hooks) == 4:
                server.io_loop.stop()

        server_load_checker = PeriodicCallback(check_done,
                                               1,
                                               io_loop=server.io_loop)
        server_load_checker.start()
        server.io_loop.start()
        server_load_checker.stop()

        # now we create a session
        client_session = pull_session(session_id='test__lifecycle_hooks',
                                      url=url(server),
                                      io_loop=server.io_loop)
        client_doc = client_session.document
        assert len(client_doc.roots) == 1

        server_session = server.get_session('/', client_session.id)
        server_doc = server_session.document
        assert len(server_doc.roots) == 1

        client_session.close()
        # expire the session quickly rather than after the
        # usual timeout
        server_session.request_expiration()

        def on_done():
            server.io_loop.stop()

        server.io_loop.call_later(0.1, on_done)

        server.io_loop.start()

    assert handler.hooks == [
        "server_loaded", "next_tick_server", "timeout_server",
        "periodic_server", "session_created", "next_tick_session", "modify",
        "timeout_session", "periodic_session", "session_destroyed",
        "server_unloaded"
    ]

    client_hook_list = client_doc.roots[0]
    server_hook_list = server_doc.roots[0]
    assert handler.load_count == 1
    assert handler.unload_count == 1
    assert handler.session_creation_async_value == 6
    assert client_doc.title == "Modified"
    assert server_doc.title == "Modified"
    # the client session doesn't see the event that adds "session_destroyed" since
    # we shut down at that point.
    assert client_hook_list.hooks == ["session_created", "modify"]
    assert server_hook_list.hooks == [
        "session_created", "modify", "session_destroyed"
    ]
示例#24
0
    def invoke(self, args):
        '''

        '''

        # protect this import inside a function so that "bokeh info" can work
        # even if Tornado is not installed
        from bokeh.server.server import Server

        argvs = {f: args.args for f in args.files}
        applications = build_single_handler_applications(args.files, argvs)

        log_level = getattr(logging, args.log_level.upper())
        basicConfig(level=log_level,
                    format=args.log_format,
                    filename=args.log_file)

        if len(applications) == 0:
            # create an empty application by default
            applications['/'] = Application()

        # rename args to be compatible with Server
        if args.keep_alive is not None:
            args.keep_alive_milliseconds = args.keep_alive

        if args.check_unused_sessions is not None:
            args.check_unused_sessions_milliseconds = args.check_unused_sessions

        if args.unused_session_lifetime is not None:
            args.unused_session_lifetime_milliseconds = args.unused_session_lifetime

        if args.stats_log_frequency is not None:
            args.stats_log_frequency_milliseconds = args.stats_log_frequency

        if args.mem_log_frequency is not None:
            args.mem_log_frequency_milliseconds = args.mem_log_frequency

        server_kwargs = {
            key: getattr(args, key)
            for key in [
                'port',
                'address',
                'allow_websocket_origin',
                'num_procs',
                'prefix',
                'index',
                'keep_alive_milliseconds',
                'check_unused_sessions_milliseconds',
                'unused_session_lifetime_milliseconds',
                'stats_log_frequency_milliseconds',
                'mem_log_frequency_milliseconds',
                'use_xheaders',
                'websocket_max_message_size',
            ] if getattr(args, key, None) is not None
        }

        server_kwargs['sign_sessions'] = settings.sign_sessions()
        server_kwargs['secret_key'] = settings.secret_key_bytes()
        server_kwargs['generate_session_ids'] = True
        if args.session_ids is None:
            # no --session-ids means use the env vars
            pass
        elif args.session_ids == 'unsigned':
            server_kwargs['sign_sessions'] = False
        elif args.session_ids == 'signed':
            server_kwargs['sign_sessions'] = True
        elif args.session_ids == 'external-signed':
            server_kwargs['sign_sessions'] = True
            server_kwargs['generate_session_ids'] = False
        else:
            raise RuntimeError(
                "argparse should have filtered out --session-ids mode " +
                args.session_ids)

        if server_kwargs['sign_sessions'] and not server_kwargs['secret_key']:
            die("To sign sessions, the BOKEH_SECRET_KEY environment variable must be set; "
                +
                "the `bokeh secret` command can be used to generate a new key."
                )

        server_kwargs['use_index'] = not args.disable_index
        server_kwargs['redirect_root'] = not args.disable_index_redirect
        server_kwargs['autoreload'] = args.dev is not None

        def find_autoreload_targets(app_path):
            path = os.path.abspath(app_path)
            if not os.path.isdir(path):
                return

            for path, subdirs, files in os.walk(path):
                for name in files:
                    if (fnmatch(name, '*.html') or fnmatch(name, '*.css')
                            or fnmatch(name, '*.yaml')):
                        log.info("Watching: " + os.path.join(path, name))
                        watch(os.path.join(path, name))

        def add_optional_autoreload_files(file_list):
            for filen in file_list:
                if os.path.isdir(filen):
                    log.warning("Cannot watch directory " + filen)
                    continue
                log.info("Watching: " + filen)
                watch(filen)

        if server_kwargs['autoreload']:
            if len(applications.keys()) != 1:
                die("--dev can only support a single app.")
            if server_kwargs['num_procs'] != 1:
                log.info("Running in --dev mode. --num-procs is limited to 1.")
                server_kwargs['num_procs'] = 1

            find_autoreload_targets(args.files[0])
            add_optional_autoreload_files(args.dev)

        with report_server_init_errors(**server_kwargs):
            server = Server(applications, **server_kwargs)

            if args.show:

                # we have to defer opening in browser until we start up the server
                def show_callback():
                    for route in applications.keys():
                        server.show(route)

                server.io_loop.add_callback(show_callback)

            address_string = 'localhost'
            if server.address is not None and server.address != '':
                address_string = server.address

            for route in sorted(applications.keys()):
                url = "http://%s:%d%s%s" % (address_string, server.port,
                                            server.prefix, route)
                log.info("Bokeh app running at: %s" % url)

            log.info("Starting Bokeh server with process id: %d" % os.getpid())
            server.run_until_shutdown()
示例#25
0
 def test_empty(self):
     a = Application()
     doc = a.create_document()
     assert not doc.roots
示例#26
0
# Bokeh runner
import tornado.web
from bokeh.application import Application
from bokeh.application.handlers import FunctionHandler
from bokeh.server.server import Server

from src import robot, inverse

server = Server(
    {
        '/robot': Application(FunctionHandler(robot.main)),
        '/inversek': Application(FunctionHandler(inverse.main))
    },
    extra_patterns=[  #('/api', api.ApiHandler),
        (r'/my_static/(.*)', tornado.web.StaticFileHandler, {
            "path": "my_static/"
        })
    ],
    allow_websocket_origin=["localhost:5006"])
server.start()

if __name__ == '__main__':
    print(
        'Opening Tornado app with embedded Bokeh application on http://localhost:5006/'
    )

    server.io_loop.start()
示例#27
0
def create_ready_app():
    return Application(ReadyHandler())
示例#28
0
def test__lifecycle_hooks(ManagedServerLoop) -> None:
    application = Application()
    handler = HookTestHandler()
    application.add(handler)
    with ManagedServerLoop(application, check_unused_sessions_milliseconds=30) as server:
        # wait for server callbacks to run before we mix in the
        # session, this keeps the test deterministic
        def check_done():
            if len(handler.hooks) == 4:
                server.io_loop.stop()
        server_load_checker = PeriodicCallback(check_done, 1)
        server_load_checker.start()
        server.io_loop.start()
        server_load_checker.stop()

        # now we create a session
        client_session = pull_session(session_id='test__lifecycle_hooks',
                                      url=url(server),
                                      io_loop=server.io_loop)
        client_doc = client_session.document
        assert len(client_doc.roots) == 1

        server_session = server.get_session('/', client_session.id)
        server_doc = server_session.document
        assert len(server_doc.roots) == 1

        # we have to capture these here for examination later, since after
        # the session is closed, doc.roots will be emptied
        client_hook_list = client_doc.roots[0]
        server_hook_list = server_doc.roots[0]

        client_session.close()
        # expire the session quickly rather than after the
        # usual timeout
        server_session.request_expiration()

        def on_done():
            server.io_loop.stop()

        server.io_loop.call_later(0.1, on_done)

        server.io_loop.start()

    assert handler.hooks == ["server_loaded",
                             "next_tick_server",
                             "timeout_server",
                             "periodic_server",
                             "session_created",
                             "modify",
                             "next_tick_session",
                             "timeout_session",
                             "periodic_session",
                             "session_destroyed",
                             "server_unloaded"]

    assert handler.load_count == 1
    assert handler.unload_count == 1
    # this is 3 instead of 6 because locked callbacks on destroyed sessions
    # are turned into no-ops
    assert handler.session_creation_async_value == 3
    assert client_doc.title == "Modified"
    assert server_doc.title == "Modified"
    # only the handler sees the event that adds "session_destroyed" since
    # the session is shut down at that point.
    assert client_hook_list.hooks == ["session_created", "modify"]
    assert server_hook_list.hooks == ["session_created", "modify"]
示例#29
0
def test_unit_spec_changes_do_not_boomerang(monkeypatch):
    application = Application()
    with ManagedServerLoop(application) as server:
        doc = document.Document()
        client_root = UnitsSpecModel()
        doc.add_root(client_root)

        client_session = push_session(
            doc,
            session_id='test_unit_spec_changes_do_not_boomerang',
            url=url(server),
            io_loop=server.io_loop)
        server_session = server.get_session('/', client_session.id)

        assert len(server_session.document.roots) == 1
        server_root = next(iter(server_session.document.roots))

        assert client_root.distance == 42
        assert server_root.angle == 0

        def change_to(new_distance, new_angle):
            got_angry = {}
            got_angry['result'] = None

            # trap any boomerang
            def get_angry(message):
                got_angry['result'] = message

            monkeypatch.setattr(client_session, '_handle_patch', get_angry)

            server_previous_distance = server_root.distance
            server_previous_angle = server_root.angle

            # Now modify the client document
            client_root.distance = new_distance
            client_root.angle = new_angle

            # wait until server side change made ... but we may not have the
            # boomerang yet
            def server_change_made():
                return server_root.distance != server_previous_distance and \
                    server_root.angle != server_previous_angle

            client_session._connection._loop_until(server_change_made)

            # force a round trip to be sure we get the boomerang if we're going to
            client_session.force_roundtrip()

            assert got_angry['result'] is None

        change_to(57, 1)
        change_to({'value': 58}, {'value': 2})
        change_to({'field': 'foo'}, {'field': 'bar'})
        change_to({
            'value': 59,
            'units': 'screen'
        }, {
            'value': 30,
            'units': 'deg'
        })

        client_session.close()
        client_session.loop_until_closed(suppress_warning=True)
        assert not client_session.connected
        server.unlisten()  # clean up so next test can run
示例#30
0
async def test__actual_port_number(ManagedServerLoop) -> None:
    application = Application()
    with ManagedServerLoop(application, port=0) as server:
        port = server.port
        assert port > 0
        await http_get(server.io_loop, url(server))
示例#31
0
    def app(self_or_cls,
            plot,
            show=False,
            new_window=False,
            websocket_origin=None,
            port=0):
        """
        Creates a bokeh app from a HoloViews object or plot. By
        default simply attaches the plot to bokeh's curdoc and returns
        the Document, if show option is supplied creates an
        Application instance and displays it either in a browser
        window or inline if notebook extension has been loaded.  Using
        the new_window option the app may be displayed in a new
        browser tab once the notebook extension has been loaded.  A
        websocket origin is required when launching from an existing
        tornado server (such as the notebook) and it is not on the
        default port ('localhost:8888').
        """
        if not isinstance(self_or_cls,
                          BokehRenderer) or self_or_cls.mode != 'server':
            renderer = self_or_cls.instance(mode='server')
        else:
            renderer = self_or_cls

        def modify_doc(doc):
            renderer(plot, doc=doc)

        handler = FunctionHandler(modify_doc)
        app = Application(handler)

        if not show:
            # If not showing and in notebook context return app
            return app
        elif self_or_cls.notebook_context and not new_window:
            # If in notebook, show=True and no new window requested
            # display app inline
            if isinstance(websocket_origin, list):
                if len(websocket_origin) > 1:
                    raise ValueError(
                        'In the notebook only a single websocket origin '
                        'may be defined, which must match the URL of the '
                        'notebook server.')
                websocket_origin = websocket_origin[0]
            opts = dict(
                notebook_url=websocket_origin) if websocket_origin else {}
            return bkshow(app, **opts)

        # If app shown outside notebook or new_window requested
        # start server and open in new browser tab
        from tornado.ioloop import IOLoop
        loop = IOLoop.current()
        if websocket_origin and not isinstance(websocket_origin, list):
            websocket_origin = [websocket_origin]
        opts = dict(allow_websocket_origin=websocket_origin
                    ) if websocket_origin else {}
        opts['io_loop'] = loop
        server = Server({'/': app}, port=port, **opts)

        def show_callback():
            server.show('/')

        server.io_loop.add_callback(show_callback)
        server.start()

        def sig_exit(*args, **kwargs):
            loop.add_callback_from_signal(do_stop)

        def do_stop(*args, **kwargs):
            loop.stop()

        signal.signal(signal.SIGINT, sig_exit)
        try:
            loop.start()
        except RuntimeError:
            pass
        return server
示例#32
0
    def test_server_changes_go_to_client(self, ManagedServerLoop) -> None:
        application = Application()
        with ManagedServerLoop(application) as server:
            doc = document.Document()

            client_session = push_session(doc,
                                          session_id='test_server_changes_go_to_client',
                                          url=url(server),
                                          io_loop=server.io_loop)
            server_session = server.get_session('/', client_session.id)

            assert len(client_session.document.roots) == 0
            server_root = SomeModelInTestClientServer(foo=42)

            def do_add_server_root():
                server_session.document.add_root(server_root)
            server.io_loop.spawn_callback(server_session.with_document_locked, do_add_server_root)

            def client_has_root():
                return len(doc.roots) > 0
            client_session._connection._loop_until(client_has_root)
            client_root = next(iter(client_session.document.roots))

            assert client_root.foo == 42
            assert server_root.foo == 42

            # Now try setting title on server side
            def do_set_server_title():
                server_session.document.title = "Server Title"
            server.io_loop.spawn_callback(server_session.with_document_locked, do_set_server_title)

            def client_title_set():
                return client_session.document.title != document.DEFAULT_TITLE
            client_session._connection._loop_until(client_title_set)

            assert client_session.document.title == "Server Title"

            # Now modify a model within the server document
            def do_set_property_on_server():
                server_root.foo = 57
            server.io_loop.spawn_callback(server_session.with_document_locked, do_set_property_on_server)

            # there is no great way to block until the server
            # has applied changes, since patches are sent
            # asynchronously. We use internal _loop_until API.
            def client_change_made():
                return client_root.foo == 57
            client_session._connection._loop_until(client_change_made)
            assert client_root.foo == 57

            def do_remove_server_root():
                server_session.document.remove_root(server_root)
            server.io_loop.spawn_callback(server_session.with_document_locked, do_remove_server_root)

            def client_lacks_root():
                return len(doc.roots) == 0
            client_session._connection._loop_until(client_lacks_root)
            assert len(client_session.document.roots) == 0

            client_session.close()
            client_session._loop_until_closed()
            assert not client_session.connected
示例#33
0
def test_application_validates_document_by_default(check_integrity):
    a = Application()
    d = Document()
    d.add_root(figure())
    a.initialize_document(d)
    assert check_integrity.called
示例#34
0
            ytmp = 100 * tmp
        new = {
            'x': [tmp],
            'y': [ytmp // (tmp + 1)],
            'color': [random.choice(['red', 'blue', 'green'])]
        }
        source.stream(new)

    doc.add_periodic_callback(update, 500)

    fig = figure(title='Simulation playback!',
                 sizing_mode='scale_height',
                 x_range=[0, 100],
                 y_range=[0, 100])
    fig.line(source=source, x='x', y='y', color='red')  # size=10)

    doc.title = "Now with live updating!"
    doc.add_root(fig)


apps = {'/': Application(FunctionHandler(make_document))}

server = Server(apps, port=5000)
server.start()

if __name__ == '__main__':
    print('Opening Bokeh application on http://localhost:5006/')

    server.io_loop.add_callback(server.show, "/")
    server.io_loop.start()
示例#35
0
文件: routing.py 项目: zmj2008/bokeh
 def _fixup(self, app: Application) -> Application:
     if not any(
             isinstance(handler, DocumentLifecycleHandler)
             for handler in app.handlers):
         app.add(DocumentLifecycleHandler())
     return app
示例#36
0
    def invoke(self, args):
        '''

        '''

        # protect this import inside a function so that "bokeh info" can work
        # even if Tornado is not installed
        from bokeh.server.server import Server

        argvs = { f : args.args for f in args.files}
        applications = build_single_handler_applications(args.files, argvs)

        log_level = getattr(logging, args.log_level.upper())
        basicConfig(level=log_level, format=args.log_format)

        # This should remain here until --host is removed entirely
        _fixup_deprecated_host_args(args)

        if len(applications) == 0:
            # create an empty application by default
            applications['/'] = Application()

        if args.keep_alive is not None:
            if args.keep_alive == 0:
                log.info("Keep-alive ping disabled")
            else:
                log.info("Keep-alive ping configured every %d milliseconds", args.keep_alive)
            # rename to be compatible with Server
            args.keep_alive_milliseconds = args.keep_alive

        if args.check_unused_sessions is not None:
            log.info("Check for unused sessions every %d milliseconds", args.check_unused_sessions)
            # rename to be compatible with Server
            args.check_unused_sessions_milliseconds = args.check_unused_sessions

        if args.unused_session_lifetime is not None:
            log.info("Unused sessions last for %d milliseconds", args.unused_session_lifetime)
            # rename to be compatible with Server
            args.unused_session_lifetime_milliseconds = args.unused_session_lifetime

        if args.stats_log_frequency is not None:
            log.info("Log statistics every %d milliseconds", args.stats_log_frequency)
            # rename to be compatible with Server
            args.stats_log_frequency_milliseconds = args.stats_log_frequency

        server_kwargs = { key: getattr(args, key) for key in ['port',
                                                              'address',
                                                              'allow_websocket_origin',
                                                              'num_procs',
                                                              'prefix',
                                                              'keep_alive_milliseconds',
                                                              'check_unused_sessions_milliseconds',
                                                              'unused_session_lifetime_milliseconds',
                                                              'stats_log_frequency_milliseconds',
                                                              'use_xheaders',
                                                            ]
                          if getattr(args, key, None) is not None }

        server_kwargs['sign_sessions'] = settings.sign_sessions()
        server_kwargs['secret_key'] = settings.secret_key_bytes()
        server_kwargs['generate_session_ids'] = True
        if args.session_ids is None:
            # no --session-ids means use the env vars
            pass
        elif args.session_ids == 'unsigned':
            server_kwargs['sign_sessions'] = False
        elif args.session_ids == 'signed':
            server_kwargs['sign_sessions'] = True
        elif args.session_ids == 'external-signed':
            server_kwargs['sign_sessions'] = True
            server_kwargs['generate_session_ids'] = False
        else:
            raise RuntimeError("argparse should have filtered out --session-ids mode " +
                               args.session_ids)

        if server_kwargs['sign_sessions'] and not server_kwargs['secret_key']:
            die("To sign sessions, the BOKEH_SECRET_KEY environment variable must be set; " +
                "the `bokeh secret` command can be used to generate a new key.")

        server_kwargs['use_index'] = not args.disable_index
        server_kwargs['redirect_root'] = not args.disable_index_redirect

        with report_server_init_errors(**server_kwargs):
            server = Server(applications, **server_kwargs)

            if args.show:
                # we have to defer opening in browser until we start up the server
                def show_callback():
                    for route in applications.keys():
                        server.show(route)
                server.io_loop.add_callback(show_callback)

            address_string = 'localhost'
            if server.address is not None and server.address != '':
                address_string = server.address

            for route in sorted(applications.keys()):
                url = "http://%s:%d%s%s" % (address_string, server.port, server.prefix, route)
                log.info("Bokeh app running at: %s" % url)

            log.info("Starting Bokeh server with process id: %d" % getpid())
            server.run_until_shutdown()
 def get_bokeh_app(cls):
     if cls._bokeh_app is None:
         cls._bokeh_app = Application(FunctionHandler(cls.modify_doc))
     return cls._bokeh_app
示例#38
0
    def test_lots_of_concurrent_messages(self):
        application = Application()
        def setup_stuff(doc):
            m1 = AnotherModelInTestClientServer(bar=43, name='m1')
            m2 = SomeModelInTestClientServer(foo=42, name='m2')
            m3 = SomeModelInTestClientServer(foo=68, name='m3')
            doc.add_root(m1)
            doc.add_root(m2)
            doc.add_root(m3)
            def timeout1():
                m1.bar += 1
            doc.add_timeout_callback(timeout1, 1)
            def timeout2():
                m2.foo +=1
            doc.add_timeout_callback(timeout2, 3)
            def periodic1():
                m1.bar += 1
                doc.remove_timeout_callback(timeout1)
                doc.add_timeout_callback(timeout1, m1.bar % 7)
            doc.add_periodic_callback(periodic1, 3)
            def periodic2():
                m2.foo += 1
                doc.remove_timeout_callback(timeout2)
                doc.add_timeout_callback(timeout2, m2.foo % 7)
            doc.add_periodic_callback(periodic2, 1)

            def server_on_change(event):
                if isinstance(event, ModelChangedEvent) and event.model is m3:
                    return
                m3.foo += 1

            doc.on_change(server_on_change)

        handler = FunctionHandler(setup_stuff)
        application.add(handler)

        # keep_alive_milliseconds=1 sends pings as fast as the OS will let us
        with ManagedServerLoop(application, keep_alive_milliseconds=1) as server:
            session = pull_session(session_id='test_lots_of_concurrent_messages',
                                   url=url(server),
                                   io_loop=server.io_loop)
            assert session.connected

            server_session = server.get_session('/', session.id)

            def client_timeout():
                m = session.document.roots[0]
                m.name = m.name[::-1]
            session.document.add_timeout_callback(client_timeout, 3)

            def client_periodic():
                m = session.document.roots[1]
                m.name = m.name[::-1]
                session.document.remove_timeout_callback(client_timeout)
                session.document.add_timeout_callback(client_timeout, 3)

            session.document.add_periodic_callback(client_periodic, 1)

            result = {}
            def end_test():
                result['connected'] = session.connected
                result['server_connection_count'] = server_session.connection_count
                result['server_close_code'] = next(iter(server._tornado._clients))._socket.close_code
                result['doc'] = session.document.to_json()
                session.close()

            # making this longer is more likely to trigger bugs, but it also
            # makes the test take however much time you put here
            session.document.add_timeout_callback(end_test, 250)

            def client_on_change(event):
                if not isinstance(event, TitleChangedEvent):
                    session.document.title = session.document.title[::-1]

            session.document.on_change(client_on_change)

            session.loop_until_closed()

            assert not session.connected

            # we should have still been connected at the end,
            # if we didn't have any crazy protocol errors
            assert 'connected' in result
            assert result['connected']

            # server should also still have been connected
            assert result['server_connection_count'] == 1
            assert result['server_close_code'] is None
示例#39
0
    def start(self, event=None, block=False):
        try:
            ioloop.IOLoop.current()
        except RuntimeError:
            if six.PY3:
                import asyncio
                asyncio.set_event_loop(asyncio.new_event_loop())
                loop = None
                try:
                    loop = ioloop.IOLoop.current()
                except:
                    pass
                if loop is None:
                    raise
            else:
                raise

        if self._scheduler_ip is None:
            kv_store = kvstore.get(options.kv_store)
            try:
                schedulers = [s.key.rsplit('/', 1)[1] for s in kv_store.read('/schedulers').children]
                self._scheduler_ip = random.choice(schedulers)
            except KeyError:
                raise KeyError('No scheduler is available')

        static_path = os.path.join(os.path.dirname(__file__), 'static')

        handlers = dict()
        for p, h in _ui_handlers.items():
            handlers[p] = Application(FunctionHandler(functools.partial(h, self._scheduler_ip)))
        extra_patterns = [
            ('/static/(.*)', BokehStaticFileHandler, {'path': static_path})
        ]
        for p, h in _api_handlers.items():
            extra_patterns.append((p, h, {'scheduler_ip': self._scheduler_ip}))

        retrial = 5
        while retrial:
            try:
                if self._port is None:
                    use_port = get_next_port()
                else:
                    use_port = self._port
                self._server = Server(
                    handlers, allow_websocket_origin=['*'],
                    address='0.0.0.0', port=use_port,
                    extra_patterns=extra_patterns,
                )
                self._server.start()
                self._port = use_port
                logger.info('Mars UI started at 0.0.0.0:%d', self._port)
                break
            except:
                if self._port is not None:
                    raise
                retrial -= 1
                if retrial == 0:
                    raise

        if not block:
            self._server_thread = threading.Thread(target=self._server.io_loop.start)
            self._server_thread.daemon = True
            self._server_thread.start()

            if event:
                event.set()
        else:
            if event:
                event.set()

            self._server.io_loop.start()
示例#40
0
    def on_transfer_function_change(self, attr, old, new):
        self.model.transfer_function = self.model.transfer_functions[new]
        self.update_image()

    def on_opacity_slider_change(self, attr, old, new):
        for renderer in self.fig.renderers:
            if hasattr(renderer, 'image_source'):
                renderer.alpha = new / 100


if __name__ == '__main__':
    parser = argparse.ArgumentParser()
    parser.add_argument('--config', help='yaml config file (e.g. nyc_taxi.yml)', required=True)
    args = vars(parser.parse_args())

    def add_roots(doc):
        model = AppState(args['config'])
        view = AppView(model)
        GetDataset.model = model
        doc.add_root(view.layout)

    app = Application()
    app.add(FunctionHandler(add_roots))
    # Start server object wired to bokeh client. Instantiating ``Server``
    # directly is used to add custom http endpoint into ``extra_patterns``.
    server = Server(app, io_loop=IOLoop(),
                    extra_patterns=[(r"/datashader", GetDataset)], port=5000)
    print('Starting server at http://localhost:5000/...')
    server.start()
示例#41
0
                line_width=1,
                hover_line_color='color',
                hover_line_alpha=1.0,
                source=source)


def modify_doc(doc):
    def x_range_change_cb(attr, old, new):
        new_range = (plot.x_range.start, plot.x_range.end)
        if None in new_range:
            return

        new_data = down_sample(data=data,
                               npoints=screenwidth,
                               limits=new_range)
        source.data = ColumnDataSource(data=new_data).data

        print('change detected!')

    plot.x_range.on_change('start', x_range_change_cb)
    plot.x_range.on_change('end', x_range_change_cb)
    doc.add_root(column(plot))


server = Server({'/': Application(FunctionHandler(modify_doc))},
                io_loop=io_loop)
server.start()

if __name__ == '__main__':
    io_loop.add_callback(server.show, "/")
    io_loop.start()