7.4.6 Method injection

In most application scenarios, most beans in the container are singletons. When a singleton bean needs to collaborate with another singleton bean, or a non-singleton bean needs to collaborate with another non-singleton bean, you typically handle the dependency by defining one bean as a property of the other. A problem arises when the bean lifecycles are different. Suppose singleton bean A needs to use non-singleton (prototype) bean B, perhaps on each method invocation on A. The container only creates the singleton bean A once, and thus only gets one opportunity to set the properties. The container cannot provide bean A with a new instance of bean B every time one is needed.

在大多数应用场景中,在容器中的大多数beans是单例的.当一个单例bean需要和另一个单例bean合作的时候,或者是一个非单例bean和另一个非单例bean合作的时候,你通常以通过定义一个bean作为另一个bean的属性的方式来处理这种依赖.当这个bean的生命周期不同时就会出现问题.假设单例bean A需要使用非单例(原型)bean B,或许在A中调用的每个方法上.容器只会创建一次单例bean A,因此只有一次机会去设置这些属性.容器不能够在bean A每次需要bean B的时候提供给bean A一个bean B的新实例.

A solution is to forego some inversion of control. You can make bean A aware of the container by implementing the ApplicationContextAware interface, and by making a getBean("B") call to the container ask for (a typically new) bean B instance every time bean A needs it. The following is an example of this approach:

一种解决方案是放弃一些反转控制.你可以让bean A意识到这个容器通过实现 ApplicationContextAware 接口,在每次bean A需要bean B的时候,通过使用getBean("B")调用这个容器去请求(一个通常的new操作)bean B.下面是这个方式的一个例子:

// a class that uses a stateful Command-style class to perform some processing
package fiona.apple;

// Spring-API imports
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;

public class CommandManager implements ApplicationContextAware {

    private ApplicationContext applicationContext;

    public Object process(Map commandState) {
        // grab a new instance of the appropriate Command
        Command command = createCommand();
        // set the state on the (hopefully brand new) Command instance
        command.setState(commandState);
        return command.execute();
    }

    protected Command createCommand() {
        // notice the Spring API dependency!
        return this.applicationContext.getBean("command", Command.class);
    }

    public void setApplicationContext(
            ApplicationContext applicationContext) throws BeansException {
        this.applicationContext = applicationContext;
    }
}

The preceding is not desirable, because the business code is aware of and coupled to the Spring Framework. Method Injection, a somewhat advanced feature of the Spring IoC container, allows this use case to be handled in a clean fashion.

前面的代码并不令人满意,因为这个商业代码被意识到并且与Spring框架耦合在了一起.方法注入是Spring IoC容器中一个稍微先进的特性,它允许在这种使用情况下以一种更简洁的方式去被处理.

猜你喜欢

转载自blog.csdn.net/weixin_41648566/article/details/80965984