NaveenKumar Namachivayam 9 min read

How to Test Kafka Message Queues with JMeter: The Complete Load Testing Guide

JMeter Kafka Load-Testing
Featured image for How to Test Kafka Message Queues with JMeter

How to Test Kafka Message Queues with JMeter: The Complete Load Testing Guide

Apache Kafka handles millions of events per second – until it doesn’t. A seemingly stable cluster can degrade under load due to a single misconfigured producer, insufficient network throughput, or slow consumer groups. The only safe way to ship Kafka‑based applications is to load‑test them with realistic traffic before production.

JMeter, the open‑source performance testing tool, now has mature Kafka sampler plugins that let you send and receive messages exactly like an HTTP test plan. In this guide I’ll walk you through selecting the right plugin, installing it manually (and why the Plugin Manager won’t help you here), configuring a producer and a consumer, interpreting results, and avoiding the pitfalls that derail most first‑time Kafka tests.

Everything below is based on real, working setups using Kafkameter 0.2.2 and Pepper‑Box 1.0, the two most battle‑tested community plugins.


1. Why JMeter for Kafka load testing?

JMeter’s advantages for Kafka:

  • Unified reporting – put Kafka messages and HTTP endpoints in one test plan.
  • Distributed testing – scale producers to hundreds of millions of messages from multiple agents.
  • Assertions & listeners – validate message content and latency without external tools.

Common testing goals:

  • Find the maximum stable throughput (messages/sec per topic).
  • Measure producer latency and consumer end‑to‑end latency.
  • Verify that compression, batching, and acknowledgment settings hold under stress.
  • Catch consumer lag before it turns into operational alerts.

2. Right plugin for the job

Because Kafka samplers are not part of JMeter core, you need a third‑party JAR. The two most reliable ones are:

PluginArtifactKey feature
Kafkameter (a.k.a. KafkaMeter)kafkameter-0.2.2.jarSimple Java Request sampler, works with any Kafka version ≥ 0.10, supports producer and consumer.
Pepper‑Boxpepper-box-1.0.jarAdds a message templating engine with JMeter functions, ideal for complex JSON payloads.

Important: Neither plugin is in the JMeter Plugins Manager repository. You must download the JAR and place it in lib/ext/ manually. (The official Kafka Backend Listener, which streams JMeter metrics to Kafka, is in Plugins Manager – but that’s for monitoring, not for generating load.)


3. Prerequisites

  • Apache JMeter 5.6+ (5.0 works, but 5.6 gives you built‑In __UUID() and updated Groovy).
  • Java 11 or 17 (Java 8 is minimum, but you’ll want the G1 garbage collector for prolonged tests).
  • Kafka cluster reachable from your test machine.
  • Kafka client JARs – if you plan to write a custom consumer in a JSR223 sampler, download the matching kafka-clients-<version>.jar and drop it into $JMETER_HOME/lib/ext/ as well. For the producer samplers, the plugin JARs already bundle their own client.

Give JMeter enough heap: open jmeter.bat or jmeter.sh and set:

HEAP="-Xms2g -Xmx4g"

4. Installing Kafka sampler plugins

Step‑by‑step (Kafkameter)

  1. Download kafkameter-0.2.2.jar from a trusted source (GitHub, GitCode, your internal artifact repo).
  2. Copy the JAR to <JMETER_HOME>/lib/ext/ (not lib/ or bin/).
  3. Restart JMeter completely – the classloader only scans lib/ext on startup.

After restart, verify:

  • Add a Thread Group.
  • Right‑click → Add → Sampler → Java Request.
  • In the Class name dropdown you should now see com.github.raccco.kafkameter.KafkaProducerSampler and KafkaConsumerSampler.

Pepper‑Box

Pepper‑Box adds a similar Java Request sampler plus config elements:

  1. Download pepper-box-1.0.jar and place it in lib/ext/.
  2. Restart JMeter.
  3. You’ll see com.gslab.pepper.sampler.PepperBoxKafkaSampler in the Java Request list, plus new Config Elements: Pepper‑Box PlainText Config and Pepper‑Box Serialized Config.

5. Building a Kafka producer test

We’ll cover both the minimalist Kafkameter approach and the richer Pepper‑Box templating.

5.1 Thread Group settings

ParameterExampleWhy
Number of Threads50Start small, then ramp.
Ramp‑Up Period60 secondsAllows brokers to warm up.
Loop CountForeverUse Runtime Controller for test duration.

Add a Runtime Controller with 600 seconds (10 minutes) to stop gracefully.

5.2 Producer via Kafkameter (Java Request)

  1. Add Sampler → Java Request.
  2. Set Class name to com.github.raccco.kafkameter.KafkaProducerSampler.
  3. Fill in the parameters:
Parameter KeyValueNotes
bootstrap.serversbroker1:9092,broker2:9092At least one broker.
kafka.topic.nameloadtest‑topicMust exist or enable auto‑create.
key.serializerorg.apache.kafka.common.serialization.StringSerializer
value.serializerorg.apache.kafka.common.serialization.StringSerializer
acks1all for highest durability.
compression.typelz4Cuts network bandwidth 2‑3×.
batch.size16384 (16 kB)
linger.ms10
buffer.memory33554432 (32 MB)

The Kafkameter sampler generates the message payload internally – usually a fixed string or random‑sized binary. For variable messages, use a JSR223 PreProcessor to set JMeter variables or switch to Pepper‑Box.

5.3 Producer via Pepper‑Box (advanced templating)

