tractor icon indicating copy to clipboard operation
tractor copied to clipboard

Document how to use `open_root_actor()`

Open goodboy opened this issue 4 years ago • 0 comments

With #185 about to land most users won't have to know about open_root_actor() however there is at least one use I can think of that might require it.

If you want to start a lone root actor that has no children but that is a long running service which can spawn workers (this also pertains to our standalone example which needs to be updated to remove tractor.run() as well) then you will need open_root_actor() to do this.

Likely code in that case is something close to:

import trio
import tractor

log = tractor.get_logger(__name__)

@tractor.stream
async def spawn_and_do_work(ctx: tractor.Context, numbers: List[int]):

    async with tractor.open_nursery() as tn:
    
        for n in numbers:
        
            # spawn an actor per entry in input sequence
            # (normally you'd probably want to retrieve results async too)
            result = await tn.run_in_actor(is_prime, num=number)
            
            # stream each result to caller
            await ctx.send_yield(result)


async def main():
    async with tractor.open_root_actor(expose_modules=[__name__]) as actor:
        log.info("yo i'm the root actor")
        await trio.sleep_forever()
    
trio.run(main)

Then, in another actor tree program you'd find and call this actor to do spawn_and_do_work() as needed but,

  1. each time a new request comes in open_root_actor() isn't called implicitly over and over inside the root nursery
  2. the actor machinery is up making it possible to find this actor in the first place using the registry system

goodboy avatar Jan 03 '21 17:01 goodboy