我们最近创建了一个新的 Standard 1 GB
专门用于分布式锁定的azure redis缓存-与我们的主redis缓存分离。这样做是为了提高我们的主要redis缓存的稳定性,这是一个非常长期的问题,这一行动似乎有很大的帮助。
在我们的新缓存中,我们观察到每1-3天在相同的几秒钟内爆发约100个错误。错误为: No connection is available to service this operation
(stackexchange.redis错误)
或: Could not acquire distributed lock: Conflicted
(redlock.net错误)
由于它们是来自不同包的错误,我怀疑redis缓存本身就是问题所在。在这段时间内,没有一项统计数据看起来不寻常,工作负载应该可以轻松地适应标准的1gb大小。
我猜这可能是广告上说的 Low
网络性能广告,这可能是原因吗?
2条答案
按热度按时间5n0oy7gb1#
你的理论听起来有道理。
检查网络带宽是否不足
下面是一个方便的表格,显示了不同定价层的最大观测带宽。看看你的sku所观察到的最大带宽,然后前往azure门户中的redis刀片并选择度量。将聚合设置为max,然后查看缓存读取和缓存写入的总和。这是您消耗的总带宽。将这两个值的总和与发生错误的时间段叠加,看看问题是否出在网络吞吐量上。如果是这样,那就扩大规模。
正在检查服务器负载
同样在metrics选项卡上,查看服务器负载。这是redis繁忙且无法处理请求的百分比。如果您达到100%,redis将无法响应新请求,您将遇到超时问题。如果是这样,那就扩大规模。
重用connectionmultiplexer
如果要为每个请求旋转stackexchange.redis.connectionmultiplexer的新示例,也可能会耗尽与redis服务器的连接。基于您的sku的可用连接数的服务限制在定价页的此处。您可以在“度量”选项卡上查看是否超出了sku允许的最大连接数,选择“最大聚合”,然后选择“连接的客户端”作为度量。
线程耗尽
这听起来不像是你的错误,但为了完整起见,我将把它包含在这个流氓的redis问题库中,它将与azure web应用一起使用。默认情况下,线程池将以4个线程开始,这些线程可以立即分配给工作。当你需要四个以上的线程时,它们会以每500毫秒一个线程的速度分配出去。因此,如果你在短时间内将大量请求转储到一个web应用程序上,你可能会结束排队工作,最终在请求到达redis之前被丢弃。要测试这是否是一个问题,请转到web应用的度量,选择线程并将聚合设置为最大值。如果您在短时间内看到与您的问题相对应的巨大峰值,您就找到了罪魁祸首。解决方法包括正确使用async/await。当这不能让你更进一步的时候,使用threadpool.setminthreads到一个更高的值,最好是接近或者高于你在突发事件中看到的最大线程使用量。
ni65a41a2#
rob提出了一些很好的建议,但确实想添加有关排除流量突发和糟糕的线程池设置的信息。请参阅:针对redis客户端问题的azure缓存疑难解答
突发流量加上糟糕的线程池设置可能会导致处理redis服务器已经发送但尚未在客户端使用的数据的延迟。
使用示例threadpoollogger监视线程池统计信息随时间的变化。您可以使用stackexchange.redis的timeoutexception消息(如下所示)进行进一步调查:
注意,在
IOCP
部分和WORKER
你有一个Busy
大于Min
价值观。这种差异意味着ThreadPool
设置需要调整。你也可以看到
in: 64221
. 此值表示已在客户端的内核套接字层接收到64211字节,但应用程序尚未读取。这种差异通常意味着应用程序(例如,stackexchange.redis)从网络读取数据的速度不如服务器发送给您的速度快。您可以配置线程池设置,以确保线程池在突发情况下快速扩展。
我希望你发现这些额外的信息是有帮助的。