有没有一种方式可以告诉WCF服务在一定时间内做出响应(有或没有中止处理),即使它还没有完成,类似于服务器端的超时策略?
我想你可以在WCF操作开始时启动一个新的线程来实现这个功能。真正的工作是在新的线程上进行的,而原始的WCF请求线程则使用Thread.Join()和特定的超时时间等待。如果超时发生,则可以使用Thread.Abort()取消工作线程。
大概就像这样:
public string GetData(int value)
{
string result = "";
var worker = new Thread((state) =>
{
// Simulate l0ng running
Thread.Sleep(TimeSpan.FromSeconds(value));
result = string.Format("You entered: {0}", value);
});
worker.Start();
if (!worker.Join(TimeSpan.FromSeconds(5)))
{
worker.Abort();
throw new FaultException("Work took to long.");
}
return result;
}
我已经解决了同样的问题并创建了一篇博客文章:
http://kanchengcao.blogspot.com/2012/06/adding-timeout-and-congestion.html
简而言之:因此,我实现了一种方法,如果服务器过载且预计会导致更多超时,则放弃请求。
使用异步模型实现您的服务,并编写一些代码来监视未完成的请求,以查看它们是否花费了太长时间。
然后,如果在真正的方式下无法回答请求之前发生超时,则调用它们的回调函数。当WCF调用您的时候,WCF堆栈会提供此功能。
BeginFoo( fooParam1, fooParam2, AsyncCallback callback, object state)
然后在相应的 EndFoo()
方法中抛出或返回您的错误/超时异常或响应。
确保如果真正的答案最终出现,不要再次调用它们的回调函数。
异步 WCF 编程需要一些适应时间,但是显然没有服务器端设置。
此外,您应该尝试使用支持超时或可取消请求的客户端,因为您可能无法依赖服务器为您超时请求。可能存在连接问题或服务器机器可能有其他问题。
祝好, Chris
我不知道你为什么想要这样做 - 你应该编辑你的问题,说明你想要实现什么。
如果我必须这样做,那么我会让 Web 服务将请求传递给一个单独的 Windows 服务,可能使用 WCF over MSMQ。我会在该请求上设置超时时间。如果请求没有及时完成,我会简单地返回一个超时故障。实际请求不会受到影响。