我怎样才能将spring.net注入方法?

时间:2011-07-11 23:52:58

标签: c# asp.net inversion-of-control spring.net dep

我在spring.net论坛上发布了以下内容,但也希望我可以在这里获得一些有价值的观点:

我正在寻找一些关于如何达到以下要求的建议。

首先是一些背景 - 我使用Spring.NET来实现IOC depdenecny注入我的asp.net c#多层Web应用程序。通过spring.net xml配置文件实现注入,通过开发针对接口并在需要的接口实现类中注入来实现我的所有开发。这对我来说都很好。我相信,我的知识将是中等水平。

我遇到了这个问题并希望找到解决方案。

举个例子,我有一个包含多个方法的类,它们都从数据库中检索,数据被缓存一段时间。

我希望能够自由地为每个方法注入缓存的特征,例如。时间让它存在于缓存等中。因此,我希望能够将值注入到方法中,而不是在类中注入其所需的位置。

我可以继续为每个方法创建类的属性,但是这会变得混乱,或者在我的类中注入设置。我倾向于通过弹簧注射来控制每种方法。

所以任何想法如何实现,因为我期望它可能遇到的事情。

我想出的一个可能的想法是以某种方式通过spring为每个方法注入一个属性,属性具有属性,该属性具有方法中所需的值,例如缓存持续时间等。这是一个可行的解决方案吗?如果是这样,任何人都可以协助我配置这样的。

如果有人有任何其他想法,那就太棒了。

2 个答案:

答案 0 :(得分:6)

如果你采用bbaia的方法,它可能看起来像下面的例子。 它有点简化,但你可以将它应用到你的情况。 假设我们有一个带有单个参数IDoWorkForSomeTime的接口time

public interface IDoWorkForSomeTime
{
    void Work(int time);
}

TimeBoundWorkerAdvisedTimeBoundWorker实施:

public class TimeBoundWorker : IDoWorkForSomeTime
{
    public void Work(int time)
    {
        Console.WriteLine("Working for {0} hours", time);
    }
}

public class AdvisedTimeBoundWorker : IDoWorkForSomeTime
{
    /* *** Note The Attribute *** */
    [ChangeParameter]
    public void Work(int time)
    {
        Console.WriteLine("Working for {0} hours", time);
    }
}

然后我们可以配置一个AOP代理来在运行时更改时间参数, 所以当我们运行以下程序时:

class Program
{
    static void Main(string[] args)
    {
        IApplicationContext ctx = new XmlApplicationContext("objects.xml");
        var worker = (IDoWorkForSomeTime)ctx.GetObject("plainWorker");
        var advisedWorker = (IDoWorkForSomeTime)ctx.GetObject("advisedWorker");

        worker.Work(4);
        advisedWorker.Work(4);
    }
}

输出:

Working for 4 hours
Working for 8 hours

所以虽然我用值4来调用它,advisedWorker使用值8,我在spring配置文件中配置了它。 spring容器看到​​[ChangeParameter]属性,并且从我的配置中知道它必须应用以下方法拦截器:

public class ChangeParamInterceptor : IMethodInterceptor
{
    public int NewValue { get; set; }  // set in spring cofig

    public object Invoke(IMethodInvocation invocation)
    {
        invocation.Arguments[0] = NewValue; // change the argument
        object rval = invocation.Proceed();
        return rval;
    }
}

它需要objects.xml中的弹簧配置:

<?xml version="1.0" encoding="utf-8" ?>
<objects xmlns="http://www.springframework.net">

  <object id="plainWorker"
          type="Examples.Aop.Shared.TimeBoundWorker, Examples.Aop.Shared"
          singleton="true">
  </object>

  <object id="advisedWorker"
          type="Examples.Aop.Shared.AdvisedTimeBoundWorker, Examples.Aop.Shared"
          singleton="true">
  </object>

  <!-- AOP configuration: -->

  <object id="changeParamAdvice"
          type="Examples.Aop.Shared.ChangeParamInterceptor, Examples.Aop.Shared">
    <!-- AH! there's the 8 -->
    <property name="NewValue" value="8" />
  </object>

  <object id="attributePointcut" type="Spring.Aop.Support.AttributeMatchMethodPointcut, Spring.Aop">
    <property name="Attribute" value="Examples.Aop.Shared.ChangeParameterAttribute, Examples.Aop.Shared" />
  </object>

  <object id="changeParamAspect" type="Spring.Aop.Support.DefaultPointcutAdvisor, Spring.Aop">
    <property name="Pointcut" ref="attributePointcut" />
    <property name="Advice" ref="changeParamAdvice"/>
  </object>

  <object id="ProxyCreator" 
          type="Spring.Aop.Framework.AutoProxy.DefaultAdvisorAutoProxyCreator, Spring.Aop" />     
</objects>

您可以使用更多选项来配置AOP并应用ChangeParamInterceptor等建议。请阅读Spring.NET documentation on AOP

中的更多内容

答案 1 :(得分:0)

您可以尝试使用Spring.NET AOP。您可以在运行时更改方法参数。