score:4

Accepted answer

You should either forward the message to the slaves (which keeps the same sender), or include the sender in the message to the slaves. For example:

def receive = {
  case Calculate => slave ! CalculateWithSender(sender)

  case res @ Result(value, originalSender) =>        
    val result = resultMap(originalSender) + res   // assuming results are just added
    resultMap += (originalSender -> result) 
    if (resultsAreFinished(originalSender))    
      originalSender ! result
}

or

def receive = {
  case Calculate => slave.forward(Calculate)

  case res @ Result(value, originalSender) => 
    val result = resultMap(originalSender) + res   // assuming results are just added 
    resultMap += (originalSender -> result) 
    if (resultsAreFinished(originalSender))    
      originalSender ! result
}

or

def receive = {
  case Calculate => slave.tell(Calculate, sender)

  case res @ Result(value, originalSender) => 
    val result = resultMap(originalSender) + res   // assuming results are just added 
    resultMap += (originalSender -> result) 
    if (resultsAreFinished(originalSender))    
      originalSender ! result
}

I'm not familiar with Play promises, but ? (ask) returns a Akka Future. If .asPromise converts an Akka Future to a Play Promise then you're set.

score:1

Spin up a new actor for each calculation. forward the Calculate message to the new actor. The new actor stores the original sender. When the result is ready, the result is sent to the original sender, and the ephemeral actor dies:

class CalculateActor extends Actor {
    var origSender : ActorRef = _
    def receive {
        case Calculate => {
            origSender = sender
            slaveActors ! doStuff
            //....
    }
    case Result(value) => {
        if(results are ready) {
            origSender ! results
            self ! PoisonPill  // I'm done, time to die
        }
    }
}

class MasterActor extends Actor {
    def receive {
        case msg @ Calculate => {
            // forward sends without changing the sender
            context.actorOf(Props(new CalculateActor)).forward(msg)
        }
    }
}

Related Query

More Query from same tag