断路器模式, ,来自书中 释放它!, ,在远程服务发生故障(或恢复)时保护其免受请求,并帮助客户端管理重复的远程服务故障。我喜欢 Davy Brion 的状态断路器Ayende 的懒惰超时修复 很干净。

不过我还没有看到很多 过滤的实现 哪些异常会导致断路器故障计数增加。


不要担心显示锁定,除非您的实现特别依赖于巧妙的锁定。仅供参考,菲尔·哈克 (Phil Haack) 似乎有 最新版本的定时锁, ,用于 Davy Brion 的文章中。

有帮助吗?

解决方案

按谓词过滤

A 谓词 可以提供扩展的标准和过滤逻辑。

public void AttemptCall(Action action, Predicate<Exception> match)
{
    try
    {
        action();
    }
    catch(Exception e)
    {
        if(match(e))
            state.ActUponException(e);

        throw;
    }
}

例如,您可能只想在某个设备上增加断路器 WebException 超时引起的。

circuitBreaker.AttemptCall(() => service.DoWork(), e =>
    {
        WebException local = e as WebException;
        if(local == null)
            return false;

        return local.Status == WebExceptionStatus.Timeout;
    });

其他提示

过滤哪些类型会增加计数

您的第一个想法可能是使用泛型构造一个泛型方法调用 try... catch 堵塞。但是,由于以下原因,以下内容将不起作用 .NET 错误, , 请参见 这些 问题 了解更多信息。

public void AttemptCall<TException>(Action action)
    where TException : Exception
{
    try
    {
        action();
    }
    catch(TException e)
    {
         state.ActUponExcpetion(e);
         throw;
    }
}

你需要 捕获所有异常 并调查其类型。

public void AttemptCall<TException>(Action action)
    where TException : Exception
{
    try
    {
        action();
    }
    catch(TException e)
    {
         if(e is TException)
             state.ActUponExcpetion(e);

         throw;
    }
}

过滤哪些类型不会增加计数

蒂姆·罗斯写过这篇文章.

private readonly List<Exception> ignored = new List<Exception>();

public void Ignore<TException>() 
    where TException : Exception
{
    Type type = typeof(TException);
    if(ignored.Contains(type))
        return;

    ignored.Add(type);
}

public void AttemptCall(Action action)
{
     try
     {
         action();
     }
     catch(Exception e)
     {
         if(!ignore.Contains(e.GetType()))
             state.ActUponException(e);

         throw;
     }
}
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top