在 Play 中将 Json 转换为 Joda DateTime!斯卡拉 2.5
Convert Json to Joda DateTime in Play! scala 2.5
我已经阅读了这篇文章 (以及其他关于 SO 的文章),但我仍然无法将 JsValue
转换为带有 Joda DateTime 的案例 class .
这是 JSON 我有:
val json = Json.parse(
"""
{
"message": "Bla bla bla",
"updated_time": "2016-09-17T12:48:12+0000"
}
"""
)
而对应的案例class是:
import org.joda.time.DateTime
final case class FacebookPost(message: String, updated_time: DateTime)
我还添加了这个隐式 DateTime reader(我也尝试了其他一些):
implicit val readsJodaLocalDateTime = Reads[DateTime](js =>
js.validate[String].map[DateTime](dtString => new DateTime(dtString)))
但是当我尝试将我的 json 转换为相应的大小写 class (json.as[FacebookPost]
) 时,我收到此错误:
play.api.libs.json.JsResultException: `JsResultException(errors:List((/updated_time,List(ValidationError(List(error.expected.jodadate.format),WrappedArray(yyyy-MM-dd))))))`
我做错了什么?
您的问题是日期时间的格式:2016-09-17T12:48:12+0000
。
默认情况下,Joda 的 DateTime
class 无法自动识别您正在使用的格式,因此您必须使用 DateTimeFormat
.[=21= 提供提示]
我们的自定义示例 Reads[DateTime]
:
import play.api.libs.json._
import play.api.libs.json.Reads._
import play.api.libs.functional.syntax._
val dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
val customReads = Reads[DateTime](js =>
js.validate[String].map[DateTime](dtString =>
DateTime.parse(dtString, DateTimeFormat.forPattern(dateFormat))
)
)
implicit val reads: Reads[FacebookPost] = (
(__ \ "message").read[String] and
(__ \ "updated_time").read[DateTime](customReads)
)(FacebookPost.apply _)
然后,可以执行以下操作:
val json = Json.parse(
"""
{
"message": "Bla bla bla",
"updated_time": "2016-09-17T12:48:12+0000"
}
""")
val post = json.validate[FacebookPost]
// => JsSuccess(FacebookPost(Bla bla bla,2016-09-17T14:48:12.000+02:00))
编辑:
您不需要从头开始创建 Read[DateTime]
,Play 中有一个预定义的方法可以帮助您:
object CustomReads /* or wherever you want to define it */ {
val dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
implicit val jodaDateReads = play.api.libs.json.Reads.jodaDateReads(dateFormat)
}
完成。只需在需要时导入,例如在模型的伴生对象中 classes:
object FacebookPost {
import utils.CustomReads._
implicit val reads: Reads[FacebookPost] = Json.reads[FacebookPost]
}
您可以 "override" Play 提供的隐式 Read[DateTime]
,方法是将其从您的导入中排除:
import play.api.libs.json.Reads.{DefaultJodaDateReads => _, _}
我已经阅读了这篇文章 JsValue
转换为带有 Joda DateTime 的案例 class .
这是 JSON 我有:
val json = Json.parse(
"""
{
"message": "Bla bla bla",
"updated_time": "2016-09-17T12:48:12+0000"
}
"""
)
而对应的案例class是:
import org.joda.time.DateTime
final case class FacebookPost(message: String, updated_time: DateTime)
我还添加了这个隐式 DateTime reader(我也尝试了其他一些):
implicit val readsJodaLocalDateTime = Reads[DateTime](js =>
js.validate[String].map[DateTime](dtString => new DateTime(dtString)))
但是当我尝试将我的 json 转换为相应的大小写 class (json.as[FacebookPost]
) 时,我收到此错误:
play.api.libs.json.JsResultException: `JsResultException(errors:List((/updated_time,List(ValidationError(List(error.expected.jodadate.format),WrappedArray(yyyy-MM-dd))))))`
我做错了什么?
您的问题是日期时间的格式:2016-09-17T12:48:12+0000
。
默认情况下,Joda 的 DateTime
class 无法自动识别您正在使用的格式,因此您必须使用 DateTimeFormat
.[=21= 提供提示]
我们的自定义示例 Reads[DateTime]
:
import play.api.libs.json._
import play.api.libs.json.Reads._
import play.api.libs.functional.syntax._
val dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
val customReads = Reads[DateTime](js =>
js.validate[String].map[DateTime](dtString =>
DateTime.parse(dtString, DateTimeFormat.forPattern(dateFormat))
)
)
implicit val reads: Reads[FacebookPost] = (
(__ \ "message").read[String] and
(__ \ "updated_time").read[DateTime](customReads)
)(FacebookPost.apply _)
然后,可以执行以下操作:
val json = Json.parse(
"""
{
"message": "Bla bla bla",
"updated_time": "2016-09-17T12:48:12+0000"
}
""")
val post = json.validate[FacebookPost]
// => JsSuccess(FacebookPost(Bla bla bla,2016-09-17T14:48:12.000+02:00))
编辑:
您不需要从头开始创建 Read[DateTime]
,Play 中有一个预定义的方法可以帮助您:
object CustomReads /* or wherever you want to define it */ {
val dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
implicit val jodaDateReads = play.api.libs.json.Reads.jodaDateReads(dateFormat)
}
完成。只需在需要时导入,例如在模型的伴生对象中 classes:
object FacebookPost {
import utils.CustomReads._
implicit val reads: Reads[FacebookPost] = Json.reads[FacebookPost]
}
您可以 "override" Play 提供的隐式 Read[DateTime]
,方法是将其从您的导入中排除:
import play.api.libs.json.Reads.{DefaultJodaDateReads => _, _}