Spring:将启动ApplicationContext的对象注入到ApplicationContext中

4

我想在一个遗留应用程序中使用Spring。

核心部分是一个类,我们称之为LegacyPlugin,它代表应用程序中的一种可插拔的组件。问题是这个类也是数据库连接器,并且被用来创建许多其他对象,通常是通过构造函数注入...

我想从LegacyPlugin启动一个ApplicationContext,并通过BeanFactory将其注入到ApplicationContext中,例如创建其他对象。然后代码将被重写,使用setter注入等方法。

我想知道实现这一点的最佳方法是什么。到目前为止,我有一个使用ThreadLocal来保存当前正在执行的插件的静态引用的BeanFactory的工作版本,但我觉得它很丑陋...

下面是我想要最终得到的代码:

public class MyPlugin extends LegacyPlugin {

    public void execute() {
        ApplicationContext ctx = new ClassPathXmlApplicationContext();
        // Do something here with this, but what ?
        ctx.setConfigLocation("context.xml");
        ctx.refresh();
    }

 }

<!-- This should return the object that launched the context -->
<bean id="plugin" class="my.package.LegacyPluginFactoryBean" />

<bean id="someBean" class="my.package.SomeClass">
    <constructor-arg><ref bean="plugin"/></constructor-arg>
</bean>

<bean id="someOtherBean" class="my.package.SomeOtherClass">
    <constructor-arg><ref bean="plugin"/></constructor-arg>
</bean>

如果您可以访问您想要注入应用程序上下文的类,那么您可以吗?我不确定每个类持有应用程序上下文背后的理由是什么? - Fil
基本上,我想要消除插件内大量的初始化代码。 - mexique1
2个回答

4
SingletonBeanRegistry 接口允许您通过其 registerSingleton 方法手动将预配置的单例注入到上下文中,如下所示:
ApplicationContext ctx = new ClassPathXmlApplicationContext();
ctx.setConfigLocation("context.xml");

SingletonBeanRegistry beanRegistry = ctx.getBeanFactory();
beanRegistry.registerSingleton("plugin", this);

ctx.refresh();

这将把plugin bean添加到上下文中。您不需要在context.xml文件中声明它。

嗯,很有用,我不知道BeanRegistry...但我更喜欢在Spring上下文文件中明确地使用它。 - mexique1
@mexique1:为什么?这有什么区别吗? - skaffman
哦...抱歉接受晚了。毕竟,我在几个项目中使用@Service/@Component注释,而这基本上是一样的:你不知道如何实现,但是Bean就在那里。感谢您的回复。 - mexique1

0
实际上,这不起作用...它会导致以下错误:
BeanFactory not initialized or already closed
call 'refresh' before accessing beans via the ApplicationContext

最终的解决方案是使用GenericApplicationContext
GenericApplicationContext ctx = new GenericApplicationContext();
ctx.getBeanFactory().registerSingleton("plugin", this);
new XmlBeanDefinitionReader(ctx).loadBeanDefinitions(
    new ClassPathResource("context.xml"));
ctx.refresh();

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接