← Назад к вопросам

Что входит в Bean Definition?

2.0 Middle🔥 191 комментариев
#Spring Boot и Spring Data#Spring Framework

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI22 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Bean Definition в Spring: полная структура

Bean Definition — это метаданные, описывающие как Spring IoC контейнер должен создавать, конфигурировать и управлять бином (объектом). Это один из ключевых концептов Spring Framework, лежащий в основе dependency injection и управления жизненным циклом объектов.

Основные компоненты Bean Definition

1. Class (Класс бина) Полное имя класса, который будет инстанцирован контейнером:

// XML конфигурация
<bean id="userService" class="com.example.service.UserServiceImpl" />

// Java конфигурация
@Bean
public UserService userService() {
    return new UserServiceImpl();
}

// Annotation-based
@Component
public class UserServiceImpl implements UserService { }

2. Bean ID (идентификатор) Уникальный идентификатор для регистрации и поиска бина в контейнере:

<bean id="userService" class="com.example.service.UserServiceImpl" />
<bean id="anotherUserService" class="com.example.service.UserServiceImpl" />

<!-- Можно использовать name для альтернативных имён -->
<bean id="userService" name="userSvc,userServ" class="com.example.service.UserServiceImpl" />
@Bean(name = "userService", "userSvc") // Несколько имён
public UserService userService() {
    return new UserServiceImpl();
}

3. Scope (область видимости) Определяет, как долго живёт бин и сколько экземпляров будет создано:

<!-- singleton (по умолчанию): один экземпляр на всё приложение -->
<bean id="userService" scope="singleton" class="com.example.service.UserServiceImpl" />

<!-- prototype: новый экземпляр при каждом запросе -->
<bean id="userService" scope="prototype" class="com.example.service.UserServiceImpl" />

<!-- request, session, application (для web приложений) -->
<bean id="httpRequest" scope="request" class="com.example.HttpRequestContext" />
@Bean
@Scope("singleton") // По умолчанию
public UserService userService() {
    return new UserServiceImpl();
}

@Bean
@Scope(value = "prototype") // Новый экземпляр каждый раз
public UserRequest userRequest() {
    return new UserRequest();
}

4. Constructor Arguments (аргументы конструктора) Данные для инъекции через конструктор:

<bean id="userDao" class="com.example.dao.UserDao" />

<bean id="userService" class="com.example.service.UserServiceImpl">
    <constructor-arg ref="userDao" />
    <constructor-arg value="10" />
</bean>
public class UserServiceImpl implements UserService {
    private final UserDao userDao;
    private final int maxRetries;
    
    public UserServiceImpl(UserDao userDao, int maxRetries) {
        this.userDao = userDao;
        this.maxRetries = maxRetries;
    }
}

@Bean
public UserService userService(UserDao userDao) {
    return new UserServiceImpl(userDao, 10);
}

5. Properties (свойства) Данные для инъекции через setter'ы:

<bean id="userService" class="com.example.service.UserServiceImpl">
    <property name="userDao" ref="userDao" />
    <property name="timeout" value="5000" />
    <property name="maxConnections" value="100" />
</bean>
public class UserServiceImpl {
    private UserDao userDao;
    private int timeout;
    
    public void setUserDao(UserDao userDao) {
        this.userDao = userDao;
    }
    
    public void setTimeout(int timeout) {
        this.timeout = timeout;
    }
}

6. Lazy Initialization (ленивая инициализация) Когда бин должен быть создан (сразу или по требованию):

<!-- По умолчанию: создаётся при старте контейнера -->
<bean id="expensiveService" class="com.example.ExpensiveService" />

<!-- Ленивая инициализация: создаётся только при запросе -->
<bean id="expensiveService" lazy-init="true" class="com.example.ExpensiveService" />
@Bean
@Lazy // Создаётся только при запросе
public ExpensiveService expensiveService() {
    return new ExpensiveService();
}

7. Lifecycle Callbacks (методы жизненного цикла) Методы, вызываемые при создании и уничтожении бина:

<bean id="userService" 
      class="com.example.service.UserServiceImpl"
      init-method="initialize"
      destroy-method="cleanup" />
public class UserServiceImpl {
    public void initialize() {
        // Вызывается после создания бина
        System.out.println("Бин инициализирован");
    }
    
    public void cleanup() {
        // Вызывается при остановке контейнера
        System.out.println("Бин уничтожается");
    }
}

// Или через аннотации
public class UserServiceImpl {
    @PostConstruct
    public void initialize() { }
    
    @PreDestroy
    public void cleanup() { }
}

8. Autowire Mode (режим автопроводки зависимостей) Как контейнер должен разрешать зависимости:

<!-- no: без автопроводки (по умолчанию) -->
<bean id="userService" class="com.example.service.UserServiceImpl" autowire="no" />

<!-- byName: по имени свойства -->
<bean id="userService" class="com.example.service.UserServiceImpl" autowire="byName" />

<!-- byType: по типу (должен быть ровно один бин такого типа) -->
<bean id="userService" class="com.example.service.UserServiceImpl" autowire="byType" />

<!-- constructor: через конструктор -->
<bean id="userService" class="com.example.service.UserServiceImpl" autowire="constructor" />

9. Depends On (зависимости) Указание порядка создания бинов:

<!-- databaseService должен быть создан до userService -->
<bean id="userService" class="com.example.service.UserServiceImpl" depends-on="databaseService" />

10. Annotations (аннотации) Дополнительная информация через аннотации:

@Component
@Scope("singleton")
@Lazy
public class UserServiceImpl implements UserService {
    @Autowired
    private UserDao userDao;
    
    @Value("${app.maxRetries:3}")
    private int maxRetries;
}

Как Spring создаёт бин на основе Bean Definition

// Примерный процесс:
1. Прочитать Bean Definition
2. Получить класс: Class.forName("com.example.UserServiceImpl")
3. Создать экземпляр (через конструктор)
4. Инъектировать зависимости (constructor-arg или @Autowired)
5. Установить properties (setter'ы)
6. Вызвать @PostConstruct или init-method
7. Регистрировать в контейнере с id="userService"
8. При остановке: вызвать @PreDestroy или destroy-method

Практический пример полного Bean Definition

@Configuration
public class AppConfig {
    @Bean(name = "userService", initMethod = "init", destroyMethod = "destroy")
    @Scope("singleton")
    public UserService userService(UserDao userDao, UserValidator validator) {
        UserServiceImpl service = new UserServiceImpl(userDao, validator);
        return service;
    }
    
    @Bean
    @Lazy
    public UserDao userDao(DataSource dataSource) {
        return new UserDaoImpl(dataSource);
    }
}

Вывод

Bean Definition — это полный набор инструкций для Spring контейнера. Понимание всех его компонентов позволяет грамотно конфигурировать приложение, управлять жизненным циклом объектов и избегать распространённых ошибок в dependency injection.

Что входит в Bean Definition? | PrepBro