aboutsummaryrefslogtreecommitdiff
path: root/mavigator-uav/src/main/scala/mavigator/uav/Connection.scala
diff options
context:
space:
mode:
Diffstat (limited to 'mavigator-uav/src/main/scala/mavigator/uav/Connection.scala')
-rw-r--r--mavigator-uav/src/main/scala/mavigator/uav/Connection.scala73
1 files changed, 73 insertions, 0 deletions
diff --git a/mavigator-uav/src/main/scala/mavigator/uav/Connection.scala b/mavigator-uav/src/main/scala/mavigator/uav/Connection.scala
new file mode 100644
index 0000000..7399657
--- /dev/null
+++ b/mavigator-uav/src/main/scala/mavigator/uav/Connection.scala
@@ -0,0 +1,73 @@
+package mavigator.uav
+
+import akka.actor.ActorLogging
+import scala.collection.mutable.ArrayBuffer
+
+import akka.actor.Actor
+import akka.actor.ActorRef
+import akka.actor.Terminated
+import akka.actor.actorRef2Scala
+import akka.util.ByteString
+
+/** Protocol definition. */
+object Connection {
+
+ /** Any messages received and transmitted by actors implementing this protocol. */
+ sealed trait Message
+
+ /** Messages emitted by actors implementing this protocol. */
+ trait Event extends Message
+
+ /** Received data from the uav (or any other systems on the link) */
+ case class Received(bstr: ByteString) extends Event
+
+ /** The connection closed or could not be opened */
+ case class Closed(message: String) extends Event
+
+ /** Messages that can be received by actors implementing this protocol. */
+ trait Command extends Message
+
+ /** Register the sender to be notified on events */
+ case object Register extends Command
+
+ case class Unregister(client: ActorRef) extends Command
+
+ /** Send given bytes out to the uav (or any other systems on the link) */
+ case class Send(bstr: ByteString) extends Command
+
+}
+
+/** Common behavior of connection actors. */
+trait Connection { myself: Actor with ActorLogging =>
+
+ private val _clients = new ArrayBuffer[ActorRef]
+
+ /** Current clients that should be notified on incoming messages. */
+ def clients = _clients.toSeq
+
+ /** Adds a client to the client list and acquires a deathwatch. */
+ protected def register(client: ActorRef): Unit = {
+ _clients += client
+ myself.context.watch(client)
+ myself.log.info("Client registered {}", client)
+ }
+
+ /** Remove client and release deathwatch. */
+ protected def unregister(client: ActorRef): Unit = if (clients contains client) {
+ _clients -= client
+ myself.context.unwatch(client)
+ myself.log.info("Client unregistered {}", client)
+ }
+
+ /** Sends a message to all registered clients. */
+ protected def sendAll(msg: Any): Unit = clients foreach (_ ! msg)
+
+ /** Common registration behavior. Manages the messages `Register` and `Terminated` by
+ * registering and unregistering clients. */
+ protected def handleRegistration: Receive = {
+ case Connection.Register => register(sender)
+ case Terminated(client) => unregister(client)
+ case other => myself.log.warning("Unknown message: {}", other)
+ }
+
+}