【问题标题】:Nested call don't trigger interceptors嵌套调用不会触发拦截器
【发布时间】:2018-05-15 22:55:19
【问题描述】:

我想将拦截器附加到几个方法,其中一个可能会调用其他被拦截的方法,只运行第一个拦截器。我怎样才能让它工作:

class A : IWorker
{
    int Method1()
    {
        return 2*Method2();
    }

    int Method2()
    {
        return 5;
    }
}

拦截器实现

public class WorkerUsageLogger : IInterceptor
{
    public void Intercept(IInvocation invocation)
    {
        var indent = new string('\t', tabs);
        Console.WriteLine($"{indent}Calling method {invocation.Method.Name}.");
        tabs++;
        invocation.Proceed();
        tabs--;
        Console.WriteLine($"{indent}Completed method {invocation.Method.Name}");
    }
}

附加拦截器

var builder = new ContainerBuilder();
builder.RegisterInstance(new WorkerUsageLogger());
builder.RegisterType<A>().As<IWorker>().EnableInterfaceInterceptors().InterceptedBy(typeof(WorkerUsageLogger));
var container = builder.Build();
IWorker worker = container.Resolve<IWorker>();

通话中

worker.Method1();

我期待:

"Calling method Method1"
    "Calling method Method2"
    "Completed method Method2"
"Completed method Method1"

我来了

"Calling method Method1"
"Completed method Method1"

【问题讨论】:

  • 什么递归调用?我在发布的代码中没有看到任何内容
  • 拦截器是如何附加到类的?你看到什么工作?你在期待什么?你试过什么? (更新问题,不要在cmets中回答。)

标签: c# .net autofac aop interceptor


【解决方案1】:

拦截器返回一个IWorker 类型的对象,它有代码通过你的拦截器,它执行日志记录。没有实际编辑类A 中的代码来拦截、执行日志记录等。由于所述代码调用同一个A 类中的方法,即this,因此您注入到IWorker 调用中的拦截器永远不会在那些嵌套调用期间被触及。

要观察这一点,请尝试打印 worker.GetType()(或在调试器中观察类型)并注意它不会属于 A 类型。

这可以是单一职责原则的一个例子,因为你的接口实现不应该调用 this 对象上的东西,因为它会破坏日志记录和单元测试。如果您无法将解决方案分解为单独的接口,则可以考虑将实现请求设为相同接口类型的属性并调用 that

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-09-28
    • 2020-12-28
    • 2017-03-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多