Commit e2951880 by Dave Syer

Add tests for body of message

parent 7804e1bd
......@@ -14,7 +14,7 @@
<description>Spring Cloud Netflix Hystrix Stream</description>
<properties>
<main.basedir>${basedir}/..</main.basedir>
<spring-cloud-contract.version>1.1.0.RELEASE</spring-cloud-contract.version>
<spring-cloud-contract.version>1.0.5.RELEASE</spring-cloud-contract.version>
</properties>
<dependencies>
<dependency>
......@@ -114,7 +114,7 @@
<pluginExecutionFilter>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-contract-maven-plugin</artifactId>
<versionRange>[1.1.0.RELEASE,)</versionRange>
<versionRange>[1.0.0.RELEASE,)</versionRange>
<goals>
<goal>convert</goal>
<goal>generateTests</goal>
......
......@@ -18,6 +18,8 @@ package org.springframework.cloud.netflix.hystrix.stream;
import javax.annotation.PostConstruct;
import com.netflix.hystrix.HystrixCircuitBreaker;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
......@@ -27,14 +29,12 @@ import org.springframework.cloud.client.discovery.DiscoveryClient;
import org.springframework.cloud.stream.annotation.EnableBinding;
import org.springframework.cloud.stream.annotation.Output;
import org.springframework.cloud.stream.config.BindingProperties;
import org.springframework.cloud.stream.config.ChannelBindingServiceProperties;
import org.springframework.cloud.stream.config.BindingServiceProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.messaging.MessageChannel;
import org.springframework.scheduling.annotation.EnableScheduling;
import com.netflix.hystrix.HystrixCircuitBreaker;
/**
* Autoconfiguration for a Spring Cloud Hystrix on Spring Cloud Stream. Enabled by default
* if spring-cloud-stream is on the classpath, and can be switched off with
......@@ -55,7 +55,7 @@ import com.netflix.hystrix.HystrixCircuitBreaker;
public class HystrixStreamAutoConfiguration {
@Autowired
private ChannelBindingServiceProperties bindings;
private BindingServiceProperties bindings;
@Autowired
private HystrixStreamProperties properties;
......@@ -95,7 +95,8 @@ public class HystrixStreamAutoConfiguration {
@Bean
public HystrixStreamTask hystrixStreamTask(DiscoveryClient discoveryClient) {
return new HystrixStreamTask(this.outboundChannel, discoveryClient, this.properties);
return new HystrixStreamTask(this.outboundChannel, discoveryClient,
this.properties);
}
}
......@@ -16,6 +16,8 @@
package org.springframework.cloud.netflix.hystrix.stream;
import java.util.Map;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import org.junit.runner.RunWith;
......@@ -26,11 +28,13 @@ import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.cloud.client.circuitbreaker.EnableCircuitBreaker;
import org.springframework.cloud.contract.verifier.messaging.boot.AutoConfigureMessageVerifier;
import org.springframework.cloud.netflix.hystrix.stream.StreamSourceTestBase.Application;
import org.springframework.cloud.netflix.hystrix.stream.StreamSourceTestBase.TestApplication;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import static org.assertj.core.api.Assertions.assertThat;
/**
* Base class for sensor autogenerated tests (used by Spring Cloud Contract).
*
......@@ -39,21 +43,43 @@ import org.springframework.web.bind.annotation.RestController;
* @author Marius Bogoevici
*/
@RunWith(SpringJUnit4ClassRunner.class)
@SpringBootTest(classes = Application.class, properties = "spring.cloud.stream.bindings.output.destination=sensor-data")
@SpringBootTest(classes = TestApplication.class)
@AutoConfigureMessageVerifier
public abstract class StreamSourceTestBase {
@Autowired
Application application;
TestApplication application;
public void createMetricsData() {
public void createMetricsData() throws Exception {
application.hello();
}
public void assertOrigin(Object input) {
@SuppressWarnings("unchecked")
Map<String, Object> origin = (Map<String, Object>) input;
assertThat(origin.get("host")).isNotNull();
assertThat(origin.get("port")).isNotNull();
assertThat(origin.get("serviceId")).isEqualTo("application");
// TODO: should be server.port?
assertThat(origin.get("id")).isEqualTo("application:-1");
}
public void assertData(Object input) {
System.err.println(input);
@SuppressWarnings("unchecked")
Map<String, Object> data = (Map<String, Object>) input;
assertThat(data.get("type")).isEqualTo("HystrixCommand");
// TODO: should be application.hello
assertThat(data.get("name")).asString().startsWith("application.");
assertThat(data.get("group")).isNotNull();
// TODO: should be TestApplication
// assertThat(data.get("group")).isEqualTo(TestApplication.class.getSimpleName());
}
@EnableAutoConfiguration
@EnableCircuitBreaker
@RestController
public static class Application {
public static class TestApplication {
@HystrixCommand
@RequestMapping("/")
......@@ -62,7 +88,7 @@ public abstract class StreamSourceTestBase {
}
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
SpringApplication.run(TestApplication.class, args);
}
}
......
package contracts
org.springframework.cloud.contract.spec.Contract.make {
// Human readable description
description 'Should produce valid metrics data'
// Label by means of which the output message can be triggered
label 'metrics'
// input to the contract
input {
// the contract will be triggered by a method
triggeredBy('createMetricsData()')
}
// output message of the contract
outputMessage {
// destination to which the output message will be sent
sentTo 'hystrixStreamOutput'
headers {
header('contentType': 'application/json')
}
// the body of the output message
body ([
])
}
// Human readable description
description 'Should produce valid metrics data'
// Label by means of which the output message can be triggered
label 'metrics'
// input to the contract
input {
// the contract will be triggered by a method
triggeredBy('createMetricsData()')
}
// output message of the contract
outputMessage {
// destination to which the output message will be sent
sentTo 'hystrixStreamOutput'
headers {
header('contentType': 'application/json')
}
body("""
{
"origin":{
"host":"192.168.1.192",
"port":0,
"serviceId":"application",
"id":"application:0"
},
"data":{
"type":"HystrixCommand",
"name":"application.hello",
"group":"Application",
"currentTime":1494840901153,
"isCircuitBreakerOpen":false,
"errorPercentage":0,
"errorCount":0,
"requestCount":1,
"rollingCountCollapsedRequests":0,
"rollingCountExceptionsThrown":0,
"rollingCountFailure":0,
"rollingCountFallbackFailure":0,
"rollingCountFallbackRejection":0,
"rollingCountFallbackSuccess":0,
"rollingCountResponsesFromCache":0,
"rollingCountSemaphoreRejected":0,
"rollingCountShortCircuited":0,
"rollingCountSuccess":0,
"rollingCountThreadPoolRejected":0,
"rollingCountTimeout":0,
"currentConcurrentExecutionCount":0,
"latencyExecute_mean":0,
"latencyExecute":{
"0":0,
"25":0,
"50":0,
"75":0,
"90":0,
"95":0,
"99":0,
"99.5":0,
"100":0
},
"latencyTotal_mean":0,
"latencyTotal":{
"0":0,
"25":0,
"50":0,
"75":0,
"90":0,
"95":0,
"99":0,
"99.5":0,
"100":0
},
"propertyValue_circuitBreakerRequestVolumeThreshold":20,
"propertyValue_circuitBreakerSleepWindowInMilliseconds":5000,
"propertyValue_circuitBreakerErrorThresholdPercentage":50,
"propertyValue_circuitBreakerForceOpen":false,
"propertyValue_circuitBreakerForceClosed":false,
"propertyValue_circuitBreakerEnabled":true,
"propertyValue_executionIsolationStrategy":"THREAD",
"propertyValue_executionIsolationThreadTimeoutInMilliseconds":1000,
"propertyValue_executionIsolationThreadInterruptOnTimeout":true,
"propertyValue_executionIsolationThreadPoolKeyOverride":null,
"propertyValue_executionIsolationSemaphoreMaxConcurrentRequests":10,
"propertyValue_fallbackIsolationSemaphoreMaxConcurrentRequests":10,
"propertyValue_metricsRollingStatisticalWindowInMilliseconds":10000,
"propertyValue_requestCacheEnabled":true,
"propertyValue_requestLogEnabled":true,
"reportingHosts":1
}
}
""")
testMatchers {
jsonPath('$.origin', byCommand('assertOrigin($it)'))
jsonPath('$.data', byCommand('assertData($it)'))
jsonPath('$.data.errorCount', byEquality())
jsonPath('$.data.errorPercentage', byEquality())
jsonPath('$.data.requestCount', byType())
jsonPath('$.data.currentConcurrentExecutionCount', byType())
jsonPath('$.data.rollingCountFailure', byEquality())
jsonPath('$.data.rollingCountSuccess', byType())
jsonPath('$.data.rollingCountShortCircuited', byEquality())
jsonPath('$.data.rollingCountFallbackSuccess', byEquality())
jsonPath('$.data.isCircuitBreakerOpen', byEquality())
}
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment