如何阻止异常警报发生狂暴

时间:2010-10-28 15:25:45

标签: .net design-patterns exception-handling error-handling alerts

假设您有一个.NET系统,当出现错误时需要向系统管理员发送电子邮件通知。例如:

try
{
    //do something mission critical 
}
catch(Exception ex)
{
    //send ex to the system administrator
    //give the customer a user-friendly explanation
} 

这段代码被不同的用户每秒调用数百次。

现在让我们假设底层API /服务/数据库出现故障。这段代码会很多次失败。这位可怜的管理员将在他们的收件箱中发现几百万封电子邮件,开发商将会接到一个粗鲁的电话,而不是今天早上必然会发生这样的事件(咳嗽)。

很明显,这不是一个可以很好地扩展的设计。

首先想到的几个解决方案在某些方面都存在缺陷:

  • 将错误记录到数据库,然后通过HTTP运行状况检查将高错误计数暴露给外部监视服务,例如Pingdom。 (到目前为止,我最喜欢的候选人。但是,如果数据库出现故障怎么办?)
  • 拥有一个跟踪最近异常的静态缓存,警报系统始终首先检查重复项。 (看起来不必要的复杂,其次很多错误信息略有不同 - 例如,如果错误中有时间戳,那就没用了。)
  • 在发生某些错误或基于对关键依赖关系的持续监控后,以编程方式使我们的系统脱机(危险!如果出现短暂的误报怎么办?)
  • 只是不警告这些错误,并依赖系统的不同部分来监视和报告依赖关系。 (不满足我们没有预料到的'意外'错误。)

这似乎是一个必须解决的问题,我们正在以愚蠢的方式解决这个问题。建议表示赞赏,即使它们涉及完全不同的异常管理策略!

5 个答案:

答案 0 :(得分:5)

我们想到的最简单的解决方案是为此异常块分配一个ID号(如1),并将最后一次通知的时间记录给管理员。如果通知之间的经过时间不够大(例如,一小时),请不要再次通知管理员

如果这段代码通常会生成多种异常,您可能还想记录异常的类;如果相同异常的通知之间的经过时间不够大,请不要再次通知管理员

答案 1 :(得分:1)

检查相似性(可以使用通配符避免时间戳(例如?? ?? ??))并首先让它们发送给您一段时间。现在检查哪个发生了最多。

比如说,A类型有1000个例外,B类型为964,C类型为120,类型D - H为7个。

这意味着,每隔100个类型A和B发送一个电子邮件给sysadmin,每10个类型C发送一次,并在发生时每隔一次发送一次。

临:
 +准确
 +防止系统垃圾邮件
 +实施的代码不多

缺点:
  - 需要时间来制定可靠的统计数据   - 重要的例外情况可能会被忽视   - 依靠人类,可能总是失败

答案 2 :(得分:0)

我之前构建过监控应用程序的电子邮件管理员,我会羞怯地承认我一直在你的情况。解决方案是对您的电子邮件进行速率限制。节省上次发送的最后一封电子邮件的时间,并构建一个支票,查看自上次发送电子邮件之前是否已经过了最短的时间(例如,10分钟或更长时间,由您决定)。这样,您的差管理员将获得的最大电子邮件数量为<time issue has been going on> / <period>。在我以前的系统管理员工作中,这平衡了我们需要知道一个问题仍然存在,因为需要一个电子邮箱不会每小时发送1000封电子邮件。

答案 3 :(得分:0)

我们的远程应用程序中有类似的东西。它通过电子邮件发送具有所有异常的中间邮箱,并且每小时都会运行一个脚本来扫描邮件,并创建一个摘要电子邮件,该邮件将发送到我们的团队邮箱(每天最多24封邮件),并将其余数据保存到本地数据库以供将来参考。

它不是防弹,但它的设置相当快/容易。

答案 4 :(得分:0)

我知道这已经得到了解答,但我认为发布此内容仍然很有帮助。

微软一直在增加大量有关云设计模式和架构的信息,包括微服务和带有消息队列的服务总线,以及更细微的细节。这一切都在Microsoft Docs网站上,提交在Azure Architecture下。处理此类问题的具体模式是Circuit Breaker pattern

使用此模式不会完全解决问题;仍然存在“我们如何决定通知运营人员的时间?”的问题。一种可能的解决方案是让断路器跳闸,并增加内部计数器以为跳闸创建唯一的标识符(或类似的东西)。然后,后续通知可以使用此标识符。这只是一个例子 - 可能还有其他方法可以合理地实现这一目标。关键是我会使用断路器来处理决策逻辑,将其放置在您需要拥有服务的任何地方,并将其链接到其上以提供您所描述的有关通知的服务。但至少,您可以避免发送大量电子邮件。