Removed dirties context on any tests
This commit is contained in:
@@ -148,14 +148,6 @@ HTTP stubs without the need to download artifacts.
|
||||
|
||||
==== Running stubs
|
||||
|
||||
===== Limitations
|
||||
|
||||
IMPORTANT: There might be a problem with StubRunner shutting down ports between tests. You might
|
||||
have a situation in which you get port conflicts. As long as you use the same context across tests
|
||||
everything works fine. But when the context are different (e.g. different stubs or different profiles)
|
||||
then you have to either use `@DirtiesContext` to shut down the stub servers, or else run them on
|
||||
different ports per test.
|
||||
|
||||
===== Running using main app
|
||||
|
||||
You can set the following options to the main class:
|
||||
|
||||
@@ -82,6 +82,11 @@
|
||||
<groupId>com.jcraft</groupId>
|
||||
<artifactId>jsch.agentproxy.usocket-jna</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-test</artifactId>
|
||||
<optional>true</optional>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-autoconfigure-processor</artifactId>
|
||||
|
||||
@@ -25,6 +25,7 @@ import java.util.LinkedHashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
import java.util.Set;
|
||||
|
||||
import groovy.json.JsonOutput;
|
||||
import org.slf4j.Logger;
|
||||
@@ -38,12 +39,15 @@ import org.springframework.cloud.contract.stubrunner.provider.wiremock.WireMockH
|
||||
import org.springframework.cloud.contract.verifier.messaging.MessageVerifier;
|
||||
import org.springframework.cloud.contract.verifier.messaging.noop.NoOpStubMessages;
|
||||
import org.springframework.cloud.contract.verifier.util.BodyExtractor;
|
||||
import wiremock.org.eclipse.jetty.util.ConcurrentHashSet;
|
||||
|
||||
/**
|
||||
* Runs stubs for a particular {@link StubServer}
|
||||
*/
|
||||
class StubRunnerExecutor implements StubFinder {
|
||||
|
||||
static final Set<StubServer> STUB_SERVERS = new ConcurrentHashSet<>();
|
||||
|
||||
private static final Logger log = LoggerFactory.getLogger(StubRunnerExecutor.class);
|
||||
private final AvailablePortScanner portScanner;
|
||||
private final MessageVerifier<?> contractVerifierMessaging;
|
||||
@@ -261,6 +265,7 @@ class StubRunnerExecutor implements StubFinder {
|
||||
}
|
||||
});
|
||||
}
|
||||
STUB_SERVERS.add(this.stubServer);
|
||||
}
|
||||
|
||||
private boolean hasRequest(Collection<Contract> contracts) {
|
||||
|
||||
@@ -20,6 +20,7 @@ import java.io.File;
|
||||
import java.net.MalformedURLException;
|
||||
import java.net.URL;
|
||||
import java.util.Collection;
|
||||
import java.util.Objects;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
@@ -59,7 +60,14 @@ class StubServer {
|
||||
return this;
|
||||
}
|
||||
|
||||
public boolean isRunning() {
|
||||
return this.httpServerStub.isRunning();
|
||||
}
|
||||
|
||||
public void stop() {
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Stopping the server at port [" + this.getPort() + "]");
|
||||
}
|
||||
this.httpServerStub.stop();
|
||||
}
|
||||
|
||||
@@ -95,4 +103,22 @@ class StubServer {
|
||||
return this.httpServerStub.registeredMappings();
|
||||
}
|
||||
|
||||
@Override public boolean equals(Object o) {
|
||||
if (this == o)
|
||||
return true;
|
||||
if (o == null || getClass() != o.getClass())
|
||||
return false;
|
||||
StubServer that = (StubServer) o;
|
||||
return Objects.equals(this.stubConfiguration, that.stubConfiguration) && Objects
|
||||
.equals(this.contracts, that.contracts);
|
||||
}
|
||||
|
||||
@Override public int hashCode() {
|
||||
return Objects.hash(this.stubConfiguration, this.contracts);
|
||||
}
|
||||
|
||||
@Override public String toString() {
|
||||
return "StubServer{" + "stubConfiguration=" + this.stubConfiguration + ", mappingsSize="
|
||||
+ this.mappings.size() + '}';
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,63 @@
|
||||
package org.springframework.cloud.contract.stubrunner.provider.wiremock;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
||||
import com.github.tomakehurst.wiremock.stubbing.StubMapping;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.cloud.contract.stubrunner.HttpServerStub;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.test.context.TestContext;
|
||||
import org.springframework.test.context.support.AbstractTestExecutionListener;
|
||||
import org.springframework.util.Assert;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
/**
|
||||
* Stops the {@link HttpServerStub} after each test class
|
||||
*
|
||||
* @author Marcin Grzejszczak
|
||||
* @since 1.2.6
|
||||
*/
|
||||
public final class StubRunnerWireMockTestExecutionListener extends AbstractTestExecutionListener {
|
||||
|
||||
private static final Log log = LogFactory.getLog(StubRunnerWireMockTestExecutionListener.class);
|
||||
|
||||
private static Map<ApplicationContext, Map<WireMockHttpServerStub, PortAndMappings>> STUBS = new ConcurrentHashMap<>();
|
||||
|
||||
@Override public void beforeTestClass(TestContext testContext) {
|
||||
Map<WireMockHttpServerStub, PortAndMappings> stubs = STUBS
|
||||
.get(testContext.getApplicationContext());
|
||||
if (stubs != null) {
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Found a matching application context from [" + testContext.getTestClass().getName() + "]");
|
||||
}
|
||||
for (Map.Entry<WireMockHttpServerStub, PortAndMappings> entry : stubs.entrySet()) {
|
||||
while (entry.getKey().isRunning()) {
|
||||
entry.getKey().stop();
|
||||
}
|
||||
List<StubMapping> mappings = entry.getValue().mappings;
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Stopped a running WireMock instance at "
|
||||
+ "port [" + entry.getValue().port + "] with stub mappings "
|
||||
+ "size [" + mappings.size() + "]. Restarting the stub.");
|
||||
}
|
||||
entry.getKey().start(entry.getValue().port);
|
||||
entry.getKey().registerDescriptors(mappings);
|
||||
Assert.isTrue(new RestTemplate().getForEntity("http://localhost:" + entry.getValue().port + "/__admin/mappings", String.class)
|
||||
.getStatusCode().is2xxSuccessful(), "__admin/mappings endpoint wasn't accessible");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override public void afterTestClass(TestContext testContext) {
|
||||
STUBS.put(testContext.getApplicationContext(), WireMockHttpServerStub.SERVERS);
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Stopping servers " + WireMockHttpServerStub.SERVERS);
|
||||
}
|
||||
for (HttpServerStub serverStub : WireMockHttpServerStub.SERVERS.keySet()) {
|
||||
serverStub.stop();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -10,6 +10,7 @@ import java.util.Collection;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
||||
import com.github.tomakehurst.wiremock.WireMockServer;
|
||||
import com.github.tomakehurst.wiremock.client.WireMock;
|
||||
@@ -43,6 +44,8 @@ public class WireMockHttpServerStub implements HttpServerStub {
|
||||
private static final Logger log = LoggerFactory.getLogger(WireMockHttpServerStub.class);
|
||||
private static final int INVALID_PORT = -1;
|
||||
|
||||
static final Map<WireMockHttpServerStub, PortAndMappings> SERVERS = new ConcurrentHashMap<>();
|
||||
|
||||
private WireMockServer wireMockServer;
|
||||
|
||||
private WireMockConfiguration config() {
|
||||
@@ -107,6 +110,12 @@ public class WireMockHttpServerStub implements HttpServerStub {
|
||||
this.wireMockServer = new WireMockServer(config().port(port)
|
||||
.notifier(new Slf4jNotifier(true)));
|
||||
this.wireMockServer.start();
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Started WireMock at port [" + port + "]");
|
||||
}
|
||||
if (!SERVERS.containsKey(this)) {
|
||||
SERVERS.put(this, new PortAndMappings(port, new ArrayList<StubMapping>()));
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
@@ -159,20 +168,25 @@ public class WireMockHttpServerStub implements HttpServerStub {
|
||||
}
|
||||
|
||||
private void registerStubMappings(Collection<File> stubFiles) {
|
||||
WireMock wireMock = new WireMock("localhost", port(), "");
|
||||
WireMock wireMock = wireMock();
|
||||
registerDefaultHealthChecks(wireMock);
|
||||
registerStubs(stubFiles, wireMock);
|
||||
}
|
||||
|
||||
private WireMock wireMock() {
|
||||
return new WireMock("localhost", port(), "");
|
||||
}
|
||||
|
||||
private void registerDefaultHealthChecks(WireMock wireMock) {
|
||||
registerHealthCheck(wireMock, "/ping");
|
||||
registerHealthCheck(wireMock, "/health");
|
||||
}
|
||||
|
||||
private void registerStubs(Collection<File> sortedMappings, WireMock wireMock) {
|
||||
List<StubMapping> stubMappings = new ArrayList<>();
|
||||
for (File mappingDescriptor : sortedMappings) {
|
||||
try {
|
||||
wireMock.register(getMapping(mappingDescriptor));
|
||||
stubMappings.add(registerDescriptor(wireMock, mappingDescriptor));
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Registered stub mappings from [" + mappingDescriptor + "]");
|
||||
}
|
||||
@@ -183,6 +197,23 @@ public class WireMockHttpServerStub implements HttpServerStub {
|
||||
}
|
||||
}
|
||||
}
|
||||
PortAndMappings portAndMappings = SERVERS.get(this);
|
||||
SERVERS.put(this, new PortAndMappings(portAndMappings.port, stubMappings));
|
||||
}
|
||||
|
||||
private StubMapping registerDescriptor(WireMock wireMock, File mappingDescriptor) {
|
||||
StubMapping mapping = getMapping(mappingDescriptor);
|
||||
wireMock.register(mapping);
|
||||
return mapping;
|
||||
}
|
||||
|
||||
void registerDescriptors(List<StubMapping> stubMappings) {
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Registering stub mappings size [" + stubMappings.size() + "] at port [" + port() + "]");
|
||||
}
|
||||
for (StubMapping mapping : stubMappings) {
|
||||
wireMock().register(mapping);
|
||||
}
|
||||
}
|
||||
|
||||
private void registerHealthCheck(WireMock wireMock, String url) {
|
||||
@@ -194,3 +225,17 @@ public class WireMockHttpServerStub implements HttpServerStub {
|
||||
WireMock.get(WireMock.urlEqualTo(url)).willReturn(WireMock.aResponse().withBody(body).withStatus(200)));
|
||||
}
|
||||
}
|
||||
|
||||
class PortAndMappings {
|
||||
final Integer port;
|
||||
final List<StubMapping> mappings;
|
||||
|
||||
PortAndMappings(Integer port, List<StubMapping> mappings) {
|
||||
this.port = port;
|
||||
this.mappings = mappings;
|
||||
}
|
||||
|
||||
@Override public String toString() {
|
||||
return "PortAndMappings{" + "port=" + this.port + ", mappings=" + this.mappings.size() + '}';
|
||||
}
|
||||
}
|
||||
@@ -8,4 +8,8 @@ org.springframework.cloud.contract.stubrunner.messaging.integration.StubRunnerIn
|
||||
org.springframework.cloud.contract.stubrunner.spring.cloud.zookeeper.StubRunnerSpringCloudZookeeperAutoConfiguration,\
|
||||
org.springframework.cloud.contract.stubrunner.spring.cloud.eureka.StubRunnerSpringCloudEurekaAutoConfiguration,\
|
||||
org.springframework.cloud.contract.stubrunner.spring.cloud.consul.StubRunnerSpringCloudConsulAutoConfiguration,\
|
||||
org.springframework.cloud.contract.stubrunner.messaging.StubRunnerStreamsIntegrationAutoConfiguration
|
||||
org.springframework.cloud.contract.stubrunner.messaging.StubRunnerStreamsIntegrationAutoConfiguration
|
||||
|
||||
# Test Execution Listeners
|
||||
org.springframework.test.context.TestExecutionListener=\
|
||||
org.springframework.cloud.contract.stubrunner.provider.wiremock.StubRunnerWireMockTestExecutionListener
|
||||
@@ -29,7 +29,6 @@ import org.springframework.cloud.contract.stubrunner.StubFinder
|
||||
import org.springframework.cloud.contract.stubrunner.StubNotFoundException
|
||||
import org.springframework.context.annotation.Configuration
|
||||
import org.springframework.core.env.Environment
|
||||
import org.springframework.test.annotation.DirtiesContext
|
||||
import org.springframework.test.context.ActiveProfiles
|
||||
import org.springframework.test.context.ContextConfiguration
|
||||
import spock.lang.Specification
|
||||
@@ -44,7 +43,6 @@ import spock.lang.Specification
|
||||
'foo=${stubrunner.runningstubs.fraudDetectionServer.port}',
|
||||
'fooWithGroup=${stubrunner.runningstubs.org.springframework.cloud.contract.verifier.stubs.fraudDetectionServer.port}'])
|
||||
@AutoConfigureStubRunner(mappingsOutputFolder = "target/outputmappings/")
|
||||
@DirtiesContext
|
||||
@ActiveProfiles("test")
|
||||
class StubRunnerConfigurationSpec extends Specification {
|
||||
|
||||
|
||||
@@ -31,7 +31,6 @@ import org.springframework.cloud.zookeeper.ZookeeperAutoConfiguration
|
||||
import org.springframework.cloud.zookeeper.discovery.RibbonZookeeperAutoConfiguration
|
||||
import org.springframework.context.annotation.Bean
|
||||
import org.springframework.context.annotation.Configuration
|
||||
import org.springframework.test.annotation.DirtiesContext
|
||||
import org.springframework.test.context.ActiveProfiles
|
||||
import org.springframework.test.context.ContextConfiguration
|
||||
import org.springframework.web.client.RestTemplate
|
||||
@@ -50,7 +49,6 @@ import spock.lang.Specification
|
||||
stubsMode = StubRunnerProperties.StubsMode.REMOTE,
|
||||
repositoryRoot = "classpath:m2repo/repository/")
|
||||
// end::autoconfigure[]
|
||||
@DirtiesContext
|
||||
class StubRunnerSpringCloudAutoConfigurationSpec extends Specification {
|
||||
|
||||
@Autowired StubFinder stubFinder
|
||||
|
||||
@@ -33,7 +33,6 @@ import org.springframework.context.annotation.Configuration
|
||||
import org.springframework.core.env.Environment
|
||||
import org.springframework.http.ResponseEntity
|
||||
import org.springframework.messaging.Message
|
||||
import org.springframework.test.annotation.DirtiesContext
|
||||
import org.springframework.test.context.ContextConfiguration
|
||||
/**
|
||||
* @author Marcin Grzejszczak
|
||||
@@ -45,7 +44,6 @@ import org.springframework.test.context.ContextConfiguration
|
||||
repositoryRoot = "classpath:m2repo/repository/",
|
||||
stubsMode = StubRunnerProperties.StubsMode.REMOTE,
|
||||
stubsPerConsumer = true)
|
||||
@DirtiesContext
|
||||
class StubRunnerStubsPerConsumerSpec extends Specification {
|
||||
// end::test[]
|
||||
|
||||
|
||||
@@ -33,7 +33,6 @@ import org.springframework.context.annotation.Configuration
|
||||
import org.springframework.core.env.Environment
|
||||
import org.springframework.http.ResponseEntity
|
||||
import org.springframework.messaging.Message
|
||||
import org.springframework.test.annotation.DirtiesContext
|
||||
import org.springframework.test.context.ContextConfiguration
|
||||
/**
|
||||
* @author Marcin Grzejszczak
|
||||
@@ -46,7 +45,6 @@ import org.springframework.test.context.ContextConfiguration
|
||||
consumerName = "foo-consumer",
|
||||
stubsMode = StubRunnerProperties.StubsMode.REMOTE,
|
||||
stubsPerConsumer = true)
|
||||
@DirtiesContext
|
||||
class StubRunnerStubsPerConsumerWithConsumerNameSpec extends Specification {
|
||||
// end::test[]
|
||||
|
||||
|
||||
@@ -33,7 +33,6 @@ import org.springframework.cloud.contract.stubrunner.spring.AutoConfigureStubRun
|
||||
import org.springframework.cloud.contract.stubrunner.spring.StubRunnerProperties
|
||||
import org.springframework.context.annotation.Bean
|
||||
import org.springframework.context.annotation.Configuration
|
||||
import org.springframework.test.annotation.DirtiesContext
|
||||
import org.springframework.test.context.ContextConfiguration
|
||||
|
||||
import static org.mockito.BDDMockito.then
|
||||
@@ -58,7 +57,6 @@ import static org.mockito.Mockito.mock
|
||||
"org.springframework.cloud.contract.verifier.stubs:bootService"],
|
||||
stubsMode = StubRunnerProperties.StubsMode.REMOTE,
|
||||
repositoryRoot = "classpath:m2repo/repository/")
|
||||
@DirtiesContext
|
||||
class StubRunnerSpringCloudConsulAutoConfigurationSpec extends Specification {
|
||||
|
||||
@Autowired ConsulClient client
|
||||
|
||||
@@ -47,7 +47,6 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
maxPort = 10020,
|
||||
mappingsOutputFolder = "target/outputmappings/",
|
||||
properties = {"hello=world", "foo=bar"})
|
||||
@DirtiesContext
|
||||
@ActiveProfiles("test")
|
||||
public class StubRunnerSliceTests {
|
||||
|
||||
|
||||
Reference in New Issue
Block a user