Get bean method in java

@Bean

@Bean – это аннотация уровня метода и прямой аналог элемента на XML. Аннотация поддерживает некоторые атрибуты, предлагаемые , такие как:

Вы можете использовать аннотацию @Bean в классе с аннотацией @Configuration или в классе с аннотацией @Component .

Объявление бина

Чтобы объявить бин, можно аннотировать метод с помощью @Bean . Этот метод используется для регистрации определения бина в ApplicationContext того типа, который задан в качестве возвращаемого значения метода. По умолчанию имя бина совпадает с именем метода. В следующем примере показано объявление метода с аннотацией @Bean :

@Configuration public class AppConfig < @Bean public TransferServiceImpl transferService() < return new TransferServiceImpl(); >>
@Configuration class AppConfig

Предшествующая конфигурация в точности эквивалентна следующей на основе XML в Spring:

Оба объявления делают бин с именем transferService доступным в ApplicationContext , привязанном к экземпляру объекта типа TransferServiceImpl , как показано на следующем текстовом изображении:

transferService -> com.acme.TransferServiceImpl

Также можно использовать методы по умолчанию для определения бинов. Это позволяет создавать конфигурации бинов путем реализации интерфейсов с определениями бинов в методах по умолчанию.

public interface BaseConfig < @Bean default TransferServiceImpl transferService() < return new TransferServiceImpl(); >> @Configuration public class AppConfig implements BaseConfig

Можно также объявить свой метод, аннотированный @Bean , с помощью возвращаемого типа интерфейса (или базового класса), как показано в следующем примере:

@Configuration public class AppConfig < @Bean public TransferService transferService() < return new TransferServiceImpl(); >>
@Configuration class AppConfig < @Bean fun transferService(): TransferService < return TransferServiceImpl() >>

Однако это ограничивает видимость для прогнозирования расширенного типа указанным типом интерфейса (TransferService ). Затем, когда полный тип (TransferServiceImpl ) единожды распознается контейнером, создается экземпляр затронутого бина-одиночки. Экземпляры бинов-одиночек без отложенной инициализации создаются в соответствии с порядком их объявления, поэтому вы можете заметить разные результаты согласования по типам в зависимости от того, когда другой компонент пытается выполнить согласование по необъявленному типу (например, @Autowired TransferServiceImpl , который разрешается только после создания экземпляра бина transferService ).

Читайте также:  Java create annotation class

Если вы постоянно ссылаетесь на свои типы по объявленному интерфейсу службы, то ваши возвращаемые типы, помеченные аннотацией @Bean , могут без проблем следовать этому проектному решению. Однако для компонентов, реализующих несколько интерфейсов, или для компонентов, на которые потенциально можно ссылаться по их типу реализации, безопаснее объявить максимально конкретный возвращаемый тип (по крайней мере, настолько конкретный, насколько этого требуют точки внедрения, ссылающиеся на ваш бин).

Зависимости бинов

Метод, аннотированный @Bean , может иметь произвольное количество параметров, которые описывают зависимости, необходимые для создания этого бина. Например, если нашему TransferService требуется AccountRepository , мы можем осуществить эту зависимость с помощью параметра метода, как показано в следующем примере:

@Configuration public class AppConfig < @Bean public TransferService transferService(AccountRepository accountRepository) < return new TransferServiceImpl(accountRepository); >>

Источник

spring-getbean

In this tutorial, we’re going to go through different variants of the BeanFactory.getBean() method.

Simply put, as the name of the method also suggests, this is responsible for retrieving a bean instance from the Spring container.

2. Spring Beans Setup

First, let’s define a few Spring beans for testing. There are several ways in which we can provide bean definitions for the Spring container, but in our example, we’ll use annotation-based Java config:

@Configuration class AnnotationConfig < @Bean(name = ) @Scope(value = "prototype") Tiger getTiger(String name) < return new Tiger(name); >@Bean(name = "lion") Lion getLion() < return new Lion("Hardcoded lion name"); >interface Animal <> >

