本文介绍了proxyMode ScopedProxyMode.TARGET_CLASS vs ScopedProxyMode.INTERFACE的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

正如其他SO答案建议的那样,根据您的需要使用代理模式类型,我仍然感到困惑;

As other SO answers suggested, use proxy mode type as per your need, I am still confused;

@Configuration
@ComponentScan
public class Application 
{
    public static void main( String[] args )
    {
        ApplicationContext context = new AnnotationConfigApplicationContext(Application.class);

        PrototypeBeanFactory factoryBean = context.getBean(PrototypeBeanFactory.class);
        System.out.println("Let's start");
        SomeInterface b1 = factoryBean.getPrototypeBeanInstance();
        SomeInterface b2 = factoryBean.getPrototypeBeanInstance();

        System.out.println(b1.hashCode());
        System.out.println(b2.hashCode());

        b1.sayHello();
        b2.sayHello();

        b1.sayHello();
        b2.sayHello();
    }
}

@Component
public class PrototypeBeanFactory {
    @Lookup
    public PrototypeBean getPrototypeBeanInstance(){
        System.out.println("It'll be ignored");
        return null;
    }
}

@Component
@Scope(value="prototype", proxyMode = ScopedProxyMode.INTERFACES)
public class PrototypeBean {
    public PrototypeBean() {
        System.out.println("I am created");
    }

    public void sayHello() {
        System.out.println("Hello from " + this.hashCode());
    }

}

输出

Let's start
I am created
I am created
1849201180
1691875296
Hello from 1849201180
Hello from 1691875296
Hello from 1849201180
Hello from 1691875296

现在如果我将代理模式更改为TARGET_CLASS

Now if I change the proxy-mode to TARGET_CLASS

输出

Let's start
-721204056
-721204056
I am created
Hello from 172032696
I am created
Hello from 299644693
I am created
Hello from 1771243284
I am created
Hello from 2052256418

为什么,在基于类的代理的情况下,它会在每次方法调用时创建不同的对象?

Why, in case of class based proxy, it creates different object on each method invocation?

推荐答案

@Component
@Scope(value="prototype", proxyMode = ScopedProxyMode.INTERFACES)
public class PrototypeBean { ... }

在你的情况下,这将导致每次调用 getBean bean的bean作为你的 PrototypeBean 没有实现接口,因此无法创建范围内的代理。在您的情况下,您调用查找方法两次,因此您将获得2个实例。这实际上是 prototype 作用域bean的正常行为。

This, in your case, will lead to a bean per invocation of getBean bean as your PrototypeBean doesn't implement an interface and as such a scoped proxy cannot be created. In your case you call the lookup method twice and hence you will get 2 instances. This is actually the normal behavior of a prototype scoped bean.

Component
@Scope(value="prototype", proxyMode = ScopedProxyMode.TARGET_CLASS)
public class PrototypeBean { ... }

这将导致创建代理。该代理创建一次,并将在每次调用 getBean 时返回。只要在代理上调用方法,它就会根据范围创建新方法或重用现有方法。由于您已将范围指定为 prototype ,因此每个方法调用都将生成一个新对象。

This will lead to the creation of a proxy. That proxy is created once and will be returned for each call to getBean. As soon as you invoke a method on the proxy it will, based on the scope, either create a new one or reuse an existing one. As you have specified the scope as prototype each method invocation will lead to a new object.

注意:如果您的类实现了一个暴露相应方法的接口,那么<$ c $的行为就没有区别c> proxyMode = ScopedProxyMode.INTERFACES 和 proxyMode = ScopedProxyMode.TARGET_CLASS ,因为在这两种情况下都会创建一个范围代理。

Note: If your class would implement an interface which exposes the appropriate method, there would be no difference in the behavior of proxyMode = ScopedProxyMode.INTERFACES and proxyMode = ScopedProxyMode.TARGET_CLASS as in both cases a scoped proxy would be created.

这篇关于proxyMode ScopedProxyMode.TARGET_CLASS vs ScopedProxyMode.INTERFACE的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-25 05:29