【问题标题】:How to handle unhandled exception throw in monix onErrorHandle如何处理 monix onErrorHandle 中未处理的异常抛出
【发布时间】:2017-11-19 23:06:38
【问题描述】:

我正在使用 monix 任务,我正在尝试捕获 Throwable,然后转换为自定义错误。我已将代码删除/更改为简单且相关。这是代码(代码sn-p之后的问题):

import io.netty.handler.codec.http.HttpRequest
import monix.reactive.Observable
import io.netty.buffer.ByteBuf
import monix.eval.Task
import com.mypackage.Response


private[this] def handler(
      request: HttpRequest,
      body: Observable[ByteBuf]
  ): Task[Response] = {

    val localPackage = for {
      failfast <- Task.eval(1 / 0)
    } yield failfast

    // Failure case.
    localPackage.onErrorRecoverWith {
        case ex: ArithmeticException =>
          print(s"LOG HERE^^^^^^^^^^^^^^^")
          return Task.now(
            Response(HttpResponseStatus.BAD_REQUEST,
                     None,
                     None)
          )
    }.runAsync

    // Success case.
    localPackage.map { x => 
       x match {
        case Right(cool) =>
          Response(
            HttpResponseStatus.OK,
            None,
            cool
          )
        case Left(doesntmatter) => ???
      }
  }
}

我可以看到打印语句,但没有返回预期的Task.now(Response(...。相反,调用处理程序方法的方法会引发错误。我如何让它返回Task[Response]

成功案例有效,失败案例无效。

编辑 #1:修复 scala 代码中的错误。

编辑 #2 这就是我修复它的方法。

    // Success case.
    localPackage.map { x => 
       x match {
        case Right(cool) =>
          Response(
            HttpResponseStatus.OK,
            None,
            cool
          )
        case Left(doesntmatter) => ???
      }
  }.onErrorRecoverWith {
        case ex: ArithmeticException =>
          print(s"LOG HERE^^^^^^^^^^^^^^^")
          return Task.now(
            Response(HttpResponseStatus.BAD_REQUEST,
                     None,
                     None)
          )
    }

我在考虑未来,忘记了lazy eval 任务的性质。此外,我了解 CancellableFuture 值是如何在失败任务中被丢弃的。

【问题讨论】:

    标签: scala reactive-programming monix


    【解决方案1】:

    您的样本存在一些问题。

    一方面,此代码在 Scala 中无效:

    val localPackage = for {
      failfast <- 1 / 0
    } yield failfast
    

    我猜你的意思是Task.eval(1 / 0)

    另外onErrorHandle 没有Task 作为返回类型,你可能在想onErrorHandleWith。给它一个偏函数(即一个可以由于匹配错误而引发异常的函数)是一个非常糟糕的主意——如果你想匹配那个错误,那么更好的选择是onErrorRecoveronErrorRecoverWith,它们需要部分函数作为参数。

    所以这里有一个示例:

    import monix.eval._
    import monix.execution.Scheduler.Implicits.global
    
    val task = Task.eval(1 / 0).onErrorRecoverWith {
      case _: ArithmeticException => Task.now(Int.MinValue)
    }
    
    task.runAsync.foreach(println)
    //=> -2147483648
    

    希望这会有所帮助。

    【讨论】:

      猜你喜欢
      • 2013-06-08
      • 1970-01-01
      • 1970-01-01
      • 2011-10-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-03-20
      • 1970-01-01
      相关资源
      最近更新 更多