We’ve created two beans. Lion has the default singleton scope. Tiger is explicitly set to prototype scope. Additionally, please note that we defined names for each bean that we’ll use in further requests.

3. The getBean() APIs

BeanFactory provides five different signatures of the getBean() method that we’re going to examine in the following subsections.

3.1. Retrieving Bean by Name

Let’s see how we can retrieve a Lion bean instance using its name:

Object lion = context.getBean("lion"); assertEquals(Lion.class, lion.getClass());

In this variant, we provide a name, and in return, we get an instance of Object class if a bean with the given name exists in the application context. Otherwise, both this and all other implementations throw NoSuchBeanDefinitionException if the bean lookup fails.

The main disadvantage is that after retrieving the bean, we have to cast it to the desired type. This may produce another exception if the returned bean has a different type than we expected.

Suppose we try to get a Tiger using the name “lion”. When we cast the result to Tiger, it will throw a ClassCastException:

assertThrows(ClassCastException.class, () -> < Tiger tiger = (Tiger) context.getBean("lion"); >);

3.2. Retrieving Bean by Name and Type

Here we need to specify both the name and type of the requested bean:

Lion lion = context.getBean("lion", Lion.class);

Compared to the previous method, this one is safer because we get the information about type mismatch instantly:

assertThrows(BeanNotOfRequiredTypeException.class, () -> context.getBean("lion", Tiger.class)); >

3.3. Retrieving Bean by Type

With the third variant of getBean(), it is enough to specify only the bean type:

Lion lion = context.getBean(Lion.class);

In this case, we need to pay special attention to a potentially ambiguous outcome:

assertThrows(NoUniqueBeanDefinitionException.class, () -> context.getBean(Animal.class)); >

In the example above, because both Lion and Tiger implement the Animal interface, merely specifying type isn’t enough to unambiguously determine the result. Therefore, we get a NoUniqueBeanDefinitionException.

3.4. Retrieving Bean by Name with Constructor Parameters

In addition to the bean name, we can also pass constructor parameters:

Tiger tiger = (Tiger) context.getBean("tiger", "Siberian");

This method is a bit different because it only applies to beans with prototype scope.

In the case of singletons, we’re going to get a BeanDefinitionStoreException.

Because a prototype bean will return a newly created instance every time it’s requested from the application container, we can provide constructor parameters on-the-fly when invoking getBean():

Tiger tiger = (Tiger) context.getBean("tiger", "Siberian"); Tiger secondTiger = (Tiger) context.getBean("tiger", "Striped"); assertEquals("Siberian", tiger.getName()); assertEquals("Striped", secondTiger.getName());

As we can see, each Tiger gets a different name according to what we specified as a second parameter when requesting the bean.

3.5. Retrieving Bean by Type With Constructor Parameters

This method is analogous to the last one, but we need to pass the type instead of the name as the first argument:

Tiger tiger = context.getBean(Tiger.class, "Shere Khan"); assertEquals("Shere Khan", tiger.getName());

Similar to retrieving a bean by name with constructor parameters, this method only applies to beans with prototype scope.

4. Usage Considerations

Despite being defined in the BeanFactory interface, the getBean() method is most frequently accessed through the ApplicationContext. Typically, we don’t want to use the getBean() method directly in our program.

Beans should be managed by the container. If we want to use one of them, we should rely on dependency injection rather than a direct call to ApplicationContext.getBean(). That way, we can avoid mixing application logic with framework-related details.

5. Conclusion

In this quick tutorial, we went through all implementations of the getBean() method from the BeanFactory interface and described the pros and cons of each.

All the code examples shown here are available over on GitHub.

Источник

Tech Tutorials

Tutorials and posts about Java, Spring, Hadoop and many more. Java code examples and interview questions. Spring code examples.

Saturday, January 1, 2022

Passing Arguments to getBean() Method in Spring

Sometimes in a Spring application when you get a bean from the application context you may also need to initialize the bean by calling it’s constructor with parameters. In this post we’ll see how to call the Spring bean’s non-default constructor by passing parameters.

