Как получить лучшие сообщения об ошибках при разборе JSON с Argonaut и пользовательскими кодеками - PullRequest
0 голосов
/ 16 ноября 2018

Я использую Argonaut для анализа JSON с моими пользовательскими кодеками.Мой код выглядит так:

val json: String = ...
val parsed = Parse.decodeEither[MyClass](json)
val checks = if (parsed.isRight) parsed.right.get
else sys.error("Unable to parse MyClass json: " + parsed.left)

Однако я никогда не получаю никаких полезных сообщений об ошибках.Все, что я получаю, это java.lang.RuntimeException: Unable to parse MyClass json: LeftProjection(Left(String: CursorHistory(List()))).

Как правильно обрабатывать ошибки декодирования?

Редактировать : мой вопрос не в том, что делать с предоставленным сообщением об ошибке,Было бы замечательно , если бы Аргонавт мог сказать что-то вроде "Ошибка разбора в позиции X, неожиданный элемент y" или что-то в этом роде.Это возможно?

Ответы [ 2 ]

0 голосов
/ 17 ноября 2018

Я согласен, что ошибки декодирования Argonaut могут быть немного краткими, но они также значимы.Обратите внимание на объект CursorHistory .Он обеспечивает самую последнюю операцию во время декодирования.

В вашем случае похоже, что вы не можете проанализировать JSON, поскольку CursorHistory - это пустой List.

Простой пример (не проверено):

case class Person(name: String, age: Int)

object Person {
  implicit def PersonCodecJson: CodecJson[Person] =
    casecodec2(Person.apply, Person.unapply)("name", "age")
}

Person JSON:

{
  "name": "Fred"
}

Ошибка синтаксического анализа приведенного выше примера будет выглядеть примерно так: CursorHistory(List(El(CursorOpDownField(age),false))).

0 голосов
/ 16 ноября 2018

Я не совсем уверен, понимаю ли я, каков ваш настоящий вопрос ...

Вы получаете Java.lang.RuntimeException: Unable to parse MyClass json: LeftProjection(Left(String: CursorHistory(List()))), потому что это то, что делает sys.error.

Когда вы используетеметод Parse.decodeEither, результирующий тип - Either[String, MyClass].Есть много способов проверить или работать с любым из них.Один из них, который вы уже используете: проверяет, является ли результат с обеих сторон и действует на его основе.

Хотя более идиотский подход заключается в его сворачивании:

parsed.fold(
    error => //do something with error,
    myclass => //do something with myclass
)

Из Scala 2.12, Either - это монада, ориентированная на правую сторону, что означает, что вы можете использовать ее для понимания, которое будет отображаться с правой стороны.Я думаю, что чтение его документов могло бы помочь.

...