A hands-on guide to diagnose and fix common Kafka problems. Learn how to read logs, run safe commands, confirm root causes, and execute step-by-step recovery workflows.

## Intro

Kafka issues often surface first as timeouts, growing consumer lag, or alarming log lines during peak traffic. This guide gives you a practical, repeatable way to diagnose and fix the most common failures without risking data loss. You will learn how to read broker and client logs, run safe commands, confirm root causes, and execute step-by-step recovery workflows. The examples are designed for developers, DevOps consultants, and technical startup teams running Kafka alongside tools like NiFi, Apache Spark, HDFS, and Apache Airflow.

## Workflow Overview

Use this triage-to-recovery path to stay methodical under pressure:

- Stabilize and scope

- Freeze risky changes. Pause noisy automation if it is masking symptoms.

- Scope blast radius: single client, topic, broker, availability zone, or cluster-wide.

- Capture signals

- Save the last 15 to 60 minutes of logs from clients and brokers.

- Snapshot key metrics: request latencies, consumer lag, under-replicated partitions, broker disk, file descriptors, CPU, and network.

- Classify the symptom

- Producer timeouts or high latency

- Consumer lag growth or stuck partitions

- Under-replicated partitions or ISR shrink

- Authentication or authorization failures

- Broker start failures or controller flaps

- Run read-only checks first

- Describe topics, groups, brokers. Inspect configs and partition states.

- Confirm network reachability and DNS.

- Form a root-cause hypothesis

- Client-side vs broker-side vs infra (network, disk) vs security.

- Apply the smallest safe change

- Prefer reversible changes: throttles, pausing consumers, rolling restarts.

- Avoid deletes, force leadership, or config changes that reduce safety unless it is a last resort.

- Verify and unwind

- Re-check metrics and logs. Remove temporary throttles and toggles.

- Document findings

- Capture the minimal set of facts that explain the failure and fix.

## Common Symptoms and Logs

Match these log lines and metrics to likely causes:

### Producer-side symptoms

<div class="my-stack-md overflow-x-auto">
<table class="w-full min-w-[42rem] border-collapse text-left">
<thead><tr><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Log / Error</th><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Likely Meaning</th></tr></thead>
<tbody><tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">Request timed out</code>, <code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">TimeoutException</code></td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Network congestion, overloaded broker, incorrect bootstrap, or bad DNS.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">NotEnoughReplicas</code> or <code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">NotEnoughReplicasAfterAppend</code></td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">ISR too small for <code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">acks=all</code>, replicas offline or slow disk.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">RecordTooLargeException</code></td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Message exceeds topic or broker max message size.</td></tr></tbody>
</table>
</div>

### Consumer-side symptoms

<div class="my-stack-md overflow-x-auto">
<table class="w-full min-w-[42rem] border-collapse text-left">
<thead><tr><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Log / Error</th><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Likely Meaning</th></tr></thead>
<tbody><tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Lag increases even though consumer is running</td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Processing too slow, rebalance loops, or partition stuck on a dead broker.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">OffsetOutOfRange</code></td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Offsets expired due to retention or compacted away.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Rebalance storms in logs</td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Group churn, <code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">max.poll.interval.ms</code> exceeded, or unstable broker.</td></tr></tbody>
</table>
</div>

### Broker and cluster symptoms

<div class="my-stack-md overflow-x-auto">
<table class="w-full min-w-[42rem] border-collapse text-left">
<thead><tr><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Log / Metric</th><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Likely Meaning</th></tr></thead>
<tbody><tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Under-replicated partitions &gt; 0</td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">One or more replicas are lagging or offline. Check disk, network, CPU.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Controller elections or flapping controller logs</td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Metadata instability, network partitions, or quorum issues.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">SocketServer</code>, <code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">RequestHandlerPool</code> backlog</td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Broker saturation. Look at CPU and I/O.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">ReplicaFetcherThread</code> warnings</td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Followers cannot keep up due to slow disk or network.</td></tr></tbody>
</table>
</div>

### Security symptoms

<div class="my-stack-md overflow-x-auto">
<table class="w-full min-w-[42rem] border-collapse text-left">
<thead><tr><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Log / Error</th><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Likely Meaning</th></tr></thead>
<tbody><tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">SSL handshake error</code>, <code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">SASL handshake failed</code>, <code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">Client authentication failed</code></td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Mismatch in mechanism or cert trust issues.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">Authorization failed for Create/Write/Read</code></td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">ACLs are missing or principal is wrong.</td></tr></tbody>
</table>
</div>

