Merge branch '2.2.x'

This commit is contained in:
spencergibb
2021-04-20 13:19:10 -04:00
5 changed files with 88 additions and 10 deletions

View File

@@ -29,6 +29,10 @@
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-gateway</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>

View File

@@ -18,12 +18,50 @@ package org.springframework.cloud.gateway.sample;
import org.springframework.boot.SpringBootConfiguration;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication;
import org.springframework.boot.web.server.LocalServerPort;
import org.springframework.cloud.client.DefaultServiceInstance;
import org.springframework.cloud.gateway.route.RouteLocator;
import org.springframework.cloud.gateway.route.builder.RouteLocatorBuilder;
import org.springframework.cloud.loadbalancer.annotation.LoadBalancerClient;
import org.springframework.cloud.loadbalancer.core.ServiceInstanceListSupplier;
import org.springframework.cloud.loadbalancer.support.ServiceInstanceListSuppliers;
import org.springframework.context.annotation.Bean;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
/**
* @author Spencer Gibb
*/
@SpringBootConfiguration
@EnableAutoConfiguration
@RestController
@LoadBalancerClient(name = "myservice", configuration = MyServiceConf.class)
public class MvcFailureAnalyzerApplication {
@GetMapping("hello")
public String hello() {
return "Hello";
}
@Bean
@ConditionalOnWebApplication(type = ConditionalOnWebApplication.Type.REACTIVE)
public RouteLocator myRouteLocator(RouteLocatorBuilder builder) {
return builder.routes().route(r -> r.path("/myprefix/**")
.filters(f -> f.stripPrefix(1)).uri("lb://myservice")).build();
}
}
class MyServiceConf {
@LocalServerPort
private int port = 0;
@Bean
public ServiceInstanceListSupplier staticServiceInstanceListSupplier() {
return ServiceInstanceListSuppliers.from("myservice", new DefaultServiceInstance(
"myservice-1", "myservice", "localhost", port, false));
}
}

View File

@@ -23,6 +23,9 @@ import org.springframework.boot.SpringApplication;
import org.springframework.boot.test.system.CapturedOutput;
import org.springframework.boot.test.system.OutputCaptureExtension;
import org.springframework.cloud.gateway.support.MvcFoundOnClasspathException;
import org.springframework.cloud.gateway.support.MvcFoundOnClasspathFailureAnalyzer;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.test.web.reactive.server.WebTestClient;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatCode;
@@ -36,18 +39,41 @@ public class MvcFailureAnalyzerApplicationTests {
@Test
public void exceptionThrown(CapturedOutput output) {
assertThatThrownBy(() -> new SpringApplication(MvcFailureAnalyzerApplication.class).run("--server.port=0"))
.hasRootCauseInstanceOf(MvcFoundOnClasspathException.class);
assertThat(output).contains("Spring MVC found on classpath",
"Please remove spring-boot-starter-web dependency");
assertThatThrownBy(
() -> new SpringApplication(MvcFailureAnalyzerApplication.class)
.run("--server.port=0")).hasRootCauseInstanceOf(
MvcFoundOnClasspathException.class);
assertThat(output).contains(MvcFoundOnClasspathFailureAnalyzer.MESSAGE,
MvcFoundOnClasspathFailureAnalyzer.ACTION);
}
@Test
public void exceptionNotThrownWhenDisabled(CapturedOutput output) {
assertThatCode(() -> new SpringApplication(MvcFailureAnalyzerApplication.class)
.run("--spring.cloud.gateway.enabled=false", "--server.port=0")).doesNotThrowAnyException();
assertThat(output).doesNotContain("Spring MVC found on classpath",
"Please remove spring-boot-starter-web dependency");
.run("--spring.cloud.gateway.enabled=false", "--server.port=0"))
.doesNotThrowAnyException();
assertThat(output).doesNotContain(MvcFoundOnClasspathFailureAnalyzer.MESSAGE,
MvcFoundOnClasspathFailureAnalyzer.ACTION);
}
@Test
public void exceptionNotThrownWhenReactiveTypeSet(CapturedOutput output) {
assertThatCode(() -> {
ConfigurableApplicationContext context = new SpringApplication(
MvcFailureAnalyzerApplication.class).run(
"--spring.main.web-application-type=reactive",
"--server.port=0", "--debug=true");
Integer port = context.getEnvironment().getProperty("local.server.port",
Integer.class);
WebTestClient client = WebTestClient.bindToServer()
.baseUrl("http://localhost:" + port).build();
client.get().uri("/myprefix/hello").exchange().expectStatus().isOk()
.expectBody(String.class).isEqualTo("Hello");
context.close();
}).doesNotThrowAnyException();
assertThat(output).doesNotContain(MvcFoundOnClasspathFailureAnalyzer.MESSAGE,
MvcFoundOnClasspathFailureAnalyzer.ACTION);
}
}

View File

@@ -23,6 +23,7 @@ import org.springframework.boot.autoconfigure.AutoConfigureBefore;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication;
import org.springframework.cloud.gateway.support.MvcFoundOnClasspathException;
import org.springframework.context.annotation.Configuration;
@@ -37,6 +38,7 @@ public class GatewayClassPathWarningAutoConfiguration {
@Configuration(proxyBeanMethods = false)
@ConditionalOnClass(name = "org.springframework.web.servlet.DispatcherServlet")
@ConditionalOnWebApplication(type = ConditionalOnWebApplication.Type.SERVLET)
protected static class SpringMvcFoundOnClasspathConfiguration {
public SpringMvcFoundOnClasspathConfiguration() {

View File

@@ -21,11 +21,19 @@ import org.springframework.boot.diagnostics.FailureAnalysis;
public class MvcFoundOnClasspathFailureAnalyzer extends AbstractFailureAnalyzer<MvcFoundOnClasspathException> {
/**
* Message for MvcFoundOnClasspathException.
*/
public static final String MESSAGE = "Spring MVC found on classpath, which is incompatible with Spring Cloud Gateway.";
/**
* Action for MvcFoundOnClasspathException.
*/
public static final String ACTION = "Please set spring.main.web-application-type=reactive or remove spring-boot-starter-web dependency.";
@Override
protected FailureAnalysis analyze(Throwable rootFailure, MvcFoundOnClasspathException cause) {
String message = "Spring MVC found on classpath, which is incompatible with Spring Cloud Gateway.";
String action = "Please remove spring-boot-starter-web dependency.";
return new FailureAnalysis(message, action, cause);
return new FailureAnalysis(MESSAGE, ACTION, cause);
}
}