3

我正在使用 .NET HttpClient 来实现 Firebase Streaming Rest API,它本身支持 EventSource/Server-Sent Events 协议。

此 API 的文档在这里:https ://www.firebase.com/docs/rest/api/#section-streaming

下面显示的我的实现可以正常连接到 Firebase 并获取我的数据,在 Windows 服务中运行,该服务会自行更新其业务逻辑,然后每 10 分钟调用一次 GetAndProcessFirebaseHttpResponse作为新任务。

问题是,当我查看我的 Firebase 仪表板时,每次任务运行时并发连接数都会增加 1,而且我似乎无法告诉 Firebase 应该在 Firebase 端关闭连接并且不再发送数据。

这是我放入示例应用程序的代码的简化示例。每次我调用 GetAndProcessFirebaseHttpResponse 时,我的 Firebase 仪表板上都会增加另一个并发连接,即使在我取消任务后该连接仍然存在(通过 CancellationSourceToken.Token.ThrowIfCancellationRequested()):

    public void GetAndProcessFirebaseHttpResponse(CancellationTokenSource cancellationTokenSource)
    {
        HttpResponseMessage httpResponse = ListenAsync().Result;

        using (httpResponse)
        {
            using (Stream contentStream = httpResponse.Content.ReadAsStreamAsync().Result)
            {
                using (StreamReader contentStreamReader = new StreamReader(contentStream))
                {
                    while (true)
                    {
                        if (cancellationTokenSource.IsCancellationRequested)
                        {
                            httpResponse.RequestMessage.Dispose();
                        }

                        cancellationTokenSource.Token.ThrowIfCancellationRequested();

                        string read = contentStreamReader.ReadLineAsync().Result;

                        // Process the data here
                    }
                }
            }
        }
    }

    private async Task<HttpResponseMessage> ListenAsync()
    {
        // Create HTTP Client which will allow auto redirect as required by Firebase
        HttpClientHandler httpClientHandler = new HttpClientHandler();
        httpClientHandler.AllowAutoRedirect = true;

        HttpClient httpClient = new HttpClient(httpClientHandler, true);
        httpClient.BaseAddress = new Uri(_firebasePath);
        httpClient.Timeout = TimeSpan.FromSeconds(60);

        string requestUrl = _firebasePath + ".json?auth=" + _authSecret;
        Uri requestUri = new Uri(requestUrl);

        HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Get, requestUri);
        request.Headers.Accept.Add(new MediaTypeWithQualityHeaderValue("text/event-stream"));

        HttpResponseMessage response = await httpClient.SendAsync(request, HttpCompletionOption.ResponseHeadersRead);
        response.EnsureSuccessStatusCode();

        return response;
    }

HttpResponseMessage、Stream、StreamReader、HttpRequestMessage 都被释放了。HttpClient 不是,因为建议它不需要(请参阅,Do HttpClient 和 HttpClientHandler 必须被处置吗?)。这些处置自然会释放客户端上的资源,但是我猜想它们不会与Firebase 服务器就需要关闭 Firebase 端的连接进行任何沟通。

我的问题是:将 .NET HttpClient 与 Firebase REST Streaming API 一起使用,我如何与 Firebase REST 端点进行通信,说明我已完成连接并且应该在 Firebase 端关闭它?

4

0 回答 0