一个 class 的 bean 的多个实例填充了来自 application.properties 的值
Multiple instances of a bean of one class filled with values from application.properties
我打算使用 spring-boot-actuator 为 Spring 启动应用程序编写一些 HealtCheckContributors
。因此,我实施了其中两个。当然,它们用于检查不同应用程序的运行状况,但结构几乎相同,除了配置属性,...
SonarQube 对此表示不满,我想知道是否可以进行一次健康检查 class,但实例化次数与 application.properties
中定义的一样多。
一个例子:
application.properties
:
# actuator
app1.management.baseUrl=http://localhost:10000
app1.management.name=app1HealthCheckContributor
app2.management.basUrl=http://localhost:10001
app2.management.name=app2HealthCheckContributor
HealthCheckContributor
对于 app1:
@Slf4j
@Component("xxx")
public class App1HealthCheckContributor extends AbstractHealthIndicator {
private final App1Properties app1Properties;
public App1HealthCheckContributor(final App1Properties app1Properties) {
this.app1Properties = app1Properties;
}
@Override
protected void doHealthCheck(Health.Builder builder) {...}
}
...每个 HealthCheckContributor
的代码仅在其 appXProperties.
中不同
有没有可能有某种基础 class 像:
@Slf4j
@Component()
public class MyHealthCheckContributor extends AbstractHealthIndicator {
private final MyProperties myProperties;
public MyHealthCheckContributor(final MyProperties myProperties) {
this.myProperties = myProperties;
}
@Override
protected void doHealthCheck(Health.Builder builder) {...}
}
并让 Spring Boot 负责实例化两个 HealthCheckContributors
(在我们的例子中是 App1HealthCheckContributor
和 App2HealthCheckContributor
)?
这将消除代码重复。
属性示例 class 文件:
@Slf4j
@Data
@ConfigurationProperties(prefix = "app1.management")
public class App1Properties {
private String baseUrl;
private String ...;
}
我怎样才能做到这一点,application.properties
文件看起来如何才能实现我想要做的事情?
最后一题:
假设 doHealthCheck
中的代码对于要检查的所有应用程序完全相同,您可以执行以下操作。
您将从创建单个运行状况检查开始 class:
@Slf4j
public class AppHealthCheckContributor extends AbstractHealthIndicator {
private final AppProperties appProperties;
public App1HealthCheckContributor(final AppProperties appProperties) {
this.appProperties = appProperties;
}
@Override
protected void doHealthCheck(Health.Builder builder) {...}
}
属性模型如下:
@Slf4j
@Data
public class AppProperties {
private String baseUrl;
private String name;
}
这意味着配置将类似于以下内容(在 application.yml
中):
health-check:
apps:
- baseUrl: http://localhost:10000
name: app1
- baseUrl: http://localhost:10001
name: app2
最后,您需要为每个应用程序创建一个 bean 并在应用程序上下文中注册它们:
@Slf4j
@Data
@Configuration
@ConfigurationProperties(prefix = "health-check")
public class AllAppPropertiesConfiguration {
private List<AppProperties> apps;
@Autowired
private GenericApplicationContext applicationContext;
@PostConstruct
fun init() {
for (AppProperties app : apps) {
applicationContext.registerBean(app.getName(), AppHealthCheckContributor.class, app);
}
}
}
我打算使用 spring-boot-actuator 为 Spring 启动应用程序编写一些 HealtCheckContributors
。因此,我实施了其中两个。当然,它们用于检查不同应用程序的运行状况,但结构几乎相同,除了配置属性,...
SonarQube 对此表示不满,我想知道是否可以进行一次健康检查 class,但实例化次数与 application.properties
中定义的一样多。
一个例子:
application.properties
:
# actuator
app1.management.baseUrl=http://localhost:10000
app1.management.name=app1HealthCheckContributor
app2.management.basUrl=http://localhost:10001
app2.management.name=app2HealthCheckContributor
HealthCheckContributor
对于 app1:
@Slf4j
@Component("xxx")
public class App1HealthCheckContributor extends AbstractHealthIndicator {
private final App1Properties app1Properties;
public App1HealthCheckContributor(final App1Properties app1Properties) {
this.app1Properties = app1Properties;
}
@Override
protected void doHealthCheck(Health.Builder builder) {...}
}
...每个 HealthCheckContributor
的代码仅在其 appXProperties.
有没有可能有某种基础 class 像:
@Slf4j
@Component()
public class MyHealthCheckContributor extends AbstractHealthIndicator {
private final MyProperties myProperties;
public MyHealthCheckContributor(final MyProperties myProperties) {
this.myProperties = myProperties;
}
@Override
protected void doHealthCheck(Health.Builder builder) {...}
}
并让 Spring Boot 负责实例化两个 HealthCheckContributors
(在我们的例子中是 App1HealthCheckContributor
和 App2HealthCheckContributor
)?
这将消除代码重复。
属性示例 class 文件:
@Slf4j
@Data
@ConfigurationProperties(prefix = "app1.management")
public class App1Properties {
private String baseUrl;
private String ...;
}
我怎样才能做到这一点,application.properties
文件看起来如何才能实现我想要做的事情?
最后一题:
假设 doHealthCheck
中的代码对于要检查的所有应用程序完全相同,您可以执行以下操作。
您将从创建单个运行状况检查开始 class:
@Slf4j
public class AppHealthCheckContributor extends AbstractHealthIndicator {
private final AppProperties appProperties;
public App1HealthCheckContributor(final AppProperties appProperties) {
this.appProperties = appProperties;
}
@Override
protected void doHealthCheck(Health.Builder builder) {...}
}
属性模型如下:
@Slf4j
@Data
public class AppProperties {
private String baseUrl;
private String name;
}
这意味着配置将类似于以下内容(在 application.yml
中):
health-check:
apps:
- baseUrl: http://localhost:10000
name: app1
- baseUrl: http://localhost:10001
name: app2
最后,您需要为每个应用程序创建一个 bean 并在应用程序上下文中注册它们:
@Slf4j
@Data
@Configuration
@ConfigurationProperties(prefix = "health-check")
public class AllAppPropertiesConfiguration {
private List<AppProperties> apps;
@Autowired
private GenericApplicationContext applicationContext;
@PostConstruct
fun init() {
for (AppProperties app : apps) {
applicationContext.registerBean(app.getName(), AppHealthCheckContributor.class, app);
}
}
}