Логотип YeaHub

База вопросов

Собеседования

Тренажёр

База ресурсов

Обучение

Навыки

Войти

Выбери, каким будет IT завтра — вместе c нами!

YeaHub — это полностью открытый проект, призванный объединить и улучшить IT-сферу. Наш исходный код доступен для просмотра на GitHub. Дизайн проекта также открыт для ознакомления в Figma.

© 2026 YeaHub

Документы

Медиа

Назад
Вопрос про Spring: Spring, @Primary, dependency injection, bean, ambiguity

Как работает @Primary?

Вопрос проверяет понимание аннотации @Primary в Spring, которая используется для разрешения неоднозначностей при внедрении зависимостей, когда существует несколько бинов одного типа.

Короткий ответ

Аннотация @Primary в Spring указывает, что данный бин должен быть выбран по умолчанию при внедрении зависимости, если существует несколько кандидатов одного типа. Это помогает фреймворку разрешить неоднозначность автоматически, без необходимости использования @Qualifier. Например, если у вас есть два бина, реализующих один интерфейс, и один из них помечен как @Primary, то при инъекции через @Autowired будет использован именно он. Это удобно для задания реализации по умолчанию в конфигурации.

Длинный ответ

В Spring Framework, когда контейнер IoC (Inversion of Control) сталкивается с ситуацией, где несколько бинов реализуют один и тот же тип (интерфейс или класс), возникает неоднозначность при автоматическом связывании зависимостей через @Autowired. Аннотация @Primary — это один из способов указать контейнеру, какой бин следует выбирать по умолчанию в таких случаях.

Как это работает

Вы помечаете один из бинов аннотацией @Primary (обычно на уровне определения бина в конфигурационном классе с @Bean или на самом классе компонента с @Component). Когда Spring выполняет инъекцию зависимости по типу и находит несколько подходящих кандидатов, он отдаёт предпочтение тому, который помечен как @Primary. Если @Primary отсутствует, потребуется использовать @Qualifier для явного указания имени бина, иначе Spring выбросит исключение NoUniqueBeanDefinitionException.

Пример использования

Предположим, у нас есть интерфейс MessageService и две его реализации. Мы хотим, чтобы EmailService использовался по умолчанию.

public interface MessageService {
    String send(String message);
}

@Component
@Primary // Этот бин будет выбран по умолчанию
public class EmailService implements MessageService {
    public String send(String message) {
        return "Sent via email: " + message;
    }
}

@Component
public class SmsService implements MessageService {
    public String send(String message) {
        return "Sent via SMS: " + message;
    }
}

@Component
public class NotificationService {
    private final MessageService messageService;

    @Autowired
    public NotificationService(MessageService messageService) {
        // Будет внедрён EmailService, так как он @Primary
        this.messageService = messageService;
    }

    public void notifyUser(String msg) {
        System.out.println(messageService.send(msg));
    }
}

Где применяется

  • В модульных или интеграционных тестах для подмены реальных сервисов заглушками (@MockBean в Spring Boot тестах часто помечается как @Primary).
  • В конфигурациях с несколькими профилями (profiles), где для каждого профиля может быть своя реализация, а одна из них — основная.
  • Для указания реализации по умолчанию в библиотеках или модулях, где пользователь может предоставить свою кастомную реализацию.

Вывод: Используйте @Primary, когда вам нужно задать бин по умолчанию среди нескольких однотипных бинов, чтобы упростить конфигурацию и избежать необходимости явного указания @Qualifier в большинстве мест инъекции. Это особенно полезно в больших приложениях с множеством альтернативных реализаций.

Уровень

  • Рейтинг:

    4

  • Сложность:

    3

Навыки

  • Spring

    Spring

Ключевые слова

#Spring

#@Primary

#dependency injection

#bean

#ambiguity

Подпишись на Java Developer в телеграм