Pepper‑Box separates message generation from sending, which is ideal when you need data‑driven JSON.

  1. Add Sampler → Java Requestcom.gslab.pepper.sampler.PepperBoxKafkaSampler. Use the same parameters as above (bootstrap.servers, kafka.topic.name, etc.).
  2. Add Config Element → Pepper‑Box PlainText Config.
  3. Set Message Placeholder Key: payload
  4. Schema Template:
{
"userId": "${__RandomString(6,abcdef0123456789)}",
"eventType": "OrderCreated",
"timestamp": "${__time()}",
"payload": "Demo load test from thread ${__threadNum}"
}

The sampler automatically substitutes ${payload} with each rendered message. Combine with CSV Data Set Config for thousands of distinct records.


6. Building a Kafka consumer test

JMeter is primarily a load generator, so many teams run only the producer in JMeter and monitor a separate consumer (kafka‑console‑consumer, a custom app) for correctness and lag. If you need to measure end‑to‑end latency from the same JMeter instance, you can use a JSR223 sampler.

Prerequisite: Ensure the Kafka client library is on your classpath. Download kafka-clients-2.8.1.jar (match your cluster) and copy it to $JMETER_HOME/lib/ext/.

Add a JSR223 Sampler (language groovy) after the producer sampler:

import org.apache.kafka.clients.consumer.KafkaConsumer
import org.apache.kafka.clients.consumer.ConsumerConfig
import java.time.Duration
import java.util.Properties
def props = new Properties()
props.put("bootstrap.servers", "broker1:9092")
props.put("group.id", "jmeter-consumer-group")
props.put("key.deserializer", "org.apache.kafka.common.serialization.StringDeserializer")
props.put("value.deserializer", "org.apache.kafka.common.serialization.StringDeserializer")
props.put("auto.offset.reset", "earliest")
KafkaConsumer<String, String> consumer = new KafkaConsumer<>(props)
consumer.subscribe(["loadtest-topic"])
try {
def records = consumer.poll(Duration.ofMillis(1000))
records.each { record ->
long now = System.currentTimeMillis()
// Assume the message contains a 'timestamp' field
def msg = new groovy.json.JsonSlurper().parseText(record.value())
long latency = now - msg.timestamp.toLong()
// Store latency in a JMeter variable for later assertion
SampleResult.setResponseMessage("Latency: " + latency + "ms")
}
} finally {
consumer.close()
}

To reduce overhead, consider using a single consumer per thread group with a setUp Thread Group that holds the consumer open across iterations.


7. Running the test and reading results

Listeners to add

  • View Results Tree – debug a few messages.
  • Aggregate Report – gives avg/min/max/percentile producer latencies and overall throughput.
  • Simple Data Writer – exports raw results to CSV for offline analysis.
  • Backend Listener (Kafka) – streams live JMeter metrics to a Kafka topic for Grafana dashboards (install via Plugins Manager as “Kafka Backend Listener”).

Interpreting an Aggregate Report

LabelSamplesAverageMinMax99% LineThroughputError %
Kafka Producer30,250,0007 ms2 ms135 ms38 ms50,416/sec0.0%
  • Throughput: ~50,000 messages per second.
  • Latency: 99% of messages complete under 38 ms. If your SLA is “P99 < 100 ms” you’re well inside.
  • Error 0%: Healthy.

When you increase threads to 200 and the 99% line jumps to 350 ms, you’ve found a bottleneck – start looking at broker disk I/O, network saturation, or partition count.


8. Best practices to avoid false results

  1. Pre‑create the topic with the right number of partitions. Auto‑created topics often have only 1 partition, which becomes a serial bottleneck.
  2. Vary message size – identical small messages may be compressed to almost nothing, inflating throughput numbers unrealistically.
  3. Warm up the cluster – JMeter’s ramp‑up period is critical; start pumping messages slowly.
  4. Match the client version – Check the Kafka client JAR bundled with your plugin (inside the plugin JAR or its dependencies). If your cluster is 3.3 and the client is 2.4, you lose newer optimisations. Update the bundled JAR if possible.
  5. Separate producer and consumer machines – running both on the same JMeter node can skew network‑bound tests.
  6. Run endurance tests – a 10‑minute test won’t show compaction stalls or ZK session timeouts; run for 4‑8 hours.

9. Troubleshooting common pitfalls

SymptomLikely CauseSolution
Java Request class not in dropdownJAR not in lib/ext/ or JMeter not restartedCopy JAR to lib/ext/, restart JMeter.
ClassNotFoundException in JSR223 consumerMissing Kafka client JARDownload kafka-clients-<version>.jar to lib/ext/.
UnknownHostExceptionWrong bootstrap.servers IPDouble‑check broker addresses and firewall.
High latency with low load, acks=allSlow disks on brokersSwitch to acks=1 for throughput testing, or add faster disks.
Throughput plateaus at 1 partitionTopic created with default partitionsPre‑create topic with (e.g.) 12 partitions.

10. Summary

Kafka load testing with JMeter is not a black art. Grab the Kafkameter or Pepper‑Box JAR, drop it into lib/ext/, fire up a producer sampler, and watch the numbers. The key is to measure before you go live: validate that your cluster and your client settings (compression, batching, acks) hold up under 2x or 5x the expected load.

With the corrected steps above, you won’t waste time searching a non‑existent Plugin Manager entry or debugging ClassNotFoundException. You’ll go from zero to a trustworthy Kafka load test in under an hour.