KubeMQ
Client SDKsKotlinHow-to guidesQueues

Auto Ack

Use automatic acknowledgement mode to ack KubeMQ queue messages on delivery with the Kotlin SDK.

Overview

Auto-ack is the fire-and-forget receive mode for queues: the broker marks a message as consumed the instant it hands it to your client, instead of waiting for your code to settle it. Reach for it when the work is idempotent, low-value, or cheap to lose — a metrics ping, a cache warm, a best-effort notification — and you'd rather not carry the bookkeeping of explicit acknowledgment for every message.

It works by setting autoAck = true in the receiveQueuesMessages config block. With it enabled, delivery and acknowledgment happen as one atomic step on the broker side, so there's no separate msg.ack() call and no in-flight "pending" state for the message to sit in.

Gotchas: if your consumer crashes or throws after receiveQueuesMessages returns but before it finishes processing, that message is gone for good — auto-ack gives you no chance to nack or requeue it, unlike Ack & Reject. It's an at-most-once model, so never use it for messages where losing one silently would matter. And because acknowledgment happens on delivery, maxItems and waitTimeoutMs are your only throttles — there's no visibility-timeout window to tune.

Prerequisites

  • KubeMQ server running on localhost:50000
  • Kotlin SDK installed (implementation("io.kubemq.sdk:kubemq-sdk-kotlin:1.0.1"))

Code

AutoAckExample.kt
package io.kubemq.sdk.examples.queuesstream

import io.kubemq.sdk.client.KubeMQClient
import io.kubemq.sdk.queues.queueMessage
import kotlinx.coroutines.runBlocking

private const val ADDRESS = "localhost:50000"
private const val CLIENT_ID = "kotlin-queues-auto-ack"
private const val CHANNEL = "kotlin-queues.auto-ack"

fun main() = runBlocking {
    val client = KubeMQClient.queues {
        address = ADDRESS
        clientId = CLIENT_ID
    }

    client.use {
        try {
            client.createQueuesChannel(CHANNEL)

            // Send messages
            repeat(3) { i ->
                client.sendQueuesMessage(queueMessage {
                    channel = CHANNEL
                    body = "Auto-ack msg ${i + 1}".toByteArray()
                })
            }

            // Poll with auto-ack enabled (messages acknowledged automatically)
            println("Polling with autoAck=true...\n")
            val response = client.receiveQueuesMessages {
                channel = CHANNEL
                maxItems = 10
                waitTimeoutMs = 5000
                autoAck = true
            }

            response.messages.forEach { msg ->
                println("  Received (auto-acked): ${String(msg.body)}")
            }
            println("\n${response.messages.size} messages auto-acknowledged.")
        } finally {
            try { client.deleteQueuesChannel(CHANNEL) } catch (_: Exception) {}
        }
        println("Done.")
    }
}

How It Works

  • Setting autoAck = true in the receive config automatically acknowledges messages on delivery.
  • No need to call msg.ack() on individual messages.
  • Use auto-ack for fire-and-forget consumption where message loss on processing failure is acceptable.
  • For at-least-once delivery guarantees, use autoAck = false with explicit acknowledgement.

Was this page helpful?

On this page