问题描述
我的WCF服务使用netTcpBinding,并有一个回调对象。
我需要为多个并发客户端和mantain会话服务,
[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerSession,ConcurrencyMode = ConcurrencyMode.Multiple]
pre>
为避免线程死锁,回调类装饰有
[CallbackBehavior(UseSynchronizationContext = false)]
并使用
SynchronizationContext
在UI线程中执行该方法。
问题是,有时渠道gest没有理由关闭(
ICommunicationObject。
查看跟踪文件,最后一条消息是
在一些调试之后,我发现这种情况只发生在回调调用是在中间同步操作。步骤如下:
- 调用服务方法
A
与IsOneWay = true
- 调用服务方法
B
与IsOneWay = false
A
调用回调方法,但B
仍在执行。
这不应该是一个问题,因为回调有
UseSynchronizationContext = false
,因此回调调用可以在一个单独的线程中执行。
我无法在更简单的情况下重现该问题。
对任何可能发生的事情或如何识别问题有任何想法?
解决方案我认为可能发生的是客户端错误的通道,因为它收到回调消息,当它期待的回复消息。在使用net.tcp的WCF中,回调和回复使用相同的通道。
一般来说,你不应该在请求/回复IsOneWay = false)OperationContract方法。最安全的事情是在你的合同中没有任何请求/回复方法,当做双工,但你可以安全地拥有他们只要他们不回调回合约在回来之前。 (在返回之后,例如从另一个工作线程调用一个回调方法就可以了。)
My WCF service uses netTcpBinding, and has a callback object.
I need to service multiple concurrent clients, and mantain sessions, so the service is decorated with
[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerSession, ConcurrencyMode = ConcurrencyMode.Multiple]
To avoid thread deadlocks, the callback class is decorated with
[CallbackBehavior(UseSynchronizationContext=false)]
and I use
SynchronizationContext
to execute the method in the UI thread.The problem is that sometimes the channel gest closed with no reason (
ICommunicationObject.Closing
event gets fired). After that, I get exceptions in any subsequent service call.Looking in the trace file, the last message is a callback call, however, the callback method never gets invoked. There are no exceptions.
After some debugging I identified that this happens only when the callback call is made in the middle of a synchronous operation. The steps would be this:
- Call to service method
A
withIsOneWay=true
- Call to service method
B
withIsOneWay=false
A
invokes a callback method, butB
is still executing.This shouldn't be a problem because the callback has
UseSynchronizationContext=false
, so the callback call could be attended in a separate thread.I was unable to reproduce the problem in a simpler scenario. Following these steps in a simple project executes successfully.
Any idea of what could be happening or how to identify the problem?
解决方案I think what's probably happening is the client is faulting the channel because it received the callback message when it was expecting the reply message. In WCF with net.tcp, callbacks and replies use the same channel.
As a rule, you should never call a callback method inside the body of a request/reply (IsOneWay=false) OperationContract method. The safest thing would be to not have any request/reply methods in your contract whatsoever when doing duplex, but you can safely have them just so long as they don't call back into the callback contract before returning. (It would be ok to call a callback method after returning, for example from another worker thread).
这篇关于当使用回调时,WCF双工通道被关闭的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!