Jupyterhub Rest API detect if user already has server running

Using the Rest api is there a way to check on whether or not a user has a non named notebook server running. Right now I know I can use these apis to start and stop a non named notebook server using
the following apis users/{name}/server. Is there an api that can be called from javascript on the user side to be able to detect if a notebook server is running or not?

This was the simplest solution I could come up with which seems to work.


  // hook up event-stream for progress
  var evtSource = new EventSource("{{base_url}}api/users/{{user.json_escaped_name}}/server/progress");


  evtSource.onmessage = function(e) {
    var evt = JSON.parse(e.data);
    console.log(evt);    
    if (evt.ready) {
      evtSource.close();
      alert("running")
    }
    if (evt.failed) {
      evtSource.close();
      // turn progress bar red
      alert("not running")
    }
  };

I can put this in the Jupyterhub templates and it lets me know if I have a non named server running or not.

The API GET /hub/api/users/:name will return this information.

The user’s servers dict contains all ‘active’ servers keyed by name ("" for the default server). A given server can be:

  • not present (stopped)
  • ready if fully ready
  • pending if still in the process of starting or stopping

A user with a running server looks like this:

{'kind': 'user',
 'name': 'test-1',
 'admin': False,
 'groups': [],
 'server': '/user/test-1/',
 'pending': None,
 'created': '2021-02-17T08:41:53.146076Z',
 'last_activity': '2021-02-17T09:25:26.775787Z',
 'servers': {'': {'name': '',
   'last_activity': '2021-02-17T09:25:26.775787Z',
   'started': '2021-02-17T09:25:25.568339Z',
   'pending': None,
   'ready': True,
   'state': None,
   'url': '/user/test-1/',
   'user_options': {},
   'progress_url': '/hub/api/users/test-1/server/progress'}}}

For example, to check a user’s server’s status:

username = "test-1"
servername = ""  # empty for default, or pick any name

user_model = s.get(f"{hub_api}/users/{username}").json()
server = user_model["servers"].get(servername, {})
if server:
    pending = server["pending"]
    ready = server["ready"]
    # server.url is a *path*, does not include https://host unless user-subdomains are used
    url = server["url"]
else:
    # no server field, not running, nothing pending
    pending = None
    ready = False
    url = None

if ready:
    print(f"{username}/{servername} running and ready at {url}")
elif pending:
    print(f"{username}/{servername} pending {pending}")
else:
    print(f"{username}/{servername} not running")

Here’s a notebook illustrating user models for stopped, pending, and ready with more detail about what you might do about pending states.

1 Like