Джерксон (Джексон) проблема с scala.runtime.BoxedUnit?

Джерксон начал выдавать действительно странную ошибку, которую я не видел раньше.

com.fasterxml.jackson.databind.JsonMappingException: No serializer found for class scala.runtime.BoxedUnit and no properties discovered to create BeanSerializer (to avoid exception, disable SerializationConfig.SerializationFeature.FAIL_ON_EMPTY_BEANS) ) (through reference chain: scala.collection.MapWrapper["data"])

Я анализирую некоторые основные данные из API. Класс, который я определил:

case class Segmentation(
  @(JsonProperty@field)("legend_size")
  val legend_size: Int,

  @(JsonProperty@field)("data")
  val data: Data

) 

а также Data похоже:

case class Data(
  @(JsonProperty@field)("series")
  val series: List[String],

  @(JsonProperty@field)("values")
  val values: Map[String, Map[String, Any]]

)

Любая подсказка, почему это будет вызывать ошибки? Похоже на простой класс, с которым Джерксон может справиться.

Изменить: пример данных:

{"legend_size": 1, "data": {"series": ["2013-04-06", "2013-04-07", "2013-04-08", "2013-04-09", "2013-04-10", "2013-04-11", "2013-04-12", "2013-04-13", "2013-04-14", "2013-04-15"], "values": {"datapoint": {"2013-04-12": 0, "2013-04-15": 4, "2013-04-14": 0, "2013-04-08":
0, "2013-04-09": 0, "2013-04-11": 0, "2013-04-10": 0, "2013-04-13": 0, "2013-04-06": 0, "2013-04-07": 0}}}}

3 ответа

Решение

Прошло много времени с тех пор, как я впервые опубликовал этот вопрос. Решение при написании этого ответа, похоже, заключается в том, чтобы перейти от Джексона и использовать Jackson-module-scala или Json4s с бэкэндом Джексона. Многие типы Scala включены в сериализованные по умолчанию и обрабатываются изначально.

Кроме того, причина, по которой я вижу BoxedUnit потому что явный тип, который видел Джерксон, был Any (часть Map[String, Map[String, Any]]). Any является базовым типом и не дает Джерксону / Джексону информацию о том, что он десериализует. Поэтому жалуется на отсутствующий сериализатор.

Это не ответ на приведенный выше пример, но я собираюсь предложить его, потому что это был ответ на мой аналогичный сценарий "BoxedUnit":

No serializer found for class scala.runtime.BoxedUnit and no properties discovered to create BeanSerializer (to avoid exception, disable SerializationFeature.FAIL_ON_EMPTY_BEANS)

В моем случае Джексон жаловался на десериализацию экземпляра объекта scala.runtime.BoxedUnit.

Q: Так что же такое scala.runtime.BoxedUnit?

A: Это Scala Java-представление для "Unit". Основная часть Джексона (который является Java-кодом) пытается десериализовать Java-представление не-сущности модуля Scala.

Q: Так почему это случилось?

A: В моем случае это был побочный эффект, вызванный ошибочным методом с необъявленным возвращаемым значением. Рассматриваемый метод обернул предложение match, которое (непреднамеренно) не возвращало значение для каждого случая. Из-за ошибочного кода, описанного выше, Scala динамически объявляет переменную, фиксирующую результат этого метода, как "Unit". Позже в коде, когда этот var сериализуется в json, возникает ошибка Джексона.

Поэтому, если у вас возникла такая проблема, я бы посоветовал изучить любые неявно типизированные переменные / методы с неопределенными возвращаемыми значениями и убедиться, что они делают то, что, по вашему мнению, они делают.

У меня было такое же исключение. в моем случае это вызвало то, что я определил метод apply в объекте-компаньоне без '=':

object Somthing {
   def apply(s: SomthingElse)  {
      ...
   }
}

вместо

object Somthing {
   def apply(s: SomthingElse) = {
      ...
   }
}

Это привело к тому, что тип возвращаемого значения метода apply был Unit, что вызвало исключение, когда я передал объект Джексону. Не уверен, так ли это в вашем коде или этот вопрос все еще актуален, но это может помочь другим в решении этой проблемы.

Другие вопросы по тегам