HTTP 与控制台应用程序保持活动状态,并且 iHttpHandler 正在失去连接

HTTP keep alive with console application and iHttpHandler is losing connection

提问人:user2728841 提问时间:7/3/2023 最后编辑:user2728841 更新时间:7/3/2023 访问量:14

问:

我有这个简单的 HTTPHandler,它只是将 keep-alive 设置为 true,并将响应对象保存到一个列表中,以便我们稍后可以写入它。然后,再往下的全局模块有一个计时器,它每 5 秒将一些内容写入响应对象,这就是它失败的地方,因为响应对象不再可用:

Imports System.Web
Imports System.Web.Services

Public Class a
    Implements IHttpHandler

    Public Sub ProcessRequest(context As HttpContext) Implements IHttpHandler.ProcessRequest

        context.Response.ContentType = "text/event-stream"
        context.Response.CacheControl = "no-cache"
        context.Response.Headers.Add("Connection", "keep-alive")
        context.Response.Headers.Add("keep-alive", "")

        ' Register the client (response) with the global SSEClients list
        RegisterClient(context.Response)

        context.Response.Write("Session Started")

        ' Don't close the response stream after this method; let the client handle it
        context.Response.BufferOutput = False

    End Sub

    Public ReadOnly Property IsReusable As Boolean Implements IHttpHandler.IsReusable
        Get
            Return False
        End Get
    End Property

End Class

加上一个全局(静态)模块,该模块旨在每 5 秒向控制台应用程序提供一次字符串,而无需新的 HTTPGET:

Friend Module Globals

    Public SSEClients As New List(Of HttpResponse)
    Public Index As Integer = 1

    Private timer As New Threading.Timer(Sub() SendSSEEvent(), Nothing, 0, 5000)

    Public Sub RegisterClient(response As HttpResponse)

        SSEClients.Add(response)

    End Sub

    Private Sub SendSSEEvent()
        Dim eventData As String = "data: Hello, World! " & Index & vbCrLf & vbCrLf
        Index += 1
        Dim ssecopy As New List(Of HttpResponse)(SSEClients)
        For Each res As HttpResponse In ssecopy
            Try
                res.Write(eventData)
                res.Flush()
            Catch
                Try
                    SSEClients.Remove(res)
                Catch
                End Try
            End Try
        Next
    End Sub
End Module

尝试使用它的客户端是一个简单的控制台应用程序

Module Module1
    Sub Main()

        Console.WriteLine("Listening for SSE events. Press Enter to exit.")

        Dim url As String = "https://localhost:44369/a.ashx"

        Dim req As System.Net.HttpWebRequest = CType(System.Net.WebRequest.Create(url), System.Net.HttpWebRequest)

        req.KeepAlive = True
        req.Timeout = Threading.Timeout.Infinite

        Using res As System.Net.HttpWebResponse = CType(req.GetResponse, System.Net.HttpWebResponse)
            Using str As System.IO.Stream = res.GetResponseStream
                Using rdr As New System.IO.StreamReader(str)

                    While True
                        Dim line As String = rdr.ReadLine()
                        If line IsNot Nothing Then
                            Console.WriteLine(line)
                        End If
                    End While

                End Using
            End Using
        End Using

    End Sub

End Module

这在 asp.net Web 表单(即 aspx 页面)中工作正常,但自从我切换到 httphandler 以来,它就不起作用了。问题在于,一旦控制台应用程序编写了第一个“会话启动”,客户端代码中的响应对象“res”将不再可用,这意味着 res.IsClientConnected 始终等于 false。

我怎样才能让它工作,以便响应对象保持活动状态,服务器可以每隔几秒钟向客户端提供一次字符串,而无需发出新请求?Bard 和 chatgpt 尽管花了一整天的时间尝试不同的东西,但还是无法提供帮助。

asp.net vb.net httphandler keep-alive

评论


答: 暂无答案