forked from spring-projects/spring-boot
-
Notifications
You must be signed in to change notification settings - Fork 4
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add HealthContributor and refactor HealthEndpoint
Overhaul `HealthEndpoint` support to make it easier to support health groups. Prior to this commit the `HealthIndicator` interface was used for both regular indicators and composite indicators. In addition the `Health` result was used to both represent individual, system and composite health. This design unfortunately means that all health contributors need to be aware of the `HealthAggregator` and could not easily support heath groups if per-group aggregation is required. This commit reworks many aspects of the health support in order to provide a cleaner separation between a `HealthIndicator`and a composite. The following changes have been made: - A `HealthContributor` interface has been introduced to represent the general concept of something that contributes health information. A contributor can either be a `HealthIndicator` or a `CompositeHealthContributor`. - A `HealthComponent` class has been introduced to mirror the contributor arrangement. The component can be either `CompositeHealth` or `Health`. - The `HealthAggregator` interface has been replaced with a more focused `StatusAggregator` interface which only deals with `Status` results. - `CompositeHealthIndicator` has been replaced with `CompositeHealthContributor` which only provides access to other contributors. A composite can no longer directly return `Health`. - `HealthIndicatorRegistry` has been replaced with `HealthContributorRegistry` and the default implementation now uses a copy-on-write strategy. - `HealthEndpoint`, `HealthEndpointWebExtension` and `ReactiveHealthEndpointWebExtension` now extend a common `HealthEndpointSupport` class. They are now driven by a health contributor registry and `HealthEndpointSettings`. - The `HealthStatusHttpMapper` class has been replaced by a `HttpCodeStatusMapper` interface. - The `HealthWebEndpointResponseMapper` class has been replaced by a `HealthEndpointSettings` strategy. This allows us to move role related logic and `ShowDetails` to the auto-configure module. - `SimpleHttpCodeStatusMapper` and `SimpleStatusAggregator` implementations have been added which are configured via constructor arguments rather than setters. - Endpoint auto-configuration has been reworked and the `CompositeHealthIndicatorConfiguration` class has been replaced by `CompositeHealthContributorConfiguration`. - The endpoint JSON has been changed make `details` distinct from `components`. See spring-projectsgh-17926
- Loading branch information
Showing
143 changed files
with
5,267 additions
and
1,301 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
73 changes: 73 additions & 0 deletions
73
...rk/boot/actuate/autoconfigure/health/AbstractCompositeHealthContributorConfiguration.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,73 @@ | ||
/* | ||
* Copyright 2012-2019 the original author or authors. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* https://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
|
||
package org.springframework.boot.actuate.autoconfigure.health; | ||
|
||
import java.lang.reflect.Constructor; | ||
import java.util.Map; | ||
|
||
import org.springframework.beans.BeanUtils; | ||
import org.springframework.core.ResolvableType; | ||
import org.springframework.util.Assert; | ||
|
||
/** | ||
* Base class for health contributor configurations that can combine source beans into a | ||
* composite. | ||
* | ||
* @param <C> the contributor type | ||
* @param <I> the health indicator type | ||
* @param <B> the bean type | ||
* @author Stephane Nicoll | ||
* @author Phillip Webb | ||
* @since 2.2.0 | ||
*/ | ||
public abstract class AbstractCompositeHealthContributorConfiguration<C, I extends C, B> { | ||
|
||
private final Class<?> indicatorType; | ||
|
||
private final Class<?> beanType; | ||
|
||
AbstractCompositeHealthContributorConfiguration() { | ||
ResolvableType type = ResolvableType.forClass(AbstractCompositeHealthContributorConfiguration.class, | ||
getClass()); | ||
this.indicatorType = type.resolveGeneric(1); | ||
this.beanType = type.resolveGeneric(2); | ||
|
||
} | ||
|
||
protected final C createContributor(Map<String, B> beans) { | ||
Assert.notEmpty(beans, "Beans must not be empty"); | ||
if (beans.size() == 1) { | ||
return createIndicator(beans.values().iterator().next()); | ||
} | ||
return createComposite(beans); | ||
} | ||
|
||
protected abstract C createComposite(Map<String, B> beans); | ||
|
||
@SuppressWarnings("unchecked") | ||
protected I createIndicator(B bean) { | ||
try { | ||
Constructor<I> constructor = (Constructor<I>) this.indicatorType.getDeclaredConstructor(this.beanType); | ||
return BeanUtils.instantiateClass(constructor, bean); | ||
} | ||
catch (Exception ex) { | ||
throw new IllegalStateException( | ||
"Unable to create health indicator " + this.indicatorType + " for bean type " + this.beanType, ex); | ||
} | ||
} | ||
|
||
} |
91 changes: 91 additions & 0 deletions
91
...ringframework/boot/actuate/autoconfigure/health/AutoConfiguredHealthEndpointSettings.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,91 @@ | ||
/* | ||
* Copyright 2012-2019 the original author or authors. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* https://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
|
||
package org.springframework.boot.actuate.autoconfigure.health; | ||
|
||
import java.util.Collection; | ||
|
||
import org.springframework.boot.actuate.autoconfigure.health.HealthEndpointProperties.ShowDetails; | ||
import org.springframework.boot.actuate.endpoint.SecurityContext; | ||
import org.springframework.boot.actuate.health.HealthEndpointSettings; | ||
import org.springframework.boot.actuate.health.HttpCodeStatusMapper; | ||
import org.springframework.boot.actuate.health.StatusAggregator; | ||
import org.springframework.util.CollectionUtils; | ||
|
||
/** | ||
* Auto-configured {@link HealthEndpointSettings} backed by | ||
* {@link HealthEndpointProperties}. | ||
* | ||
* @author Phillip Webb | ||
* @author Andy Wilkinson | ||
*/ | ||
class AutoConfiguredHealthEndpointSettings implements HealthEndpointSettings { | ||
|
||
private final StatusAggregator statusAggregator; | ||
|
||
private final HttpCodeStatusMapper httpCodeStatusMapper; | ||
|
||
private final ShowDetails showDetails; | ||
|
||
private final Collection<String> roles; | ||
|
||
/** | ||
* Create a new {@link AutoConfiguredHealthEndpointSettings} instance. | ||
* @param statusAggregator the status aggregator to use | ||
* @param httpCodeStatusMapper the HTTP code status mapper to use | ||
* @param showDetails the show details setting | ||
* @param roles the roles to match | ||
*/ | ||
AutoConfiguredHealthEndpointSettings(StatusAggregator statusAggregator, HttpCodeStatusMapper httpCodeStatusMapper, | ||
ShowDetails showDetails, Collection<String> roles) { | ||
this.statusAggregator = statusAggregator; | ||
this.httpCodeStatusMapper = httpCodeStatusMapper; | ||
this.showDetails = showDetails; | ||
this.roles = roles; | ||
} | ||
|
||
@Override | ||
public boolean includeDetails(SecurityContext securityContext) { | ||
ShowDetails showDetails = this.showDetails; | ||
switch (showDetails) { | ||
case NEVER: | ||
return false; | ||
case ALWAYS: | ||
return true; | ||
case WHEN_AUTHORIZED: | ||
return isAuthorized(securityContext); | ||
} | ||
throw new IllegalStateException("Unsupported ShowDetails value " + showDetails); | ||
} | ||
|
||
private boolean isAuthorized(SecurityContext securityContext) { | ||
if (securityContext.getPrincipal() == null) { | ||
return false; | ||
} | ||
return CollectionUtils.isEmpty(this.roles) || this.roles.stream().anyMatch(securityContext::isUserInRole); | ||
} | ||
|
||
@Override | ||
public StatusAggregator getStatusAggregator() { | ||
return this.statusAggregator; | ||
} | ||
|
||
@Override | ||
public HttpCodeStatusMapper getHttpCodeStatusMapper() { | ||
return this.httpCodeStatusMapper; | ||
} | ||
|
||
} |
43 changes: 43 additions & 0 deletions
43
...gframework/boot/actuate/autoconfigure/health/CompositeHealthContributorConfiguration.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
/* | ||
* Copyright 2012-2019 the original author or authors. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* https://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
|
||
package org.springframework.boot.actuate.autoconfigure.health; | ||
|
||
import java.util.Map; | ||
|
||
import org.springframework.boot.actuate.health.CompositeHealthContributor; | ||
import org.springframework.boot.actuate.health.HealthContributor; | ||
import org.springframework.boot.actuate.health.HealthIndicator; | ||
|
||
/** | ||
* Base class for health contributor configurations that can combine source beans into a | ||
* composite. | ||
* | ||
* @param <I> the health indicator type | ||
* @param <B> the bean type | ||
* @author Stephane Nicoll | ||
* @author Phillip Webb | ||
* @since 2.2.0 | ||
*/ | ||
public abstract class CompositeHealthContributorConfiguration<I extends HealthIndicator, B> | ||
extends AbstractCompositeHealthContributorConfiguration<HealthContributor, I, B> { | ||
|
||
@Override | ||
protected final HealthContributor createComposite(Map<String, B> beans) { | ||
return CompositeHealthContributor.fromMap(beans, this::createIndicator); | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
43 changes: 43 additions & 0 deletions
43
...rk/boot/actuate/autoconfigure/health/CompositeReactiveHealthContributorConfiguration.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
/* | ||
* Copyright 2012-2019 the original author or authors. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* https://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
|
||
package org.springframework.boot.actuate.autoconfigure.health; | ||
|
||
import java.util.Map; | ||
|
||
import org.springframework.boot.actuate.health.CompositeReactiveHealthContributor; | ||
import org.springframework.boot.actuate.health.ReactiveHealthContributor; | ||
import org.springframework.boot.actuate.health.ReactiveHealthIndicator; | ||
|
||
/** | ||
* Base class for health contributor configurations that can combine source beans into a | ||
* composite. | ||
* | ||
* @param <I> the health indicator type | ||
* @param <B> the bean type | ||
* @author Stephane Nicoll | ||
* @author Phillip Webb | ||
* @since 2.2.0 | ||
*/ | ||
public abstract class CompositeReactiveHealthContributorConfiguration<I extends ReactiveHealthIndicator, B> | ||
extends AbstractCompositeHealthContributorConfiguration<ReactiveHealthContributor, I, B> { | ||
|
||
@Override | ||
protected final ReactiveHealthContributor createComposite(Map<String, B> beans) { | ||
return CompositeReactiveHealthContributor.fromMap(beans, this::createIndicator); | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.