【问题标题】:How to debug akka http's route dsl如何调试akka http的路由dsl
【发布时间】:2017-10-24 17:15:12
【问题描述】:

我正在尝试为 akka http 创建一个解组器,从 avro 到自定义案例类。但这给了我一个非常模糊的错误:“找不到隐含的价值”。我该如何调试或让 scala 提示问题出在哪里?

我这样设置路线:

class MetricsRoute(implicit val system: ActorSystem, implicit val materializer: ActorMaterializer) {
import system.dispatcher

  def getRoute() = {
    path("metrics") {
      put {
        decodeRequest {
          entity(as[Metrics]) { metrics: Metrics =>
            println(metrics.time)
            complete(HttpEntity(ContentTypes.`text/html(UTF-8)`, "<h1>hi!</h1>"))
          }
        }
      }
    }
  }

在同一个类中,我还创建了这样的解组器:

  implicit def avroUnmarshaller(): FromRequestUnmarshaller[Metrics] =
    Unmarshaller.withMaterializer {
      implicit ex: ExecutionContext =>
      implicit mat: Materializer =>
        request: HttpRequest => {
          val inputStream = request.entity.dataBytes.runWith(
            StreamConverters.asInputStream(FiniteDuration(3, TimeUnit.SECONDS))
          )

          val reader = new SpecificDatumReader[AvroMetrics](classOf[AvroMetrics])
          val decoder:BinaryDecoder = DecoderFactory.get().binaryDecoder(inputStream, null)

          //AvroMetrics is a case class generated from the avro schema
          val avroMetrics:AvroMetrics = AvroMetrics(0, 0, List())
          reader.read(avroMetrics, decoder)

          Future {
            //converts the avro case class to the case class specific for my application
            convertMetrics(avroMetrics)
          }
        }
  }

但这给了我非常模糊的“找不到隐含值”错误:

[error] /mypath/MetricsRoute.scala:34: could not find implicit value for parameter um: akka.http.scaladsl.unmarshalling.FromRequestUnmarshaller[my.package.types.Metrics]
[error]           entity(as[Metrics]) { metrics: Metrics =>
[error]                    ^
[error] one error found
[error] (compile:compileIncremental) Compilation failed

如何调试缺少的内容或我做错了什么?

编辑:

值得注意的是,当我自己指定解组器时,它确实有效,因此需要更改

entity(as[Metrics]) { metrics: Metrics =>

entity(avroUnmarshaller) { metrics: Metrics =>

这似乎表明编组器代码本身没有错,但我在类型上做错了什么?

【问题讨论】:

    标签: scala akka unmarshalling akka-http


    【解决方案1】:

    编译器正在寻找FromRequestUnmarshaller[Metrics],您定义的类型为() =&gt; FromRequestUnmarshaller[Metrics]

    尝试用不带空括号的方式定义你的隐式,例如

    implicit def avroUnmarshaller: FromRequestUnmarshaller[Metrics] = ???
    

    而不是

    implicit def avroUnmarshaller(): FromRequestUnmarshaller[Metrics] = ???
    

    (也可以设为val,但这与此问题无关)

    【讨论】:

    • 啊,这很有意义。太糟糕了,它没有在类型中明确显示。使用 val 而不是 def 有什么优势吗?
    • def 每次调用都会重新评估,val 只会评估一次 (stackoverflow.com/questions/4437373/…)
    猜你喜欢
    • 1970-01-01
    • 2016-09-20
    • 1970-01-01
    • 1970-01-01
    • 2021-05-07
    • 2021-12-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多