невозможно создать неявное чтение для JSON - PullRequest
0 голосов
/ 25 апреля 2018

Мой серверный код получит следующее JSON

{
    "signin-info":{
        "email" : "someemail",
        "password": "password"
    }
}

Я создал следующие 2 класса case для представления этой структуры.

case class UserSigninInfo(
  email:String,
  password:String
)
case class UserSignin(
  signinInfo: UserSigninInfo
)

Чтобы прочитать JSON, ясоздали следующие 2 Reads

  implicit val userSigninInfoReads:Reads[UserSigninInfo] = (
    (JsPath \ "email").read[String] and
    (JsPath \ "password").read[String]
  )(UserSigninInfo.apply _)

  implicit val userSigninReads:Reads[UserSignin] = (
    (JsPath \ "signin-info").read[UserSigninInfo]
  )(UserSignin.apply _)

Но для userSigninReads я получаю следующую ошибку компиляции.Что я делаю не так?

overloaded method value read with alternatives:
[error]   (t: models.UserSigninInfo)play.api.libs.json.Reads[models.UserSigninInfo] <and>
[error]   (implicit r: play.api.libs.json.Reads[models.UserSigninInfo])play.api.libs.json.Reads[models.UserSigninInfo]
[error]  cannot be applied to (models.UserSigninInfo => models.UserSignin)
[error]     (JsPath \ "signin-info").read[UserSigninInfo]
[error]                                 `

1 Ответ

0 голосов
/ 26 апреля 2018

Решение для создания операций чтения для вашего основного объекта:

implicit val userSigninReads : Reads[UserSignin] =
  (JsPath \ "signin-info").read[UserSigninInfo].map(UserSignin(_))

Это потому, что оно имеет только одно поле.

Ваша конструкция была существенно:

((JsPath \ "signin-info").read[UserSigninInfo])(UserSignin.apply _)

, который просто

(JsPath \ "signin-info").read[UserSigninInfo](UserSignin.apply _)

, потому что он просто добавляет дополнительный ().

read метод действительно имеет две альтернативы:

def read[T](t: T) = Reads.pure(t)
def read[T](implicit r: Reads[T]): Reads[T] = Reads.at[T](this)(r)

Он ожидаетлибо неявное чтение, либо явное значение, но вы передаете функцию, поэтому компилятор жалуется.

Когда вы объединяете несколько полей с and, создается другой объект, например, FunctionalBuilder[M]#CanBuild2[A, B] для 2 элементов, и у него есть метод apply для создания окончательного Reads экземпляра.

Поскольку у вас есть только один объект, вы можете создать Reads, прочитав UserSigninInfo с нужного вам пути и поместив результат в UserSignin с помощью map.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...