3

I am trying to find out if there is a Spring analogue of the ServiceLoader class which is part of the standard SDK's API. If there is such a class how is it used?

Please advise!

carlspring
  • 31,231
  • 29
  • 115
  • 197

1 Answers1

4

Assume SpringFactoriesLoader is for you. From its JavaDocs:

/*
 * General purpose factory loading mechanism for internal use within the framework.
 *
 * <p>The {@code SpringFactoriesLoader} loads and instantiates factories of a given type
 * from "META-INF/spring.factories" files. The file should be in {@link Properties} format,
 * where the key is the fully qualified interface or abstract class name, and the value
 * is a comma-separated list of implementation class names. For instance:
 *
 * <pre class="code">example.MyService=example.MyServiceImpl1,example.MyServiceImpl2</pre>
 *
 * where {@code MyService} is the name of the interface, and {@code MyServiceImpl1} and
 * {@code MyServiceImpl2} are the two implementations.
 */

The sample from one of our project:

META-INF/spring.factories:

org.springframework.integration.config.IntegrationConfigurationInitializer=\
org.springframework.integration.config.GlobalChannelInterceptorInitializer,\
org.springframework.integration.config.IntegrationConverterInitializer

The implementation:

public class IntegrationConfigurationBeanFactoryPostProcessor implements BeanFactoryPostProcessor {

    @Override
    public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
        Set<String> initializerNames = new HashSet<String>(
                SpringFactoriesLoader.loadFactoryNames(IntegrationConfigurationInitializer.class, beanFactory.getBeanClassLoader()));

        for (String initializerName : initializerNames) {
            try {
                Class<?> instanceClass = ClassUtils.forName(initializerName, beanFactory.getBeanClassLoader());
                Assert.isAssignable(IntegrationConfigurationInitializer.class, instanceClass);
                IntegrationConfigurationInitializer instance = (IntegrationConfigurationInitializer) instanceClass.newInstance();
                instance.initialize(beanFactory);
            }
            catch (Exception e) {
                throw new IllegalArgumentException("Cannot instantiate 'IntegrationConfigurationInitializer': " + initializerName, e);
            }
        }
    }

}
Joshua Taylor
  • 84,998
  • 9
  • 154
  • 353
Artem Bilan
  • 113,505
  • 11
  • 91
  • 118