2010-11-23 8 views
3

Ok, ich schreibe implizite Konvertierungen für Fallklassen in Scala mit SJSON, um Nachrichten an entfernte Akteure zu senden, die das akka-Framework verwenden. Eine der Fallklassen sieht so aus:Einen Akka actorRef an json senden

case class Example(id: String, actr: ActorRef) 

Wie würde ich gehen über die implizite für diesen Fall Klasse schreiben.

Ich habe gesehen, dass ActorRefs eine toBinary Methode haben zu tun, aber ich brauche es

zu senden toJSON

Antwort

3
  • http://doc.akkasource.org/serialization-scala. Explizite [tiefe] Serialisierung kann nur für zustandsbehaftete Akteure erforderlich sein, wenn die zugrunde liegende Akteurinstanz (unter ActorRef/RemoteActorRef) einige wichtige Laufzeitdaten enthält. Für diesen Fall sollten Sie die folgenden typeclass für Ihren Schauspieler implementieren:
/** 
* Type class definition for Actor Serialization 
*/ 
trait FromBinary[T <: Actor] { 
    def fromBinary(bytes: Array[Byte], act: T): T 
} 

trait ToBinary[T <: Actor] { 
    def toBinary(t: T): Array[Byte] 
} 

// client needs to implement Format[] for the respective actor 
trait Format[T <: Actor] extends FromBinary[T] with ToBinary[T] 

Wenn Sie ScalaJSON Serialisierung wollen, anstelle des Standard ein, sollten Sie SerializerBasedActorFormat Merkmal verwenden

trait SerializerBasedActorFormat[T <: Actor] extends Format[T] { 
    val serializer: Serializer 
    def fromBinary(bytes: Array[Byte], act: T) = serializer.fromBinary(bytes, Some(act.self.actorClass)).asInstanceOf[T] 
    def toBinary(ac: T) = serializer.toBinary(ac) 
} 

mit ScalaJSON serializer. Die SJSON-Bibliothek unterstützt die Standardisierung einfacher Scala-Objekte ohne eine zusätzliche Konfiguration (was in den meisten Fällen ausreichend ist). Wenn Sie einige Eigenschaften ignorieren oder Serialisierungsrichtlinien für eingebettete Objekte definieren müssen, lesen Sie this.

In Ihrem Fall würden Sie so etwas wie

@BeanInfo 
case class Example(id: String, 
@(JSONTypeHint @field)(value = classOf[MyActor]) 
actr: ActorRef) 

implicit object MyActorFormat extends SerializerBasedActorFormat[MyActor] { 
    val serializer = Serializer.ScalaJSON 
} 
  • Generell benötigen, brauchen Sie nicht Ihren Fall Klassen explizit serialisiert, wenn Sie Nachrichten an Remote-Akteure in Akka sind zu senden - Akka selbst serialisiert alle Daten mit Protobufs vor dem Senden über TCP.
  • Warum sollten Sie die Referenz auf den Schauspieler serialisieren? Wenn Sie den Absender nur durch den Akteur anrufen müssen, der die Nachricht empfängt, können Sie einfach self.sender verwenden, wenn die Nachricht mit ! oder gesendet wurde, wenn die Nachrichten mit !! oder !!! gesendet werden. ActorRef (oder RemoteActorRef) auf sich selbst ist nur eine abstrakte Schnittstelle zu einem Akteur, um die Implementierung des internen Akteurs zu kapseln und das Äußere nur über Nachrichten mit dem Akteur kommunizieren zu lassen (im Gegensatz zu stdlib Actors/ähnlich wie in Erlang [processes]) und enthält sehr kleine Datenmengen, die serialisiert und über Kabel gesendet werden können.
+0

Awesome Dank für die Hilfe. Wissen Sie zufällig, ob das für eine Fallklasse funktioniert, die von einem versiegelten Merkmal erbt? – trjohn06

+0

Sicher, es wird funktionieren –

Verwandte Themen