Kafka Producer Acks Explained: Replicas, ISR, and Write Guarantees
In the previous article Kafka Consumer Graceful Shutdown Explained, we discussed how Kafka consumers should shut down gracefully to avoid duplicate processing and offset inconsistencies.
Now let’s move to the producer side of Kafka.
When a producer sends a message, an important question arises:
When should the producer consider the write successful?
Kafka answers this through a configuration called producer acknowledgments, commonly referred to as acks.
But before we understand acks, we need to clarify two important Kafka concepts that directly influence reliability:
- Replicas
- ISR (In-Sync Replicas)
These concepts define how Kafka maintains durability and availability in a distributed cluster.
Replicas vs ISR in Kafka
When a Kafka topic is created, each partition is replicated across multiple brokers. This replication is controlled by the replication factor.
For example:
replication.factor = 3
This means a partition has:
- 1 Leader replica
- 2 Follower replicas
Together they form the replica set.
Replicas
Replicas are all copies of a partition across brokers. They are fixed when the topic is created.
Example:
Partition-0
- Leader: Broker 1
- Follower: Broker 2
- Follower: Broker 3
These three together form the replica set.
ISR (In-Sync Replicas)
The ISR is a subset of replicas that are:
- Alive
- Fully caught up with the leader
Unlike replicas, ISR is dynamic.
If a follower falls behind or becomes unavailable, Kafka removes it from the ISR.
Example:
- Replicas: Broker1, Broker2, Broker3
- ISR: Broker1, Broker2
Kafka uses ISR — not all replicas — when determining if a write is successful.
This becomes especially important when acks=all.
Kafka Producer Acknowledgments
The acks configuration controls how many brokers must confirm a write before the producer considers it successful.
There are three main settings:
acks=0acks=1acks=all(oracks=-1)
Each option provides a different balance between throughput, durability, and latency.
acks = 0
With this configuration, the producer does not wait for any acknowledgment from the broker.
The producer simply sends the record and moves on.
Characteristics
- No confirmation from the broker
- Highest throughput
- Minimal network overhead
- Possible data loss
What Happens Internally
- Producer sends the message.
- Producer immediately considers the write successful.
- Broker response is not waited for.
If the leader broker is unavailable or crashes, the producer will not know.
Important Note
Retries do not help much here because the producer never receives failure feedback.
Typical Use Cases
This configuration is generally used when data loss is acceptable, for example:
- Logs
- Metrics
- Non-critical telemetry data
acks = 1
Here the producer waits for acknowledgment from the leader broker only.
The leader writes the message to its local log and then sends the acknowledgment back to the producer.
What Happens Internally
- Producer sends record to leader.
- Leader writes record to its log.
- Leader sends acknowledgment.
- Replication to followers happens asynchronously.
Risk Scenario
If the leader crashes before followers replicate the message, the data may be lost.
Characteristics
- Good throughput
- Moderate durability
- Lower latency compared to acks=all
Historically, acks=1 was the default configuration in Kafka up to version 2.x.
acks = all (or acks = -1)
This is the strongest durability guarantee Kafka offers for producers.
Here the leader waits for all replicas in the ISR to acknowledge the write.
However, this works together with another configuration:
min.insync.replicas
min.insync.replicas
min.insync.replicas defines the minimum number of ISR replicas that must acknowledge a write.
Default value:
min.insync.replicas = 1
If the ISR size drops below this value, the broker rejects the write.
Write Flow with acks=all
When a producer sends a message:
- Leader appends the record to its log.
- Leader replicates the record to all ISR members.
- Leader waits for acknowledgments.
- Write succeeds only if:
ISR size >= min.insync.replicas
If this condition fails, the broker returns errors such as:
NOT_ENOUGH_REPLICASNOT_ENOUGH_REPLICAS_AFTER_APPEND
The producer then receives an exception.
Kafka 3.x Default Behavior
This is a detail that often confuses people.
Even in Kafka 3.x:
acks=1
still appears as the default producer configuration.
However:
enable.idempotence=true
is enabled by default starting from Kafka 3.0.
Idempotent producers automatically require:
acks=all
So although the configuration may show acks=1, producers effectively behave like acks=all unless idempotence is disabled.
Write Availability vs Durability
Now let’s connect these settings to cluster availability.
Assume:
replication.factor = 3
With acks=0 or acks=1
As long as the leader broker is available, writes can succeed.
Even if follower replicas are down, the producer can still write.
With acks=all
Write availability now depends on min.insync.replicas.
Case 1 min.insync.replicas = 1
Writes succeed as long as the leader is alive.
This means two brokers can fail and writes will still be accepted.
Case 2 min.insync.replicas = 2
Now at least:
- Leader
- One follower
must be present in ISR.
This means one broker failure can be tolerated.
Case 3 min.insync.replicas = 3
All replicas must acknowledge the write.
This means no broker failure can be tolerated.
While technically possible, this setup is rarely used because Kafka systems are designed to tolerate node failures.
However, it may be used in scenarios where:
- Extremely high durability is required
- Write unavailability is preferred over potential data loss
General Rule for Failure Tolerance
If:
- replication.factor = N
- min.insync.replicas = M
Then the system can tolerate:
- N - M brokers failing
While still accepting writes when using acks=all.
The ISR size can be at most equal to the replication factor, but may shrink dynamically if followers fall behind.
Choosing the Right Acknowledgment Strategy
A quick rule of thumb used in many production systems:
| Setting | Throughput | Durability | Typical Usage |
|---|---|---|---|
| acks=0 | Highest | Lowest | Logs, metrics |
| acks=1 | High | Moderate | General workloads |
| acks=all | Lower | Highest | Financial or critical data |
Most modern Kafka deployments prefer:
- acks=all
- enable.idempotence=true
- min.insync.replicas >= 2
This combination provides strong guarantees without sacrificing too much availability.
Closing Thoughts
Producer acknowledgments directly impact data durability and system availability.
Understanding the relationship between:
- Replication factor
- ISR
- min.insync.replicas
- Producer acks
is essential when designing reliable Kafka pipelines.
Misconfiguring these settings can either lead to:
- Data loss
- Unnecessary write failures
- Reduced throughput
A balanced configuration ensures both reliability and performance in production systems.
Summary
Kafka producer acknowledgments determine when a write is considered successful.
- acks=0 prioritizes throughput but risks data loss
- acks=1 waits for leader acknowledgment
- acks=all ensures replication across ISR members
Combined with replication.factor and min.insync.replicas, these settings control the balance between durability and availability.
What’s Next?
Now that we understand acknowledgments and replication, the next step is exploring the following:
- Retries
- Idempotent producers
These features build on top of the acknowledgment mechanism and are critical for building robust event-driven systems.
If you found this useful and want to share your thoughts, this article is also published on Dev.to where discussions are more active. You can read it there and leave a comment if you’d like:
I always appreciate feedback and different perspectives.