【问题标题】:Is it problematic to use a caching mechanism for throttling?使用缓存机制进行节流是否有问题?
【发布时间】:2017-11-13 16:12:43
【问题描述】:

我在 Azure Web 作业上实施了一个限制机制。我们网络工作的“工作”是全天不断地从第三方 api 下载单独的 .wav 文件。它每天(现在)大约执行 5,000 次。但是,第 3 方 api 有使用限制,每 60 秒最多只能下载 10 个 wav 文件。如果我们检查一下,接下来 60 秒内的每个请求都会收到 429 错误。

所以我实现了一个小代码来限制我们对这个 api 的请求。这是现在在每个请求之前执行的代码块:

        var maxPerPeriod = 10;
        var keyPrefix = RingCentralId;
        var intervalPeriod = 60000;
        var sleepInterval = 5000;
        var recentTransactions = MemoryCache.Default.Count(x => x.Key.StartsWith(keyPrefix));
        while (recentTransactions >= maxPerPeriod)
        {
            System.Threading.Thread.Sleep(sleepInterval);
            recentTransactions = MemoryCache.Default.Count(x => x.Key.StartsWith(keyPrefix));
        }
        var key = keyPrefix + "_" + DateTime.Now.ToUniversalTime().ToString("yyyyMMddHHmmss");
        var existing = MemoryCache.Default.Where(x => x.Key.StartsWith(key));
        if (existing != null && existing.Any())
        {
            var counter = 2;
            var last = existing.OrderBy(x => x.Key).Last();
            var pieces = last.Key.Split('_');
            if (pieces.Count() > 2)
            {
                var lastCount = 0;
                if (int.TryParse(pieces[2], out lastCount))
                {
                    counter = lastCount + 1;
                }
            }
            key = key + "_" + counter;
        }
        var policy = new CacheItemPolicy
        {
            AbsoluteExpiration = DateTimeOffset.UtcNow.AddMilliseconds(intervalPeriod)
        };
        MemoryCache.Default.Set(key, 1, policy);

这实际上效果很好(至少现在是这样)。如您所见,我使用的缓存具有每个持续 60 秒的唯一键。这种机制会搜索缓存,如果缓存中当前有 10 个或更多,则意味着我们需要等到它们过期。我通过实现while 循环来做到这一点。这是我最关心的部分。我没有很多使用MemoryCache 的经验。我是否可能在某个时间点引入无限循环?还有什么我可以忽略的可能会导致问题的东西,尤其是当我们扩大到每天 1,000,000 个请求时?

【问题讨论】:

  • 如果简单得多,难道不是一个简单的计时器吗?
  • 这是个好主意。但是,我们希望它尽可能快地运行。如果我们使用计时器,我们必须有一个硬编码的时间间隔,可能设置为 60 秒,以便每个单独的 wav 文件运行。这将导致我们的处理速度可能慢 6 倍(60 秒与 10 秒相比)。

标签: c# azure caching azure-webjobs memorycache


【解决方案1】:

如果您不打算让多个 WebJob 实例来完成这项工作,为什么不使用 TimerTrigger 并将调用间隔均匀?

Here's the link 到文档中。

【讨论】:

  • 我还没有听说过定时器触发器。我得调查一下。
  • 我已经包含了文档的链接。它非常易于使用,并且会调用您在设定的时间表上指定的方法。
  • 是的,您也可以将应用服务指定为始终开启,并包含一个带有“计划”元素的 settings.job 文件。如果您的工作是连续的,这将起到同样的作用。
猜你喜欢
  • 1970-01-01
  • 2015-07-02
  • 1970-01-01
  • 2015-05-22
  • 1970-01-01
  • 2011-07-21
  • 2021-09-03
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多