Skip to content

Commit

Permalink
Add support for awaitables
Browse files Browse the repository at this point in the history
  • Loading branch information
jtpio committed Feb 29, 2020
1 parent 7c42ce8 commit 9c43df7
Show file tree
Hide file tree
Showing 4 changed files with 75 additions and 8 deletions.
34 changes: 32 additions & 2 deletions examples/commands.ipynb
Expand Up @@ -40,7 +40,7 @@
"metadata": {},
"outputs": [],
"source": [
"app.commands.list_commands()"
"sorted(app.commands.list_commands())"
]
},
{
Expand Down Expand Up @@ -158,6 +158,36 @@
"out"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Await a command"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"import asyncio\n",
"\n",
"from ipylab import JupyterFrontEnd\n",
"from ipywidgets import Output\n",
"\n",
"app = JupyterFrontEnd()\n",
"\n",
"\n",
"async def sequence():\n",
" await app.ready()\n",
" for i in range(4):\n",
" result = await app.commands.execute('filebrowser:toggle-main')\n",
" await asyncio.sleep(1)\n",
"\n",
"asyncio.create_task(sequence());"
]
},
{
"cell_type": "markdown",
"metadata": {},
Expand Down Expand Up @@ -307,7 +337,7 @@
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.8.1"
"version": "3.8.2"
},
"widgets": {
"application/vnd.jupyter.widget-state+json": {
Expand Down
26 changes: 26 additions & 0 deletions ipylab/awaitable.py
@@ -0,0 +1,26 @@
# Copyright (c) Jeremy Tuloup.
# Distributed under the terms of the Modified BSD License.

import asyncio

from uuid import uuid4


class Awaitable:
def __init__(self, *args, **kwargs):
self._futures = {}

def _on_frontend_msg(self, _, content, buffers):
if content.get("event", "") == "future":
future_id = content.get("future_id")
result = content.get("result", None)
if future_id in self._futures:
self._futures[future_id].set_result(result)
del self._futures[future_id]

def register_future(self):
future_id = uuid4().hex
loop = asyncio.get_running_loop()
fut = loop.create_future()
self._futures[future_id] = fut
return future_id, fut
13 changes: 11 additions & 2 deletions ipylab/commands.py
Expand Up @@ -6,6 +6,7 @@
from ipywidgets import CallbackDispatcher, Widget
from traitlets import List, Unicode

from .awaitable import Awaitable
from ._frontend import module_name, module_version


Expand Down Expand Up @@ -33,7 +34,7 @@ def add_item(self, command_id, category, *, args=None, rank=None):
)


class CommandRegistry(Widget):
class CommandRegistry(Widget, Awaitable):
_model_name = Unicode("CommandRegistryModel").tag(sync=True)
_model_module = Unicode(module_name).tag(sync=True)
_model_module_version = Unicode(module_version).tag(sync=True)
Expand All @@ -49,10 +50,18 @@ def _on_frontend_msg(self, _, content, buffers):
if content.get("event", "") == "execute":
command_id = content.get("id")
self._execute_callbacks[command_id]()
super()._on_frontend_msg(_, content, buffers)

def execute(self, command_id, args=None):
args = args or {}
self.send({"func": "execute", "payload": {"id": command_id, "args": args}})
fut_id, fut = super().register_future()
self.send(
{
"func": "execute",
"payload": {"id": command_id, "args": args, "future_id": fut_id},
}
)
return fut

def list_commands(self):
return self._commands
Expand Down
10 changes: 6 additions & 4 deletions src/widgets/commands.ts
Expand Up @@ -38,7 +38,7 @@ export class CommandRegistryModel extends WidgetModel {
private _onMessage(msg: any) {
switch (msg.func) {
case 'execute':
this._execute(msg.payload);
void this._execute(msg.payload);
break;
case 'addCommand':
void this._addCommand(msg.payload);
Expand All @@ -57,9 +57,11 @@ export class CommandRegistryModel extends WidgetModel {
this.save_changes();
}

private _execute(payload: any) {
const { id, args } = payload;
void this.commands.execute(id, args);
private async _execute(payload: any) {
const { id, args, future_id } = payload;
await this.commands.execute(id, args);
// TODO: send result back if possible?
this.send({ event: 'future', future_id }, {});
}

private async _addCommand(payload: any): Promise<void> {
Expand Down

0 comments on commit 9c43df7

Please sign in to comment.