I am trying to write a framework where plugins can be dynamically loaded. One step in this loading process is to load in a properties file “properties.plugin” I would like to load this into a PropertyPlaceholderConfigurer however it appears that this uses a different Classloader than the one the GenericApplicationContext has been set to use.
My code for creating the context:
GenericApplicationContext ctx = new GenericApplicationContext();
if(classLoader !=null)
ctx.setClassLoader(classLoader);
ctx.getDefaultListableBeanFactory().setAllowBeanDefinitionOverriding(false);
XmlBeanDefinitionReader xmlReader = new XmlBeanDefinitionReader(ctx);
xmlReader.setBeanClassLoader(classLoader);
int totalBeanCount = 0;
List<Resource> processedResources = new ArrayList<Resource>(resources.length);
for(Resource r:resources)
{
try
{
int loadedBeanCount = xmlReader.loadBeanDefinitions(r);
totalBeanCount += loadedBeanCount;
processedResources.add(r);
}
catch(BeanDefinitionStoreException e)
{
throw e;
}
}
classLoader in the above code gets set at start up.
The bean is setup as follows:
<bean name="ReloadedPropertiesPlaceholderConfigurer" class="myProject.MyPropertyPlaceholderConfigurer" >
<property name="locationNames" ref="locationNamesList" />
<property name="ignoreUnresolvablePlaceholders" value="true"/>
</bean>
<bean name="locationNamesList" class="java.util.ArrayList">
<constructor-arg>
<list>
<value>properties/properties.plugin</value>
</list>
</constructor-arg>
</bean>
myProject.MyPropertyPlaceholderConfigurer simply extends PropertyPlaceholderConfigurer
When I call ctx.refresh() later in the code i see a log message saying could not find properties/properties.plugin
The following code
classLoader.getResource("properties/properties.plugin");
Works if i add it just before setting the class loader on the context.
I have also tried classpath:properties/properties.plugin, properties.plugin, classpath*:properties.plugin.
Is it the case that this PropertyPlaceholderConfigurer is using a different classloader than the one set on ctx and if so is there a way to set the class loader it uses?
I don’t see a setClassLoader method.
Seems to make it work so it must be using this class loader instead of the one set on the context.