--- title: "Spring Boot adapter" description: "The Spring Boot adapter (babelqueue-spring) — a Spring AMQP MessageConverter, an injectable publisher, and auto-configuration that wires the canonical envelope into RabbitTemplate and @RabbitListener." source: https://babelqueue.com/docs/babelqueue-java/1.x/spring/ updated: 2026-06-07T00:00:00.000Z --- # Spring Boot adapter `com.babelqueue:babelqueue-spring` plugs the Java core into **Spring AMQP**. Its auto-configuration registers a `MessageConverter` that encodes/decodes the canonical envelope, so Boot wires it into both the `RabbitTemplate` (producing) and your `@RabbitListener` containers (consuming) — no manual setup. ## Install Maven: ```xml com.babelqueue babelqueue-spring 1.0.0 ``` Gradle: ```kotlin implementation("com.babelqueue:babelqueue-spring:1.0.0") implementation("org.springframework.boot:spring-boot-starter-amqp") ``` Requirements: **Spring Boot 3**, **Java 17+**, RabbitMQ. The core (`babelqueue-core`) comes transitively. ## Configuration ```yaml # application.yaml babelqueue: default-queue: orders # written to meta.queue; used when no queue is given ``` Auto-configuration exposes one `MessageConverter` bean (`BabelQueueMessageConverter`) and a `BabelQueuePublisher`. Both **back off** if your app defines its own. Boot's RabbitMQ auto-config injects the single converter into the `RabbitTemplate` and the default listener container factory. ## Produce Inject `BabelQueuePublisher`. Its `publish(...)` methods return the message `meta.id`: ```java import com.babelqueue.spring.BabelQueuePublisher; import java.util.Map; import org.springframework.stereotype.Service; @Service class Orders { private final BabelQueuePublisher babelQueue; Orders(BabelQueuePublisher babelQueue) { this.babelQueue = babelQueue; } void create() { babelQueue.publish("urn:babel:orders:created", Map.of("order_id", 1042L), "orders"); } } ``` Available overloads: `publish(urn, data)`, `publish(urn, data, queue)`, `publish(urn, data, queue, traceId)`, and — for a typed message implementing `com.babelqueue.PolyglotMessage` — `publish(message)` / `publish(message, queue)`. Each message carries the contract AMQP properties: `type` = URN, `correlationId` = `trace_id`, `messageId` = `meta.id`, plus `x-attempts` / `x-schema-version` / `x-source-lang` headers, `application/json` and persistent delivery. ## Consume A normal `@RabbitListener` receives a decoded core `Envelope`; route by URN with `EnvelopeCodec.urn(...)`: ```java import com.babelqueue.Envelope; import com.babelqueue.EnvelopeCodec; import org.springframework.amqp.rabbit.annotation.RabbitListener; import org.springframework.stereotype.Component; @Component class OrderListener { @RabbitListener(queues = "orders") void onMessage(Envelope envelope) { if ("urn:babel:orders:created".equals(EnvelopeCodec.urn(envelope))) { var orderId = envelope.data().get("order_id"); // ... use envelope.traceId(), envelope.data() } } } ``` Non-conformant messages (missing URN, unsupported `meta.schema_version`, blank `trace_id`, or missing `data`) are rejected by the converter — route them to a dead-letter exchange the usual Spring AMQP way. Because the wire format is the [canonical envelope](/docs/spec/1.x/envelope/), a message your Spring app consumes may have been produced by any BabelQueue SDK, and vice-versa.