How to programmatically create bean definition with injected properties?
36,118
Solution 1
Use RuntimeBeanReference
:
values.addPropertyValue("beanProperty", new RuntimeBeanReference("beanName"));
Solution 2
I would add a bean like this that has access to the applicationContext:
public class AppContextExtendingBean implements ApplicationContextAware{
@Override
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException{
AutowireCapableBeanFactory beanFactory = applicationContext.getAutowireCapableBeanFactory();
// do it like this
version1(beanFactory);
// or like this
version2(beanFactory);
}
// let spring create a new bean and then manipulate it (works only for singleton beans, obviously)
private void version1(AutowireCapableBeanFactory beanFactory){
MyObject newBean = (MyObject) beanFactory.createBean(MyObject.class,AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
newBean.setBar("baz");
newBean.setFoo("foo");
newBean.setPhleem("phleem");
beanFactory.initializeBean(newBean, "bean1");
}
// create the object manually and then inject it into the spring context
private void version2(AutowireCapableBeanFactory beanFactory){
MyObject myObject=new MyObject("foo","phleem");
myObject.setBar("baz");
beanFactory.autowireBean(myObject);
beanFactory.initializeBean(myObject, "bean2");
}
}
Solution 3
I found the solution. I have to use another BeanDefinition
as a property, like this:
GenericBeanDefinition bd2 = new GenericBeanDefinition();
bd2.setBeanClass(Dependency.class);
GenericBeanDefinition bd1 = new GenericBeanDefinition();
bd1.setBeanClass(Component.class);
MutablePropertyValues values = new MutablePropertyValues();
values.addPropertyValue("dependency", bd2);
bd1.setPropertyValues(values);
Comments
-
Fixpoint almost 2 years
I want to programmatically add a bean definition to an application context, but some properties of that definition are other beans from that context (I know their names). How can I do this so that those properties will be injected?
For example:
GenericBeanDefinition beanDef = new GenericBeanDefinition(); beanDef.setBeanClass(beanClass); MutablePropertyValues values = new MutablePropertyValues(); values.addPropertyValue("intProperty", 10); values.addPropertyValue("stringProperty", "Hello, world"); values.addPropertyValue("beanProperty", /* What should be here? */); beanDef.setPropertyValues(values);
I'm using Spring 3.0.
-
Fixpoint almost 14 yearsI can't use Javaconfig because I need to create these definitions dynamically. How can I use
BeanDefinitionParser
? -
Bozho almost 14 yearsjavaconfig should do fine in all cases. Look at some implementations of BeanDefinitionParser to see how they work. (checkout the spring sources)
-
Fixpoint almost 14 yearsAre there any differences with using a BeanDefinition as a property?
-
axtavt almost 14 years@Shooshpanchick:
BeanDefinition
creates a new inner bean of the specified class, whenRuntimeBeanReference
creates a reference to the exisiting one. -
rayman almost 12 yearsHi after lots of research I found your post and that worked fine. I am using version2. but tell me: using AutowireCapableBeanFactory would cost any memory leak or performances? thanks.
-
rayman almost 12 yearsHi, But how do you finally add the GenericBeanDefinition to the container?
-
Mohammad Adnan over 11 yearsThis solution is seems to be fine. MyObject is seems to be a prototype bean(since we are creating objects from our own every time). do we need to provide any kind of annotation like @Component or @Scope? how spring decides to create it's scope?