Как использовать шаблон Akka ask без блокировки


Привет у меня есть актер, который отвечает за извлечение данных из базы данных, превращение их в список и отправку обратно отправителю. Я использую шаблон ask, чтобы получить ответ от моего актера, потому что я не хочу использовать await.result, потому что этот подход заблокирует поток, который не является хорошим.

Я написал следующий код, чтобы получить ответ от моего актера (я просто пропустил код db, чтобы сохранить его простым, но логика остается прежней):

class MyActor extends Actor{
   var list = new MutableList[Int]()
   list+=1
   list+=2
   list+=3
   list+=4

   def receive ={
     case "returnAlist"=>
       println("sending back list "+list +"of size "+list.size)
       sender ! list
     case message => 
       unhandled(message)
   }
}

object Test extends App{
  val system = ActorSystem("testing")
  val MyActor = system.actorOf(Props[MyActor], name = "InstitutionUserSuggestion")
  implicit val timeout = Timeout(15 seconds)
  var ResultList = new MutableList[Int]()
  val future:Future[MutableList[Int]] = ask(MyActor,"returnAlist").mapTo[MutableList[Int]] 
  future.onComplete { 
    case Success(result)=>
      println(" in sucees start")
      println("value of result "+ result.size)
      println("ResultList=result")
      ResultList = result
      println("value of ResultList "+ ResultList.size)
      println("in Success end")
    case Failure(e)=>
      println(" in failure")
      e.printStackTrace()
  }

  println("returned list size is " + ResultList.size + " and its contents" + ResultList)


}

Вот результат работы код выше:

sending back list MutableList(1, 2, 3, 4)of size 4
returned list size is 0 and its contenstsMutableList()
in sucees start
value of result 4
 ResultList=result
value of ResultList 4
 in Success end

Моя проблема в том, что код onComplete выполняется в конце мне нужно отобразить содержимое моего списка ResultList на консоли, но эта строка

println("returned list size is "+ResultList.size +" and its contensts" +ResultList)

, который я пишу после блока onComplete, я думаю, что он выполняется перед блоком onComplete, поэтому в конце ничего нет в списке ResultList, поэтому я не могу распечатать его элементы на консоль.

Пожалуйста, помогите мне, что я должен сделать, чтобы получить список предметов от актера без блокировки и после этого отобразить его на экране. приставка.

1 3

1 ответ:

Вы не хотите блокировать, ожидая ответа актера, поэтому вы используете Future Правильно. Код в функции onComplete выполняется, когда ваш актер отвечает списком.

И поскольку вы не хотите блокировать и обрабатывать его асинхронно, ваш последний оператор println выполняется, пока ваш актер еще не ответил.

Вы можете распечатать содержимое списка в блоке onComplete:

object Test extends App{
  val system = ActorSystem("testing")
  val MyActor = system.actorOf(Props[MyActor], name = "InstitutionUserSuggestion")
  implicit val timeout = Timeout(15 seconds)

  val future: Future[List[Int]] = ask(MyActor,"returnAlist").mapTo[List[Int]] 
  future.onComplete { 
    case Success(result)=>
      println("returned list size is " + result.size +" and its contents" + result)
    case Failure(e)=>
      println("in failure")
      e.printStackTrace()
  }
}

В качестве примечания я использовал неизменяемый List, который более идиоматичен Scala, чем использование изменяемых коллекций, таких как MutableList.