Close

Spring - Programmatic Lookup of dependencies via ObjectProvider

[Last Updated: Dec 22, 2023]

Spring Framework 4.3 introduced ObjectProvider<T> which extends the existing ObjectFactory<T> interface. This new interface provides improved programmatic resolution of dependencies.

Obtaining an instance of ObjectProvider

Instance of ObjectProvider can be injected in any Spring managed bean.

For example

@Autowired
private ObjectProvide<ExampleBean> objectProvider;


Also Spring 5.1 added following methods in BeanFactory to get an instance of ObjectProvider

ObjectProvider<T> getBeanProvider(Class<T> requiredType);

Example:

ObjectProvider<ExampleBean> beanProvider = context.getBeanProvider(ExampleBean.class);

ObjectProvider<T> getBeanProvider(ResolvableType requiredType);

Example:

 ResolvableType resolvableType = ResolvableType.forClass(ExampleBean.class);
 ObjectProvider<ExampleBean> beanProvider = context.getBeanProvider(resolvableType);

ObjectProvider methods

Spring 4.3 introduced following methods:

T getIfAvailable()  throws BeansException

Returns bean's instance if registered with Spring Context, otherwise returns null.


T getIfUnique()  throws BeansException

Returns bean's instance if only one bean (of type T) is registered with the container. If there are more than one beans registered then this method returns null instead of throwing NoUniqueBeanDefinitionException. If there are no beans registered then this method returns null.


T getObject()  throws BeansException

Returns bean's instance. If no bean of type T registered then this method will throw NoSuchBeanDefinitionException. If more than one beans of type T are registered, then this method will throw NoUniqueBeanDefinitionException. This method is inherited from ObjectFactory.


T getObject(java.lang.Object... args)  throws BeansException

This method is same as the last method but allows to specify explicit construction arguments.


More methods have been added to ObjectProvider in Spring 5.0 and Spring 5.1 which we will discuss in coming tutorials.

Examples

Example bean

public class ExampleBean {

  public void doSomething() {
      System.out.println("in example bean");
  }
}

getIfAvailable() example

@Configuration
public class GetIfAvailableExample {
  //remove @Bean then getIfAvailable will return null
  @Bean
  ExampleBean exampleBean() {
      return new ExampleBean();
  }

  public static void main(String[] args) {
      AnnotationConfigApplicationContext context =
              new AnnotationConfigApplicationContext(GetIfAvailableExample.class);
      ObjectProvider<ExampleBean> beanProvider = context.getBeanProvider(ExampleBean.class);
      ExampleBean exampleBean = beanProvider.getIfAvailable();
      System.out.println("example bean: " + exampleBean);
      if (exampleBean != null) {
          exampleBean.doSomething();
      }
  }
}

Output

example bean: com.logicbig.example.ExampleBean@3911b7d7
in example bean

getIfUnique() example

@Configuration
public class GetIfUnique {

  @Bean
  ExampleBean exampleBean() {
      return new ExampleBean();
  }

  //uncomment following then getIfUnique will return null
  /*@Bean
  ExampleBean exampleBean2() {
      return new ExampleBean();
  }*/

  public static void main(String[] args) {
      AnnotationConfigApplicationContext context =
              new AnnotationConfigApplicationContext(GetIfUnique.class);
      ObjectProvider<ExampleBean> beanProvider = context.getBeanProvider(ExampleBean.class);
      ExampleBean exampleBean = beanProvider.getIfUnique();
      System.out.println("example bean: " + exampleBean);
      if (exampleBean != null) {
          exampleBean.doSomething();
      }
  }
}

Output

example bean: com.logicbig.example.ExampleBean@4132c9ac
in example bean

getObject() example

@Configuration
public class GetObjectExample {
  @Bean
  ExampleBean exampleBean() {
      return new ExampleBean();
  }

  public static void main(String[] args) {
      AnnotationConfigApplicationContext context =
              new AnnotationConfigApplicationContext(GetObjectExample.class);
      ObjectProvider<ExampleBean> beanProvider = context.getBeanProvider(ExampleBean.class);
      ExampleBean exampleBean = beanProvider.getObject();
      exampleBean.doSomething();
  }
}

Output

in example bean

getObject(args) example

public class ExampleBean2 {
  private String arg;

  public ExampleBean2(String arg) {
      this.arg = arg;
  }

  public void doSomething() {
      System.out.println("in example bean2, arg: " + arg);
  }
}
@Configuration
public class GetObjectWithArgs {
  @Bean
  @Lazy
  ExampleBean2 exampleBean(String arg) {
      return new ExampleBean2(arg);
  }

