Je suis confronté à de sérieux problèmes pour essayer de mettre en œuvre une solution répondant à mes besoins, concernant KafkaConsumer (> = 0.9).
Imaginons que j'ai une fonction qui doit lire seulement n les messages d'un sujet kafka.
Par exemple: getMsgs(5)
-> reçoit les 5 prochains messages kafka dans la rubrique.
Donc, j'ai une boucle qui ressemble à ceci:
for (boolean exit= false;!exit;)
{
Records = consumer.poll(200);
for (Record r:records) {
processRecord(r); //do my things
numMss++;
if (numMss==maximum) //maximum=5
exit=true;
}
}
Compte tenu de cela, le problème est que la méthode poll () peut recevoir plus de 5 messages. Par exemple, s'il reçoit 10 messages, mon code oubliera ces 5 autres messages, car Kafka pensera qu'ils sont déjà consommés.
J'ai essayé de commettre l'offset mais cela ne semble pas fonctionner:
consumer.commitSync(Collections.singletonMap(partition,
new OffsetAndMetadata(record.offset() + 1)));
Même avec la configuration offset, chaque fois que je relance le consommateur, il ne commencera pas à partir du 6ème message (rappelez-vous, je voulais juste 5 messages), mais à partir du 11ème (depuis le premier sondage a consommé 10 messages).
Y at-il une solution pour cela, ou peut-être (très sûrement) est-ce que je manque quelque chose?
Merci d'avance!!
Vous pouvez définir max.poll.records
sur le numéro de votre choix de manière à obtenir autant d’enregistrements que chaque sondage.
Pour votre cas d'utilisation que vous avez déclaré dans ce problème, vous n'avez pas à commettre explicitement des compensations par vous-même. vous pouvez simplement définir enable.auto.commit
sur true
et définir auto.offset.reset
sur earliest
pour qu'il se déclenche lorsqu'il n'y a pas de consommateur group.id
(autrement dit lorsque vous êtes sur le point de commencer à lire une partition pour la toute première fois). Une fois que vous avez un group.id et des compensations de consommateurs stockés dans Kafka et si votre processus de consommateur Kafka meurt, il continue à partir du dernier décalage validé, car il s’agit du comportement par défaut car lorsqu’un client démarre, il recherchera en premier les décalages validés et, si tel est le cas, continueront à partir du dernier décalage corrigé et auto.offset.reset
ne sera pas kick in.
définissez la propriété auto.offset.reset sur "dernière". Ensuite, essayez de consommer, vous obtiendrez les enregistrements consommés à partir du décalage engagé.
Ou bien vous utilisez consumer.seek (TopicPartition, offset) api avant poll.
Si vous aviez désactivé la validation automatique en définissant enable.auto.commit sur false. Vous devez désactiver cette option si vous souhaitez valider manuellement le décalage. Sans ce prochain appel à poll (), le dernier décalage des messages que vous avez reçu de poll précédent sera automatiquement validé.
Depuis Kafka 0.9, les noms de paramètres auto.offset.reset ont été modifiés.
Que faire s'il n'y a pas d'offset initial dans Kafka ou si l'offset actuel n'existe plus sur le serveur (par exemple, parce que ces données ont été supprimées):
earliest: automatically reset the offset to the earliest offset
latest: automatically reset the offset to the latest offset
none: throw exception to the consumer if no previous offset is found for the consumer's group
anything else: throw exception to the consumer.