KubeMQ Java SDK

March 16, 2026 · View on GitHub

Maven Central CI codecov Javadoc License: MIT

Description

KubeMQ is a message queue and message broker designed for containerized workloads. The KubeMQ Java SDK provides a type-safe client for all KubeMQ messaging patterns — Events, Events Store, Commands, Queries, and Queues — over gRPC transport with built-in TLS, authentication, and reconnection support.

Migrating from v1? See MIGRATION.md for the upgrade guide.

Table of Contents

Installation

Prerequisites

  • Java 11 or higher (LTS releases 11, 17, and 21 are tested in CI)
  • KubeMQ server running (default: localhost:50000) — install guide
  • Maven 3.6+ or Gradle 7+

Maven

<dependency>
    <groupId>io.kubemq.sdk</groupId>
    <artifactId>kubemq-sdk-Java</artifactId>
    <version>2.1.1</version>
</dependency>

Gradle

implementation 'io.kubemq.sdk:kubemq-sdk-Java:2.1.1'

Quick Start

The simplest way to send and receive a message:

// Publish an event (fire-and-forget)
PubSubClient client = PubSubClient.builder()
    .address("localhost:50000")
    .clientId("quick-start")
    .build();

client.sendEventsMessage(EventMessage.builder()
    .channel("hello")
    .body("Hello KubeMQ!".getBytes())
    .build());

client.close();

See Messaging Patterns below for per-pattern quick starts including subscribing.

Messaging Patterns

PatternDelivery GuaranteeUse WhenExample Use Case
EventsAt-most-onceFire-and-forget broadcasting to multiple subscribersReal-time notifications, log streaming
Events StoreAt-least-once (persistent)Subscribers must not miss messages, even if offlineAudit trails, event sourcing, replay
QueuesAt-least-once (with ack)Work must be processed by exactly one consumer with acknowledgmentJob processing, task distribution
CommandsAt-most-once (request/reply)You need confirmation that an action was executedDevice control, configuration changes
QueriesAt-most-once (request/reply)You need to retrieve data from a responderData lookups, service-to-service reads

Quick Start: Events (Pub/Sub)

Publish an event:

PubSubClient client = PubSubClient.builder()
    .address("localhost:50000")
    .clientId("events-sender")
    .build();
EventSendResult result = client.sendEventsMessage(EventMessage.builder()
    .channel("notifications")
    .body("Hello KubeMQ!".getBytes())
    .build());
System.out.println("Event sent: " + result.getId());
client.close();

Subscribe to events:

PubSubClient client = PubSubClient.builder()
    .address("localhost:50000")
    .clientId("events-receiver")
    .build();
client.subscribeToEvents(EventsSubscription.builder()
    .channel("notifications")
    .onReceiveEventCallback(event ->
        System.out.println("Received: " + new String(event.getBody())))
    .onErrorCallback(err -> System.err.println("Error: " + err.getMessage()))
    .build());
Thread.sleep(30000);
client.close();

Expected output (subscriber):

Received: Hello KubeMQ!

Quick Start: Queues

Send a queue message:

QueuesClient client = QueuesClient.builder()
    .address("localhost:50000")
    .clientId("queue-sender")
    .build();
QueueSendResult result = client.sendQueuesMessage(QueueMessage.builder()
    .channel("tasks")
    .body("Process this job".getBytes())
    .build());
System.out.println("Sent, expired: " + result.isExpired());
client.close();

Receive and acknowledge:

QueuesClient client = QueuesClient.builder()
    .address("localhost:50000")
    .clientId("queue-receiver")
    .build();
QueuesPollResponse response = client.receiveQueuesMessages(QueuesPollRequest.builder()
    .channel("tasks")
    .pollMaxMessages(1)
    .pollWaitTimeoutInSeconds(10)
    .build());
for (QueueMessageReceived msg : response.getMessages()) {
    System.out.println("Processing: " + new String(msg.getBody()));
    msg.ack();
}
client.close();

Expected output (receiver):

Processing: Process this job

Quick Start: RPC (Commands & Queries)

Handle a command (responder):

CQClient client = CQClient.builder()
    .address("localhost:50000")
    .clientId("command-handler")
    .build();
client.subscribeToCommands(CommandsSubscription.builder()
    .channel("device.control")
    .onReceiveCommandCallback(cmd -> {
        System.out.println("Executing: " + new String(cmd.getBody()));
        return CommandResponseMessage.builder()
            .requestId(cmd.getId())
            .isExecuted(true)
            .build();
    })
    .onErrorCallback(err -> System.err.println("Error: " + err.getMessage()))
    .build());

Send a command (caller):

