我还没有看到这个回答,非常简单的设置...
问题:我遇到了僵局,我想知道如何避免它,因为我的设置。
我有实现IServiceA的ServiceA和实现IServiceB的ServiceB。这两项服务都被标记为" perSession"和"重新进入" ...
IServiceA支持这种方法:
DataA GetDataA( );
IServiceB支持此方法:
DataB GetDataB( );
在我的应用中,我称之为ServiceA的GetDataA( )
方法,而在ServiceA的GetDataA方法中,它会打开与ServiceB的代理连接,并调用GetDataB( )
。
服务端的GetDataB(不是客户端)正确执行(调试日志这样说)但是当它试图将数据返回给ServiceA时,它就会死锁。
我假设这是因为当我从" user"调用ServiceA时,它获得了IO完成端口"交付锁定" (或者它可能被称为每次会话的WCF"锁定。无论如何,都会锁定。我假设当ServiceB的GetDataB( )
试图返回时价值,它真正完成的是在渠道周围翻转,并试图在ServiceA上调用一个接收方法,这需要锁定和死锁。
在我到目前为止所读到的每个问题中,人们都会问这样的问题"是否可以将一个服务从另一个服务链接起来,每个(愚蠢的)答案都是,#34;当然!前进!什么都没有!服务不知道他们是否被正常的.NET代码调用,或者他们是否正在从另一个服务调用它们!"。烦人。肯定会有#34;即使它有点微不足道。
我已经读过,我无法将返回值的方法标记为"单向"。并将它们标记为"重新进入" ......是否应该起作用?我知道如果在我的服务中,我调用了一个回调,锁定会被静默释放。如果我打电话给其他服务怎么办WCF是否足够智能以在这种情况下释放锁定?
我可以将我的服务标记为"多个"而不是"重新进入",但我想知道(a)真的是我认为的僵局,还是来自别的东西,(b)有更好的这个方法呢?
答案 0 :(得分:1)
想出来。我必须说实话,我开始通过阅读MSDN来学习WCF,但它一直在喋喋不休,所以我转到了一些WCF在线书籍(By Lowy& others)。我应该继续阅读MSDN。
我从WCF团队的一位开发者那里得到了这个答案:
"锁定不在传输层发生,它发生在实例上下文层。当服务A中的客户端向服务B发出传出请求 - 回复呼叫时,回复不会返回到服务A,它将返回到服务A正在使用的服务B的客户端。"
这是有道理的。但除了这些信息,我还学到了这一点:
"如果你使用WCF服务来调用任何方法(call out = callback或其他WCF服务),并且你被标记为" reenttrant",WCF将释放InstanceLock&#34 ;.
(因此,我在上面看到的僵局(可能)是我自己的错......)
我在这里找到了这个消息:
https://channel9.msdn.com/Forums/TechOff/254330-WCF-ConcurrencyModeReentrant-Confusion
这导致我在这里看到这篇有价值的文章:
https://msdn.microsoft.com/en-us/library/aa395214(v=vs.110).aspx
引用:在重入模式的情况下,InstanceContext在服务进行OUTGOING CALL之前解锁,从而允许后续调用(可以重复,如示例中所示)在下次进入时获取锁定服务。