Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/json/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/unit-testing/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Json 如何将自定义封送拆收器添加到akka http?_Json_Scala_Marshalling_Spray_Akka Http - Fatal编程技术网

Json 如何将自定义封送拆收器添加到akka http?

Json 如何将自定义封送拆收器添加到akka http?,json,scala,marshalling,spray,akka-http,Json,Scala,Marshalling,Spray,Akka Http,作为scala和akka http的初学者,我正在尝试连接到序列化过程中 该项目使用akka@2.5.2和阿克卡-http@10.0.10“。此外,它还包含akka-http-spray-json依赖项 在代码库中,我们使用Java.Util.Currency(它可能已被弃用,这并不重要,因为我仍然想知道如何添加自定义封送拆收器。) 给定此示例控制器: def getCurrencyExample: Route = { path("currencyExample") { va

作为scala和akka http的初学者,我正在尝试连接到序列化过程中

该项目使用akka@2.5.2和阿克卡-http@10.0.10“。此外,它还包含
akka-http-spray-json
依赖项

在代码库中,我们使用
Java.Util.Currency
(它可能已被弃用,这并不重要,因为我仍然想知道如何添加自定义封送拆收器。)

给定此示例控制器:

def getCurrencyExample: Route = {
    path("currencyExample") {
      val currency: Currency = Currency.getInstance("EUR")
      val code: String = currency.getCurrencyCode

      val shouldBeFormated = collection.immutable.HashMap(
        "currencyCode" -> code,
        "currencyObject" -> currency
      )

      complete(shouldBeFormated)
    }
  }
我得到这样一个响应,其中currency对象变为空:

 {
  currencyObject: { },
  currencyCode: "EUR",
 }
我预计会出现以下情况:

 {
  currencyObject: "EUR",
  currencyCode: "EUR",
 }
currency
对象应该转换为JSON字符串。由于我不想手动转换每个响应,所以我想挂接到编组过程中,并在后台完成

我只想为
Java.Util.Currency
对象添加一个自定义marhaller,但即使是我也不确定如何继续。 这里描述了多种方法,我不确定哪种方法适合我的需要,或者从哪里开始


我尝试创建自己的
CurrencyJsonProtocol

package com.foo.api.marshallers

import java.util.Currency

import spray.json.{DefaultJsonProtocol, JsString, JsValue, RootJsonFormat}

object CurrencyJsonProtocol extends DefaultJsonProtocol {

  implicit object CurrencyJsonFormat extends RootJsonFormat[Currency] {
    override def read(json: JsValue): Currency = {
      Currency.getInstance(json.toString)
    }

    override def write(obj: Currency): JsValue = {
      JsString(obj.getCurrencyCode)
    }
  }

}
然而,仅仅是文件的存在就破坏了我的项目:

[error] RouteDefinitons.scala:90:16: type mismatch;
[error]  found   : scala.collection.immutable.HashMap[String,java.io.Serializable]
[error]  required: akka.http.scaladsl.marshalling.ToResponseMarshallable
[error]       complete(shouldBeFormated)
[error]                ^
[error] one error found
[error] (Compile / compileIncremental) Compilation failed

我也不知道为什么。(由于我的包名被称为
marshaller
,它崩溃了。这完全破坏了项目的编译。

你有
JsonFormat[Currency]
?如果有,请修复它

如果没有,则应遵循以下步骤并创建:

  • 作为域模型,保存答案的特定结果类型,例如
    案例类CurrencyResult(货币:货币,代码:字符串)
  • trait JsonSupport
    中:a
    JsonFormat[Currency]
  • trait JsonSupport
    中:a
    JsonFormat[CurrencyResult]

  • 作为上述第1点的替代方案,您可能可以将地图键入为:
    map[String,JsValue]
    我使用Spray支持已有多年。也许我应该尝试另一种。无论如何,在Spray中,类型的自定义格式化程序很简单。例如squants.market.currency


    据我所知,你有所有的部分,你只需要把它们放在一起

    Spray json支持封送常见类型,如Int、String、Boolean、List、Map等。但它不知道如何封送“Currency”。为了解决这个问题,您已经为“Currency”对象创建了一个自定义封送器。您只需将其插入正确的位置。您所要做的就是从
    Curre导入封送器ncyJsonProtocol
    插入控制器,如下所示:

    import CurrencyJsonProtocol.\uu

    此外,请确保您还具有以下导入:

    导入spray.httpx.SprayJsonSupport_
    导入spray.json.DefaultJsonProtocol.\uz

    你应该会自动把它捡起来


    要了解它是如何工作的,您需要了解scala中的。虽然像我这样来自java世界的人看起来很神奇,但我可以向您保证这对我没有帮助。

    这对我没有帮助,因为它假定了一些我不具备的知识。您能解释一下吗?此外,我想对任何Case类中的任何货币对象进行操作no m请查看我的更新问题,因为我尝试使用自定义JsonProtocol,但它破坏了我的项目,我不知道原因。这是因为序列化程序不在范围内。只需导入它,它就应该编译。使用Spray,您应该扩展SprayJsonSupport。请注意,您应该添加依赖库Dependencies+=”com.typesafe.akka“%%”akka http spray json“%”10.1.1"我不完全确定这是问题所在。你看到我更新的问题了吗?json转换必须有一些类型信息。但是,使用HashMap会丢失这些类型信息。这就是为什么我建议你在我的回答中使用
    case类
    ,这样你就不会丢失所需的类型编队,以多写一个
    JsonFormat
    为代价。刚刚更新了我的answer@FredericA我有很多响应对象,都是case类,其中很多都有不同嵌套级别和顺序的currency对象。hash映射只是一个例子来展示这个问题。我想要currency对象无论类出现在何处,都要在任何情况下转换。当前,我只得到
    {}
    。从我目前的理解来看,似乎我必须为每个case类创建一个看似冗余和冗长的封送拆收器。您必须为每个case类创建一个
    JsonFormat
    ,是的。但是,对于
    Currency
    等成员,您只需编写一次
    JsonFormat
    ,它们将通过隐式解析。单独编写每个
    JsonFormat
    被认为是正常的,因为它们代表了模块/应用程序的公共接口。也就是说,我仍然不明白为什么您的
    货币
    被格式化为
    {}
    您已经有了
    JsonFormat
    吗?
    import squants.market.{ Currency, Money }
    import squants.market._
    
     trait MoneyJsonProtocol extends DefaultJsonProtocol {
    
      implicit object CurJsonFormat extends JsonFormat[Currency] {
        def write(currency: Currency): JsValue = JsString(currency.code)
        def read(value: JsValue): Currency = value match {
          case JsString(currency) =>
            defaultCurrencyMap.get(currency) match {
              case Some(c) => c
              case None => // throw an exception, for example
            }
          case _ => // throw another exception, for example
        }
      }
    
      implicit def toJavaBigDecimal(b: math.BigDecimal): java.math.BigDecimal = b.underlying
    
    }