Example #1
0
        /// <summary>
        ///   Invoked when a router gets a message.
        /// </summary>
        /// <param name="sender">
        ///   The <see cref="IMessageRouter"/>.
        /// </param>
        /// <param name="msg">
        ///   The message.
        /// </param>
        /// <remarks>
        ///   Invokes any topic handlers and publishes the messages on the other routers.
        /// </remarks>
        private void Router_MessageReceived(object sender, PublishedMessage msg)
        {
            ++MesssagesReceived;

            // Check for duplicate message.
            if (_tracker.RecentlySeen(msg.MessageId))
            {
                ++DuplicateMesssagesReceived;
                return;
            }

            // Call local topic handlers.
            var handlers = _topicHandlers.Values
                           .Where(th => msg.Topics.Contains(th.Topic));

            foreach (var handler in handlers)
            {
                try
                {
                    handler.Handler(msg);
                }
                catch (Exception e)
                {
                    _log.Error($"Topic handler for '{handler.Topic}' failed.", e);
                }
            }

            // Tell other message routers.
            _ = Task.WhenAll(Routers
                             .Where(r => r != sender)
                             .Select(r => r.PublishAsync(msg, CancellationToken.None))
                             );
        }
Example #2
0
        /// <inheritdoc />
        public Task PublishAsync(PublishedMessage message, CancellationToken cancel)
        {
            cancel.ThrowIfCancellationRequested();

            if (!_tracker.RecentlySeen(message.MessageId))
            {
                MessageReceived?.Invoke(this, message);
            }

            return(Task.CompletedTask);
        }
Example #3
0
        /// <inheritdoc />
        public Task PublishAsync(PublishedMessage message, CancellationToken cancel)
        {
            if (_tracker.RecentlySeen(message.MessageId))
            {
                return(Task.CompletedTask);
            }

            // Find a set of peers that are interested in the topic(s).
            // Exclude author and sender
            var peers = message.Topics
                        .SelectMany(topic => RemoteTopics.GetPeers(topic))
                        .Where(peer => peer != message.Sender)
                        .Where(peer => peer != message.Forwarder);

            // Forward the message.
            var forward = new PubSubMessage
            {
                PublishedMessages = new[] { message }
            };

            return(SendAsync(forward, peers, cancel));
        }