我正在创建我在控制台应用程序中托管的服务。它包含一个从服务获取数据的方法,以及几个可以在服务器上执行的方法。
为了测试服务,我制作了一个简单的 WinForms 应用程序,它连接到服务并调用主机上的操作。这似乎工作得很好,但是当我将服务跟踪添加到配置文件以查看发生了什么时,我注意到一旦我关闭 UI 客户端就会在服务端引发异常:
<TraceRecord xmlns="http://schemas.microsoft.com/2004/10/E2ETraceEvent/TraceRecord" Severity="Error">
<TraceIdentifier>http://msdn.microsoft.com/nb-NO/library/System.ServiceModel.Diagnostics.ThrowingException.aspx</TraceIdentifier>
<Description>Throwing an exception.</Description>
<AppDomain>WCF.Host.vshost.exe</AppDomain>
<Exception>
<ExceptionType>System.Net.Sockets.SocketException, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</ExceptionType>
<Message>
An existing connection was forcibly closedby the remote host
</Message>
<StackTrace>
at System.ServiceModel.Channels.SocketConnection.HandleReceiveAsyncCompleted() at System.ServiceModel.Channels.SocketConnection.OnReceiveAsync(Object sender, SocketAsyncEventArgs eventArgs) at System.Net.Sockets.SocketAsyncEventArgs.FinishOperationAsyncFailure(SocketError socketError, Int32 bytesTransferred, SocketFlags flags) at System.Net.Sockets.SocketAsyncEventArgs.CompletionPortCallback(UInt32 errorCode, UInt32 numBytes, NativeOverlapped* nativeOverlapped) at System.Threading._IOCompletionCallback.PerformIOCompletionCallback(UInt32errorCode, UInt32 numBytes, NativeOverlapped* pOVERLAP)
</StackTrace>
<ExceptionString>
System.Net.Sockets.SocketException (0x80004005): An existing connection was forcibly closed by the remote host
</ExceptionString>
<NativeErrorCode>2746</NativeErrorCode>
</Exception>
</TraceRecord>
(我在配置中添加了一个 ConsoleTraceListener 以便我可以在警告发生时立即看到它们。)
发生这种情况时,据我所知,它不会影响服务器端,托管服务的控制台应用程序中不会引发异常,如果我重新启动 UI 客户端,它会很高兴地让我对主机执行操作。
即便如此,这是一个我非常想在主机端捕获的异常,以便我可以处理它。在我看来,应该调查跟踪日志中的任何异常迹象,但我根本不明白在我的代码中哪里可以捕捉到这个错误。通道上的 Closed 和 Faulted 事件似乎根本没有触发。
我在这个 VS 2012 解决方案中重新创建了问题,可以在这里下载:http: //db.tt/7l2Dnkpr (110 kB)
它由三个项目、一个带有服务定义的 DLL、一个控制台主机和一个 WinForms UI 客户端组成。这复制了我在实际应用程序中的设置,但这个测试要简单得多。该解决方案设置为启动多个项目,因此应该直接对其进行测试。
WCF.Host 应用程序创建一个正在侦听net.tcp://localhost:5000/singleservice的主机 在 UI 客户端中,单击“ GetObjects ”。这将创建到服务主机的通道并在其上调用GetObjects()方法。现在,退出 UI 应用程序并注意控制台窗口中的跟踪输出。
谁能看到发生这种情况的原因,和/或我如何处理代码中的异常?