Challenges with time.sleep
and input
#
One of the big challenge with educational environments like turtle or robotics
is that the programs often need to pause, either to get input from the user with
the input
function or to show an animation step.
Note
The upcoming Javascript Promise Integration API of WASM will probably allow
Pyodide to provide synchronous sleep
and input
functions working
natively. This may well greatly simplify everything.
Pausing execution#
The TigerJython environment typically provides a delay(ms)
command that
pauses the program execution for ms
milliseconds. This is super easy to do
in standard Python with the time.sleep(s)
synchronuous function. It is
another story in the browser which has a completely different execution model
and does not support blocking a program by default.
There are different ways to handle this issue, but none is simple and they all require some kind of understanding of the browser inner workings.
Asyncify the code#
One way of implementing a delay
function is to use Python coroutines, that
is to adapt the code to the asynchronous nature of the browser. This can be
easily done with the asyncio
module integrated in Pyodide and allows pyodide
to wait for the delay.
import asyncio
async def delay(ms):
await asyncio.sleep(ms / 1000)
async def greet(name):
print('Hello ')
await delay(1000)
print(name)
async def main():
await greet('Dennis')
asyncio.run(main())
The issue with this code is that it is absolutely inappropriate for beginners.
Even professionnal developers often struggle understanding async programming.
One solution is to take a student written synchronous program and to generate a
corresponding asynchronous program run by Pyodide. This is feasible using the
ast
module and working on the abstract syntax tree.
However, this trick adds an other layer of complexity for the environment and complicates debugging as Python reports errors relative to the asynchronous program and not the original program written by the students.
Service Workers#
Another way of implementing de delay(ms)
function is to use a service
worker. Originally, service workers are used to make web applications work
offline by implementing advanced caching strategies where HTTP requests are
intercepted by the service worker before leaving the browser and responded
according to the caching strategy without even reaching the server.
WebAssembly stack switching#
Stack switching could also be usefull