Как создать кастомный Spring Boot Starter?

«Как создать кастомный Spring Boot Starter?» — вопрос из категории Spring, который задают на 10% собеседований Java Разработчик. Ниже — развёрнутый ответ с разбором ключевых моментов.

Ответ

Spring Boot Starter — это артефакт, который предоставляет готовую к использованию конфигурацию для определенной функциональности. Создание своего стартера включает следующие шаги:

1. Структура проекта Создаются два модуля (или два отдельных проекта):

  • autoconfigure: Содержит логику автоконфигурации (@Configuration классы).
  • starter: Пустой jar-файл, который зависит от autoconfigure и необходимых библиотек. Пользователь подключает только этот артефакт.

2. Ядро автоконфигурации (в модуле autoconfigure)

// Файл: ApiAutoConfiguration.java
@Configuration(proxyBeanMethods = false)
@ConditionalOnClass(ApiClient.class) // Конфигурация активируется, если класс в classpath
@EnableConfigurationProperties(ApiProperties.class) // Включает кастомные свойства
public class ApiAutoConfiguration {

    @Bean
    @ConditionalOnMissingBean // Создает бин, только если пользователь его не определил
    public ApiClient apiClient(ApiProperties properties) {
        return new ApiClient(properties.getEndpoint(), properties.getTimeout());
    }
}

3. Файл свойств конфигурации

// Файл: ApiProperties.java
@ConfigurationProperties(prefix = "app.api")
public class ApiProperties {
    private String endpoint = "http://default.api";
    private Duration timeout = Duration.ofSeconds(30);
    // геттеры и сеттеры
}

4. Регистрация автоконфигурации В ресурсах модуля autoconfigure создается файл: src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports Содержимое — полное имя класса конфигурации:

com.example.api.autoconfigure.ApiAutoConfiguration

5. Метаданные для подсказок в IDE (опционально, но рекомендуется) В src/main/resources/META-INF/ создается additional-spring-configuration-metadata.json:

{
  "properties": [
    {
      "name": "app.api.endpoint",
      "type": "java.lang.String",
      "description": "Base URL for the external API."
    },
    {
      "name": "app.api.timeout",
      "type": "java.time.Duration",
      "description": "Timeout for API calls.",
      "defaultValue": "30s"
    }
  ]
}

6. Сборка стартера (модуль starter) Его pom.xml должен содержать зависимости на autoconfigure и необходимые библиотеки:

<dependencies>
    <dependency>
        <groupId>com.example</groupId>
        <artifactId>api-spring-boot-autoconfigure</artifactId>
        <version>${project.version}</version>
    </dependency>
    <!-- Другие обязательные библиотеки -->
</dependencies>

Ключевые принципы:

  • Не навязывать: Использовать @Conditional аннотации, чтобы конфигурация активировалась только при наличии нужных классов в classpath.
  • Позволять переопределять: Всегда использовать @ConditionalOnMissingBean, чтобы пользователь мог определить свой бин.
  • Четкое пространство имен: Использовать уникальный префикс для свойств (например, app.api.*).
  • Полное тестирование: Тестировать автоконфигурацию с помощью @SpringBootTest и различных профилей.