Scala Akka演员-遇到死信

时间:2018-11-08 01:36:28

标签: scala akka actor

我正在和Akka演员一起使用Scala。我知道一个演员有一个邮箱。因此,与actor的任何通信都会被序列化。我有一个从事特定工作的演员-比如说它下载图像。

class DownloadImageActor(implicit val injector: Injector) extends Actor with Injectable {
  val imageDownloadService = inject[ImageDownloadService]
  implicit val ec = inject[ExecutionContext]

  override def receive: Receive = {
    case DownloadImage(jobId, imageUrl) =>
      imageDownloadService.downloadImage(imageUrl).onComplete {
        case Success(image) =>
          sender() ! ImageDownloadSuccess(imageUrl, image, jobId)
        case Failure(e) =>
          sender() ! ImageDownloadFail(imageUrl, e, jobId)
      }
  }
}

如您所见,actor以异步方式下载图像。 imageDownloadService.downloadImage返回一个Future,消息完成后将向发送者发送一条消息。现在,我在这里收到dead letters encountered消息。

我哪里出错了?



编辑#1

将消息发送给下载actor的父actor

class ParentActor(implicit val injector : Injector) extends Actor with Injectable {

  val downloadImageActor = inject[ActorRef](identified by "ImageDownloadActor")


  override def receive: Receive = {
    case DownloadImages(urls, _id) => urls.foreach(url =>
      downloadImageActor ! DownloadImage(id, imageUrl = url)
    )
    case ImageDownloadSuccess(image : Image) =>
  }
}

1 个答案:

答案 0 :(得分:-1)

不知道是否还有其他问题,但是您在sender中使用Future的方法是错误的,您需要将其分配给新变量,然后结合onComplete回调它形成一个闭包,其他actor句柄不会覆盖它。

在您的代码中,需要添加lineA,并将lineB,lineC替换为lineD,lineE。或者,您可能想看看Future的pipeTo功能。

class DownloadImageActor(implicit val injector : Injector)  extends Actor with Injectable{
  val imageDownloadService = inject[ImageDownloadService]
  implicit val ec = inject[ExecutionContext]

  override def receive: Receive = {
    case DownloadImage(jobId, imageUrl) => 
      val client = sender // lineA
      imageDownloadService.downloadImage(imageUrl).onComplete {
      //case Success(image) => sender() !  ImageDownloadSuccess(imageUrl, image, jobId) // lineB
      //case Failure(e) => sender() !  ImageDownloadFail(imageUrl,e, jobId) // lineC
      case Success(image) => client !  ImageDownloadSuccess(imageUrl, image, jobId) // lineD
      case Failure(e) => client !  ImageDownloadFail(imageUrl,e, jobId) // lineE
    }
  }
}