2016-04-14 24 views
1

o 2.4 Çal/Scala böyle bir şey yapmak mümkün mü oynayın:2.4 parametreli cebirsel veri türleri JSON doğrulama

sealed trait Location { val `type`: String } 
case class CityLocation(zip_code: String, override val `type`: String = "city") extends Location 
case class AddressLocation(
    society: Option[String], 
    first_name: String, 
    last_name: String, 
    ... 
    override val `type`: String = "address" 
) extends Location 

sealed trait Point[T <: Location] { val `type`: String; val location: T } 
case class ShippingPoint[T](override val location: T, override val `type`: String = "shipping") extends Point[T] 
case class PickupPoint[T](override val location: T, override val `type`: String = "pickup") extends Point[T] 

object CityLocation { 
    implicit val format = Json.format[CityLocation] 
} 
object AddressLocation { 
    implicit val format = Json.format[AddressLocation] 
} 
object ShippingPoint { 
    implicit def write[T] = Json.writes[ShippingPoint[T]] 
    implicit def read[T]: Reads[ShippingPoint[T]] = (
    (__ \ "location").read[T] and 
     (__ \ "type").read[String](exactWordRead("shipping", "error.route.shipping.type")) 
)(ShippingPoint[T].apply _) 
} 
object PickupPoint { 
    implicit def write[T] = Json.writes[ShippingPoint[T]] 
    implicit def read[T]: Reads[PickupPoint[T]] = (
    (__ \ "location").read[T] and 
     (__ \ "type").read[String](exactWordRead("pickup", "error.route.pickup.type")) 
)(PickupPoint[T].apply _) 
} 

??

Şimdilik, Derleme yapmıyor.

sealed trait Location { val `type`: String } 
case class CityLocation(zip_code: String, override val `type`: String = "city") extends Location 
case class AddressLocation(
    society: Option[String], 
    first_name: String, 
    last_name: String, 
    ... 
    override val `type`: String = "address" 
) extends Location 

sealed trait Point[T <: Location] { val location: T; val `type`: String } 
case class ShippingPoint[T](override val location: T, override val `type`: String = "shipping") extends Point[T] 
case class PickupPoint[T](override val location: T, override val `type`: String = "pickup") extends Point[T] 

object CityLocation { 
    implicit val format = Json.format[CityLocation] 
} 
object AddressLocation { 
    implicit val format = Json.format[AddressLocation] 
} 
object ShippingPoint { 
    implicit def format[T: Format]: Format[ShippingPoint[T]] = (
    (__ \ "location").format[T] and 
     (__ \ "type").format[String](exactWordRead("shipping", "error.route.shipping.type")) 
)(ShippingPoint.apply, unlift(ShippingPoint.unapply)) 
} 
object PickupPoint { 
    implicit def format[T: Format]: Format[PickupPoint[T]] = (
    (__ \ "location").format[T] and 
     (__ \ "type").format[String](exactWordRead("pickup", "error.route.pickup.type")) 
)(PickupPoint.apply, unlift(PickupPoint.unapply)) 
} 
:

Öyle bir adım bu cevap https://stackoverflow.com/a/29834113/2431728 ileri sayesinde hizmetçi gibi görünüyor:

def exactWordRead(word: String, errorMessage: String): Reads[String] = Reads.constraints.pattern(s"^$word${"$"}".r, errorMessage) 

Düzenleme:

exactWordRead yöntem aşağıdaki gibi tanımlanır

Ancak, yok Henüz derlemedim. derleme hatadır: Sahip olduğunuz bir tarafta derleyici tarafından söylediği gibi

[error] type arguments [T] do not conform to trait Point's type parameter bounds [T <: services.coliswebApi.data.Location] 
[error] case class ShippingPoint[T](override val location: T, override val `type`: String = "shipping") extends Point[T] 
[error]                          ^
[error] type arguments [T] do not conform to trait Point's type parameter bounds [T <: services.coliswebApi.data.Location] 
[error] case class PickupPoint[T](override val location: T, override val `type`: String = "pickup") extends Point[T] 

cevap

1

Ben de Nitekim bu

implicit def format[T <: Location: Format]: Format[ShippingPoint[T]] = (
     (__ \ "location").format[T] and 
     (__ \ "type").format[String](exactWordRead("shipping", "error.route.shipping.type")) 
    )(ShippingPoint.apply, unlift(ShippingPoint.unapply)) 
+1

Bu derler! Thaaaanks çok = D –

2

,

sealed trait Point[T <: Location] 

... ve diğer tarafta,

case class ShippingPoint[T](???) extends Point[T] 
case class PickupPoint[T](???) extends Point[T] 

Ama hiçbir şey de ShippingPoint ve PickupPoint bildirimleri, tür parametresinin Point kapsamını genişletmek için gerekli olan kısıtlaması <: Location ile uyumlu olduğunu kanıtlıyor.

Bunu düzeltmeniz gerekiyor.

case class ShippingPoint[T <: Location](???) extends Point[T] 
case class PickupPoint[T <: Location](???) extends Point[T] 
+0

sevdiği biçimde türünü bağlı gerektiğini düşünüyorum. Ama şimdi derleme olmayan formatlar. Onları nasıl düzelteceğiniz hakkında bir fikrin var mı? –

+1

Nedeni aynı. – cchantep

+0

Gerçekten. Yardım için teşekkürler =) –