在处理来自Kafka的消息时避免数据丢失

时间:2019-05-12 10:20:10

标签: apache-kafka kafka-consumer-api file-writing

寻找设计我的Kafka Consumer的最佳方法。基本上,我想看看什么情况下最好的避免数据丢失的方法 处理消息期间的异常/错误。

我的用例如下。

enter image description here

a)我使用SERVICE处理消息的原因是-将来我计划编写一个将在一天结束时运行的ERROR PROCESSOR应用程序,它将尝试处理失败的消息(不是所有消息,但由于诸如父项之类的任何依赖项丢失而导致消息失败)。

b)我想确保消息丢失为零,因此在将消息保存到DB时出现任何问题时,我会将消息保存到文件中。

c)在生产环境中,可能有多个使用者和服务实例正在运行,因此,多个应用程序极有可能尝试写入 同一文件。

Q-1)写入文件是否是避免数据丢失的唯一选择?

Q-2)如果这是唯一的选择,那么如何确保多个应用程序写入同一文件并同时读取?以后请考虑一下错误处理程序 是构建版本,则可能是在另一个应用程序尝试写入该文件的同时从同一文件读取消息。

错误处理器-我们的消息来源是事件驱动机制,因此很有可能有时依赖事件(例如某事物的父实体)可能会延迟几天。因此,在那种情况下,我希望我的错误处理器多次处理相同的消息。

2 个答案:

答案 0 :(得分:1)

我以前遇到过类似的情况。因此,直接探讨您的问题:

  • 不一定,您可以在一个新主题(例如-error-topic)中将这些消息发送回Kafka。因此,当您的错误处理器准备就绪时,它可以侦听此error-topic并在消息进入时使用它们。

  • 我认为这个问题已经针对第一个问题进行了解答。因此,与使用文件进行读写操作以及同时打开多个文件句柄来同时执行此操作相比,Kafka可能是一个更好的选择,因为它是针对此类问题而设计的。

注意 :基于我对问题域的有限了解,以下几点值得深思。因此,您可以选择安全地忽略它。

service组件的设计上还需要考虑一点-您最好将所有错误消息发送回Kafka,以考虑合并点4和5。这样一来,您便可以以一致的方式处理所有错误消息,而不是将某些消息放入错误数据库中,而将某些消息放入Kafka中。

编辑:根据有关ERROR PROCESSOR要求的其他信息,这是解决方案设计的示意图。

enter image description here

我现在故意保留ERROR PROCESSOR抽象的输出,只是为了使其通用。

我希望这会有所帮助!

答案 1 :(得分:1)

如果在写入数据库之前不提交消耗的消息,则在Kafka保留消息的过程中不会丢失任何消息。这样做的权衡是,如果使用者确实提交了数据库,但是Kafka偏移提交失败或超时,则您最终将再次使用记录,并可能在服务中处理重复记录。

即使您确实写入了文件,也不能保证顺序订购,除非您为每个分区打开一个文件,并确保所有使用方仅在单台计算机上运行(因为您在那里保存了状态,所以不会容错)。重复数据删除仍然需要处理。

此外,您可以考虑使用Kafka Connect框架,而不是将自己的使用者写入数据库。为了验证消息,您可以类似地部署Kafka Streams应用程序,以从输入主题中过滤出不良消息,然后过滤掉主题以发送给数据库