CQClient client = CQClient.builder()
    .address("localhost:50000")
    .clientId("command-sender")
    .build();
CommandResponseMessage response = client.sendCommandRequest(CommandMessage.builder()
    .channel("device.control")
    .body("restart".getBytes())
    .timeout(5000)
    .build());
System.out.println("Executed: " + response.isExecuted());
client.close();

Expected output (sender):

Executed: true

For more examples, see the examples directory.

Configuration

ParameterTypeDefaultDescription
addressStringlocalhost:50000KubeMQ server gRPC address (host:port). Falls back to KUBEMQ_ADDRESS env var.
clientIdStringAuto-generated UUIDUnique identifier for this client instance
authTokenStringnullJWT authentication token for server access
tlsbooleanfalseEnable TLS encryption for the connection
tlsCertFileStringnullPath to TLS certificate file (PEM format)
tlsKeyFileStringnullPath to TLS private key file (PEM format)
tlsCaCertFileStringnullPath to CA certificate for server verification
maxReceiveSizeint104857600Maximum inbound message size in bytes (100MB)
reconnectIntervalSecondsint5Seconds between reconnection attempts
logLevelLevelINFOLogging level (TRACE, DEBUG, INFO, WARN, ERROR, OFF)

Example:

PubSubClient client = PubSubClient.builder()
    .address("kubemq-server:50000")
    .clientId("my-service")
    .authToken("eyJ...")
    .tls(true)
    .tlsCertFile("/certs/client.pem")
    .tlsKeyFile("/certs/client-key.pem")
    .tlsCaCertFile("/certs/ca.pem")
    .reconnectIntervalSeconds(10)
    .build();

Error Handling

The SDK uses a typed exception hierarchy rooted at KubeMQException:

ExceptionCategoryWhen
ConnectionExceptionRetryableServer unavailable, network failure
KubeMQTimeoutExceptionRetryableDeadline exceeded, server too slow
AuthenticationExceptionNon-retryableInvalid or expired auth token
AuthorizationExceptionNon-retryableInsufficient permissions
ValidationExceptionNon-retryableInvalid request parameters
GRPCExceptionVariesgRPC transport errors
try {
    client.sendEventsMessage(message);
} catch (ConnectionException e) {
    log.warn("Connection failed (retryable): {}", e.getMessage());
} catch (AuthenticationException e) {
    log.error("Auth failed (fix credentials): {}", e.getMessage());
} catch (ValidationException e) {
    log.error("Invalid request: {}", e.getMessage());
} catch (KubeMQException e) {
    log.error("SDK error: {}", e.getMessage());
}

Troubleshooting

ProblemLikely CauseQuick Fix
UNAVAILABLE: io exceptionServer not running or wrong addressVerify server is running and address is correct
UNAUTHENTICATED: invalid tokenMissing or expired auth tokenCheck .authToken() value and expiry
Subscriber not receiving messagesWrong channel name or subscriber started after publisherVerify channel names match; for Events, subscriber must be running first
RESOURCE_EXHAUSTED: message too largeMessage body exceeds 100MB defaultIncrease maxReceiveSize or split payload
SSLHandshakeExceptionTLS misconfigurationVerify cert paths and expiry; ensure server TLS mode matches client

For detailed solutions with code examples, see TROUBLESHOOTING.md.

Performance

CharacteristicValueNotes
Max message size100 MBConfigurable via maxReceiveSize
Connection modelSingle gRPC channelAll operations multiplex over one HTTP/2 connection
SerializationProtocol BuffersBinary encoding for efficient wire format
Batch sendSupportedsendQueuesMessages(List<QueueMessage>)
Batch receiveSupportedpollMaxMessages in QueuesPollRequest

Tips:

  1. Reuse client instances — one client per pattern handles all operations efficiently
  2. Use batch APIs for high-throughput queue workloads
  3. Do not block subscription callbacks — offload heavy work to a separate executor
  4. Close clients when done — all client classes implement AutoCloseable

See BENCHMARKS.md for JMH benchmark results.

Compatibility

Java VersionStatus
Java 11 (LTS)Supported (minimum, compile target)
Java 17 (LTS)Supported (tested in CI)
Java 21 (LTS)Supported (tested in CI)

See COMPATIBILITY.md for the full SDK-to-server version matrix.

Security

See SECURITY.md for vulnerability reporting. The SDK supports TLS and mTLS connections — for configuration details, see How to Connect with TLS.

Additional Resources

Contributing

We welcome contributions! Please see CONTRIBUTING.md for guidelines on:

  • Development setup and building
  • Commit message format
  • Pull request process
  • Deprecation policy

License

This project is licensed under the MIT License — see the LICENSE file for details.