0

I am working with a non asyncio library that does not do i/o, only simple calculations. One of its features is a series of callbacks on a set of user provided observers in the order they happen, while the user controls a higher level api.

class Calculator:
    def __init__(self):
        self._internal = 0
        self._observers = [

    def register(observer):
        self._observers.append(observer)

    def add(int val):
        for i in range(val):
            self._internal += 1

    def _call_observers(self):
        for o in self._observers:
            o.on_add()

    @property
    def value(self):
        return self._internal

I need to use this from a couroutine to call other coroutines. One idea I had was to subclass an AsyncCalculator and override relevant methods to be coroutines, storing a reference to the event loop.

(not real code)

class AsyncCalculator(Calculator):
    def __init__(self, loop):
        ...

    async def _call_observers(self):
        ...

I was wondering if there is a way to wait on a coroutine from a normal function if there is a reference to the event loop or any other structure available? It seems that if the function is being called from a coroutine, then there might be some hacky way to await another coroutine from the function. Then maybe that hack could be thrown in a utility?

1 Answer 1

1

If an Calculator method is being invoked from a running event loop, you can instruct a coroutine to resume from a synchronous function. (Asyncio does such things internally all the time.) To do that, you don't need to make _call_observers async, you can do something like this:

class _Observer:
    def __init__(self, fut):
        self.fut = fut
    def on_add(self):
        self.fut.set_result('add')

async def my_coro(calc):
    loop = asyncio.get_event_loop()
    fut = loop.create_future()
    calc.register(_Observer(fut))
    # wait for the observer to be invoked
    op = await fut
    if op == 'add':
        ...

This requires the whole thing to be running inside the event loop, regardless of whether IO is occurring.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.