2015-10-12 49 views
3

我是Java開發人員,對scala很新穎。如何爲spray + akka actor設置隱式json轉換

我正在實現一些使用噴霧和akka的其他API API應該公開某種用戶CRUD。我只用在這個問題上創建用戶...

trait DefaultJsonFormats extends DefaultJsonProtocol with SprayJsonSupport with MetaMarshallers {} 

class RegistrationService(registration: ActorRef) 
    (implicit executionContext: ExecutionContext) 
         extends Directives with DefaultJsonFormats { 
implicit val timeout = Timeout(2.seconds) 
implicit val userFormat = jsonFormat3(User) 
implicit val registerFormat = jsonFormat1(Register) 
implicit val registeredFormat = jsonFormat1(Registered) 

    val route = 
    path("register") { 
     post { handleWith { ru: Register => (registration ? ru).mapTo[Registered] } } 
} 

// ------演員

object RegistrationActor { 
    case class User(id:String, name:String) 
    case class Register(user: User) 
    case class Registered(status: String) 
    case object NotRegistered 
} 

class RegistrationActor(implDef: String) extends Actor { 
def receive: Receive = { 
    case Register(user)=> 
     val status=// create user real code with return status 
     sender ! new Registered(status) 
} } 

在這種方法中JSON序列化和desiarelization是煩了。對於每一個對象,我需要處理的API我必須定義相應的格式

implicit val userFormat = jsonFormat3(User) 
implicit val registerFormat = jsonFormat1(Register) 
implicit val registeredFormat = jsonFormat1(Registered) 

我想避免這樣的定義,並使用一些通用的JSON轉換器,並返回一個POJO對象,所以轉換將下the-發生引擎蓋

問題是如何更改此代碼以默認使用Gson/Jackson/Spray默認轉換器並避免隱式的定義... jsonFormats?

回答

3

對於每一個對象,我需要處理的API我必須定義相應的格式

這是正常的,這樣做一次,在「JsonProtocol」類和進口是在需要的地方,而不是定義

import MyJsonProtocol._ 

val route = 
    path("register") { 
    post { handleWith { ru: Register => (registration ? ru).mapTo[Registered] } } 

我怎樣才能改變這種代碼默認GSON /傑克遜/噴霧默認轉換器使用,避免隱性的定義... jsonFormats:每次有新的格式?

您將需要從Registered聲明的隱含編組到HttpResponse(或類似String中間值),這是由傑克遜,而不是spray-json支持,然後導入編組,而不是SprayJsonSupport

看看the implementation of SprayJsonSupport看看如何做到這一點。如果你對隱式轉換感到滿意,這很簡單。

你也可以在Spray中看到Json4sSupport的完成情況 - 對於所有類型T,該特徵實現了Marshaller[T, String]。然後,在運行時,Json4s庫將嘗試將該對象序列化爲JSON。

在這種方法中JSON序列化和desiarelization是煩

還有的spray-json的做法在傑克遜的兩個主要優點:

  • 沒有反射,所以它比較快在運行時
  • 這是沒有運行時確定的JSON格式,因此任何問題都在編譯時捕獲
+0

謝謝,我已經研究過JsonProtocol的例子 - 它不完全一樣的我的問題已經做了(如隱VAL userFormat = jsonFormat3(用戶)...),我找了一個代碼版本,其中編組將自動發生在handle_with {}塊 – Julias

+0

「它完全相同」 - 是的,沒錯;它只是更可重用。 「我在尋找一個代碼版本」 - 我不明白你的意思。如果我能爲你澄清答案,請告訴我。 – Rich

+0

我已經看到與Json4sSupport和路由定義如方法:pathPrefix( 「登記」){{PATHEND文{ 實體(如[註冊]){RU =>的RequestContext => ...在該方法中轉化率發生withing --as--運算符,並沒有必要定義jsonFormat1(...)但我找不到一個方法來做這樣的事情與句柄 – Julias