7

我目前正在开发一个托管在 Azure 上的应用程序,该应用程序使用 Azure 事件中心。基本上,我正在从 Web API 向事件中心发送消息(或者应该说是事件),并且我有两个侦听器:

  • 用于实时分析的流分析任务
  • 一个标准工作角色,它根据接收到的事件计算一些东西,然后将它们存储到 Azure SQL 数据库中(这是一个 lambda 体系结构)。

我目前正在使用EventProcessorHost库从我的辅助角色中的事件中心检索我的事件。

我正在尝试找到一些关于如何使用事件中心的最佳实践(使用事件中心比使用服务总线队列更难,即流式处理与消息消耗),我发现有些人说我不应该这样做EventData从我的事件中心检索事件后进行大量处理

具体来说 :

请记住,您希望保持您正在做的事情相对较快 - 即不要尝试从这里做很多流程 - 这就是消费者群体的目的。

本文作者在 Event Hub 和 worker 角色之间添加了一个队列(从评论中不清楚是否真的需要)。

所以问题是:我应该直接在事件中心之后(即在ProcessEventsAsnyc我的IEventProcessor实现方法中)完成所有处理工作,还是应该在事件中心和处理工作之间使用队列

任何有关如何正确使用事件中心的事件的建议都将不胜感激,文档目前有点......丢失。

4

1 回答 1

6

这属于问题的类别,一旦 EventProcessorHost 的源可用,其答案将更加明显,我被告知这将会发生。

简短的回答是您不需要使用队列。但是,我会保持 ProcessEventsAsync 返回 Task 的时间相对较短。

虽然这个建议听起来很像第一篇文章,但关键区别在于它是返回任务的时间而不是任务完成的时间。我的假设是 ProcessEventsAsync 在用于 EventProcessorHost 的线程上被调用以用于其他目的。在这种情况下,您需要快速返回,以便其他工作可以继续;这项工作可能正在为另一个分区调用 ProcessEventsAsync (但如果不进行调试我们不会知道我没有发现有必要这样做或在可用时阅读代码)。

我通过从 ProcessEventsAsync 传递整个 IEnumerable,在每个分区的单独线程上进行处理。这与从 IEnumerable 中取出所有项目并将它们放入队列以供处理线程使用形成对比。另一个线程在完成消息处理后完成由 ProcessEventsAsync 返回的任务。(我实际上给了我的处理线程一个 IEnumerable,它通过将块链接在一起并在需要时在调用 MoveNext 时完成任务来隐藏 ProcessEventsAsync 的详细信息)。

简而言之:在 ProcessEventsAsync 中,将工作移交给另一个线程,无论是您已经拥有的线程,您都知道如何与 TPL 通信或启动一个新任务。

将所有消息放入 ProcessEventsAsync 内部的队列中还不错,这不是将事件块传递给另一个线程的最有效方法。

如果您决定将事件放入队列(或在处理代码中有一个下游队列)并完成批处理任务,则应确保限制代码/队列中未完成的项目数以避免运行在 EventHub 为您提供项目的速度比您的代码处理它们的速度由于流量高峰的情况下内存不足。

Java EventHub 用户 2016 年 10 月 27 日注意事项:由于我注意到了这一点,因此有描述如何调用 onEvents 的描述,而onEvents缓慢不会是悲剧,因为它在每个分区的线程上,它的速度似乎会影响速度收到下一批。因此,取决于您对此处延迟非常快的关心程度,这对于您的场景可能相对重要。

于 2015-04-29T20:11:57.933 回答