### Storage and OS symptoms

<div class="my-stack-md overflow-x-auto">
<table class="w-full min-w-[42rem] border-collapse text-left">
<thead><tr><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Log / Metric</th><th scope="col" class="border border-outline-variant bg-surface-container-low px-4 py-3 text-left font-label-md font-semibold text-on-surface">Likely Meaning</th></tr></thead>
<tbody><tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Disk at or near 100%</td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">Retention too long, compaction backlog, or log cleanup stuck.</td></tr>
<tr><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant"><code class="font-mono text-[0.9em] bg-surface-container px-1 py-0.5 rounded">Too many open files</code></td><td class="border border-outline-variant px-4 py-3 align-top text-body-md text-on-surface-variant">File descriptor limit too low for topic-partition count.</td></tr></tbody>
</table>
</div>

## Root-Cause Checks

### Client checks

- Verify bootstrap servers, security.protocol , and auth settings.

- Measure producer retry rate, batch sizes, and compression effectiveness.

- For consumers, confirm max.poll.interval.ms , max.poll.records , and processing time.

### Network checks

- Test DNS resolution of brokers and advertised.listeners .

- Check cross-AZ or cross-DC latency and packet loss.

- Confirm firewall or security group rules on broker ports.

### Broker checks

- Describe brokers and topics to find leaders, ISR, and replica states.

- Look for thread pool starvation, GC pauses, and page cache pressure.

- Validate min.insync.replicas vs acks=all behavior.

### Storage checks

- Ensure adequate free space on log.dirs . Kafka needs headroom for segment rollover and compaction.

- Monitor disk throughput and iowait. Slow disks cause ISR shrink.

### Metadata and quorum checks

- Verify controller stability. If using ZooKeeper, check session stability. If using KRaft, check quorum voters and election logs.

- Watch for frequent leader changes which can cascade into client timeouts.

### Security checks

- Confirm principals, mechanisms, and truststores. Align client and broker configs.

- Check ACLs for required operations on the target topics and groups.

## Safe Commands and Recovery

Use read-only commands first. Prefer --describe and --list before making changes. Replace <...> placeholders with your values.

### Topic and broker state

# List topics
kafka-topics.sh --bootstrap-server <broker:9092> --list

# Describe a topic in detail
kafka-topics.sh --bootstrap-server <broker:9092> --describe --topic <topic>

# Describe brokers (via metadata dump if available) or check server logs for node IDs and listener info. 

### Consumer groups

 # List groups
kafka-consumer-groups.sh --bootstrap-server <broker:9092> --list

# Describe lag for a group
kafka-consumer-groups.sh --bootstrap-server <broker:9092> --describe --group <group>

# Safely reset offsets (dry run first)
kafka-consumer-groups.sh --bootstrap-server <broker:9092> \
 --group <group> --topic <topic> --reset-offsets --to-latest --dry-run

# Apply only after verifying
kafka-consumer-groups.sh --bootstrap-server <broker:9092> \
 --group <group> --topic <topic> --reset-offsets --to-latest --execute 

### Configs

 # Inspect topic configs
kafka-configs.sh --bootstrap-server <broker:9092> --entity-type topics \
 --entity-name <topic> --describe

# Update a topic config safely (example: temporary retention increase)
kafka-configs.sh --bootstrap-server <broker:9092> --entity-type topics \
 --entity-name <topic> --alter --add-config retention.ms=<value> 

### Partition movement

- Generate and apply a reassignment plan with throttle. Always review the plan and apply during a low-traffic window.

### Throttling

- Temporarily throttle producers or use quotas to reduce load while recovering.

### Caution

- Avoid force leader elections and disabling safety configs unless you accept data loss risk. Document risks before proceeding.

- Prefer rolling any broker change. Change one broker, validate, then continue.

## Practical Examples

### Example 1: Consumer lag spike after a deploy

 Goal: Restore steady consumption without losing messages.

- Verify lag and assignment

kafka-consumer-groups.sh --bootstrap-server <broker:9092> --describe --group <group> 

- Look for partitions with high lag and check if the consumer is assigned.

- Check consumer logs

- Signs: Rebalance loops, CommitFailedException , processing taking too long.

- Hypothesize

- The deploy increased processing time or reduced poll frequency, hitting max.poll.interval.ms (default 300000 ms / 5 minutes).

- Safe actions

- Increase max.poll.interval.ms moderately (e.g., to 600000 ms / 10 minutes) or reduce per-record work.

- Temporarily scale out consumers to match partition count.

