【发布时间】:2014-11-24 12:49:44
【问题描述】:
我正在尝试实现故障恢复机制,该机制将在错误时处理 WCF 连接(然后定期尝试重新连接并重试)
基本上相关的代码只是
try
{
_client.DoSomthing();
}
catch
{
_client.Dispose();
}
问题是上述代码在 TPL 数据流块内运行,并且必须是线程安全的。我在其他线程使用时处理客户端时遇到问题。我不真的想锁定整个事情,因为我会丢失并发上传并且性能会受到影响。
我正在寻找某种方法来阻止使用客户端的新线程,但在我知道任何当前调用已完成之前不要尝试处理。然后确保只有一个线程执行 dispose。
我正在按照以下(伪)代码的方式对一些机制进行成像
using (var counter = new ThreadCounter())
{
try
{
if (!faulted)
_client.DoSomthing();
}
catch
{
faulted = true;
counter.BlockNewThreadsEntering()
if (counter == 1)
_client.Dispose();
}
}
框架中是否有任何东西可以让我实现这一目标?或者有什么其他建议?
【问题讨论】:
-
AFAIK 以任何方式同时使用同一个客户端都是不安全的。因此,我怀疑这永远无法可靠地工作。
-
@usr - 嗯?当然,您可以同时使用同一个客户端。是的,这确实使事情变得有些复杂,但是异步调用现在或多或少是正常的,如果您的服务器将其并发模式设置为多线程,那么它可以很好地处理它。
-
@ErikFunkenbusch 服务器不知道也不关心正在使用什么客户端。客户端不知道也不关心服务器设置了什么并发模式。这都是关于 ClientBase 类是否是线程安全的。文档说不是。
-
@usr - 服务器不知道哪个客户端是不正确的,因为服务器根据会话处理并发(如果正在使用会话)。它知道两个不同的会话是两个不同的客户端,如果您的实例模式是每个会话并且并发是多个,它将允许每个客户端(即每个会话)多个请求。默认情况下,服务器会限制每个实例的多个调用,一次只允许一个调用。但是多个实例可以同时运行,如果您已将并发配置为 Multiple,则会发生对同一实例的多个客户端请求。
-
@usr - 我不确定您提到的有关 ClientBase 的哪些文档,但线程安全(或不是)与能够处理并发调用不同,因为并发调用可能发生在与 async 相同的线程。
标签: c# multithreading wcf concurrency tpl-dataflow