2017-06-13 16 views

回答

0

我已经找到一种方法来看到有关创建原型豆实际的图片。 我使用免费VisualVM内存分析器。

采样器标签中,您可以看到创建的类的所有实例,包括singleton和prototype bean。

你会看到你自己的软件包和类的名称。在这种情况下:

  • 原型是我的原型豆一包。

  • singleton是与我的单身豆包。

  • newclasses是与我通过运算符创建类的包。

另外,垃圾收集后将清理内存,您将在这里看到的结果。

enter image description here

1

你可以通过发布和收听应用程序事件来完成。

  1. 创建您自己的活动。
  2. 原型bean创建时发送事件。
  3. 创建计数ApplicationListener,并聆听收入创建事件。

我这里是 Spring – Publish and Listen Application Events

春不管理的原型bean的整个生命周期:容器初始化,配置,装饰或者是装配一个原型对象,将它交给客户端,然后有对原型实例没有进一步的了解。

简单的变体:

public class PrototypeCreationEvent extends ApplicationEvent { 
    private String beanName; 

    public PrototypeCreationEvent(Object source , String beanName) { 
     super(source); 
     this.beanName = beanName; 
    } 

    public String getBeanName(){ 
     return beanName; 
    } 
} 

public class PrototypeCreationListener implements ApplicationListener<PrototypeCreationEvent> { 
    private ConcurrentMap<String,AtomicInteger> prototypeCreationStatistic = new ConcurrentHashMap<>(); 
    //or from guava AtomicLongMap prototypeCreationStatistic = AtomicLongMap.create(); 

    @Override 
    public void onApplicationEvent(PrototypeCreationEvent event) { 
     prototypeCreationStatistic.computeIfAbsent(event.getBeanName() , k->new AtomicInteger(0)).incrementAndGet(); 

     System.out.println(event); 
    } 

    public ConcurrentMap<String,AtomicInteger> getPrototypeCreationStatistic(){ 
     return prototypeCreationStatistic; 
    } 
} 

public abstract class PrototypeCreationPublisher implements BeanNameAware , ApplicationEventPublisherAware ,InitializingBean { 
    private String beanName; 
    private ApplicationEventPublisher applicationEventPublisher; 


    @Override 
    public void setBeanName(String name) { 
     this.beanName = name; 
    } 

    @Override 
    public void afterPropertiesSet() throws Exception { 
     System.out.println(); 
    } 

    @Override 
    public void setApplicationEventPublisher(ApplicationEventPublisher applicationEventPublisher) { 
     this.applicationEventPublisher = applicationEventPublisher; 
    } 

    @PostConstruct //or use interface InitializingBean 
    public void sendEventAfterCreation() throws Exception { 
     applicationEventPublisher.publishEvent(new PrototypeCreationEvent(this , beanName)); 
    } 
} 

@Component(value = BeanDefinition.SCOPE_PROTOTYPE) 
public class PrototypeA extends PrototypeCreationPublisher{ 
} 

@Component(value = BeanDefinition.SCOPE_PROTOTYPE) 
public class PrototypeB extends PrototypeCreationPublisher{ 
} 

例如:

PrototypeA prototypeA1 = context.getBean(PrototypeA.class); 
    PrototypeA prototypeA2 = context.getBean(PrototypeA.class); 
    PrototypeA prototypeA3 = context.getBean(PrototypeA.class); 
    PrototypeB prototypeB1 = context.getBean(PrototypeB.class); 

    PrototypeCreationListener statistic = context.getBean(PrototypeCreationListener.class); 
    statistic.getPrototypeCreationStatistic().entrySet().forEach(s->{ 
     System.out.println(s.getKey() + " count = "+s.getValue()); 
    }); 

结果:

PrototypeB count = 1 
    PrototypeA count = 3 
+0

谢谢。有什么办法从ApplicationContext获取信息吗? –

+0

好的。我会尽力。 –

+0

可能是我不明白的东西......但我可以通过仅从bean的构造函数打印控制台中的信息来获取有关创建bean的信息。请看我更正的问题。在我们的项目中,我们有400多个原型bean,所以我想检查一下原型bean的创建和数量。 –

相关问题