- If lag is ancient and acceptable to skip, plan an offsets reset with --dry-run first.

- Verify

- Lag should trend down. Watch rebalance frequency and consumer processing time metrics.

### Example 2: Under-replicated partitions after a broker disk fills

 Goal: Restore ISR and replication health safely.

- Confirm scope

kafka-topics.sh --bootstrap-server <broker:9092> --describe --topic <topic> 

- Monitor cluster metric: under-replicated partitions.

- Broker inspection

- Check disk free space on the affected broker. Review server logs for disk errors.

- Stabilize

- Temporarily throttle producers or pause high-volume ingestion.

- Consider temporarily increasing retention.ms only if you need headroom to compact or move data later (e.g., from 604800000 ms / 7 days to 1209600000 ms / 14 days).

- Remediate disk

- Free space safely or add capacity on log.dirs .

- Avoid manual deletion of Kafka log segments unless you fully understand the implications.

- Recover and verify

- Restart the affected broker if required. Confirm ISR grows back.

- Watch ReplicaFetcherThread and network throughput.

### Example 3: Producer timeouts and RecordTooLargeException

 Goal: Restore producer throughput without breaking consumers.

- Confirm error

- Producer logs show RecordTooLargeException or similar.

- Options

- Reduce message size by splitting payloads or increasing compression.

- If needed, adjust broker or topic limits cautiously:

- Topic config: max.message.bytes

- Broker configs that interact: message.max.bytes , replica.fetch.max.bytes

- Make changes incrementally and prefer a topic-level change over cluster-wide.

- Example: If your messages are 2 MB, set topic max.message.bytes to 2097152 (2 MB) and broker message.max.bytes to at least 2097152.

- Verify end-to-end

- Ensure consumers can fetch larger messages. Validate no spike in fetch timeouts.

### Example 4: Authentication failures after certificate rotation

Goal: Restore client-broker trust.

- Check logs

- Look for SSL handshake errors or SASL mechanism mismatches.

- Validate configs

- Align security.protocol and mechanism on both sides.

- Verify keystore and truststore paths, passwords, and that the CA chain is present.

- Test connectivity

- From the client host, confirm TCP reachability to the broker listener.

- Verify fix

- Successful connection and stable produce-consume loop.

### Example 5: Controller flapping and frequent leader changes

Goal: Stabilize metadata to reduce client timeouts.

- Observe

- Broker logs show frequent controller elections. Clients see NotLeaderForPartition and timeouts.

- Check quorum stability

- For ZooKeeper: verify session stability and network between brokers and ZooKeeper.

- For KRaft: confirm voter set, connectivity, and that the controller node is healthy.

- Remediate

- Fix network partitions, remove noisy restarts, and ensure clocks are in sync.

- Apply rolling restarts only after confirming quorum health.

- Verify

- Controller becomes stable. Leader changes drop to normal levels.

## Local Pilot Plan

Objective: Prove a small set of troubleshooting workflows locally before touching shared environments.

### Scope

- Pick 2 scenarios: consumer lag spike and RecordTooLargeException .

- Use a single test topic with 3 partitions and a small replication factor.

### Plan

- Prepare tooling

- Scripts to capture logs and run describe commands quickly.

- A dashboard or simple charts for lag, latency, and under-replicated partitions.

- Run scenarios

- Generate small messages, then inject a large message to trigger RecordTooLargeException .

- Slow down consumer processing to trigger lag growth.

- Practice recovery

- For large records: split payloads or adjust topic max.message.bytes in a controlled way.

- For lag: tune consumer poll settings and scale out workers.

- Measure

- Time to detect symptom: target under 2 minutes.

- Time to confirm root cause: target under 10 minutes.

- Time to safe recovery: target under 20 minutes.

- Codify

- Turn the commands and checks into a short runbook with copy-paste snippets.

This narrow, measurable pilot is easy to inspect locally and builds confidence before cluster-wide changes.

## Conclusion

A steady troubleshooting workflow turns Kafka incidents into predictable operations work. Start with read-only inspection, classify the symptom, test the smallest safe change, and verify. Practice with a local pilot so the team can execute under stress. Keep a short runbook of commands and log patterns. Over time, you will reduce recovery time and avoid risky last-resort actions.

### Quick checklist

- Can I scope the blast radius fast?

- Do I have the last hour of client and broker logs?

- What error category am I in: producer, consumer, broker, security, or storage?

- Which read-only command will confirm my hypothesis?

- What is the smallest safe change, and how will I roll it back?

- Did metrics recover, and did I remove any temporary throttles?