コード例 #1
0
        public async Task TestMonitorCancelsAfterTargetChannelChanges()
        {
            var connectionFactory = new Mock <Connection.IConnectionFactory>();
            var connection        = new Mock <Connection.IConnection>();
            var channel           = new Mock <IChannelProxy>();
            var rabbitChannel1    = new Mock <R.IModel>();
            var rabbitChannel2    = new Mock <R.IModel>();
            var target            = new AtomicReference <R.IModel>(rabbitChannel1.Object);

            channel.Setup(c => c.TargetChannel).Returns(() => target.Value);

            connectionFactory.Setup((f) => f.CreateConnection()).Returns(connection.Object);
            connection.Setup((c) => c.CreateChannel(It.IsAny <bool>())).Returns(channel.Object);
            connection.Setup((c) => c.IsOpen).Returns(true);
            channel.Setup(c => c.IsOpen).Returns(true);

            rabbitChannel1.Setup(c => c.CreateBasicProperties()).Returns(new MockRabbitBasicProperties());
            rabbitChannel2.Setup(c => c.CreateBasicProperties()).Returns(new MockRabbitBasicProperties());
            channel.Setup(c => c.QueueDeclarePassive(It.IsAny <string>())).Returns(new R.QueueDeclareOk("test", 0, 0));

            var consumer = new AtomicReference <R.IBasicConsumer>();
            var latch1   = new CountdownEvent(1);
            var latch2   = new CountdownEvent(1);

            channel.Setup(c =>
                          c.BasicConsume(It.IsAny <string>(), It.IsAny <bool>(), It.IsAny <string>(), It.IsAny <bool>(), It.IsAny <bool>(), It.IsAny <IDictionary <string, object> >(), It.IsAny <R.IBasicConsumer>()))
            .Callback <string, bool, string, bool, bool, IDictionary <string, object>, R.IBasicConsumer>(
                (queue, autoAck, consumerTag, noLocal, exclusive, args, cons) =>
            {
                consumer.Value = cons;
                latch1.Signal();
            })
            .Returns("consumerTag");

            channel.Setup(c => c.BasicCancel("consumerTag"))
            .Callback(() =>
            {
                consumer.Value.HandleBasicCancelOk("consumerTag");
                latch2.Signal();
            });
            var container = new DirectMessageListenerContainer(null, connectionFactory.Object);

            container.SetQueueNames("test");
            container.PrefetchCount   = 2;
            container.MonitorInterval = 100;
            container.MessageListener = new TestListener2(target, rabbitChannel2.Object);
            container.AcknowledgeMode = AcknowledgeMode.MANUAL;
            container.Initialize();
            await container.Start();

            Assert.True(container._startedLatch.Wait(TimeSpan.FromSeconds(10)));

            Assert.True(latch1.Wait(TimeSpan.FromSeconds(10)));
            var props = new MockRabbitBasicProperties();

            consumer.Value.HandleBasicDeliver("consumerTag", 1ul, false, string.Empty, string.Empty, props, new byte[1]);
            Assert.True(latch2.Wait(TimeSpan.FromSeconds(10)));
            await container.Stop();
        }
コード例 #2
0
        public void TestBatch()
        {
            var bs      = new SimpleBatchingStrategy(2, 10_000, 10_000L);
            var headers = new RabbitHeaderAccessor();

            headers.ContentType = "test/plain";
            var message = Message.Create(Encoding.UTF8.GetBytes("test1"), headers.MessageHeaders);

            bs.AddToBatch("foo", "bar", message);
            message = Message.Create(Encoding.UTF8.GetBytes("test2"), headers.MessageHeaders);
            var batched = bs.AddToBatch("foo", "bar", message);

            Assert.True(batched.HasValue);
            var batchMessage    = batched.Value.Message;
            var batchHeaders    = batchMessage.Headers;
            var headerConverter = new DefaultMessageHeadersConverter();
            var props           = new MockRabbitBasicProperties();

            headerConverter.FromMessageHeaders(batchHeaders, props, Encoding.UTF8);
            props.ContentType = "text/plain";

            var config   = new ConfigurationBuilder().Build();
            var services = new ServiceCollection().BuildServiceProvider();
            var context  = new GenericApplicationContext(services, config);
            var channel  = new Mock <R.IModel>();

            channel.Setup(c => c.IsOpen).Returns(true);

            var getResponse = new R.BasicGetResult(123Ul, false, "ex", "rk", 0, props, (byte[])batchMessage.Payload);

            channel.Setup(c => c.BasicGet("foo", false)).Returns(getResponse);
            var connection = new Mock <R.IConnection>();

            connection.Setup(c => c.IsOpen).Returns(true);
            connection.Setup(c => c.CreateModel()).Returns(channel.Object);
            var connectionFactory = new Mock <R.IConnectionFactory>();

            connectionFactory.Setup(f => f.CreateConnection(It.IsAny <string>())).Returns(connection.Object);

            var ccf      = new CachingConnectionFactory(connectionFactory.Object);
            var source   = new RabbitMessageSource(context, ccf, "foo");
            var received = source.Receive();

            Assert.NotNull(received);
            var asList = received.Payload as List <object>;

            Assert.NotNull(asList);
            Assert.Contains("test1", asList);
            Assert.Contains("test2", asList);
        }
