Beispiel #1
0
        /// <summary>
        /// Acquires an appropriate event envelope.
        /// </summary>
        /// <returns></returns>
        private static MeshEvent Create(MeshEventType type)
        {
            // Get the appropriate packet
            switch (type)
            {
            case MeshEventType.Error:
            case MeshEventType.Ping:
            case MeshEventType.PingAck:
            case MeshEventType.HandshakeAck:
                return(MeshEvent.Acquire());

            case MeshEventType.Handshake:
                return(MeshHandshake.Acquire());

            case MeshEventType.GossipDigest:
            case MeshEventType.GossipSince:
            case MeshEventType.GossipUpdate:
                return(MeshGossip.Acquire());

            case MeshEventType.Subscribe:
            case MeshEventType.Unsubscribe:
            case MeshEventType.Custom:
                return(MeshEmitterEvent.Acquire());

            default:
                throw new InvalidOperationException("Unknown mesh packet");
            }
        }
Beispiel #2
0
        /// <summary>
        /// Sends a mesh Handshake through the specified channel.
        /// </summary>
        /// <param name="channel">The channel to send the packet to.</param>
        internal static void SendMeshHandshakeAck(this Connection channel)
        {
            var provider = Service.Providers.Resolve <MeshProvider>();

            if (provider == null)
            {
                return;
            }

            // Send the ack
            channel.Send(MeshEvent.Acquire(MeshEventType.HandshakeAck, provider.BroadcastEndpoint.ToString()));
        }
Beispiel #3
0
        /// <summary>
        /// Handles the command.
        /// </summary>
        /// <param name="channel">The channel sending the command.</param>
        /// <param name="command">The command received.</param>
        private static void OnHandshakeAck(Connection channel, MeshEvent command)
        {
            // Attempt to register
            MeshMember node;
            IPEndPoint ep;

            if (!MeshMember.TryParseEndpoint(command.Value, out ep))
            {
                Service.Logger.Log(LogLevel.Error, "Unable to parse endpoint: " + command.Value);
                channel.Close();
                return;
            }

            // Register the endpoint
            if (Service.Mesh.Members.TryRegister(ep, channel, out node))
            {
                // Send an event since we're connected to the node
                Service.InvokeNodeConnect(new ClusterEventArgs(node));
            }
            else
            {
                channel.Close();
            }
        }
Beispiel #4
0
 /// <summary>
 /// Sends a mesh PingAck through the specified channel.
 /// </summary>
 /// <param name="channel">The channel to send the packet to.</param>
 internal static void SendMeshPingAck(this Connection channel)
 {
     // Send the ack
     channel.Send(MeshEvent.Acquire(MeshEventType.PingAck));
 }
Beispiel #5
0
 /// <summary>
 /// Sends a mesh ping through the specified channel.
 /// </summary>
 /// <param name="server">The channel to send the packet to.</param>
 internal static void SendMeshPing(this IServer server)
 {
     server.Send(MeshEvent.Acquire(MeshEventType.Ping));
 }
Beispiel #6
0
 /// <summary>
 /// Sends a mesh PingAck through the specified channel.
 /// </summary>
 /// <param name="channel">The channel to send the packet to.</param>
 /// <param name="ex">The exception to wrap.</param>
 internal static void SendMeshError(this Connection channel, Exception ex)
 {
     // Send the error back
     channel.Send(MeshEvent.Acquire(MeshEventType.Error, ex.Message));
 }
Beispiel #7
0
 /// <summary>
 /// Handles the custom commands, JSON-encoded.
 /// </summary>
 /// <param name="server">The server which is sending the command.</param>
 /// <param name="event">The event.</param>
 /// <returns>The processing state of the event.</returns>
 public abstract ProcessingState ProcessEvent(IServer server, MeshEvent @event);
Beispiel #8
0
        /// <summary>
        /// Handles a command.
        /// </summary>
        public static ProcessingState Process(Connection channel, MeshEvent ev)
        {
            // Trace the operation number and the length of the packet
            //if (ev.Type != MeshEventType.Gossip)
            //    NetTrace.WriteLine("Incoming " + ev.ToString(), channel, NetTraceCategory.Mesh);

            try
            {
                switch (ev.Type)
                {
                // Acknowledge the Heartbeat/Ping
                case MeshEventType.Ping:
                    OnPing(channel);
                    break;

                // Acknowledge the handshake
                case MeshEventType.Handshake:
                    OnHandshake(channel, ev as MeshHandshake);
                    break;

                // On the ack, the remote node sends its identifier to us
                case MeshEventType.HandshakeAck:
                    OnHandshakeAck(channel, ev);
                    break;

                // When a node receives a gossip digest
                case MeshEventType.GossipDigest:
                    OnGossipDigest(channel, ev as MeshGossip);
                    break;

                // When a node receives a gossip since request
                case MeshEventType.GossipSince:
                    OnGossipSince(channel, ev as MeshGossip);
                    break;

                // When a node receives a gossip update
                case MeshEventType.GossipUpdate:
                    OnGossipUpdate(channel, ev as MeshGossip);
                    break;

                // When a custom command is received
                case MeshEventType.Custom:
                default:
                    var node = Service.Mesh.Members.Get(channel.MeshIdentifier);
                    if (node == null)
                    {
                        break;
                    }

                    // Only invoke if we have a properly established connection
                    Service.Mesh.OnEvent(node, ev);
                    break;
                }
            }
            catch (Exception ex)
            {
                // Send the error back
                //Service.Logger.Log("Error On " + ev.ToString() + ": " + ex.Message);
                Service.Logger.Log(ex);
                channel.SendMeshError(ex);
            }

            // We do not need to process further, as we've handled the command
            return(ProcessingState.Success);
        }