我们使用 Nest.Js 开发了一个后端系统,目前托管在 Heroku 上。 我们有时会遇到因 H12 请求超时错误而导致的崩溃。这些崩溃是随机发生的,与我们应用程序的任何特定部分无关。
我们系统中的每个功能都会在 10-25 毫秒内执行查询并响应,我们使用 Sentry 和 Atatus 进行监控。尽管如此,我们还是收到了来自 Heroku 的 H12 请求超时错误,这表明某些请求需要很长时间才能完成。我们的日志记录工具无法查明问题的根源,因为崩溃似乎是在应用程序中的随机点发生的。
我们已经尝试过
1.日志记录和监控:我们使用Sentry和Atatus实现了详细的日志记录。然而,这两个工具都没有揭示超时或崩溃的原因。
2.性能指标回顾:我们分析了内存使用情况和一般性能指标,所有这些指标都显得正常。
3.个别功能的调查:鉴于崩溃是随机出现的,并且与任何特定功能无关,我们审查了代码是否存在潜在的低效或错误,但没有发现可以解释间歇性 H12 错误的原因。
任何关于其他调试策略、监控方法或 Heroku 特定配置的建议都可以帮助我们识别和解决这些间歇性崩溃的根本原因,我们将不胜感激。
还有其他几个原因可能导致您获得
H12
。
没有对单个测功机进行健康检查
Heroku 无法对测功机执行健康检查。 Heroku 负载均衡器不使用用户可配置的端点来执行运行状况检查。如果一个测功机出现问题,即使它可能出现故障并且无法服务请求,它仍然会继续接收请求。
应用程序启动前路由请求
由于 Heroku 缺乏健康检查功能,因此它也无法辨别应用程序是否已完全启动。如果应用程序的服务器绑定到其指定端口,Heroku 就会认为该应用程序已启动。通常,Web 应用程序会绑定到其端口,但之后会继续加载所需的库、类等。
仪器采样率
APM 工具通常不会记录所有流量,而是记录示例请求。该采样率可能远低于 1%。如果您的请求确实很慢,但极其罕见(认为占总数的 0.01%),那么它们最终出现在 APM 中的概率为 0.0001%。 Sentry 具体有一个参数,叫做:
tracesSampleRate
。默认情况下是 1
,但我从未在生产服务器上将其设置为 1
。检查您的工具是否可以配置为显式捕获异常值并以 100% 采样异常值,或者考虑临时将采样率设置为 100%,即使这样做的成本很高。
错误的请求破坏仪器
例如,如果请求导致崩溃(是的,如果带有二进制扩展的包中存在错误,则可能会出现这种情况),这可能会导致整个服务器及其仪器崩溃。该请求可能会被悬而未决,因此您会得到
H12
。几年前,我在使用 Ruby 时遇到过类似的问题。有时,崩溃是由试图利用您的应用程序的安全扫描程序发出的恶意请求引起的。专门检查您的日志,看看是否有与 H12
事件同时发生的测功机重新启动。
一般来说,除非您知道客户受到影响,否则您可能会想忽略这些。由于各种原因(包括间歇性网络和客户端错误),总会出现异常值。只要这些极其罕见,就可以安全地忽略。