Rename configuration-analyzer

Rename `spring-boot-configuration-analyzer` to
`spring-boot-deprecated-properties-support`.

Also renamed classes to match and polished some of the code.

See gh-11301
This commit is contained in:
Phillip Webb
2018-01-22 14:06:00 -08:00
parent 66f8279f65
commit d0ca1a3eea
15 changed files with 190 additions and 194 deletions

View File

@@ -21,7 +21,7 @@
<module>spring-boot-actuator</module> <module>spring-boot-actuator</module>
<module>spring-boot-actuator-autoconfigure</module> <module>spring-boot-actuator-autoconfigure</module>
<module>spring-boot-autoconfigure</module> <module>spring-boot-autoconfigure</module>
<module>spring-boot-configuration-analyzer</module> <module>spring-boot-deprecated-properties-support</module>
<module>spring-boot-devtools</module> <module>spring-boot-devtools</module>
<module>spring-boot-test</module> <module>spring-boot-test</module>
<module>spring-boot-test-autoconfigure</module> <module>spring-boot-test-autoconfigure</module>

View File

@@ -1,2 +0,0 @@
org.springframework.context.ApplicationListener=\
org.springframework.boot.configurationalayzer.LegacyPropertiesAnalyzerListener

View File

@@ -8,9 +8,9 @@
<version>${revision}</version> <version>${revision}</version>
<relativePath>../spring-boot-parent</relativePath> <relativePath>../spring-boot-parent</relativePath>
</parent> </parent>
<artifactId>spring-boot-configuration-analyzer</artifactId> <artifactId>spring-boot-deprecated-properties-support</artifactId>
<name>Spring Boot Configuration Analyzer</name> <name>Spring Boot Deprecated Properties Support</name>
<description>Spring Boot Configuration Analyzer</description> <description>Spring Boot Deprecated Properties Support</description>
<properties> <properties>
<main.basedir>${basedir}/../..</main.basedir> <main.basedir>${basedir}/../..</main.basedir>
</properties> </properties>

View File