  public static void main(String[] args) {
      AnnotationConfigApplicationContext context =
              new AnnotationConfigApplicationContext(GetObjectWithArgs.class);
      ObjectProvider<ExampleBean2> beanProvider = context.getBeanProvider(ExampleBean2.class);
      ExampleBean2 exampleBean = beanProvider.getObject("test arg");
      exampleBean.doSomething();
  }
}

Output

in example bean2, arg: test arg

Injecting ObjectProvider

@Configuration
public class InjectingObjectProviderExample {

    @Bean
    ClientBean clientBean() {
        return new ClientBean();
    }

    @Bean
    ExampleBean exampleBean() {
        return new ExampleBean();
    }

    public static void main(String[] args) {
        new AnnotationConfigApplicationContext(InjectingObjectProviderExample.class);
    }

    private static class ClientBean {
        @Autowired
        ObjectProvider<ExampleBean> objectProvider;

        @PostConstruct
        void postConstruct() {
            if (objectProvider != null) {
                ExampleBean exampleBean = objectProvider.getObject();
                if (exampleBean != null) {
                    exampleBean.doSomething();
                }
            }
        }
    }
}

Output

in example bean

Example Project

Dependencies and Technologies Used:

  • spring-context 6.1.2 (Spring Context)
     Version Compatibility: 5.1.0.RELEASE - 6.1.2Version List
    ×

    Version compatibilities of spring-context with this example:

    • 5.1.0.RELEASE
    • 5.1.1.RELEASE
    • 5.1.2.RELEASE
    • 5.1.3.RELEASE
    • 5.1.4.RELEASE
    • 5.1.5.RELEASE
    • 5.1.6.RELEASE
    • 5.1.7.RELEASE
    • 5.1.8.RELEASE
    • 5.1.9.RELEASE
    • 5.1.10.RELEASE
    • 5.1.11.RELEASE
    • 5.1.12.RELEASE
    • 5.1.13.RELEASE
    • 5.1.14.RELEASE
    • 5.1.15.RELEASE
    • 5.1.16.RELEASE
    • 5.1.17.RELEASE
    • 5.1.18.RELEASE
    • 5.1.19.RELEASE
    • 5.1.20.RELEASE
    • 5.2.0.RELEASE
    • 5.2.1.RELEASE
    • 5.2.2.RELEASE
    • 5.2.3.RELEASE
    • 5.2.4.RELEASE
    • 5.2.5.RELEASE
    • 5.2.6.RELEASE
    • 5.2.7.RELEASE
    • 5.2.8.RELEASE
    • 5.2.9.RELEASE
    • 5.2.10.RELEASE
    • 5.2.11.RELEASE
    • 5.2.12.RELEASE
    • 5.2.13.RELEASE
    • 5.2.14.RELEASE
    • 5.2.15.RELEASE
    • 5.2.16.RELEASE
    • 5.2.17.RELEASE
    • 5.2.18.RELEASE
    • 5.2.19.RELEASE
    • 5.2.20.RELEASE
    • 5.2.21.RELEASE
    • 5.2.22.RELEASE
    • 5.2.23.RELEASE
    • 5.2.24.RELEASE
    • 5.2.25.RELEASE
    • 5.3.0
    • 5.3.1
    • 5.3.2
    • 5.3.3
    • 5.3.4
    • 5.3.5
    • 5.3.6
    • 5.3.7
    • 5.3.8
    • 5.3.9
    • 5.3.10
    • 5.3.11
    • 5.3.12
    • 5.3.13
    • 5.3.14
    • 5.3.15
    • 5.3.16
    • 5.3.17
    • 5.3.18
    • 5.3.19
    • 5.3.20
    • 5.3.21
    • 5.3.22
    • 5.3.23
    • 5.3.24
    • 5.3.25
    • 5.3.26
    • 5.3.27
    • 5.3.28
    • 5.3.29
    • 5.3.30
    • 5.3.31
    • Compatible Java Version: 17+
    • 6.0.0
    • 6.0.1
    • 6.0.2
    • 6.0.3
    • 6.0.4
    • 6.0.5
    • 6.0.6
    • 6.0.7
    • 6.0.8
    • 6.0.9
    • 6.0.10
    • 6.0.11
    • 6.0.12
    • 6.0.13
    • 6.0.14
    • 6.0.15
    • 6.1.0
    • 6.1.1
    • 6.1.2

    Versions in green have been tested.

  • jakarta.annotation-api 2.1.1 (Jakarta Annotations API)
  • JDK 17
  • Maven 3.8.1

ObjectProvider examples Select All Download
  • spring-object-provider-example
    • src
      • main
        • java
          • com
            • logicbig
              • example
                • GetObjectExample.java

    See Also