BeanFactory interface getBean() method

  • getBean(java.lang.String name, java.lang.Object. args)— Return an instance, which may be shared or independent, of the specified bean. Allows for specifying explicit constructor arguments / factory method arguments, overriding the specified default arguments (if any) in the bean definition.

Using this method to get the bean from the context you can also specify the constructor parameters. Note that ApplicationContext interface extends the BeanFactory interface so this method is available for use with in Context.

Spring example initializing bean with constructor parameters

Let’s say we have a Spring component MessagePrinter which has a constructor with one String parameter message.

@Component @Scope("prototype") public class MessagePrinter < private String message; public MessagePrinter(String message) < this.message = message; >public void displayMessage() < System.out.println("Passed message is- " + message); >>
@Component public class TaskExecutorDemo implements ApplicationContextAware < private ApplicationContext applicationContext; @Override public void setApplicationContext(ApplicationContext applicationContext) throws BeansException < this.applicationContext = applicationContext; >public void printMessages() < // Bean initialized with constructor params MessagePrinter messagePrinter = applicationContext.getBean( MessagePrinter.class, "Hello"); messagePrinter.displayMessage(); >>

This class implements ApplicationContextAware interface so that it has reference to the ApplicationContext. Also, you can see when getBean() method is called to get an instance of MessagePrinter bean, String parameter is also passed to initialize it

Since Spring Java config is used so we need a Configuration class. That configuration is used just for passing packages for component scanning.

@Configuration @ComponentScan(basePackages = «org.netjs.service») public class AppConfig

Java class to run the application

That’s all for this topic Passing Arguments to getBean() Method in Spring. If you have any doubt or any suggestions to make please drop a comment. Thanks!

Источник

Basic Concepts: @Bean and @Configuration

The central artifacts in Spring’s Java configuration support are @Configuration -annotated classes and @Bean -annotated methods.

The @Bean annotation is used to indicate that a method instantiates, configures, and initializes a new object to be managed by the Spring IoC container. For those familiar with Spring’s XML configuration, the @Bean annotation plays the same role as the element. You can use @Bean -annotated methods with any Spring @Component . However, they are most often used with @Configuration beans.

Annotating a class with @Configuration indicates that its primary purpose is as a source of bean definitions. Furthermore, @Configuration classes let inter-bean dependencies be defined by calling other @Bean methods in the same class. The simplest possible @Configuration class reads as follows:

@Configuration public class AppConfig < @Bean public MyServiceImpl myService() < return new MyServiceImpl(); >>
@Configuration class AppConfig < @Bean fun myService(): MyServiceImpl < return MyServiceImpl() >>

The preceding AppConfig class is equivalent to the following Spring XML:

When @Bean methods are declared within classes that are not annotated with @Configuration , they are referred to as being processed in a “lite” mode. Bean methods declared in a @Component or even in a plain old class are considered to be “lite”, with a different primary purpose of the containing class and a @Bean method being a sort of bonus there. For example, service components may expose management views to the container through an additional @Bean method on each applicable component class. In such scenarios, @Bean methods are a general-purpose factory method mechanism.

Unlike full @Configuration , lite @Bean methods cannot declare inter-bean dependencies. Instead, they operate on their containing component’s internal state and, optionally, on arguments that they may declare. Such a @Bean method should therefore not invoke other @Bean methods. Each such method is literally only a factory method for a particular bean reference, without any special runtime semantics. The positive side-effect here is that no CGLIB subclassing has to be applied at runtime, so there are no limitations in terms of class design (that is, the containing class may be final and so forth).

In common scenarios, @Bean methods are to be declared within @Configuration classes, ensuring that “full” mode is always used and that cross-method references therefore get redirected to the container’s lifecycle management. This prevents the same @Bean method from accidentally being invoked through a regular Java call, which helps to reduce subtle bugs that can be hard to track down when operating in “lite” mode.

The @Bean and @Configuration annotations are discussed in depth in the following sections. First, however, we cover the various ways of creating a spring container by using Java-based configuration.

Источник

Оцените статью