Testing your extension

To write automated tests for your extension, you can use the official HiveMQ Testcontainer.

The HiveMQ Testcontainer can automatically create HiveMQ Docker containers and deploy your extension inside.

Packaging extensions with the HiveMQ Testcontainer

The HiveMQ Testcontainer is able to automatically build extensions that use maven by invoking the package task.All dependencies and resources are included. You only need to provide the location of the extension’s pom.xml in the constructor of the MavenHiveMQExtensionSupplier. MavenHiveMQExtensionSupplier.direct() returns a MavenHiveMQExtensionSupplier that targets the current project.

JUnit 4

To add the HiveMQ Testcontainer to your project, add these dependencies to your pom.xml:

<dependency>
    <groupId>com.hivemq</groupId>
    <artifactId>hivemq-testcontainer-junit4</artifactId>
    <version>1.1.0</version>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>junit</groupId>
    <artifactId>junit</artifactId>
    <version>4.13</version>
    <scope>test</scope>
</dependency>

In this example, the extension modifies all 'PUBLISH' payloads to contain the string 'modified'. To test the HiveMQ extension, do the following:

  1. Create a new HiveMQTestContainerRule

  2. Register the Rule with JUnit 4

  3. Use MavenHiveMQExtensionSupplier.direct() to add the HiveMQ extension to the HiveMQTestContainerRule.

  4. Connect your MQTT clients to the HiveMQ instance that is running inside the container. Use the port that you retrieve from the rule with the getMqttPort() method.

  5. Assert the expected behavior.

public class TestMqttIT {

@Rule (2)
public final @NotNull HiveMQTestContainerRule container = (1)
    new HiveMQTestContainerRule()
        .withExtension(MavenHiveMQExtensionSupplier.direct().get()); (3)

@Test
void test_mqtt() throws InterruptedException {
    final Mqtt5BlockingClient publisher = Mqtt5Client.builder()
        .serverPort(container.getMqttPort()) (4)
        .identifier("publisher")
        .buildBlocking();

    publisher.connect();

    final Mqtt5BlockingClient subscriber = Mqtt5Client.builder()
        .serverPort(container.getMqttPort()) (4)
        .identifier("subscriber")
        .buildBlocking();

    subscriber.connect();

    subscriber.subscribeWith().topicFilter("topic/test").send();

    publisher.publishWith()
        .topic("topic/test")
        .payload("Hello World!".getBytes()).send();

    final Mqtt5Publish receive = subscriber.publishes(MqttGlobalPublishFilter.ALL).receive();

    assertNotNull(receive); (5)
    assertEquals("modified", new String(receive.getPayloadAsBytes())); (5)
}

JUnit5

If you want to use JUnit 5, add these dependencies to your pom.xml:

<dependency>
    <groupId>com.hivemq</groupId>
    <artifactId>hivemq-testcontainer-junit5</artifactId>
    <version>1.1.0</version>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>org.junit.jupiter</groupId>
    <artifactId>junit-jupiter-engine</artifactId>
    <version>5.6.1</version>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>org.junit.jupiter</groupId>
    <artifactId>junit-jupiter-api</artifactId>
    <version>5.6.1</version>
    <scope>test</scope>
</dependency>

In this example, the extension modifies all 'PUBLISH' to contain the string 'modified'. To test the HiveMQ extension, do the following:

  1. Create a new HiveMQTestContainerExtension

  2. Register the Extensions with JUnit 5

  3. Use MavenHiveMQExtensionSupplier.direct() to add the HiveMQ extension to the HiveMQTestContainerRule.

  4. Connect your MQTT clients to the HiveMQ instance that is running inside the container. Use the port that you retrieve from the rule with the getMqttPort() method.

  5. Assert the expected behavior.

public class TestMqttIT {

@RegisterExtension (2)
public final @NotNull HiveMQTestContainerExtension container = (1)
    new HiveMQTestContainerExtension()
        .withExtension(MavenHiveMQExtensionSupplier.direct().get()); (3)

@Test
void test_mqtt() throws InterruptedException {
    final Mqtt5BlockingClient publisher = Mqtt5Client.builder()
        .serverPort(container.getMqttPort()) (4)
        .identifier("publisher")
        .buildBlocking();

    publisher.connect();

    final Mqtt5BlockingClient subscriber = Mqtt5Client.builder()
        .serverPort(container.getMqttPort()) (4)
        .identifier("subscriber")
        .buildBlocking();

    subscriber.connect();

    subscriber.subscribeWith().topicFilter("topic/test").send();

    publisher.publishWith()
        .topic("topic/test")
        .payload("Hello World!".getBytes()).send();

    final Mqtt5Publish receive = subscriber.publishes(MqttGlobalPublishFilter.ALL).receive();

    assertNotNull(receive); (5)
    assertEquals("modified", new String(receive.getPayloadAsBytes())); (5)
}

Debug with HiveMQ Testcontainer

You can debug the extension in the same way as described in [debug-intellij] and [debug-eclipse]. Simply set the port binding for the debug port:

@Rule
public final @NotNull HiveMQTestContainerRule rule = new HiveMQTestContainerRule()
    .withDebugging(5005);
Select a port that is not used by another application.