I am currently trying to override the KafkaTemplate to force a synchronous send method similar to the suggestion here.
Here is the code:
public class SyncKafkaTemplate<K, V> extends KafkaTemplate<K, V> {
public SyncKafkaTemplate(ProducerFactory<K, V> producerFactory) {
super(producerFactory);
}
@Override
public ListenableFuture<SendResult<K, V>> send(ProducerRecord<K, V> record) {
ListenableFuture<SendResult<K, V>> future = super.send(record);
try {
SendResult<K, V> result = future.get();
if (!result.getRecordMetadata().hasOffset()) {
throw new RuntimeException("Produce request failed to return valid offset");
}
} catch (Exception ex) {
throw new RuntimeException(ex);
}
return future;
}
}
Is the .hasOffset()
check here necessary to ensure the message was produced successfully? Or will an exception always be thrown by the send request if a valid offset isn't returned to the Producer?
I've been trying to understand the internal source code for the KafkaTemplate but it's unclear to me if an exception would always be thrown by the .get()
call. I've also been searching the internet for any reason a negative offset would be returned but can't find anything relevant.
When running without the bad offset check, very rarely a message would be dropped by my service. It would show no errors on the producer side, but would never be committed to a partition on the server. I've added the offset check now, but without a way to replicate the dropped messages I don't know if this is a real solution.