Akka 动作顺序清除代码
我有一个用scala编写的基于角色的应用程序(使用)。现在我有了一个actor,它应该通过按预定义顺序发送各种HTTP请求来配置网络中的设备 我将所有HTTP内容封装在一个单独的类中,供我的参与者访问。 当然,每个配置步骤都可能失败,因此我使用了Akka 动作顺序清除代码,akka,scala,coding-style,Akka,Scala,Coding Style,我有一个用scala编写的基于角色的应用程序(使用)。现在我有了一个actor,它应该通过按预定义顺序发送各种HTTP请求来配置网络中的设备 我将所有HTTP内容封装在一个单独的类中,供我的参与者访问。 当然,每个配置步骤都可能失败,因此我使用了Try[Int]作为处理与设备通信的方法的返回类型(将HTTP响应代码作为Try的内容返回) 现在我的问题是,每个配置步骤都依赖于之前的所有步骤才能成功完成,因此我的代码变得难以阅读(在我的工作中) 我基本上是这样实现的 action1 match {
Try[Int]
作为处理与设备通信的方法的返回类型(将HTTP响应代码作为Try
的内容返回)
现在我的问题是,每个配置步骤都依赖于之前的所有步骤才能成功完成,因此我的代码变得难以阅读(在我的工作中)
我基本上是这样实现的
action1 match {
case Failure(err) => //report error
case Success(retCode) if retCode < 400 =>
nextStep match {
...
}
}
action1匹配{
案例失败(err)=>//报告错误
如果retCode<400=>
下一步匹配{
...
}
}
在几次行动之后,这就变成了一个巨大的声明,你无法第一眼看到正在发生的事情
那么我该如何以一种干净的代码风格来编写这篇文章呢?您可以将您的操作序列实现为。。。行动顺序: 阻止版本:
def seq: Seq[() => Try[Int]] = ???
// find first failure
def failed: Option[Try[Int]] = seq.view.map{ _() }.find {
case Failure(err) =>
//report error
true
case Success(retCode) => retCode > 400
}
对于非阻塞版本,您应该使用Future
而不是Try
:
val seq: List[() => Future[Int]] = ???
def isSuccess(actions: List[() => Future[Int]]): Future[Boolean] = actions match {
case h :: tail => h().flatMap { c =>
if (c > 400) Future(false)
else isSuccess(tail)
}
case Nil => Future(true)
}
Ahh right
find
如果得到true
则停止执行。事后看来,这是一个很明显的解决方案^^如果它在这里受阻,其实并不重要,因为这个参与者的全部目的是执行这些动作,他们必须互相等待anyway@mgttlinger:我不知道您是如何得到HTTP
响应的,但如果库提供Future[Response]
您不应该将其转换为尝试使用等待
。我正在使用,并且据我所知,它没有提供作为未来
@mgttlinger的响应代码:阻止解决方案时出错。请参阅更新版本。