Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/scala/19.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/spring-mvc/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Scala 如何摆脱;额外的;阿克卡河流量阶段的未来?_Scala_Akka_Akka Stream - Fatal编程技术网

Scala 如何摆脱;额外的;阿克卡河流量阶段的未来?

Scala 如何摆脱;额外的;阿克卡河流量阶段的未来?,scala,akka,akka-stream,Scala,Akka,Akka Stream,我正在使用Akka Streams,并尝试使用Flowstages来最有效地描述整个图形。在某些阶段,我通过ask模式向参与者发送消息 当然,当我使用ask模式时,我需要使用mapTo,以获得进一步处理所需的类型 以下是一个例子: val runnableGraph = Source.single(CheckEntity(entity)) .map { check => (postgresActor ? check) .mapTo[CheckEntityResult

我正在使用Akka Streams,并尝试使用
Flow
stages来最有效地描述整个图形。在某些阶段,我通过
ask
模式向参与者发送消息

当然,当我使用
ask
模式时,我需要使用
mapTo
,以获得进一步处理所需的类型

以下是一个例子:

val runnableGraph = Source.single(CheckEntity(entity))
  .map { check =>
    (postgresActor ? check)
      .mapTo[CheckEntityResult]
      .map {
        case failure: PostgresFailure => Left(failure.message)
        case pEntity: PEntity => Right(check)
    }
  }
  .map {
    _.map {
      case Left(msg) => Future(Left(msg))
      case Right(check) =>
        (redisActor ? pEntity)
          .mapTo[CheckEntityResult]
          .map {
            case failure: RedisFailure => Left(failure.message)
            case rEntity: REntity => Right(rEntity)
          }
    }
  }
  .toMat(Sink.head)(Keep.right)

//The result's type is Future[Future[Either[String, Entity]]]
val futureResult = runnableGraph.run()

如何摆脱阶段之间嵌套的
Future

一个使通过流传播
CheckEntity
元素更容易的方法是更改
CheckEntityResult
类以包含相应的
CheckEntity
实例。这看起来像这样:

abstract class CheckEntityResult(entity: CheckEntity) extends Entity

case class PEntity(entity: CheckEntity) extends CheckEntityResult(entity)
case class PostgresFailure(entity: CheckEntity, message: String) extends CheckEntityResult(entity)

case class REntity(entity: CheckEntity) extends CheckEntityResult(entity)
case class RedisFailure(entity: CheckEntity, message: String) extends CheckEntityResult(entity)
然后,在调整参与者以处理这些消息后,您可以使用和
mapsync
(根据需要调整并行级别)与参与者交互,并避免物化值中嵌套的
Future

implicit val askTimeout = Timeout(5.seconds)

val runnableGraph = Source.single(CheckEntity(entity))
  .ask[CheckEntityResult](parallelism = 3)(postgresActor)
  .map {
    case PostgresFailure(_, msg) => msg
    case PEntity(e) => e
  }
  .mapAsync(parallelism = 3) {
    case failureMsg: String => Future.successful(failureMsg)
    case e: CheckEntity => (redisActor ? e).mapTo[CheckEntityResult]
  }
  .map {
    case failureMsg: String => Left(failureMsg)
    case RedisFailure(_, msg) => Left(msg)
    case r: REntity => Right(r)
  }
  .toMat(Sink.head)(Keep.right)

val futureResult = runnableGraph.run() // Future[Either[String, Entity]]

使通过流传播
CheckEntity
元素更容易的一个方法是将
CheckEntityResult
类更改为包含相应的
CheckEntity
实例。这看起来像这样:

abstract class CheckEntityResult(entity: CheckEntity) extends Entity

case class PEntity(entity: CheckEntity) extends CheckEntityResult(entity)
case class PostgresFailure(entity: CheckEntity, message: String) extends CheckEntityResult(entity)

case class REntity(entity: CheckEntity) extends CheckEntityResult(entity)
case class RedisFailure(entity: CheckEntity, message: String) extends CheckEntityResult(entity)
然后,在调整参与者以处理这些消息后,您可以使用和
mapsync
(根据需要调整并行级别)与参与者交互,并避免物化值中嵌套的
Future

implicit val askTimeout = Timeout(5.seconds)

val runnableGraph = Source.single(CheckEntity(entity))
  .ask[CheckEntityResult](parallelism = 3)(postgresActor)
  .map {
    case PostgresFailure(_, msg) => msg
    case PEntity(e) => e
  }
  .mapAsync(parallelism = 3) {
    case failureMsg: String => Future.successful(failureMsg)
    case e: CheckEntity => (redisActor ? e).mapTo[CheckEntityResult]
  }
  .map {
    case failureMsg: String => Left(failureMsg)
    case RedisFailure(_, msg) => Left(msg)
    case r: REntity => Right(r)
  }
  .toMat(Sink.head)(Keep.right)

val futureResult = runnableGraph.run() // Future[Either[String, Entity]]

可以考虑将您的Actudio查询转换为<代码>流以及<代码> MAPASYNC (具有适当的并行性):

使用转换后的流,您的runnableGraph可以按如下方式进行组装,结果类型为
Future[other[]]

val runnableGraph = Source.single(CheckEntity(entity))
  .via(postgresCheckFlow(parallelism))
  .via(redisCheckFlow(parallelism))
  ...

可以考虑将您的Actudio查询转换为<代码>流以及<代码> MAPASYNC (具有适当的并行性):

使用转换后的流,您的runnableGraph可以按如下方式进行组装,结果类型为
Future[other[]]

val runnableGraph = Source.single(CheckEntity(entity))
  .via(postgresCheckFlow(parallelism))
  .via(redisCheckFlow(parallelism))
  ...

谢谢答案真的很全面!谢谢答案真的很全面!非常感谢在撰写之前在不同阶段分解图表的想法:)非常感谢在撰写之前在不同阶段分解图表的想法:)