Autofac(WebApi)IAutofacExceptionFilter OnException调用两次

时间:2013-12-03 14:01:57

标签: c# dependency-injection asp.net-web-api autofac filterattribute

我在使用autofac进行web api时出现问题。我有一个自定义ExceptionFilterAttribute,它覆盖OnException以记录和处理可能发生的任何异常。 ExceptionFilterAttribute应用于一个ApiController类。

过滤器代码如下:

public class ExceptionFilterAttribute : ExceptionFilterAttribute, IAutofacExceptionFilter
{
    private ILogger _logger;

    public ExceptionFilterAttribute()
    {

    }

    public ExceptionFilterAttribute(ILogger logger)
    {
        _logger = logger;
    }

    public override void OnException(HttpActionExecutedContext context)
    {
        // Removed for brevity
    }
}

在autofac配置中,注册了很多类型,我从下面删除了它们类似的地方:

var builder = new ContainerBuilder();
builder.RegisterApiControllers(Assembly.GetExecutingAssembly());
builder.RegisterType<ReflectionClassReader>().As<IClassReader>();
builder.RegisterType<Logger>().As<ILogger>();

builder.RegisterModule<DataModule>();

builder.Register(c => new ExceptionFilterAttribute(c.Resolve<ILogger>()))
       .AsWebApiExceptionFilterFor<ApiController>().SingleInstance();

builder.RegisterWebApiFilterProvider(GlobalConfiguration.Configuration);

var container = builder.Build();
configuration.DependencyResolver = new AutofacWebApiDependencyResolver(container);

当抛出异常并冒泡到ApiController时,ExceptionFilterAttribute.OnException方法被调用两次。第一次调用时,_logger由Autofac正确填充;第二个,_logger为null。

我无法理解为什么要两次调用它。我调试时没有堆栈跟踪,因为它是一个属性。

我只能假设它被调用了两次,因为我已经完成了一些autofac配置,但我完全被卡住了。我已尝试根据我在网上找到的一些例子改变配置的顺序,但无济于事。

我在使用带有webapi的IAutofacExceptionFilter时发现的唯一真实信息是http://alexmg.com/post/2012/09/01/New-features-in-the-Autofac-MVC-4-and-Web-API-%28Beta%29-Integrations

有没有人有任何想法?非常感谢!

2 个答案:

答案 0 :(得分:0)

尝试删除该行。

builder.RegisterWebApiFilterProvider(GlobalConfiguration.Configuration);

我认为发生的事情是导致两次注册异常过滤器。如果您有其他需要注册的过滤器,则几乎没有选项

一个。尝试仅使用AutoFac构建器来注册这些过滤器。我的意思是只使用一种机制寄存器过滤器。

湾创建CustomFilter Provider,如果它们已被复制等,您可以删除/添加过滤器。(网上有很多例子,但超出了这个问题的范围)

答案 1 :(得分:0)

认为这里的问题是您同时使用属性和过滤器。 因此会由于属性而被api调用,那将是一个空的记录器,然后再次通过过滤器注册由autofac进行调用,这将填充由autofac创建的记录器

尝试将类更新为此

public class ExceptionFilterAttribute : IAutofacExceptionFilter

删除ExceptionFilterAttribute,