Example #1
0
        public async Task TestIisHostReceiver()
        {
            touched = 0;
            CancellationTokenSource tokenSource = new CancellationTokenSource();

            // Start the listener on another thread.
            Task t = await Task.Factory.StartNew(Listener2, tokenSource.Token);

            var stopwatch = new Stopwatch();

            Assert.Equal(0, Interlocked.Read(ref touched));

            var messages = new List <Message>();
            var tags     = new Dictionary <string, string>
            {
                { "key", "value" }
            };

            for (int i = 0; i < 1000; i++)
            {
                messages.Add(
                    new Message("Order.Test.OutQ.Listener", Encoding.UTF8.GetBytes(Guid.NewGuid().ToString()), string.Empty, Guid.NewGuid().ToString(), tags)
                    );
            }


            Assert.Equal(0, Interlocked.Read(ref touched));

            QueueStream queue = new QueueStream("localhost:50000", "Demo.Test.IISHost", null);

            stopwatch.Start();

            await queue.Send(new SendRequest(messages));

            stopwatch.Stop();

            Logger.Technical().Debug($"Messages sent in {stopwatch.ElapsedMilliseconds} ms.").Log();

            stopwatch.Reset();
            stopwatch.Start();


            do
            {
                await Task.Delay(10);
            } while (Interlocked.Read(ref touched) < 1000 && stopwatch.ElapsedMilliseconds < 10000);

            stopwatch.Stop();

            Logger.Technical().Debug($"Messages read in {stopwatch.ElapsedMilliseconds} ms.").Log();

            tokenSource.Cancel();

            await Task.Delay(150);

            Assert.Equal(1000, Interlocked.Read(ref touched));
            Task.WaitAll(t);
            queue.Close();
        }
        /// <summary>
        /// All the messages must be of the same type.
        /// </summary>
        /// <param name="messages"></param>
        private void SendToQueueInBatch(IEnumerable <QueueMessage> messages)
        {
            using (var activity = _activitySource?.StartActivity("Send messages to KubeMQ", ActivityKind.Producer))
            {
                var definition = GetDefiniton(messages.First().Value.GetType());

                var policy = definition.RetryPolicy(Policy.Handle <Exception>());

                QueueStream queue = null;
                policy.Execute(() => queue = _queueStreamManager.Get(definition));

                if (null == queue)
                {
                    throw new NullReferenceException($"No queue was created for Address: {definition.Address} and Identitfier {definition.Identifier}");
                }



                var serializer = GetSerializer(definition);
                var _messages  = new List <Message>(messages.Count());

                string activityId = _applicationContext?.Principal?.ActivityID.ToString() ?? Guid.NewGuid().ToString();


                using (var serializerActivity = _activitySource?.StartActivity("Serialize.", ActivityKind.Producer))
                {
                    serializerActivity?.AddTag("Count", messages.Count());
                    // I use messageType because we consider that we send a message of the same type...
                    // Doing it by ChannelParameter will be more efficient...
                    foreach (var message in messages)
                    {
                        _messages.Add(
                            new Message(definition.Namespace, serializer.Serialize(message.Value), String.Empty, Guid.NewGuid().ToString(), BuildTags(message.Value.GetType(), message.Tags, activityId))
                        {
                            Policy = BuildPolicy(definition, message.SendAfterSeconds, message.ExpireAfterSeconds)
                        }
                            );
                    }
                }

                policy.Execute(() =>
                {
                    using (var sendActivity = _activitySource?.StartActivity("Send to KubeMQ", ActivityKind.Producer))
                        queue.Send(new SendRequest(_messages));
                });
            }
        }
        public void Send <TMessage>(TMessage message, Dictionary <string, string> tags = null, uint?sendAfterSeconds = null, uint?expireAfterSeconds = null) where TMessage : notnull
        {
            using (var activity = _activitySource?.StartActivity("Send message to KubeMQ", ActivityKind.Producer))
            {
                activity?.AddTag("Delay message [s]", sendAfterSeconds);
                activity?.AddTag("Expire message after [s]", expireAfterSeconds);

                if (message is IEnumerable)
                {
                    throw new ArgumentException("Collection are not accepted!");
                }

                var messageType = typeof(TMessage);

                var definition = GetDefiniton(messageType);

                var policy = definition.RetryPolicy(Policy.Handle <Exception>());

                QueueStream queue = null;
                policy.Execute(() => queue = _queueStreamManager.Get(definition));

                if (null == queue)
                {
                    throw new NullReferenceException($"No queue was created for Address: {definition.Address} and Identitfier {definition.Identifier}");
                }

                var serializer = GetSerializer(definition);

                string activityId = _applicationContext?.Principal?.ActivityID.ToString() ?? Guid.NewGuid().ToString();

                Message _message = null;
                using (var serializerActivity = _activitySource?.StartActivity("Serialize.", ActivityKind.Producer))
                    _message = new Message(definition.Namespace, serializer.Serialize(message), String.Empty, Guid.NewGuid().ToString(), BuildTags(messageType, tags, activityId))
                    {
                        Policy = BuildPolicy(definition, sendAfterSeconds, expireAfterSeconds)
                    };

                using (var sendActivity = _activitySource?.StartActivity("Send to KubeMQ", ActivityKind.Producer))
                    queue.Send(new SendRequest(new List <Message>(1)
                    {
                        _message
                    }));
            }
        }
