я запускаю проект весенней загрузки, и я пытаюсь условно загрузить некоторые bean-компоненты. У меня есть следующий файл конфигурации:
application:
components:
componentA:
- ex1
ex2
ex3
componentB:
- ex1
ex2
ex3
componentC:
- ex1
ex2
ex3
use: componentA
и следующие классы конфигурации
@Configuration
@ConfigurationProperties(prefix = "application.components")
@Primary
@Getter
@Setter
@NoArgsConstrutor
public class MainConfig
{
private List<ComponentAConfig> componentA = new ArrayList<ComponentAConfig>();
private List<ComponentBConfig> componentB = new ArrayList<ComponentBConfig>();
private List<ComponentCConfig> componentC = new ArrayList<ComponentCConfig>();
}
@Getter
@Setter
@NoArgsConstrutor
public abstract class ComponentConfig
{
private String ex1;
private String ex2;
private String ex3;
}
@Configuration
@ConditionalOnProperty(prefix = "application", name = "use", havingValue = "componentA")
public class ComponentAConfig extends ComponentConfig
{
}
@Configuration
@ConditionalOnProperty(prefix = "application", name = "use", havingValue = "componentB")
public class ComponentBConfig extends ComponentConfig
{
}
@Configuration
@ConditionalOnProperty(prefix = "application", name = "use", havingValue = "componentC")
public class ComponentCConfig extends ComponentConfig
{
}
Несмотря на то, что у меня есть @ConditionalOnProperty, определенный для каждого класса конфигурации, он все равно загружает их все. Как я могу загрузить только список компонентов A и игнорировать остальные 2? Спасибо
О, теперь я понял, что вы пытаетесь сделать... И я думаю, что это не может работать таким образом.
Я думаю, вы неправильно используете конфигурацию. В классе MainConfig вы хотите заполнить поля свойствами приложения. В то же время вы аннотировали классы компонентов как @Configuration, что странно, поскольку я ожидал, что они будут классами POJO. Или, если это конфигурации и их существование должно быть условным, зачем там MainConfig? Наверное, я не очень понимаю, чего вы хотите достичь.




Думаю, я бы сделал так. (Отредактировано на основе более позднего комментария)
Класс части конфигурации:
@Data
@NoArgsConstructor
public class ComponentConfigPart {
private String ex1;
private String ex2;
private String ex3;
}
Базовый класс для бина
@Data
public abstract class ComponentConfig {
private List<ComponentConfigPart> parts = new ArrayList<>();
@PostConstruct
public void init() {
System.out.println("Created instance of " + this.getClass().getSimpleName());
System.out.println("Created " + this);
}
}
Класс ComponentA
@Component
@ConfigurationProperties(prefix = "application.components.a")
@ConditionalOnProperty(prefix = "application", name = "use", havingValue = "componentA")
@ToString(callSuper = true)
public class ComponentAConfig extends ComponentConfig {
}
Класс ComponentB:
@Component
@ConfigurationProperties(prefix = "application.components.b")
@ConditionalOnProperty(prefix = "application", name = "use", havingValue = "componentB")
@ToString(callSuper = true)
public class ComponentBConfig extends ComponentConfig {
}
и MainConfig, который хочет получить «выбранный» компонент:
@Configuration
public class MainConfig {
@Autowired
private ComponentConfig config;
@PostConstruct
public void init() {
System.out.println("MainConfig has autowired class of " + config.getClass().getSimpleName());
}
}
Теперь свойства такие:
application:
components:
a:
parts:
- ex1: a
ex2: aa
ex3: aaa
- ex1: a2
ex2: aa2
ex3: aaa2
b:
parts:
- ex1: b
ex2: bb
ex3: bbb
- ex1: b2
ex2: bb2
ex3: bbb2
use: componentA
И результаты в журналах консоли:
Created instance of ComponentAConfig
Created ComponentAConfig(super=ComponentConfig(parts=[ComponentConfigPart(ex1=a, ex2=aa, ex3=aaa), ComponentConfigPart(ex1=a2, ex2=aa2, ex3=aaa2)]))
MainConfig has autowired class of ComponentAConfig
Точно так же, если свойства похожи на:
application:
components:
a:
parts:
- ex1: a
ex2: aa
ex3: aaa
- ex1: a2
ex2: aa2
ex3: aaa2
b:
parts:
- ex1: b
ex2: bb
ex3: bbb
- ex1: b2
ex2: bb2
ex3: bbb2
use: componentB
Результат:
Created instance of ComponentBConfig
Created ComponentBConfig(super=ComponentConfig(parts=[ComponentConfigPart(ex1=b, ex2=bb, ex3=bbb), ComponentConfigPart(ex1=b2, ex2=bb2, ex3=bbb2)]))
MainConfig has autowired class of ComponentBConfig
Это то поведение, которое я ищу, но каждый компонент должен представлять собой список, подобный этому:
application:
components:
componentA:
- ex1
ex2
ex3
- ex1
ex2
ex3
componentB:
- ex1
ex2
ex3
- ex1
ex2
ex3
componentC:
- ex1
ex2
ex3
- ex1
ex2
ex3
use: componentA
Вот почему у меня был класс MainConfig с каждым списком.
Я обновил ответ, так что он ближе к вашей цели.
Не могли бы вы предоставить ссылку на полный пример проекта, чтобы мы могли его попробовать? Кажется, это работает при копировании в мой проект.