lor*_*lan 5 scala playframework phantom-types
对于处理大量独立实体的服务,我试图拥有一些强类型。为了实现这一点,我使用了一种基于幻像类型/标记类型的技术,因为它可以在无形状或 scalaz 中找到。(我不想使用AnyVal,因为我真的不想支付装箱/拆箱的费用)
我做了一个最小的例子,遇到了以下编译错误:
class type required but String with controllers.TestController.Tagged[controllers.MyId] found
以下是文件:
package controllers
import javax.inject._
import controllers.TestController.TString
import play.api.mvc._
trait MyId
object TestController {
trait Tagged[U]
type TString[T] = String with Tagged[T]
def TString[T](s: String) = s.asInstanceOf[String with Tagged[T]]
implicit def tStringPathBindable[T](implicit binder : PathBindable[String]) : PathBindable[TString[T]] =
binder.transform(TString,identity)
}
@Singleton
class TestController @Inject() extends Controller {
def index(id : TString[MyId]) = Action { implicit request =>
Ok("")
}
}
Run Code Online (Sandbox Code Playgroud)
会议/路线
GET /myroute/:id 控制器.TestController.index(id : TString[MyId])
构建.sbt
name := """play-tag"""
lazy val root = (project in file(".")).enablePlugins(PlayScala)
scalaVersion := "2.11.11"
// Adds additional packages into conf/routes
play.sbt.routes.RoutesKeys.routesImport ++=
Seq(
"controllers.MyId",
"controllers.TestController._"
)
Run Code Online (Sandbox Code Playgroud)
项目/build.properties
sbt.版本=0.13.15
项目/plugins.sbt
addSbtPlugin("com.typesafe.play" % "sbt-plugin" % "2.5.14")
有办法解决这个错误吗?如果不是,原因是什么?必然的问题,实现我想要做的事情的最佳实践是什么?例如,我对公开 Id 由字符串组成的事实不太满意,但我也不想太多样板,因为我有很多实体需要处理。