Jupyter compatibility

Use FastHTML in Jupyter notebooks
from httpx import get, AsyncClient

Helper functions


source

nb_serve

 nb_serve (app, log_level='error', port=8000, host='0.0.0.0', **kwargs)

Start a Jupyter compatible uvicorn server with ASGI app on port with log_level


source

nb_serve_async

 nb_serve_async (app, log_level='error', port=8000, host='0.0.0.0',
                 **kwargs)

Async version of nb_serve


source

is_port_free

 is_port_free (port, host='localhost')

Check if port is free on host


source

wait_port_free

 wait_port_free (port, host='localhost', max_wait=3)

Wait for port to be free on host

Using FastHTML in Jupyter


source

show

 show (*s)

Same as fasthtml.components.show, but also adds htmx.process()


source

render_ft

 render_ft ()

source

htmx_config_port

 htmx_config_port (port=8000)

source

JupyUvi

 JupyUvi (app, log_level='error', host='0.0.0.0', port=8000, start=True,
          **kwargs)

Start and stop a Jupyter compatible uvicorn server with ASGI app on port with log_level

Creating an object of this class also starts the Uvicorn server. It runs in a separate thread, so you can use normal HTTP client functions in a notebook.

app = FastHTML()
rt = app.route

@app.route
def index(): return 'hi'

port = 8000
server = JupyUvi(app, port=port)
get(f'http://localhost:{port}').text
'hi'

You can stop the server, modify routes, and start the server again without restarting the notebook or recreating the server or application.

Using a notebook as a web app

You can also run an HTMX web app directly in a notebook. To make this work, you have to add the default FastHTML headers to the DOM of the notebook with show(*def_hdrs()). Additionally, you might find it convenient to use auto_id mode, in which the ID of an FT object is automatically generated if not provided.

fh_cfg['auto_id' ]=True

After importing fasthtml.jupyter and calling render_ft(), FT components render directly in the notebook.

(c := Div('Cogito ergo sum'))
Cogito ergo sum

Handlers are written just like a regular web app:

@rt
def hoho(): return P('loaded!'), Div('hee hee', id=c, hx_swap_oob='true')

All the usual hx_* attributes can be used:

P('not loaded', hx_get=hoho, hx_trigger='load')

not loaded

FT components can be used directly both as id values and as hx_target values.

(c := Div(''))
@rt
def foo(): return Div('foo bar')
P('hi', hx_get=foo, hx_trigger='load', hx_target=c)

hi

server.stop()

Running apps in an IFrame

Using an IFrame can be a good idea to get complete isolation of the styles and scripts in an app. The HTMX function creates an auto-sizing IFrame for a web app.


source

HTMX

 HTMX (path='', app=None, host='localhost', port=8000, height='auto',
       link=False, iframe=True)

An iframe which displays the HTMX application in a notebook.

@rt
def index():
    return Div(
        P(A('Click me', hx_get=update, hx_target='#result')),
        P(A('No me!', hx_get=update, hx_target='#result')),
        Div(id='result'))

@rt
def update(): return Div(P('Hi!'),P('There!'))
server.start()
# Run the notebook locally to see the HTMX iframe in action
HTMX()
server.stop()

source

ws_client

 ws_client (app, nm='', host='localhost', port=8000, ws_connect='/ws',
            frame=True, link=True, **kwargs)