Search code examples
scalaakkaakka-stream

Future[Source] pipeTo an Actor


There are two local actors (the remoting is not used). Actors were simplified for the example:

class ProcessorActor extends Actor {
  override def receive: Receive = {
    case src:Source[Int, NotUsed] =>
      //TODO processing of `src` here
  }
}

class FrontendActor extends Actor {
  val processor = context.system.actorOf(Props[ProcessorActor])
  ...

  override def receive: Receive = {
    case "Hello" =>
      val f:Future[Source[Int, NotUsed]] = Future (Source(1 to 100))

      f pipeTo processor
  }
}

// entry point:
val frontend = system.actorOf(Props[FrontendActor])
frontend ! "Hello"

Thus the FrontendActor sends Source to ProcessorActor. In the above example it is works successfully.

Is such approach okay?


Solution

  • Thus the FrontendActor sends Source to ProcessorActor. In the above example it is works successfully.

    Is such approach okay?

    It's unclear what your concern is.

    Sending a Source from one actor to another actor on the same JVM is fine. Because inter-actor communication on the same JVM, as the documentation states, "is simply done via reference passing," there is nothing unusual about your example1. Essentially what is going on is that a reference to a Source is passed to ProcessorActor once the Future is completed. A Source is an object that defines part of a stream; you can send a Source from one actor to another actor locally just as you can any JVM object.

    (However, once you cross the boundary of a single JVM, you have to deal with serialization.)


    1 A minor, tangential observation: FrontendActor calls context.system.actorOf(Props[ProcessorActor]), which creates a top-level actor. Typically, top-level actors are created in the main program, not within an actor.