如何确定我的后台任务将在生产中调用多少个 3rd 方 Web api 调用?

Posted

技术标签:

【中文标题】如何确定我的后台任务将在生产中调用多少个 3rd 方 Web api 调用?【英文标题】:How do I determine how many 3rd party web api calls my background task will make in production? 【发布时间】:2022-01-15 07:29:46 【问题描述】:

我的 ASP.NET Core MVC Web 应用程序运行一个后台任务,该任务以设定的时间间隔从 CoinGecko Api 请求加密市场数据。我正在使用SignalR 在客户端和服务器之间创建一个开放连接,以便显示的数据始终是最新的,而无需客户端手动向服务器请求。

CoinGecko 的速率限制为 50 次调用/分钟。我想显示 4 个特定硬币的数据。根据我要显示的数据,我估计我必须拨打 25 次电话才能更新所有信息。我会分解电话:

1 次调用 /coin/markets 以获取所有 4 种代币的市值、流通供应等信息 24 次调用 /coins/id/market_chart 以获取所有 4 个硬币的 1 小时、1 天、7 天、30 天、90 天和 1 年价格图表(4 个硬币 x 6 个时间间隔)

假设我每分钟进行所有 25 次调用以保持数据更新,那么客户端数量是否会影响我进行的 API 调用次数?我猜它不会,因为数据是在后端请求的,然后通过 SignalR 集线器提供给所有客户端。

CryptoHttpListener.cs(后台任务):

protected override async Task ExecuteAsync(CancellationToken stoppingToken)
        
            while (!stoppingToken.IsCancellationRequested)
            
                HttpResponseMessage response = client.GetAsync(client.BaseAddress + "/simple/price?ids=bitcoin%2Cethereum%2Ccardano%2Cshiba-inu&vs_currencies=usd").Result;
                if (response.IsSuccessStatusCode)
                
                    string data = response.Content.ReadAsStringAsync().Result;
                    _logger.LogInformation("data", data);
                    cryptoData = JsonConvert.DeserializeObject<CryptoDataModel>(data);
                    await SendMessage(cryptoData);
                
                else
                
                    _logger.LogError("API call failed");
                
                await Task.Delay(10*1000, stoppingToken);
            
        

        public async Task SendMessage(CryptoDataModel cryptoData)
        
            decimal Bitcoin = cryptoData.Bitcoin.Usd;
            decimal Ethereum = cryptoData.Ethereum.Usd;
            decimal Cardano = cryptoData.Cardano.Usd;
            decimal ShibaInu = cryptoData.ShibaInu.Usd;
            await _hubContext.Clients.All.CryptoPriceUpdated(Bitcoin, Ethereum, Cardano, ShibaInu);
        

SignalR 集线器:

public class CryptoPriceHub : Hub<ICryptoPriceClient>
    

    

public interface ICryptoPriceClient
    
        Task CryptoPriceUpdated(decimal Bitcoin, decimal Ethereum, decimal Cardano, decimal ShibaInu);
    

索引.cshtml

<p id="bitcoin">placeholder text</p>
<p id="ethereum">placeholder text</p>
<p id="cardano">placeholder text</p>
<p id="shibainu">placeholder text</p>

@section Scripts 
    <script src="~/lib/aspnet/signalr/dist/browser/signalr.min.js"></script>
    <script type="text/javascript">
        var connection = new signalR.HubConnectionBuilder().withUrl("/hub").build();
        connection.on("CryptoPriceUpdated", function (Bitcoin, Ethereum, Cardano, ShibaInu) 
            //Update the DOM
            console.log(Bitcoin + ' ' + Ethereum + ' ' + Cardano + ' ' + ShibaInu);
            document.getElementById("bitcoin").innerText = Bitcoin;
            document.getElementById("ethereum").innerText = Ethereum;
            document.getElementById("cardano").innerText = Cardano;
            document.getElementById("shibainu").innerText = ShibaInu;
        );
        connection.start();

    </script>

【问题讨论】:

【参考方案1】:

tldr;您需要确保您的后端服务器正确缓存 API 调用。

如果 API 结果缓存在服务器上,并且缓存的结果用于面向公众的请求,那么只有后台的 API 调用才会计入速率限制。

但是,如果每个面向公众的请求都会导致 API 调用,那么您将在 2 个请求后达到 50/分钟的速率限制。

总结:确保您的服务器正确缓存 API 调用。

【讨论】:

我在上面发布了我当前的代码以获得更多上下文。我将我的响应保存在一个变量中,对其进行反序列化,并将每个硬币价格存储在一个变量中,然后通过_hubContext.Clients.All.CryptoPriceUpdated(Bitcoin, Ethereum, Cardano, ShibaInu) 将其发送给客户。由于我将我的 http 初始响应保存在变量中,是否还需要缓存数据? 看起来确实是从变量返回值。但是,这取决于这些变量的存储方式。我建议您只使用您拥有的代码并多次点击您的/hub 端点并验证 API 速率限制。

以上是关于如何确定我的后台任务将在生产中调用多少个 3rd 方 Web api 调用?的主要内容,如果未能解决你的问题,请参考以下文章

如何从 C++ 后台任务(Windows 通用应用程序)调用 C# 函数?

在生产中使用 Firebase

Spatie / Laravel cors在生产中的问题[重复]

我应该在生产中使用 rails5 ActiveJob 默认异步适配器来进行小型后台作业吗?

如何修复在生产中失败的应用内购买?

Sklearn Transformers:如何将编码器应用于多个列并在生产中重用?