コード例 #3
0
        public void TestAck()
        {
            var config   = new ConfigurationBuilder().Build();
            var services = new ServiceCollection().BuildServiceProvider();
            var context  = new GenericApplicationContext(services, config);
            var channel  = new Mock <R.IModel>();

            channel.Setup(c => c.IsOpen).Returns(true);
            var props       = new MockRabbitBasicProperties();
            var getResponse = new R.BasicGetResult(123Ul, false, "ex", "rk", 0, props, Encoding.UTF8.GetBytes("foo"));

            channel.Setup(c => c.BasicGet("foo", false)).Returns(getResponse);
            var connection = new Mock <R.IConnection>();

            connection.Setup(c => c.IsOpen).Returns(true);
            connection.Setup(c => c.CreateModel()).Returns(channel.Object);
            var connectionFactory = new Mock <R.IConnectionFactory>();

            connectionFactory.Setup(f => f.CreateConnection(It.IsAny <string>())).Returns(connection.Object);

            var ccf    = new CachingConnectionFactory(connectionFactory.Object);
            var source = new RabbitMessageSource(context, ccf, "foo");

            source.RawMessageHeader = true;
            var received   = source.Receive();
            var rawMessage = received.Headers.Get <IMessage>(RabbitMessageHeaderErrorMessageStrategy.AMQP_RAW_MESSAGE);
            var sourceData = received.Headers.Get <IMessage>(IntegrationMessageHeaderAccessor.SOURCE_DATA);

            Assert.NotNull(rawMessage);
            Assert.Same(rawMessage, sourceData);
            Assert.Equal("foo", received.Headers.Get <string>(RabbitMessageHeaders.CONSUMER_QUEUE));

            // make sure channel is not cached
            var conn      = ccf.CreateConnection();
            var notCached = conn.CreateChannel(false);

            connection.Verify(c => c.CreateModel(), Times.Exactly(2));
            var callback = received.Headers.Get <IAcknowledgmentCallback>(IntegrationMessageHeaderAccessor.ACKNOWLEDGMENT_CALLBACK);

            callback.Acknowledge(Status.ACCEPT);
            channel.Verify(c => c.BasicAck(123ul, false));
            var cached = conn.CreateChannel(false); // should have been "closed"

            connection.Verify(c => c.CreateModel(), Times.Exactly(2));
            notCached.Close();
            cached.Close();
            ccf.Destroy();
            channel.Verify(c => c.Close(), Times.Exactly(2));
            connection.Verify(c => c.Close(30000));
        }
コード例 #4
0
        private void TestNackOrRequeue(bool requeue)
        {
            var config   = new ConfigurationBuilder().Build();
            var services = new ServiceCollection().BuildServiceProvider();
            var context  = new GenericApplicationContext(services, config);

            var channel = new Mock <R.IModel>();

            channel.Setup(c => c.IsOpen).Returns(true);
            var props       = new MockRabbitBasicProperties();
            var getResponse = new R.BasicGetResult(123Ul, false, "ex", "rk", 0, props, Encoding.UTF8.GetBytes("bar"));

            channel.Setup(c => c.BasicGet("foo", false)).Returns(getResponse);
            var connection = new Mock <R.IConnection>();

            connection.Setup(c => c.IsOpen).Returns(true);
            connection.Setup(c => c.CreateModel()).Returns(channel.Object);
            var connectionFactory = new Mock <R.IConnectionFactory>();

            connectionFactory.Setup(f => f.CreateConnection(It.IsAny <string>())).Returns(connection.Object);

            var ccf      = new CachingConnectionFactory(connectionFactory.Object);
            var source   = new RabbitMessageSource(context, ccf, "foo");
            var received = source.Receive();

            connection.Verify(c => c.CreateModel());
            var callback = received.Headers.Get <IAcknowledgmentCallback>(IntegrationMessageHeaderAccessor.ACKNOWLEDGMENT_CALLBACK);

            if (requeue)
            {
                callback.Acknowledge(Status.REQUEUE);
            }
            else
            {
                callback.Acknowledge(Status.REJECT);
            }

            channel.Verify(c => c.BasicReject(123ul, requeue));
            connection.Verify(c => c.CreateModel());
            ccf.Destroy();
            channel.Verify(c => c.Close());
            connection.Verify(c => c.Close(30000));
        }
