akka-http:找不到参数解组的隐式值

Posted

技术标签:

【中文标题】akka-http:找不到参数解组的隐式值【英文标题】:akka-http : could not find implicit value for parameter unmarshalling 【发布时间】:2016-02-08 00:51:45 【问题描述】:

我的喷雾 json 支持看起来像这样

object MarshallingSupport extends SprayJsonSupport 
  implicit def json4sFormats: Formats = DefaultFormats

在我的路线中,我想将请求映射到 dto

object Main extends App with AppConfig with BaseService with MainActorSystem 

  val processor = system.actorOf(Props(), "processorActor")
  val view = system.actorOf(Props(), "processorActor")

  override protected implicit val executor: ExecutionContext = system.dispatcher
  override protected val log: LoggingAdapter = Logging(system, getClass)
  override protected implicit val materializer: ActorMaterializer = ActorMaterializer()

  Http().bindAndHandle(routes(processor, view), httpInterface, httpPort)


trait BaseServiceRoute 
  protected implicit def executor: ExecutionContext
  protected implicit def materializer: ActorMaterializer
  protected def log: LoggingAdapter


trait MainActorSystem 
  implicit val system = ActorSystem("booking")


final case class CalculatePriceForRangeDto(unitId: Int, from: Long, to: Long)

trait PriceServiceRoute extends BaseServiceRoute 

  implicit val timeout = Timeout(30 seconds)

  import com.example.crudapi.utils.MarshallingSupport._

  def customersRoute(command: ActorRef, query: ActorRef) = pathPrefix("price") 
    post 
      path("calculate") 
        decodeRequest 
          entity(as[CalculatePriceForRangeDto]) 
            priceForRange => onComplete((query ? CalculatePriceForRange(

但我得到了

Error:(32, 20) could not find implicit value for parameter um: akka.http.scaladsl.unmarshalling.FromRequestUnmarshaller[com.example.crudapi.http.routes.CalculatePriceForRangeDto]
      entity(as[CalculatePriceForRangeDto]) 
               ^

已查看所有相关的 SO 问题,但没有解决我的问题。奇怪的是我尝试了 Typesafe 模板 akka-dddd-cqrs 并且它工作正常,代码相同。

我是否遗漏了隐含上下文的内容? 有什么想法吗?

【问题讨论】:

【参考方案1】:

SprayJsonSupport 适用于 spray-json(不适用于 json4s)。因此,您需要按如下方式定义编组器

trait JsonMarshallers extends DefaultJsonProtocol 
  implicit val DigestItemWireFormat = jsonFormat6(DigestItemWire.apply)

  implicit val LocalDateTimeFormat = new JsonFormat[LocalDateTime] 

    private val iso_date_time = DateTimeFormatter.ISO_DATE_TIME

    def write(x: LocalDateTime) = JsString(iso_date_time.format(x))

    def read(value: JsValue) = value match 
      case JsString(x) => LocalDateTime.parse(x, iso_date_time)
      case x => throw new RuntimeException(s"Unexpected type %s on parsing of LocalDateTime type".format(x.getClass.getName))
    
  

然后在你使用它们的范围内导入JsonMarshallers._,或者与PriceServiceRoute混合,在文件开头导入akka.http.scaladsl.marshallers.sprayjson.SprayJsonSupport._

【讨论】:

DigestItemWire 是一个什么样的类?不在范围内。 @Reeebuuk 这只是您想要序列化/反序列化的案例类的示例,例如您的案例中的CalculatePriceForRangeDto @Reeebuuk 试试jsonFormat3(CalculatePriceForRangeDto.apply)。方法名称末尾的数字表示您的案例类中的字段数。 嗯,请尝试在文件开头添加import akka.http.scaladsl.marshallers.sprayjson.SprayJsonSupport._ @Reeebuuk 很高兴能帮上忙。请不要忘记接受答案。 json4s 使用反射(很慢),因此不需要显式序列化器。

以上是关于akka-http:找不到参数解组的隐式值的主要内容,如果未能解决你的问题,请参考以下文章

找不到参数元组的隐式值

找不到参数 e 的隐式值

Scala 类型参数化,Shapeless - 找不到参数 Generic 的隐式值

找不到参数的隐式值

找不到参数 flash 的隐式值

找不到参数 enc 的隐式值:CsvEncoder[Shape]