Example #4
0
        public async Task TestBasicSendAndReceive()
        {
            QueueStream queue = new QueueStream("localhost:50000", "Demo.Test.Basic", null);

            var messages = new List <Message>();
            var tags     = new Dictionary <string, string>
            {
                { "key", "value" }
            };

            for (int i = 0; i < 1000; i++)
            {
                messages.Add(
                    new Message("Order.Test.OutQ.Basic", Encoding.UTF8.GetBytes(Guid.NewGuid().ToString()), string.Empty, Guid.NewGuid().ToString(), tags)
                    );
            }

            var res = await queue.Send(new SendRequest(messages));

            PollRequest pollRequest = new()
            {
                Queue       = "Order.Test.OutQ.Basic",
                WaitTimeout = 1000,
                MaxItems    = 100,
                AutoAck     = false
            };

            var read = 0;

            while (read < 1000)
            {
                PollResponse response = await queue.Poll(pollRequest);

                if (!response.HasMessages)
                {
                    continue;
                }

                Logger.Technical().Debug($"{response.Messages.Count()} message(s) received from the PollResponse.").Log();

                Parallel.ForEach(response.Messages, msg =>
                {
                    try
                    {
                        Assert.Equal(1, msg.Tags.Count());

                        Assert.True(Guid.TryParse(Encoding.UTF8.GetString(msg.Body), out var guid));

                        msg.Ack();
                    }
                    catch (Exception)
                    {
                        msg.NAck();
                    }
                });

                read += response.Messages.Count();
            }

            Assert.Equal(1000, read);
            queue.Close();
        }
        private void SendToQueueInBatch(IEnumerable <QueueMessage> messages, int splitByQueues)
        {
            using (var activity = _activitySource?.StartActivity("Send messages to KubeMQ", ActivityKind.Producer))
            {
                activity?.AddTag("Split", splitByQueues);

                if (splitByQueues < 2)
                {
                    throw new ArgumentOutOfRangeException("Number of queues must be greater than 1!");
                }

                if (splitByQueues > 10)
                {
                    splitByQueues = 10;
                    _logger.Technical().Warning("Cap the number of queues to 10").Log();
                }

                var messageType = messages.First().Value.GetType();
                // All the messages are assumed to be of the same type.
                var definition = GetDefiniton(messageType);

                var policy = definition.RetryPolicy(Policy.Handle <Exception>());

                QueueStream queue = null;
                policy.Execute(() => queue = _queueStreamManager.Get(definition));

                if (null == queue)
                {
                    throw new NullReferenceException($"No queue was created for Address: {definition.Address} and Identitfier {definition.Identifier}");
                }

                var serializer = GetSerializer(definition);

                string activityId = _applicationContext?.Principal?.ActivityID.ToString() ?? Guid.NewGuid().ToString();

                var messagesByQueue = Math.DivRem(messages.Count(), splitByQueues, out var rem);
                var _messages       = new List <Message>(messagesByQueue + rem);

                int idx      = 0;
                int queueIdx = 1;
                foreach (var message in messages)
                {
                    using (var createactivity = _activitySource?.StartActivity("Create KubeMQ messages", ActivityKind.Producer))
                    {
                        createactivity?.AddTag("Count", messages.Count());
                        createactivity?.AddTag("QueueName", $"{definition.Namespace}.{queueIdx}");

                        _messages.Add(
                            new Message($"{definition.Namespace}.{queueIdx}", serializer.Serialize(message.Value), String.Empty, Guid.NewGuid().ToString(), BuildTags(messageType, message.Tags, activityId))
                        {
                            Policy = BuildPolicy(definition, message.SendAfterSeconds, message.ExpireAfterSeconds)
                        }
                            );
                    }
                    idx++;

                    if (0 == idx % messagesByQueue) // we have on batch.
                    {
                        policy.Execute(() =>
                        {
                            using (var sendActivity = _activitySource?.StartActivity("Send to KubeMQ", ActivityKind.Producer))
                                queue.Send(new SendRequest(_messages));
                        });

                        queueIdx++;
                        idx = 0;
                        _messages.Clear();
                    }
                }
            }
        }