This is an automated email from the ASF dual-hosted git repository. btellier pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/james-project.git
commit 2aa58d119481b02d63165ab77cee60e7484b9865 Author: Benoit Tellier <[email protected]> AuthorDate: Fri Apr 17 09:13:56 2020 +0700 JAMES-3142 Management API should allow to list bindings --- .../backends/rabbitmq/RabbitMQManagementAPI.java | 79 ++++++++++++++++++++++ .../james/backends/rabbitmq/RabbitMQFixture.java | 1 + .../james/backends/rabbitmq/RabbitMQTest.java | 46 +++++++++++++ 3 files changed, 126 insertions(+) diff --git a/backends-common/rabbitmq/src/main/java/org/apache/james/backends/rabbitmq/RabbitMQManagementAPI.java b/backends-common/rabbitmq/src/main/java/org/apache/james/backends/rabbitmq/RabbitMQManagementAPI.java index e6b94d0..42406ab 100644 --- a/backends-common/rabbitmq/src/main/java/org/apache/james/backends/rabbitmq/RabbitMQManagementAPI.java +++ b/backends-common/rabbitmq/src/main/java/org/apache/james/backends/rabbitmq/RabbitMQManagementAPI.java @@ -22,6 +22,7 @@ package org.apache.james.backends.rabbitmq; import java.util.Date; import java.util.List; import java.util.Map; +import java.util.Objects; import com.fasterxml.jackson.annotation.JsonFormat; import com.fasterxml.jackson.annotation.JsonProperty; @@ -227,6 +228,81 @@ public interface RabbitMQManagementAPI { } } + class BindingSource { + private final String source; + private final String vhost; + private final String destination; + private final String destinationType; + private final String routingKey; + private final Map<String, String> arguments; + private final String propertiesKey; + + public BindingSource(@JsonProperty("source") String source, + @JsonProperty("vhost") String vhost, + @JsonProperty("destination") String destination, + @JsonProperty("destination_type") String destinationType, + @JsonProperty("routing_key") String routingKey, + @JsonProperty("arguments") Map<String, String> arguments, + @JsonProperty("properties_key") String propertiesKey) { + this.source = source; + this.vhost = vhost; + this.destination = destination; + this.destinationType = destinationType; + this.routingKey = routingKey; + this.arguments = arguments; + this.propertiesKey = propertiesKey; + } + + public String getSource() { + return source; + } + + public String getVhost() { + return vhost; + } + + public String getDestination() { + return destination; + } + + public String getDestinationType() { + return destinationType; + } + + public String getRoutingKey() { + return routingKey; + } + + public Map<String, String> getArguments() { + return arguments; + } + + public String getPropertiesKey() { + return propertiesKey; + } + + @Override + public final boolean equals(Object o) { + if (o instanceof BindingSource) { + BindingSource that = (BindingSource) o; + + return Objects.equals(this.source, that.source) + && Objects.equals(this.vhost, that.vhost) + && Objects.equals(this.destination, that.destination) + && Objects.equals(this.destinationType, that.destinationType) + && Objects.equals(this.routingKey, that.routingKey) + && Objects.equals(this.arguments, that.arguments) + && Objects.equals(this.propertiesKey, that.propertiesKey); + } + return false; + } + + @Override + public final int hashCode() { + return Objects.hash(source, vhost, destination, destinationType, routingKey, arguments, propertiesKey); + } + } + static RabbitMQManagementAPI from(RabbitMQConfiguration configuration) { RabbitMQConfiguration.ManagementCredentials credentials = configuration.getManagementCredentials(); return Feign.builder() @@ -256,6 +332,9 @@ public interface RabbitMQManagementAPI { @RequestLine(value = "DELETE /api/queues/{vhost}/{name}", decodeSlash = false) void deleteQueue(@Param("vhost") String vhost, @Param("name") String name); + @RequestLine(value = "GET /api/exchanges/{vhost}/{name}/bindings/source", decodeSlash = false) + List<BindingSource> listBindings(@Param("vhost") String vhost, @Param("name") String name); + @RequestLine("GET /api/exchanges") List<Exchange> listExchanges(); } \ No newline at end of file diff --git a/backends-common/rabbitmq/src/test/java/org/apache/james/backends/rabbitmq/RabbitMQFixture.java b/backends-common/rabbitmq/src/test/java/org/apache/james/backends/rabbitmq/RabbitMQFixture.java index c1d73f5..53e49b0 100644 --- a/backends-common/rabbitmq/src/test/java/org/apache/james/backends/rabbitmq/RabbitMQFixture.java +++ b/backends-common/rabbitmq/src/test/java/org/apache/james/backends/rabbitmq/RabbitMQFixture.java @@ -32,6 +32,7 @@ public interface RabbitMQFixture { String EXCHANGE_NAME = "exchangeName"; String ROUTING_KEY = "routingKey"; String WORK_QUEUE = "workQueue"; + String WORK_QUEUE_2 = "workQueue2"; String DEFAULT_USER = "guest"; String DEFAULT_PASSWORD_STRING = "guest"; diff --git a/backends-common/rabbitmq/src/test/java/org/apache/james/backends/rabbitmq/RabbitMQTest.java b/backends-common/rabbitmq/src/test/java/org/apache/james/backends/rabbitmq/RabbitMQTest.java index 79020df..a12e831 100644 --- a/backends-common/rabbitmq/src/test/java/org/apache/james/backends/rabbitmq/RabbitMQTest.java +++ b/backends-common/rabbitmq/src/test/java/org/apache/james/backends/rabbitmq/RabbitMQTest.java @@ -31,6 +31,7 @@ import static org.apache.james.backends.rabbitmq.Constants.REQUEUE; import static org.apache.james.backends.rabbitmq.RabbitMQFixture.EXCHANGE_NAME; import static org.apache.james.backends.rabbitmq.RabbitMQFixture.ROUTING_KEY; import static org.apache.james.backends.rabbitmq.RabbitMQFixture.WORK_QUEUE; +import static org.apache.james.backends.rabbitmq.RabbitMQFixture.WORK_QUEUE_2; import static org.apache.james.backends.rabbitmq.RabbitMQFixture.awaitAtMostOneMinute; import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThatThrownBy; @@ -67,6 +68,8 @@ import com.rabbitmq.client.ConnectionFactory; import com.rabbitmq.client.DeliverCallback; import com.rabbitmq.client.Delivery; +import nl.jqno.equalsverifier.EqualsVerifier; + class RabbitMQTest { public static final ImmutableMap<String, Object> NO_QUEUE_DECLARE_ARGUMENTS = ImmutableMap.of(); @@ -429,6 +432,49 @@ class RabbitMQTest { } @Test + void bindingSourceShouldMatchBeanContract() { + EqualsVerifier.forClass(RabbitMQManagementAPI.BindingSource.class) + .verify(); + } + + @Test + void listBindingsShouldReturnEmptyWhenNone() throws Exception { + assertThat(rabbitMQExtension.managementAPI() + .listBindings("/", EXCHANGE_NAME) + .stream() + .map(RabbitMQManagementAPI.BindingSource::getDestination)) + .isEmpty(); + } + + @Test + void listBindingsShouldAllowRetrievingDestination() throws Exception { + channel1.exchangeDeclare(EXCHANGE_NAME, "direct", DURABLE); + channel1.queueDeclare(WORK_QUEUE, DURABLE, !EXCLUSIVE, !AUTO_DELETE, Constants.WITH_SINGLE_ACTIVE_CONSUMER); + channel1.queueBind(WORK_QUEUE, EXCHANGE_NAME, ROUTING_KEY); + + assertThat(rabbitMQExtension.managementAPI() + .listBindings("/", EXCHANGE_NAME) + .stream() + .map(RabbitMQManagementAPI.BindingSource::getDestination)) + .containsExactly(WORK_QUEUE); + } + + @Test + void listBindingsShouldAllowRetrievingDestinations() throws Exception { + channel1.exchangeDeclare(EXCHANGE_NAME, "direct", DURABLE); + channel1.queueDeclare(WORK_QUEUE, DURABLE, !EXCLUSIVE, !AUTO_DELETE, Constants.WITH_SINGLE_ACTIVE_CONSUMER); + channel1.queueDeclare(WORK_QUEUE_2, DURABLE, !EXCLUSIVE, !AUTO_DELETE, Constants.WITH_SINGLE_ACTIVE_CONSUMER); + channel1.queueBind(WORK_QUEUE, EXCHANGE_NAME, ROUTING_KEY); + channel1.queueBind(WORK_QUEUE_2, EXCHANGE_NAME, ROUTING_KEY); + + assertThat(rabbitMQExtension.managementAPI() + .listBindings("/", EXCHANGE_NAME) + .stream() + .map(RabbitMQManagementAPI.BindingSource::getDestination)) + .containsExactly(WORK_QUEUE, WORK_QUEUE_2); + } + + @Test void rabbitMQShouldDeliverMessageToFallbackSingleActiveConsumer() throws Exception { channel1.exchangeDeclare(EXCHANGE_NAME, "direct", DURABLE); channel1.queueDeclare(WORK_QUEUE, DURABLE, !EXCLUSIVE, !AUTO_DELETE, Constants.WITH_SINGLE_ACTIVE_CONSUMER); --------------------------------------------------------------------- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
