捕获Scala进程失败

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了捕获Scala进程失败相关的知识,希望对你有一定的参考价值。

我有一个基于scala构建的RESTful API。其中一个路由调用外部命令并使用ProcessLogger捕获输出。当我在服务器上放置少量负载时(通过单元测试),外部命令调用开始间歇性地失败。没有响应返回,HTTP请求超时。没有填充Process调用的返回代码,没有抛出异常......我无法在日志中捕获或查找任何内容。是否有一种特定的方法来捕获scala中的Process调用的所有问题,这可能有助于我调试最新进展?

我的代码看起来像这样......

try { 
  var resultCode:Int = 
    (Seq("echo",data) #| 
      Seq("external-command-to-call")) !
      ProcessLogger(stdout append _, stderr append _)

  println("Output "+resultCode)
  println(stderr)
  println(stdout)

  // check return code
  if(resultCode > 0) {
    Left("An error occurred")
  }
} catch {
   case e: Exception => {
     Left("An exception occurred")
   }
}

10次​​中的9次将打印“输出”,但间歇性地它将在外部呼叫中死亡,从不打印“输出”。两个“左”都没有被触发。我尝试使用Try / Success / Failure并捕捉“Throwable”但没有快乐。

答案

这只是我的一个想法。我们不能使用Scala Futures来解决这个问题:)我希望你可以使用Future onFailure来处理这种情况。我在StackOverflow中找到了关于Scala Process Logger的类似文章,希望这对您有所帮助。 Scala ProcessLogger & Future: How can I make sure all line callbacks are called BEFORE the onComplete block?

斯卡拉未来[T]

当Future用值完成时,它是成功完成的。如果Future以异常完成,则失败。 https://docs.scala-lang.org/overviews/core/futures.html

`val f: Future[List[String]] = Future {
  session.getRecentPosts
}

f onFailure {
  case t => println("An error has occured: " + t.getMessage)
}

f onSuccess {
  case posts => for (post <- posts) println(post)
} `
另一答案

因此,使用Scala的Future monad可以解决问题,你需要做的是更改那些processLogger方法以返回Future [Int]现在你不应该使用Future的onSuccess和onFailure方法,因为它们已被弃用,所以你可以通过它来保证它在此Future上添加回调。通过使用onCompletemapforeach

result.onComplete{
case Success(x) => println(x)

case Failure(ex)=>ex.printStackTrace}

以上是关于捕获Scala进程失败的主要内容,如果未能解决你的问题,请参考以下文章

linux打开终端如何启动scala,如何在终端下运行Scala代码片段?

如何使用 RxSwift 在一个地方捕获来自两个请求的错误

从片段中捕获图像

如何在片段中从相机捕获图像,

从命名管道捕获非零退出代码

Scala:静默捕获所有异常