【问题标题】:TypeInterceptor replacement for Structuremap 3Structuremap 3 的 TypeInterceptor 替换
【发布时间】:2016-04-25 18:36:34
【问题描述】:

从 StructureMap 2 升级到版本 3 时,似乎找不到任何有用的指南来说明如何在我的代码库中重现 TypeInterceptor 当前提供的功能(由于我们没有使用 .NET 4.6,因此无法升级到 v4但是)。

拦截器所做的基本上是这样的:

public class TheInterceptor : TypeInterceptor
{
    private Dictionary<string, string> typesToIntercept;

    public TheInterceptor(IDictionary<string, string> typesToIntercept)
    {
        // Passed in on ctor, comes from XML configuration section.
        this.typesToIntercept = typesToIntercept;
    }

    public object Process(object target, StructureMap.IContext ctx)
    {
        var typedTarget = target as BaseType;
        var key = target.GetType().FullName;

        if (typedTarget == null || !typesToIntercept.ContainsKey(key))
        {
            return target;
        }

        var propertyOverrideType = typesToIntercept[key];

        typedTarget.BaseProperty = ctx.GetInstance<IBaseInterface>(propertyOverrideType);

        return typedTarget;
    }
}

所以我们基本上是在维护一个字典,其中键是我们要拦截的类型,值是实现已知接口的特定类型,我们要在被拦截对象的属性上设置它。

FWIW 我没有编写原始代码,我只是无法弄清楚在 StructureMap 3 中镜像这种行为的正确方法是什么。我觉得这是可以在没有拦截器的情况下完成的事情,但我相信它是这样实现的,以便可以在多个站点(它在共享库中)使用此行为,而无需每个站点都必须明确处理拦截行为,所以如果可能的话,我想保留这种用法。

【问题讨论】:

    标签: c# structuremap3


    【解决方案1】:

    所以我最终通过反复试验解决了这个问题。您需要的是一个 ActivatorInterceptor 并使用 Action 委托来执行以前在 TypeInterceptor 的 Process 方法中执行的逻辑。所以从我上面的代码sn-p,就变成了:

    public class InterceptorPolicy : IInterceptorPolicy
    {
        private readonly IDictionary<string, string> typesToIntercept;
    
        public InterceptorPolicy(IDictionary<string, string> types)
        {
            this.typesToIntercept = types;
        }
    
        public IEnumerable<IInterceptor> DetermineInterceptors(Type pluginType, Instance instance)
        {
            if (instance.ReturnedType.IsSubclassOf(typeof(BaseType)))
            {
                yield return new ActivatorInterceptor<BaseType>((ctx, x) => this.Activate(ctx, x));
            }
        }
    
        private void Activate(IContext ctx, BaseType instance)
        {
            var key = instance.GetType().FullName;
    
            if (this.typesToIntercept.ContainsKey(key))
            {
                var propertyOverrideType = this.typesToIntercept[key];
    
                instance.BaseProperty = ctx.GetInstance<IBaseInterface>(propertyOverrideType);
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-06-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多