コード例 #5
0
        public async Task TestDeferredAcks()
        {
            var connectionFactory = new Mock <Connection.IConnectionFactory>();
            var connection        = new Mock <Connection.IConnection>();
            var channel           = new Mock <IChannelProxy>();
            var rabbitChannel     = new Mock <R.IModel>();

            channel.Setup(c => c.TargetChannel).Returns(rabbitChannel.Object);
            connectionFactory.Setup((f) => f.CreateConnection()).Returns(connection.Object);
            connection.Setup((c) => c.CreateChannel(It.IsAny <bool>())).Returns(channel.Object);
            connection.Setup((c) => c.IsOpen).Returns(true);
            channel.Setup((c) => c.IsOpen).Returns(true);
            rabbitChannel.Setup(c => c.CreateBasicProperties()).Returns(new MockRabbitBasicProperties());
            channel.Setup(c => c.QueueDeclarePassive(It.IsAny <string>())).Returns(new R.QueueDeclareOk("test", 0, 0));

            var consumer = new AtomicReference <R.IBasicConsumer>();
            var latch1   = new CountdownEvent(1);

            channel.Setup(c =>
                          c.BasicConsume(It.IsAny <string>(), It.IsAny <bool>(), It.IsAny <string>(), It.IsAny <bool>(), It.IsAny <bool>(), It.IsAny <IDictionary <string, object> >(), It.IsAny <R.IBasicConsumer>()))
            .Callback <string, bool, string, bool, bool, IDictionary <string, object>, R.IBasicConsumer>(
                (queue, autoAck, consumerTag, noLocal, exclusive, args, cons) =>
            {
                consumer.Value = cons;
                cons.HandleBasicConsumeOk("consumerTag");
                latch1.Signal();
            })
            .Returns("consumerTag");
            var qos = new AtomicInteger();

            channel.Setup(c => c.BasicQos(It.IsAny <uint>(), It.IsAny <ushort>(), It.IsAny <bool>()))
            .Callback <uint, ushort, bool>((size, count, global) =>
            {
                qos.Value = count;
            });
            var latch2 = new CountdownEvent(1);
            var latch3 = new CountdownEvent(1);

            channel.Setup(c => c.BasicAck(It.IsAny <ulong>(), It.IsAny <bool>()))
            .Callback <ulong, bool>((tag, multi) =>
            {
                if (tag == 10ul || tag == 16ul)
                {
                    latch2.Signal();
                }
                else if (tag == 17ul)
                {
                    latch3.Signal();
                }
            });
            var latch4 = new CountdownEvent(1);

            channel.Setup(c => c.BasicNack(It.IsAny <ulong>(), It.IsAny <bool>(), It.IsAny <bool>()))
            .Callback <ulong, bool, bool>((tag, multi, re) =>
            {
                latch4.Signal();
            });
            var container = new DirectMessageListenerContainer(null, connectionFactory.Object);

            container.SetQueueNames("test");
            container.PrefetchCount   = 2;
            container.MonitorInterval = 100;
            container.MessagesPerAck  = 10;
            container.AckTimeout      = 100;
            container.MessageListener = new TestListener();
            container.Initialize();
            await container.Start();

            Assert.True(container._startedLatch.Wait(TimeSpan.FromSeconds(10)));

            Assert.True(latch1.Wait(TimeSpan.FromSeconds(10)));
            Assert.Equal(10, qos.Value);
            var props = new MockRabbitBasicProperties();

            var body = new byte[1];

            for (long i = 1; i < 16; i++)
            {
                consumer.Value.HandleBasicDeliver("consumerTag", (ulong)i, false, string.Empty, string.Empty, props, body);
            }

            Thread.Sleep(200);

            consumer.Value.HandleBasicDeliver("consumerTag", 16ul, false, string.Empty, string.Empty, props, body);

            // should get 2 acks #10 and #16 (timeout)
            Assert.True(latch2.Wait(TimeSpan.FromSeconds(10)));
            consumer.Value.HandleBasicDeliver("consumerTag", 17ul, false, string.Empty, string.Empty, props, body);
            channel.Verify(c => c.BasicAck(10ul, true));
            channel.Verify(c => c.BasicAck(15ul, true));

            Assert.True(latch3.Wait(TimeSpan.FromSeconds(10)));

            // monitor task timeout
            channel.Verify(c => c.BasicAck(17ul, true));
            consumer.Value.HandleBasicDeliver("consumerTag", 18ul, false, string.Empty, string.Empty, props, body);
            consumer.Value.HandleBasicDeliver("consumerTag", 19ul, false, string.Empty, string.Empty, props, body);
            Assert.True(latch4.Wait(TimeSpan.FromSeconds(10)));

            // pending acks before nack
            channel.Verify(c => c.BasicAck(18ul, true));
            channel.Verify(c => c.BasicNack(19ul, true, true));
            consumer.Value.HandleBasicDeliver("consumerTag", 20ul, false, string.Empty, string.Empty, props, body);
            var latch5 = new CountdownEvent(1);

            channel.Setup(c => c.BasicCancel("consumerTag"))
            .Callback(() =>
            {
                consumer.Value.HandleBasicCancelOk("consumerTag");
                latch5.Signal();
            });

            await container.Stop();

            Assert.True(latch5.Wait(TimeSpan.FromSeconds(10)));
            channel.Verify((c) => c.BasicAck(20ul, true));
        }