【问题标题】:How to set up init-method for a bean when spring is configured by annotation driven?注释驱动配置spring时如何为bean设置init-method?
【发布时间】:2011-12-24 02:51:23
【问题描述】:

我使用spring roo构建项目,它是注解驱动的,XML文件中没有bean定义。所有配置信息都在 *.aj 文件中。

现在我想为没有默认构造函数的 bean 设置一个 init 方法(该 bean 来自第三方,它有一个带参数的构造函数,我无法删除它们或提供默认构造函数给它。)

请问有谁可以告诉我怎么做吗?

之所以要这样做,是因为我想使用applicationContext.getBean("thatBeanName")来动态获取bean并使用它。因为 bean 没有默认构造函数,所以我总是得到错误:java.lang.NoSuchMethodException: com.to.that.bean.<init>() 这就是为什么我想将 init-method 添加到 bean。

【问题讨论】:

    标签: spring configuration annotations initialization spring-roo


    【解决方案1】:

    使用@PostConstruct,如下例所示。相当于init-method="initialize()"

    @PostConstruct
    public void initialize() {
        messages.put("English", "Welcome");
        messages.put("Deutsch", "Willkommen");
    }
    

    【讨论】:

    • 它不等效恕我直言@Bean(initMethod="init") 是正确的,如果可能的话,我会避免使用@PostConstruct 作为initMethod。
    • @magulla 为什么会这样?
    • @DoNuT 在这里看到我的推理,把它放在答案中stackoverflow.com/a/46569019/1479668
    【解决方案2】:
    @Bean(initMethod="init")
    public MyBean getMyBean() {
     ...
    }
    

    【讨论】:

    • 如果您无权访问您尝试创建的 bean 的源代码,请使用此选项。否则,使用@PostConstruct。
    【解决方案3】:

    在 spring 容器中,最后调用的是“init”方法,
    @postconstruct 在 afterPropertiesSet 之前调用。所以如果有人错过使用它会更安全。 "为同一个bean配置的多个生命周期机制,不同的初始化方法,调用如下:

    1.使用@PostConstruct注解的方法

    2.由 InitializingBean 回调接口定义的afterPropertiesSet()

    1. 自定义配置的 init() 方法 [https://docs.spring.io/spring/docs/current/spring-framework-reference/core.html#beans-java-lifecycle-callbacks][1]

    虽然,今天我更愿意独立于 Spring 并使用 @Postconstract,甚至配置默认的 init 方法识别。只有有意义的方法名称表明它应该用于初始化 - 从框架中清除,从注释中清除。

    【讨论】:

      【解决方案4】:

      正如@Pangea 所说,@PostConstruct 是最佳选择。您还可以实现 initializingBean 并在 afterPropertiesSet 方法中进行初始化。请查看here 了解此方法。

      【讨论】:

        【解决方案5】:

        我意识到有多个答案试图解决这个问题。但是引入了@Configuration,它在Spring Boot中被广泛使用。事情发生了一些变化。

        如果您在@Configuration 注释类中使用@Bean 注释,例如:

        @Configuration
        class FooClass {
            @Bean
            public Bar bar() {
                return new Bar();
            }
        }
        

        如果您想在初始化期间对 bean 实例使用自动调用的方法,您有以下两种选择:

        选项1:

        @Configuration
        class FooClass {
            @Bean(initMethod="init")
            public Bar bar() {
                return new Bar();
            }
        }
        

        选项2:

        @Configuration
        class FooClass {
            @Bean
            public Bar bar() {
                Bar bar = new Bar();
                bar.init();
                return bar;
            }
        }
        

        但是,正如@Bean Java Doc 中所述:

         /**
        
             * 在初始化期间调用 bean 实例的方法的可选名称。
        
             * 不常用,因为可以直接以编程方式调用该方法
        
             * 在 Bean 注释方法的主体内。
        
             * 默认值为{@code ""},表示不调用init方法。
        
             */

        第二个被认为是更好的答案。见链接here

        【讨论】:

          猜你喜欢
          • 2015-04-28
          • 2012-10-25
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2010-09-23
          • 1970-01-01
          • 2018-10-25
          • 1970-01-01
          相关资源
          最近更新 更多