我有MyFormat
的自定义格式化程序(例如org.joda.DateTime
),它提供Format[org.joda.DateTime]
。
Play为play.api.libs.json
包中的同一个类提供默认格式化程序。
我想在我的应用程序中使用MyFormat
,而不是Play提供的那个。我已经通过显式导入/ mixins完成了这个工作,但是在更改或遗漏时,当这些被删除时,序列化默认为Play格式化程序,我最终会遇到运行时错误。这似乎非常容易出错。
最终,如果需要一个MyFormat
范围内的org.joda.DateTime
,我希望我的代码不要编译。
有没有一种安全可靠的方法呢?
答案 0 :(得分:0)
你有两个选择,但它们都不是你想要的。问题的关键在于Scala将在相关的伴随对象中寻找隐含。例如,如果需要查找隐式Format[DateTime]
,它将在Format
的伴随对象和DateTime
的伴随对象中查找。在这种情况下,Format
内的隐式def会产生所需的(或者在你的情况下,不需要的)Format[DateTime]
并且没有什么可以摆脱它,除了分叉和黑客播放。
解决方法1 :使用自定义格式化程序创建对象,并将其全局导入:
package my.project
object Formats {
implicit val dateTimeFormat: Format[DateTime] = ???
}
(在其他文件中)
import my.project.Formats._
导入到本地范围的Format[DateTime]
将取代从Format
对象解析的DateTime
。但是,如果没有它,您就无法阻止代码编译(除非您有某种scalastyle规则或需要导入的东西)。
解决方法2 :使用Format
创建DateTime
的包装器,并将其隐式转换为case class MyDateTime(dt: DateTime) {
implicit def toDateTime: DateTime = dt
}
object MyDateTime {
implicit val fmt: Format[MyDateTime] = ???
implicit def fromDateTime(dt: DateTime): MyDateTime = MyDateTime(dt)
}
。
DateTime
这不是一个完整的例子,而是关于如何实现它的想法。 MyDateTime
可以与大多数地方MyDateTime
进行交换,但可能需要围绕ToStatement[MyDateTime]
进行其他隐含。例如,当我尝试将它与Anorm一起使用时,我需要一个隐式的Format[DateTime]
,可能还需要一些其他的 - 所以这是明显的缺点。但是,这将明确避免使用默认的itemizedlist
。