@@ -14,12 +14,10 @@
* limitations under the License. * limitations under the License.
*/ */
package org.springframework.boot.configurationalayzer; package org.springframework.boot.deprecatedproperties;
import java.io.IOException; import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import org.apache.commons.logging.Log; import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory; import org.apache.commons.logging.LogFactory;
@@ -37,20 +35,21 @@ import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
/** /**
* An {@link ApplicationListener} that inspects the {@link ConfigurableEnvironment * An {@link ApplicationListener} that inspects the {@link ConfigurableEnvironment
* environment} for legacy configuration keys. Automatically renames the keys that * environment} for deprecated configuration keys. Automatically renames the keys that
* have a matching replacement and log a report of what was discovered. * have a matching replacement and log a report of what was discovered.
* *
* @author Stephane Nicoll * @author Stephane Nicoll
* @since 2.0.0 * @since 2.0.0
*/ */
public class LegacyPropertiesAnalyzerListener public class DeprecatedPropertiesListener
implements ApplicationListener<SpringApplicationEvent> { implements ApplicationListener<SpringApplicationEvent> {
private static final Log logger = LogFactory.getLog(LegacyPropertiesAnalyzerListener.class); private static final Log logger = LogFactory
.getLog(DeprecatedPropertiesListener.class);
private LegacyPropertiesAnalysis analysis; private DeprecatedPropertiesReport report;
private boolean analysisLogged; private boolean reported;
@Override @Override
public void onApplicationEvent(SpringApplicationEvent event) { public void onApplicationEvent(SpringApplicationEvent event) {
@@ -65,49 +64,45 @@ public class LegacyPropertiesAnalyzerListener
private void onApplicationPreparedEvent(ApplicationPreparedEvent event) { private void onApplicationPreparedEvent(ApplicationPreparedEvent event) {
ConfigurationMetadataRepository repository = loadRepository(); ConfigurationMetadataRepository repository = loadRepository();
ConfigurableEnvironment environment = DeprecatedPropertiesReporter reporter = new DeprecatedPropertiesReporter(repository,
event.getApplicationContext().getEnvironment(); event.getApplicationContext().getEnvironment());
LegacyPropertiesAnalyzer validator = new LegacyPropertiesAnalyzer( this.report = reporter.getReport();
repository, environment);
this.analysis = validator.analyseLegacyProperties();
}
private void logLegacyPropertiesAnalysis() {
if (this.analysis == null || this.analysisLogged) {
return;
}
String warningReport = this.analysis.createWarningReport();
String errorReport = this.analysis.createErrorReport();
if (warningReport != null) {
logger.warn(warningReport);
}
if (errorReport != null) {
logger.error(errorReport);
}
this.analysisLogged = true;
} }
private ConfigurationMetadataRepository loadRepository() { private ConfigurationMetadataRepository loadRepository() {
try { try {
ConfigurationMetadataRepositoryJsonBuilder builder = ConfigurationMetadataRepositoryJsonBuilder.create(); return loadRepository(ConfigurationMetadataRepositoryJsonBuilder.create());
for (InputStream inputStream : getResources()) {
builder.withJsonResource(inputStream);
}
return builder.build();
} }
catch (IOException ex) { catch (IOException ex) {
throw new IllegalStateException("Failed to load metadata", ex); throw new IllegalStateException("Failed to load metadata", ex);
} }
} }
private List<InputStream> getResources() throws IOException { private ConfigurationMetadataRepository loadRepository(
ConfigurationMetadataRepositoryJsonBuilder builder) throws IOException {
Resource[] resources = new PathMatchingResourcePatternResolver() Resource[] resources = new PathMatchingResourcePatternResolver()
.getResources("classpath*:/META-INF/spring-configuration-metadata.json"); .getResources("classpath*:/META-INF/spring-configuration-metadata.json");
List<InputStream> result = new ArrayList<>();
for (Resource resource : resources) { for (Resource resource : resources) {
result.add(resource.getInputStream()); try (InputStream inputStream = resource.getInputStream()) {
builder.withJsonResource(inputStream);
}
} }
return result; return builder.build();
}
private void logLegacyPropertiesAnalysis() {
if (this.report == null || this.reported) {
return;
}
String warningReport = this.report.getWarningReport();
if (warningReport != null) {
logger.warn(warningReport);
}
String errorReport = this.report.getErrorReport();
if (errorReport != null) {
logger.error(errorReport);
}
this.reported = true;
} }
} }

View File

@@ -14,7 +14,7 @@
* limitations under the License. * limitations under the License.
*/ */
package org.springframework.boot.configurationalayzer; package org.springframework.boot.deprecatedproperties;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
@@ -28,32 +28,30 @@ import org.springframework.boot.configurationmetadata.ConfigurationMetadataPrope
import org.springframework.util.StringUtils; import org.springframework.util.StringUtils;
/** /**
* Describes the outcome of the environment analysis. * Provides a deprecated properties report.
* *
* @author Stephane Nicoll * @author Stephane Nicoll
*/ */
class LegacyPropertiesAnalysis { class DeprecatedPropertiesReport {
private final Map<String, PropertySourceAnalysis> content = new LinkedHashMap<>(); private final Map<String, DeprecatedProperties> content = new LinkedHashMap<>();
/** /**
* Create a report for all the legacy properties that were automatically renamed. If * Return a report for all the legacy properties that were automatically renamed. If
* no such legacy properties were found, return {@code null}. * no such legacy properties were found, return {@code null}.
* @return a report with the configurations keys that should be renamed * @return a report with the configurations keys that should be renamed
*/ */
public String createWarningReport() { public String getWarningReport() {
Map<String, List<LegacyProperty>> content = this.content.entrySet().stream() Map<String, List<DeprecatedProperty>> content = getContent(
.filter(e -> !e.getValue().handledProperties.isEmpty()) DeprecatedProperties::getRenamed);
.collect(Collectors.toMap(Map.Entry::getKey,
e -> new ArrayList<>(e.getValue().handledProperties)));
if (content.isEmpty()) { if (content.isEmpty()) {
return null; return null;
} }
StringBuilder report = new StringBuilder(); StringBuilder report = new StringBuilder();
report.append(String.format("%nThe use of configuration keys that have been " report.append(String.format("%nThe use of configuration keys that have been "
+ "renamed was found in the environment:%n%n")); + "renamed was found in the environment:%n%n"));
appendProperties(report, content, metadata -> append(report, content, (metadata) -> "Replacement: "
"Replacement: " + metadata.getDeprecation().getReplacement()); + metadata.getDeprecation().getReplacement());
report.append(String.format("%n")); report.append(String.format("%n"));
report.append("Each configuration key has been temporarily mapped to its " report.append("Each configuration key has been temporarily mapped to its "
+ "replacement for your convenience. To silence this warning, please " + "replacement for your convenience. To silence this warning, please "
@@ -63,24 +61,23 @@ class LegacyPropertiesAnalysis {
} }
/** /**
* Create a report for all the legacy properties that are no longer supported. If * Return a report for all the legacy properties that are no longer supported. If no
* no such legacy properties were found, return {@code null}. * such legacy properties were found, return {@code null}.
* @return a report with the configurations keys that are no longer supported * @return a report with the configurations keys that are no longer supported
*/ */
public String createErrorReport() { public String getErrorReport() {
Map<String, List<LegacyProperty>> content = this.content.entrySet().stream() Map<String, List<DeprecatedProperty>> content = getContent(
.filter(e -> !e.getValue().notHandledProperties.isEmpty()) DeprecatedProperties::getUnsupported);
.collect(Collectors.toMap(Map.Entry::getKey,
e -> new ArrayList<>(e.getValue().notHandledProperties)));
if (content.isEmpty()) { if (content.isEmpty()) {
return null; return null;
} }
StringBuilder report = new StringBuilder(); StringBuilder report = new StringBuilder();
report.append(String.format("%nThe use of configuration keys that are no longer " report.append(String.format("%nThe use of configuration keys that are no longer "
+ "supported was found in the environment:%n%n")); + "supported was found in the environment:%n%n"));
appendProperties(report, content, metadata -> append(report, content,
"Reason: " + (StringUtils.hasText(metadata.getDeprecation().getReason()) metadata -> "Reason: "
? metadata.getDeprecation().getReason() : "none")); + (StringUtils.hasText(metadata.getDeprecation().getReason())
? metadata.getDeprecation().getReason() : "none"));
report.append(String.format("%n")); report.append(String.format("%n"));
report.append("Please refer to the migration guide or reference guide for " report.append("Please refer to the migration guide or reference guide for "
+ "potential alternatives."); + "potential alternatives.");
@@ -88,21 +85,29 @@ class LegacyPropertiesAnalysis {
return report.toString(); return report.toString();
} }
private void appendProperties(StringBuilder report, private Map<String, List<DeprecatedProperty>> getContent(
Map<String, List<LegacyProperty>> content, Function<DeprecatedProperties, List<DeprecatedProperty>> extractor) {
return this.content.entrySet().stream()
.filter((entry) -> !extractor.apply(entry.getValue()).isEmpty())
.collect(Collectors.toMap(Map.Entry::getKey,
(entry) -> new ArrayList<>(extractor.apply(entry.getValue()))));
}
private void append(StringBuilder report,
Map<String, List<DeprecatedProperty>> content,
Function<ConfigurationMetadataProperty, String> deprecationMessage) { Function<ConfigurationMetadataProperty, String> deprecationMessage) {
content.forEach((name, properties) -> { content.forEach((name, properties) -> {
report.append(String.format("Property source '%s':%n", name)); report.append(String.format("Property source '%s':%n", name));
properties.sort(LegacyProperty.COMPARATOR); properties.sort(DeprecatedProperty.COMPARATOR);
properties.forEach((property) -> { properties.forEach((property) -> {
ConfigurationMetadataProperty metadata = property.getMetadata(); ConfigurationMetadataProperty metadata = property.getMetadata();
report.append(String.format("\tKey: %s%n", metadata.getId())); report.append(String.format("\tKey: %s%n", metadata.getId()));
if (property.getLineNumber() != null) { if (property.getLineNumber() != null) {
report.append(String.format("\t\tLine: %d%n", report.append(
property.getLineNumber())); String.format("\t\tLine: %d%n", property.getLineNumber()));
} }
report.append(String.format("\t\t%s%n", report.append(
deprecationMessage.apply(metadata))); String.format("\t\t%s%n", deprecationMessage.apply(metadata)));
}); });
report.append(String.format("%n")); report.append(String.format("%n"));
}); });
@@ -111,29 +116,36 @@ class LegacyPropertiesAnalysis {
/** /**
* Register a new property source. * Register a new property source.
* @param name the name of the property source * @param name the name of the property source
* @param handledProperties the properties that were renamed * @param renamed the properties that were renamed
* @param notHandledProperties the properties that are no longer supported * @param unsupported the properties that are no longer supported
*/ */
void register(String name, List<LegacyProperty> handledProperties, void add(String name, List<DeprecatedProperty> renamed,
List<LegacyProperty> notHandledProperties) { List<DeprecatedProperty> unsupported) {
List<LegacyProperty> handled = (handledProperties != null this.content.put(name, new DeprecatedProperties(renamed, unsupported));
? new ArrayList<>(handledProperties) : Collections.emptyList());
List<LegacyProperty> notHandled = (notHandledProperties != null
? new ArrayList<>(notHandledProperties) : Collections.emptyList());
this.content.put(name, new PropertySourceAnalysis(handled, notHandled));
} }
private static class DeprecatedProperties {
private static class PropertySourceAnalysis { private final List<DeprecatedProperty> renamed;
private final List<LegacyProperty> handledProperties; private final List<DeprecatedProperty> unsupported;
private final List<LegacyProperty> notHandledProperties; DeprecatedProperties(List<DeprecatedProperty> renamed,
List<DeprecatedProperty> unsupported) {
this.renamed = asNewList(renamed);
this.unsupported = asNewList(unsupported);
}
PropertySourceAnalysis(List<LegacyProperty> handledProperties, private <T> List<T> asNewList(List<T> source) {
List<LegacyProperty> notHandledProperties) { return (source == null ? Collections.emptyList() : new ArrayList<T>(source));
this.handledProperties = handledProperties; }
this.notHandledProperties = notHandledProperties;
public List<DeprecatedProperty> getRenamed() {
return this.renamed;
}
public List<DeprecatedProperty> getUnsupported() {
return this.unsupported;
} }
} }

View File

@@ -14,7 +14,7 @@
* limitations under the License. * limitations under the License.
*/ */
package org.springframework.boot.configurationalayzer; package org.springframework.boot.deprecatedproperties;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
@@ -40,19 +40,20 @@ import org.springframework.util.MultiValueMap;
import org.springframework.util.StringUtils; import org.springframework.util.StringUtils;
/** /**
* Analyse {@link LegacyProperty legacy properties}. * Report on {@link DeprecatedProperty deprecated properties}.
* *
* @author Stephane Nicoll * @author Stephane Nicoll
*/ */
class LegacyPropertiesAnalyzer { class DeprecatedPropertiesReporter {
private final Map<String, ConfigurationMetadataProperty> allProperties; private final Map<String, ConfigurationMetadataProperty> allProperties;
private final ConfigurableEnvironment environment; private final ConfigurableEnvironment environment;
LegacyPropertiesAnalyzer(ConfigurationMetadataRepository metadataRepository, DeprecatedPropertiesReporter(ConfigurationMetadataRepository metadataRepository,
ConfigurableEnvironment environment) { ConfigurableEnvironment environment) {
this.allProperties = Collections.unmodifiableMap(metadataRepository.getAllProperties()); this.allProperties = Collections
.unmodifiableMap(metadataRepository.getAllProperties());
this.environment = environment; this.environment = environment;
} }
@@ -61,60 +62,59 @@ class LegacyPropertiesAnalyzer {
* legacy properties if a replacement exists. * legacy properties if a replacement exists.
* @return the analysis * @return the analysis
*/ */
public LegacyPropertiesAnalysis analyseLegacyProperties() { public DeprecatedPropertiesReport getReport() {
LegacyPropertiesAnalysis analysis = new LegacyPropertiesAnalysis(); DeprecatedPropertiesReport report = new DeprecatedPropertiesReport();
Map<String, List<LegacyProperty>> properties = getMatchingProperties(deprecatedFilter()); Map<String, List<DeprecatedProperty>> properties = getMatchingProperties(
deprecatedFilter());
if (properties.isEmpty()) { if (properties.isEmpty()) {
return analysis; return report;
} }
properties.forEach((name, candidates) -> { properties.forEach((name, candidates) -> {
PropertySource<?> propertySource = mapPropertiesWithReplacement(analysis, PropertySource<?> propertySource = mapPropertiesWithReplacement(report,
name, candidates); name, candidates);
if (propertySource != null) { if (propertySource != null) {
this.environment.getPropertySources().addBefore(name, propertySource); this.environment.getPropertySources().addBefore(name, propertySource);
} }
}); });
return analysis; return report;
} }
private PropertySource<?> mapPropertiesWithReplacement( private PropertySource<?> mapPropertiesWithReplacement(
LegacyPropertiesAnalysis analysis, String name, DeprecatedPropertiesReport report, String name,
List<LegacyProperty> properties) { List<DeprecatedProperty> properties) {
List<LegacyProperty> matches = new ArrayList<>(); List<DeprecatedProperty> renamed = new ArrayList<>();
List<LegacyProperty> unhandled = new ArrayList<>(); List<DeprecatedProperty> unsupported = new ArrayList<>();
for (LegacyProperty property : properties) { properties.forEach((property) -> {
if (hasValidReplacement(property)) { (isRenamed(property) ? renamed : unsupported).add(property);
matches.add(property); });
} report.add(name, renamed, unsupported);
else { if (renamed.isEmpty()) {
unhandled.add(property);
}
}
analysis.register(name, matches, unhandled);
if (matches.isEmpty()) {
return null; return null;
} }
String target = "migrate-" + name; String target = "migrate-" + name;
Map<String, OriginTrackedValue> content = new LinkedHashMap<>(); Map<String, OriginTrackedValue> content = new LinkedHashMap<>();
for (LegacyProperty candidate : matches) { for (DeprecatedProperty candidate : renamed) {
OriginTrackedValue value = OriginTrackedValue.of( OriginTrackedValue value = OriginTrackedValue.of(
candidate.getProperty().getValue(), candidate.getProperty().getOrigin()); candidate.getProperty().getValue(),
candidate.getProperty().getOrigin());
content.put(candidate.getMetadata().getDeprecation().getReplacement(), value); content.put(candidate.getMetadata().getDeprecation().getReplacement(), value);
} }
return new OriginTrackedMapPropertySource(target, content); return new OriginTrackedMapPropertySource(target, content);
} }
private boolean hasValidReplacement(LegacyProperty property) { private boolean isRenamed(DeprecatedProperty property) {
String replacementId = property.getMetadata().getDeprecation().getReplacement(); ConfigurationMetadataProperty metadata = property.getMetadata();
String replacementId = metadata.getDeprecation().getReplacement();
if (StringUtils.hasText(replacementId)) { if (StringUtils.hasText(replacementId)) {
ConfigurationMetadataProperty replacement = this.allProperties.get(replacementId); ConfigurationMetadataProperty replacement = this.allProperties
.get(replacementId);
if (replacement != null) { if (replacement != null) {
return replacement.getType().equals(property.getMetadata().getType()); return replacement.getType().equals(metadata.getType());
} }
replacement = getMapProperty(replacementId); replacement = getMapProperty(replacementId);
if (replacement != null) { if (replacement != null) {
return replacement.getType().startsWith("java.util.Map") return replacement.getType().startsWith("java.util.Map")
&& replacement.getType().endsWith(property.getMetadata().getType() + ">"); && replacement.getType().endsWith(metadata.getType() + ">");
} }
} }
return false; return false;
@@ -128,17 +128,19 @@ class LegacyPropertiesAnalyzer {
return null; return null;
} }
private Map<String, List<LegacyProperty>> getMatchingProperties( private Map<String, List<DeprecatedProperty>> getMatchingProperties(
Predicate<ConfigurationMetadataProperty> filter) { Predicate<ConfigurationMetadataProperty> filter) {
MultiValueMap<String, LegacyProperty> result = new LinkedMultiValueMap<>(); MultiValueMap<String, DeprecatedProperty> result = new LinkedMultiValueMap<>();
List<ConfigurationMetadataProperty> candidates = this.allProperties.values() List<ConfigurationMetadataProperty> candidates = this.allProperties.values()
.stream().filter(filter).collect(Collectors.toList()); .stream().filter(filter).collect(Collectors.toList());
getPropertySourcesAsMap().forEach((name, source) -> { getPropertySourcesAsMap().forEach((name, source) -> {
candidates.forEach(metadata -> { candidates.forEach(metadata -> {
ConfigurationProperty configurationProperty = source.getConfigurationProperty( ConfigurationProperty configurationProperty = source
ConfigurationPropertyName.of(metadata.getId())); .getConfigurationProperty(
ConfigurationPropertyName.of(metadata.getId()));
if (configurationProperty != null) { if (configurationProperty != null) {
result.add(name, new LegacyProperty(metadata, configurationProperty)); result.add(name,
new DeprecatedProperty(metadata, configurationProperty));
} }
}); });
}); });
@@ -146,14 +148,15 @@ class LegacyPropertiesAnalyzer {
} }
private Predicate<ConfigurationMetadataProperty> deprecatedFilter() { private Predicate<ConfigurationMetadataProperty> deprecatedFilter() {
return p -> p.getDeprecation() != null return (property) -> property.getDeprecation() != null
&& p.getDeprecation().getLevel() == Deprecation.Level.ERROR; && property.getDeprecation().getLevel() == Deprecation.Level.ERROR;
} }
private Map<String, ConfigurationPropertySource> getPropertySourcesAsMap() { private Map<String, ConfigurationPropertySource> getPropertySourcesAsMap() {
Map<String, ConfigurationPropertySource> map = new LinkedHashMap<>(); Map<String, ConfigurationPropertySource> map = new LinkedHashMap<>();
ConfigurationPropertySources.get(this.environment); ConfigurationPropertySources.get(this.environment);
for (ConfigurationPropertySource source : ConfigurationPropertySources.get(this.environment)) { for (ConfigurationPropertySource source : ConfigurationPropertySources
.get(this.environment)) {
map.put(determinePropertySourceName(source), source); map.put(determinePropertySourceName(source), source);
} }
return map; return map;

View File

@@ -14,7 +14,7 @@
* limitations under the License. * limitations under the License.
*/ */
package org.springframework.boot.configurationalayzer; package org.springframework.boot.deprecatedproperties;
import java.util.Comparator; import java.util.Comparator;
@@ -28,9 +28,10 @@ import org.springframework.boot.origin.TextResourceOrigin;
* *
* @author Stephane Nicoll * @author Stephane Nicoll
*/ */
class LegacyProperty { class DeprecatedProperty {
static final LegacyPropertyComparator COMPARATOR = new LegacyPropertyComparator(); public static final Comparator<DeprecatedProperty> COMPARATOR = Comparator
.comparing((property) -> property.getMetadata().getId());
private final ConfigurationMetadataProperty metadata; private final ConfigurationMetadataProperty metadata;
@@ -38,7 +39,7 @@ class LegacyProperty {
private final Integer lineNumber; private final Integer lineNumber;
LegacyProperty(ConfigurationMetadataProperty metadata, DeprecatedProperty(ConfigurationMetadataProperty metadata,
ConfigurationProperty property) { ConfigurationProperty property) {
this.metadata = metadata; this.metadata = metadata;
this.property = property; this.property = property;
@@ -68,13 +69,4 @@ class LegacyProperty {
return this.lineNumber; return this.lineNumber;
} }
private static class LegacyPropertyComparator implements Comparator<LegacyProperty> {
@Override
public int compare(LegacyProperty p1, LegacyProperty p2) {
return p1.getMetadata().getId().compareTo(p2.getMetadata().getId());
}
}
} }

View File

@@ -15,6 +15,6 @@
*/ */
/** /**
* Support for analyzing the environment. * Support for migrating deprecated Spring Boot properties.
*/ */
package org.springframework.boot.configurationalayzer; package org.springframework.boot.deprecatedproperties;

View File

@@ -0,0 +1,2 @@
org.springframework.context.ApplicationListener=\
org.springframework.boot.deprecatedproperties.DeprecatedPropertiesListener

View File

@@ -14,7 +14,7 @@
* limitations under the License. * limitations under the License.
*/ */
package org.springframework.boot.configurationalayzer; package org.springframework.boot.deprecatedproperties;
import org.junit.After; import org.junit.After;
import org.junit.Rule; import org.junit.Rule;
@@ -28,11 +28,11 @@ import org.springframework.context.annotation.Configuration;
import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThat;
/** /**
* Tests for {@link LegacyPropertiesAnalyzerListener}. * Tests for {@link DeprecatedPropertiesListener}.
* *
* @author Stephane Nicoll * @author Stephane Nicoll
*/ */
public class LegacyPropertiesAnalyzerListenerTests { public class DeprecatedPropertiesListenerTests {
@Rule @Rule
public final OutputCapture output = new OutputCapture(); public final OutputCapture output = new OutputCapture();
@@ -48,8 +48,7 @@ public class LegacyPropertiesAnalyzerListenerTests {
@Test @Test
public void sampleReport() { public void sampleReport() {
this.context = createSampleApplication() this.context = createSampleApplication().run("--banner.charset=UTF8");
.run("--banner.charset=UTF8");
assertThat(this.output.toString()).contains("commandLineArgs") assertThat(this.output.toString()).contains("commandLineArgs")
.contains("spring.banner.charset") .contains("spring.banner.charset")
.contains("Each configuration key has been temporarily mapped") .contains("Each configuration key has been temporarily mapped")
@@ -60,7 +59,6 @@ public class LegacyPropertiesAnalyzerListenerTests {
return new SpringApplication(TestApplication.class); return new SpringApplication(TestApplication.class);
} }
@Configuration @Configuration
public static class TestApplication { public static class TestApplication {

View File

@@ -14,7 +14,7 @@
* limitations under the License. * limitations under the License.
*/ */
package org.springframework.boot.configurationalayzer; package org.springframework.boot.deprecatedproperties;
import java.io.IOException; import java.io.IOException;
import java.util.ArrayList; import java.util.ArrayList;
@@ -38,13 +38,12 @@ import org.springframework.mock.env.MockEnvironment;
import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThat;
/** /**
* Tests for {@link LegacyPropertiesAnalyzer}. * Tests for {@link DeprecatedPropertiesReporter}.
* *
* @author Stephane Nicoll * @author Stephane Nicoll
*/ */
public class LegacyPropertiesAnalyzerTests { public class DeprecatedPropertiesReporterTests {
private ConfigurableEnvironment environment = new MockEnvironment(); private ConfigurableEnvironment environment = new MockEnvironment();
@@ -64,56 +63,53 @@ public class LegacyPropertiesAnalyzerTests {
propertySources.addFirst(one); propertySources.addFirst(one);
propertySources.addAfter("one", two); propertySources.addAfter("one", two);
assertThat(propertySources).hasSize(3); assertThat(propertySources).hasSize(3);
createAnalyzer(loadRepository("metadata/sample-metadata.json")) createAnalyzer(loadRepository("metadata/sample-metadata.json")).getReport();
.analyseLegacyProperties(); assertThat(mapToNames(propertySources)).containsExactly("one", "migrate-two",
assertThat(mapToNames(propertySources)).containsExactly("one", "two", "mockProperties");
"migrate-two", "two", "mockProperties"); assertMappedProperty(propertySources.get("migrate-two"), "test.two", "another",
assertMappedProperty(propertySources.get("migrate-two"), getOrigin(two, "wrong.two"));
"test.two", "another", getOrigin(two, "wrong.two"));
} }
@Test @Test
public void warningReport() throws IOException { public void warningReport() throws IOException {
this.environment.getPropertySources().addFirst(loadPropertySource("test", this.environment.getPropertySources().addFirst(
"config/config-warnings.properties")); loadPropertySource("test", "config/config-warnings.properties"));
this.environment.getPropertySources().addFirst(loadPropertySource("ignore", this.environment.getPropertySources()
"config/config-error.properties")); .addFirst(loadPropertySource("ignore", "config/config-error.properties"));
String report = createWarningReport(loadRepository( String report = createWarningReport(
"metadata/sample-metadata.json")); loadRepository("metadata/sample-metadata.json"));
assertThat(report).isNotNull(); assertThat(report).isNotNull();
assertThat(report).containsSubsequence("Property source 'test'", assertThat(report).containsSubsequence("Property source 'test'",
"wrong.four.test", "Line: 5", "test.four.test", "wrong.four.test", "Line: 5", "test.four.test", "wrong.two", "Line: 2",
"wrong.two", "Line: 2", "test.two"); "test.two");
assertThat(report).doesNotContain("wrong.one"); assertThat(report).doesNotContain("wrong.one");
} }
@Test @Test
public void errorReport() throws IOException { public void errorReport() throws IOException {
this.environment.getPropertySources().addFirst(loadPropertySource("test1", this.environment.getPropertySources().addFirst(
"config/config-warnings.properties")); loadPropertySource("test1", "config/config-warnings.properties"));
this.environment.getPropertySources().addFirst(loadPropertySource("test2", this.environment.getPropertySources()
"config/config-error.properties")); .addFirst(loadPropertySource("test2", "config/config-error.properties"));
String report = createErrorReport(loadRepository( String report = createErrorReport(
"metadata/sample-metadata.json")); loadRepository("metadata/sample-metadata.json"));
assertThat(report).isNotNull(); assertThat(report).isNotNull();
assertThat(report).containsSubsequence("Property source 'test2'", assertThat(report).containsSubsequence("Property source 'test2'", "wrong.one",
"wrong.one", "Line: 2", "This is no longer supported."); "Line: 2", "This is no longer supported.");
assertThat(report).doesNotContain("wrong.four.test") assertThat(report).doesNotContain("wrong.four.test").doesNotContain("wrong.two");
.doesNotContain("wrong.two");
} }
@Test @Test
public void errorReportNoReplacement() throws IOException { public void errorReportNoReplacement() throws IOException {
this.environment.getPropertySources().addFirst(loadPropertySource("first", this.environment.getPropertySources().addFirst(loadPropertySource("first",
"config/config-error-no-replacement.properties")); "config/config-error-no-replacement.properties"));
this.environment.getPropertySources().addFirst(loadPropertySource("second", this.environment.getPropertySources()
"config/config-error.properties")); .addFirst(loadPropertySource("second", "config/config-error.properties"));
String report = createErrorReport(loadRepository( String report = createErrorReport(
"metadata/sample-metadata.json")); loadRepository("metadata/sample-metadata.json"));
assertThat(report).isNotNull(); assertThat(report).isNotNull();
assertThat(report).containsSubsequence( assertThat(report).containsSubsequence("Property source 'first'", "wrong.three",
"Property source 'first'", "wrong.three", "Line: 6", "none", "Line: 6", "none", "Property source 'second'", "wrong.one", "Line: 2",
"Property source 'second'", "wrong.one", "Line: 2",
"This is no longer supported."); "This is no longer supported.");
assertThat(report).doesNotContain("null").doesNotContain("server.port") assertThat(report).doesNotContain("null").doesNotContain("server.port")
.doesNotContain("debug"); .doesNotContain("debug");
@@ -132,6 +128,7 @@ public class LegacyPropertiesAnalyzerTests {
return ((OriginLookup<String>) propertySource).getOrigin(name); return ((OriginLookup<String>) propertySource).getOrigin(name);
} }
@SuppressWarnings("unchecked")
private void assertMappedProperty(PropertySource<?> propertySource, String name, private void assertMappedProperty(PropertySource<?> propertySource, String name,
Object value, Origin origin) { Object value, Origin origin) {
assertThat(propertySource.containsProperty(name)).isTrue(); assertThat(propertySource.containsProperty(name)).isTrue();
@@ -146,15 +143,16 @@ public class LegacyPropertiesAnalyzerTests {
private PropertySource<?> loadPropertySource(String name, String path) private PropertySource<?> loadPropertySource(String name, String path)
throws IOException { throws IOException {
ClassPathResource resource = new ClassPathResource(path); ClassPathResource resource = new ClassPathResource(path);
PropertySource<?> propertySource = new PropertiesPropertySourceLoader() PropertySource<?> propertySource = new PropertiesPropertySourceLoader().load(name,
.load(name, resource, null); resource, null);
assertThat(propertySource).isNotNull(); assertThat(propertySource).isNotNull();
return propertySource; return propertySource;
} }
private ConfigurationMetadataRepository loadRepository(String... content) { private ConfigurationMetadataRepository loadRepository(String... content) {
try { try {
ConfigurationMetadataRepositoryJsonBuilder builder = ConfigurationMetadataRepositoryJsonBuilder.create(); ConfigurationMetadataRepositoryJsonBuilder builder = ConfigurationMetadataRepositoryJsonBuilder
.create();
for (String path : content) { for (String path : content) {
Resource resource = new ClassPathResource(path); Resource resource = new ClassPathResource(path);
builder.withJsonResource(resource.getInputStream()); builder.withJsonResource(resource.getInputStream());
@@ -167,18 +165,16 @@ public class LegacyPropertiesAnalyzerTests {
} }
private String createWarningReport(ConfigurationMetadataRepository repository) { private String createWarningReport(ConfigurationMetadataRepository repository) {
return createAnalyzer(repository).analyseLegacyProperties() return createAnalyzer(repository).getReport().getWarningReport();
.createWarningReport();
} }
private String createErrorReport(ConfigurationMetadataRepository repository) { private String createErrorReport(ConfigurationMetadataRepository repository) {
return createAnalyzer(repository).analyseLegacyProperties() return createAnalyzer(repository).getReport().getErrorReport();
.createErrorReport();
} }
private LegacyPropertiesAnalyzer createAnalyzer( private DeprecatedPropertiesReporter createAnalyzer(
ConfigurationMetadataRepository repository) { ConfigurationMetadataRepository repository) {
return new LegacyPropertiesAnalyzer(repository, this.environment); return new DeprecatedPropertiesReporter(repository, this.environment);
} }
} }