Compare commits

..

10 commits

Author SHA1 Message Date
Sander Hautvast
abe2f7f5ab implemented request body matching 2015-07-07 15:28:01 +02:00
Sander Hautvast
9b70d03814 readme updated 2015-06-11 16:34:35 +02:00
Sander Hautvast
1407b21b4d added json upload and response headers 2015-06-11 16:33:34 +02:00
Sander Hautvast
506bea5d0e Merge branch 'master' of https://github.com/shautvast/everest 2015-06-11 14:23:04 +02:00
Sander Hautvast
13df0260cc Update README.md 2015-06-10 12:00:50 +02:00
Sander Hautvast
82fffaae47 build fixes 2015-06-10 12:00:22 +02:00
Sander Hautvast
96fa40d4b3 Update README.md 2015-06-10 10:32:15 +02:00
Sander Hautvast
d5ba7d7ba7 Update README.md 2015-06-10 10:31:23 +02:00
Sander Hautvast
c7732f21ed Update README.md 2015-06-10 10:29:56 +02:00
Sander Hautvast
c869f65d99 Update README.md 2015-06-10 10:26:32 +02:00
21 changed files with 426 additions and 104 deletions

1
.gitignore vendored
View file

@ -5,3 +5,4 @@
/.gradle
/.settings
/bin
/everest_data

View file

@ -1,5 +1,33 @@
Simple universal mocking tool for http requests
<h3>what is it?</h3>
-set up expectations using json files in $PROJECT/everest directory
-start using gradlew run
-replay
Simple universal mocking tool for http requests
- requires java 8
- set up expectations using json files in $PROJECT/everest_data directory
- or start java with -Deverest.data=[..] for a different data directory
- start using gradlew run
- replay
<h3>Sample json</h3>
{<br/>
"name": "wehkamp.nl",<br/>
"url": "http://www.wehkamp.nl",<br/>
"method": "GET",<br/>
"requestHeaders": {<br/>
&nbsp;&nbsp;"Accept": ["application/json"]<br/>
&nbsp;&nbsp;},<br/>
"response": "<html>",<br/>
"responseStatus": 200<br/>
"responseHeaders": <br/>
&nbsp;&nbsp;"Accept": ["application/json"]<br/>
&nbsp;&nbsp;},<br/>
}<br/>
- url can be java regex expression
<h4>api for json upload</h4>
- the JSON above can be uploaded to a running server using a POST to http://[server]:[port]/__api/upload
- use Content-Type=application/json
<h3>TODO's</h3>
- reload json files on the fly
- build a proxy that generates the json from actual requests/responses

View file

@ -20,8 +20,8 @@ repositories{
}
targetCompatibility=1.7
sourceCompatibility=1.7
targetCompatibility=1.8
sourceCompatibility=1.8
configurations {
all*.exclude group: 'commons-logging' //http://docs.spring.io/spring-framework/docs/current/spring-framework-reference/htmlsingle/#overview-not-using-commons-logging
@ -35,6 +35,7 @@ dependencies{
compile 'org.springframework.boot:spring-boot-starter-web'
compile 'commons-io:commons-io:2.0.1'
compile 'com.fasterxml.jackson.jaxrs:jackson-jaxrs-json-provider:2.2.1'
// compile 'org.littleshoot:littleproxy:1.0.0-beta7'
testCompile 'org.testng:testng:6.8'
testCompile "org.springframework:spring-test:4.0.6.RELEASE"
@ -43,4 +44,4 @@ dependencies{
}
springBoot { mainClass = "nl.wehkamp.everest.App" }
springBoot { mainClass = "nl.wehkamp.everest.WebServer" }

View file

@ -2,7 +2,7 @@ package nl.wehkamp.everest;
import javax.servlet.Servlet;
import nl.wehkamp.everest.web.MockingServlet;
import nl.wehkamp.everest.web.PredictableResponseServlet;
import org.springframework.beans.BeansException;
import org.springframework.boot.SpringApplication;
@ -30,12 +30,12 @@ public class WebServer implements ApplicationContextAware {
@Bean
public ServletRegistrationBean servletRegistrationBean() {
return new ServletRegistrationBean(mockingServlet(), "/*");
return new ServletRegistrationBean(predictableResponseServlet(), "/*");
}
@Bean
public Servlet mockingServlet() {
return new MockingServlet();
public Servlet predictableResponseServlet() {
return new PredictableResponseServlet();
}
public static void main(String[] args) {

View file

@ -32,15 +32,15 @@ import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;
@Component("requestResponseRepository")
public class RequestResponseJsonFileRepository extends RequestResponseMemoryRepository {
private static final Logger log = LoggerFactory.getLogger(RequestResponseJsonFileRepository.class);
@Component
public class PredictionJsonFileRepository extends PredictionMemoryRepository {
private static final Logger log = LoggerFactory.getLogger(PredictionJsonFileRepository.class);
private String dataDirectoryName = System.getProperty("everest.data", "everest_data");
private ObjectMapper jackson = new ObjectMapper();
public RequestResponseJsonFileRepository() {
public PredictionJsonFileRepository() {
createDataDirectoryIfAbsent();
fillCacheIfEmpty();
}
@ -55,7 +55,9 @@ public class RequestResponseJsonFileRepository extends RequestResponseMemoryRepo
throw new RuntimeException(e);
} finally {
try {
os.close();
if (os != null) {
os.close();
}
} catch (IOException e) {
}
}
@ -79,10 +81,13 @@ public class RequestResponseJsonFileRepository extends RequestResponseMemoryRepo
try {
DirectoryStream<Path> directoryStream = newDirectoryStream(get(dataDirectoryName));
for (Path pathForJsonFile : directoryStream) {
Prediction requestResponse = readRequestResponseFromJson(pathForJsonFile);
requestResponse.setName(filename(pathForJsonFile));
cache.add(requestResponse);
log.info("reading {} into memory, mapping path {}", pathForJsonFile, requestResponse.getUrl());
if (pathForJsonFile.toString().endsWith(".json")) {
log.info("reading {}", pathForJsonFile);
Prediction requestResponse = readRequestResponseFromJson(pathForJsonFile);
requestResponse.setName(filename(pathForJsonFile));
cache.add(requestResponse);
log.info("reading {} into memory, mapping path {}", pathForJsonFile, requestResponse.getUrl());
}
}
} catch (IOException x) {
throw new RuntimeException(x);

View file

@ -1,14 +1,15 @@
package nl.wehkamp.everest.dao;
import java.util.HashSet;
import java.util.Optional;
import java.util.Set;
import nl.wehkamp.everest.model.Prediction;
import org.springframework.stereotype.Repository;
@Repository("requestResponseMemoryRepository")
public class RequestResponseMemoryRepository implements RequestResponseRepository {
@Repository
public class PredictionMemoryRepository implements PredictionRepository {
protected Set<Prediction> cache = new HashSet<>();
@Override
@ -24,4 +25,13 @@ public class RequestResponseMemoryRepository implements RequestResponseRepositor
public void clear() {
cache.clear();
}
public Optional<Prediction> findByName(String name) {
for (Prediction p : cache) {
if (p.getName().equals(name)) {
return Optional.of(p);
}
}
return Optional.empty();
}
}

View file

@ -4,9 +4,9 @@ import java.util.Set;
import nl.wehkamp.everest.model.Prediction;
public interface RequestResponseRepository {
public interface PredictionRepository {
void save(Prediction record);
void save(Prediction prediction);
Set<Prediction> findAll();

View file

@ -5,6 +5,7 @@ import java.util.Enumeration;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import javax.servlet.http.HttpServletRequest;
@ -34,6 +35,10 @@ public class Headers {
}
}
public Set<String> getHeaderNames() {
return headers.keySet();
}
/**
* returns all header values for a given name. Or null if none set
*/

View file

@ -1,7 +1,10 @@
package nl.wehkamp.everest.model;
import static java.util.Optional.empty;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.regex.Pattern;
import nl.wehkamp.everest.util.Uuids;
@ -15,12 +18,14 @@ public class Prediction {
private String url;
private String method;
private Headers requestHeaders;
private String requestBody = "";
private String response;
private int responseStatus;
private Optional<Headers> responseHeaders = empty();
public boolean requestMatches(String requesturl) {
return urlPattern.matcher(requesturl).matches();
public boolean requestUrlMatches(String requesturl) {
return urlPattern.matcher(requesturl).find();
}
public Prediction() {
@ -28,13 +33,15 @@ public class Prediction {
}
private Prediction(Dto predictionDto) {
this.id = predictionDto.id;
this.id = predictionDto.id != null ? predictionDto.id : Uuids.create();
this.name = predictionDto.name;
setUrl(predictionDto.url);
this.method = predictionDto.method;
this.requestHeaders = new Headers(predictionDto.requestHeaders);
this.requestBody = predictionDto.requestBody;
this.response = predictionDto.response;
this.responseStatus = predictionDto.responseStatus;
this.responseHeaders = predictionDto.getResponseHeaders() != null ? Optional.of(new Headers(predictionDto.getResponseHeaders())) : empty();
}
public String getMethod() {
@ -89,6 +96,26 @@ public class Prediction {
this.responseStatus = responseStatus;
}
public boolean hasReponseHeaders() {
return responseHeaders.isPresent();
}
public Headers getResponseHeaders() {
return responseHeaders.get();
}
public void setResponseHeaders(Headers responseHeaders) {
this.responseHeaders = Optional.ofNullable(responseHeaders);
}
public String getRequestBody() {
return requestBody;
}
public void setRequestBody(String requestBody) {
this.requestBody = requestBody;
}
@Override
public int hashCode() {
final int prime = 31;
@ -114,7 +141,7 @@ public class Prediction {
return true;
}
public boolean containsHeaders() {
public boolean containsRequestHeaders() {
return requestHeaders != null && requestHeaders.areSet();
}
@ -124,7 +151,8 @@ public class Prediction {
}
public Dto toDto() {
return new Dto(id, name, url, method, requestHeaders.getContent(), response, responseStatus);
Map<String, List<String>> responseHeaderMap = hasReponseHeaders() ? getResponseHeaders().getContent() : null;
return new Dto(id, name, url, method, requestHeaders.getContent(), response, responseStatus, responseHeaderMap);
}
public static Prediction fromDto(Dto predictionDto) {
@ -137,15 +165,18 @@ public class Prediction {
private String url;
private String method;
private String requestBody;
private Map<String, List<String>> requestHeaders;
private String response;
private int responseStatus;
private Map<String, List<String>> responseHeaders;
public Dto() {
}
private Dto(String id, String name, String url, String method, Map<String, List<String>> requestHeaders, String response, int responseStatus) {
private Dto(String id, String name, String url, String method, Map<String, List<String>> requestHeaders, String response, int responseStatus,
Map<String, List<String>> responseHeaders) {
super();
this.id = id;
this.name = name;
@ -154,6 +185,7 @@ public class Prediction {
this.requestHeaders = requestHeaders;
this.response = response;
this.responseStatus = responseStatus;
this.responseHeaders = responseHeaders;
}
public String getId() {
@ -196,6 +228,14 @@ public class Prediction {
this.requestHeaders = requestHeaders;
}
public String getRequestBody() {
return requestBody;
}
public void setRequestBody(String requestBody) {
this.requestBody = requestBody;
}
public String getResponse() {
return response;
}
@ -212,6 +252,14 @@ public class Prediction {
this.responseStatus = responseStatus;
}
public Map<String, List<String>> getResponseHeaders() {
return responseHeaders;
}
public void setResponseHeaders(Map<String, List<String>> responseHeaders) {
this.responseHeaders = responseHeaders;
}
@Override
public int hashCode() {
final int prime = 31;

View file

@ -0,0 +1,29 @@
//package nl.wehkamp.everest.proxy;
//
//import io.netty.channel.ChannelHandlerContext;
//import io.netty.handler.codec.http.HttpRequest;
//
//import org.littleshoot.proxy.HttpFilters;
//import org.littleshoot.proxy.HttpFiltersAdapter;
//import org.littleshoot.proxy.HttpFiltersSourceAdapter;
//import org.littleshoot.proxy.HttpProxyServer;
//import org.littleshoot.proxy.impl.DefaultHttpProxyServer;
//
//public class Proxy {
// private int port = 8080;
// private HttpProxyServer server;
//
// public void start() {
// server = DefaultHttpProxyServer.bootstrap().withPort(port).withFiltersSource(new HttpFiltersSourceAdapter() {
// public HttpFilters filterRequest(HttpRequest originalRequest, ChannelHandlerContext ctx) {
// return new HttpFiltersAdapter(originalRequest) {
//
// };
// }
// }).start();
// }
//
// public void setPort(int port) {
// this.port = port;
// }
// }

View file

@ -0,0 +1,17 @@
package nl.wehkamp.everest.service;
import static nl.wehkamp.everest.model.Prediction.fromDto;
import java.io.IOException;
import nl.wehkamp.everest.model.Prediction;
import com.fasterxml.jackson.databind.ObjectMapper;
public class PredictionFactory {
private static ObjectMapper objectMapper = new ObjectMapper();
public static Prediction newPrediction(String json) throws IOException {
return fromDto(objectMapper.readValue(json, Prediction.Dto.class));
}
}

View file

@ -8,12 +8,14 @@
*/
package nl.wehkamp.everest.service;
import java.io.BufferedReader;
import java.io.IOException;
import java.util.Optional;
import java.util.Set;
import javax.servlet.http.HttpServletRequest;
import nl.wehkamp.everest.dao.RequestResponseRepository;
import nl.wehkamp.everest.dao.PredictionRepository;
import nl.wehkamp.everest.model.Prediction;
import org.springframework.beans.factory.annotation.Autowired;
@ -25,31 +27,54 @@ import org.springframework.stereotype.Service;
@Service
public class ResponseFinder {
@Autowired
private RequestResponseRepository requestResponseRepository;
private PredictionRepository predictionJsonFileRepository;
public Optional<Prediction> find(HttpServletRequest request) {
Optional<Prediction> response = Optional.empty();
Set<Prediction> all = requestResponseRepository.findAll();
Set<Prediction> all = predictionJsonFileRepository.findAll();
for (Prediction prediction : all) {
response = matchRequestBody(request, response, prediction);
}
return response;
}
private Optional<Prediction> matchRequestBody(HttpServletRequest request, Optional<Prediction> response, Prediction prediction) {
String requestbody = getBody(request);
if (prediction.getRequestBody().equals(requestbody)) {
response = matchUrlAndMethodAndHeaders(request, response, prediction);
}
return response;
}
private Optional<Prediction> matchUrlAndMethodAndHeaders(HttpServletRequest request, Optional<Prediction> response, Prediction rr) {
if (rr.requestMatches(request.getPathInfo())) {
response = matchMethodAndHeaders(request, response, rr);
private Optional<Prediction> matchUrlAndMethodAndHeaders(HttpServletRequest request, Optional<Prediction> response, Prediction prediction) {
if (prediction.requestUrlMatches(request.getPathInfo())) {
response = matchMethodAndHeaders(request, response, prediction);
}
return response;
}
private Optional<Prediction> matchMethodAndHeaders(HttpServletRequest request, Optional<Prediction> response, Prediction rr) {
if (rr.getMethod().equals(request.getMethod())) {
if (rr.containsHeaders()) {
response = matchHeaders(request, response, rr);
private String getBody(HttpServletRequest request) {
BufferedReader reader;
try {
reader = request.getReader();
String line = null;
StringBuilder buffer = new StringBuilder();
while ((line = reader.readLine()) != null) {
buffer.append(line);
}
return buffer.toString();
} catch (IOException e) {
throw new RuntimeException(e);
}
}
private Optional<Prediction> matchMethodAndHeaders(HttpServletRequest request, Optional<Prediction> response, Prediction prediction) {
if (prediction.getMethod().equals(request.getMethod())) {
if (prediction.containsRequestHeaders()) {
response = matchHeaders(request, response, prediction);
} else {
response = Optional.of(rr);
response = Optional.of(prediction);
}
}
return response;
@ -62,7 +87,7 @@ public class ResponseFinder {
return response;
}
public void setRequestResponseRepository(RequestResponseRepository requestResponseRepository) {
this.requestResponseRepository = requestResponseRepository;
public void setPredictionRepository(PredictionRepository predictionJsonFileRepository) {
this.predictionJsonFileRepository = predictionJsonFileRepository;
}
}

View file

@ -1,40 +0,0 @@
package nl.wehkamp.everest.web;
import java.io.IOException;
import java.util.Optional;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import nl.wehkamp.everest.model.Prediction;
import nl.wehkamp.everest.service.ResponseFinder;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.servlet.DispatcherServlet;
/**
* Mocks http requests
*
*/
@SuppressWarnings("serial")
@Controller
public class MockingServlet extends DispatcherServlet {
@Autowired
private ResponseFinder responseFinder;
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
Optional<Prediction> someRequestResponse = responseFinder.find(req);
if (someRequestResponse.isPresent()) {
Prediction requestResponse = someRequestResponse.get();
resp.getWriter().print(requestResponse.getResponse());
resp.setStatus(requestResponse.getResponseStatus());
} else {
resp.getWriter().print("Not found");
resp.setStatus(404);
}
}
}

View file

@ -0,0 +1,106 @@
package nl.wehkamp.everest.web;
import static nl.wehkamp.everest.service.PredictionFactory.newPrediction;
import java.io.BufferedReader;
import java.io.IOException;
import java.util.Optional;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import nl.wehkamp.everest.dao.PredictionRepository;
import nl.wehkamp.everest.model.Prediction;
import nl.wehkamp.everest.service.ResponseFinder;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.servlet.DispatcherServlet;
/**
* Mocks http requests using prefabricated predictions
*
*/
@SuppressWarnings("serial")
@Controller
public class PredictableResponseServlet extends DispatcherServlet {
private final static Logger log = LoggerFactory.getLogger(PredictableResponseServlet.class);
@Autowired
private ResponseFinder responseFinder;
@Autowired
private PredictionRepository predictionJsonFileRepository;
@Override
protected void service(HttpServletRequest httpRequest, HttpServletResponse httpResponse) throws ServletException, IOException {
if (isUploadRequest(httpRequest)) {
handleUpload(httpRequest, httpResponse);
} else {
handleMockRequest(httpRequest, httpResponse);
}
}
private void handleMockRequest(HttpServletRequest httpRequest, HttpServletResponse httpResponse) throws IOException {
Optional<Prediction> someRequestResponse = responseFinder.find(httpRequest);
if (someRequestResponse.isPresent()) {
Prediction prediction = someRequestResponse.get();
setPredictedResponseValues(httpResponse, prediction);
} else {
httpResponse.getWriter().print("Not found");
httpResponse.setStatus(404);
}
}
private void setPredictedResponseValues(HttpServletResponse httpResponse, Prediction prediction) throws IOException {
httpResponse.getWriter().print(prediction.getResponse());
httpResponse.setStatus(prediction.getResponseStatus());
if (prediction.hasReponseHeaders()) {
setPredictedResponseHeaders(httpResponse, prediction);
}
}
private void setPredictedResponseHeaders(HttpServletResponse httpResponse, Prediction prediction) {
for (String headername : prediction.getResponseHeaders().getHeaderNames()) {
for (String headervalue : prediction.getResponseHeaders().getAll(headername)) {
httpResponse.addHeader(headername, headervalue);
}
}
}
private void handleUpload(HttpServletRequest httpRequest, HttpServletResponse httpResponse) throws IOException {
try {
predictionJsonFileRepository.save(newPrediction(readJsonFromHttpBody(httpRequest)));
httpResponse.setStatus(201);
} catch (IOException e) {
httpResponse.setStatus(500);
httpResponse.getWriter().print(e.getClass().getName() + ":" + e.getMessage());
}
}
private String readJsonFromHttpBody(HttpServletRequest httprequest) throws IOException {
BufferedReader reader = httprequest.getReader();
String line;
StringBuilder builder = new StringBuilder();
while ((line = reader.readLine()) != null) {
builder.append(line);
}
String json = builder.toString();
log.info("upload of json {}", json);
return json;
}
private boolean isUploadRequest(HttpServletRequest req) {
return req.getMethod().equals("POST") && req.getPathInfo().startsWith("/__api/upload") && req.getHeader("Content-Type").equals("application/json");
}
public void setPredictionRepository(PredictionRepository predictionJsonFileRepository) {
this.predictionJsonFileRepository = predictionJsonFileRepository;
}
}

View file

@ -11,6 +11,7 @@ import java.util.List;
import nl.wehkamp.everest.model.Headers;
import nl.wehkamp.everest.model.Prediction;
import nl.wehkamp.everest.util.FileLoader;
import nl.wehkamp.everest.util.Uuids;
import org.testng.annotations.AfterMethod;
@ -21,7 +22,7 @@ public class RecordRepositoryTest {
@AfterMethod
public void teardown() throws IOException {
Uuids.removeTestValue();
Files.delete(Paths.get("everest_data", "wehkamp.nl.json"));
// Files.delete(Paths.get("everest_data", "wehkamp.nl.json"));
}
@Test
@ -37,15 +38,13 @@ public class RecordRepositoryTest {
record.setHeaders(headers);
record.setResponseStatus(200);
record.setResponse("<html>");
new RequestResponseJsonFileRepository().save(record);
new PredictionJsonFileRepository().save(record);
List<String> lines = Files.readAllLines(Paths.get("everest_data", "wehkamp.nl.json"), StandardCharsets.UTF_8);
assertFalse(lines.isEmpty());
System.out.println(lines.get(0));
assertEquals(
lines.get(0),
"{\"id\":\"91f83cd9-a0a5-49f5-b740-78ba8f504797\",\"name\":\"wehkamp.nl\",\"url\":\"http://www.wehkamp.nl\",\"method\":\"GET\",\"requestHeaders\":{\"Accept\":[\"application/json\"]},\"response\":\"<html>\",\"responseStatus\":200}");
assertEquals(lines.get(0), FileLoader.load("test.json"));
}
}

View file

@ -0,0 +1,16 @@
package nl.wehkamp.everest.util;
import java.io.IOException;
import org.apache.commons.io.IOUtils;
import org.springframework.core.io.ClassPathResource;
public class FileLoader {
public static String load(String resource) {
try {
return IOUtils.toString(new ClassPathResource(resource).getInputStream());
} catch (IOException e) {
throw new RuntimeException(e);
}
}
}

View file

@ -1,21 +1,24 @@
package nl.wehkamp.everest.web;
package nl.wehkamp.everest.util;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.util.Map;
import org.apache.commons.io.IOUtils;
import org.apache.http.HttpEntity;
import org.apache.http.HttpHost;
import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.ByteArrayEntity;
import org.apache.http.impl.client.HttpClients;
public class TestClient {
private static HttpClient httpclient = HttpClients.createDefault();
private static HttpHost target = new HttpHost("localhost", 8080, "http");
public static String get(String url) {
public static String httpGet(String url) {
try {
HttpGet httpGet = new HttpGet(url);
HttpResponse httpResponse = httpclient.execute(target, httpGet);
@ -26,7 +29,7 @@ public class TestClient {
}
}
public static String get(String url, Map<String, String> headers) {
public static String httpGet(String url, Map<String, String> headers) {
HttpGet httpGet = new HttpGet(url);
for (Map.Entry<String, String> header : headers.entrySet()) {
httpGet.addHeader(header.getKey(), header.getValue());
@ -40,9 +43,21 @@ public class TestClient {
}
}
public static String post(String url, String postBody) {
public static String httpPost(String url, String postBody) {
try {
HttpPost httpPost = new HttpPost(url);
HttpPost httpPost = createPost(url, postBody, null);
HttpResponse httpResponse = httpclient.execute(target, httpPost);
String responseBody = IOUtils.toString(httpResponse.getEntity().getContent());
return httpResponse.getStatusLine().getStatusCode() + ":" + responseBody;
} catch (IOException e) {
throw new RuntimeException(e);
}
}
public static String httpPost(String url, String postBody, Map<String, String> headers) {
try {
HttpPost httpPost = createPost(url, postBody, headers);
HttpResponse httpResponse = httpclient.execute(target, httpPost);
String body = IOUtils.toString(httpResponse.getEntity().getContent());
return httpResponse.getStatusLine().getStatusCode() + ":" + body;
@ -50,4 +65,17 @@ public class TestClient {
throw new RuntimeException(e);
}
}
private static HttpPost createPost(String url, String postBody, Map<String, String> headers) throws UnsupportedEncodingException {
HttpPost httpPost = new HttpPost(url);
HttpEntity entity = new ByteArrayEntity(postBody.getBytes("UTF-8"));
httpPost.setEntity(entity);
if (headers != null) {
for (Map.Entry<String, String> header : headers.entrySet()) {
httpPost.addHeader(header.getKey(), header.getValue());
}
}
return httpPost;
}
}

View file

@ -1,11 +1,11 @@
package nl.wehkamp.everest.web;
import static java.util.Collections.singletonMap;
import static nl.wehkamp.everest.web.TestClient.get;
import static nl.wehkamp.everest.web.TestClient.post;
import static nl.wehkamp.everest.util.TestClient.httpGet;
import static nl.wehkamp.everest.util.TestClient.httpPost;
import static org.testng.Assert.assertEquals;
import nl.wehkamp.everest.WebServer;
import nl.wehkamp.everest.dao.RequestResponseMemoryRepository;
import nl.wehkamp.everest.dao.PredictionMemoryRepository;
import nl.wehkamp.everest.model.Prediction;
import nl.wehkamp.everest.service.ResponseFinder;
@ -18,14 +18,14 @@ import org.testng.annotations.Test;
*/
public class MockingServletTests {
private RequestResponseMemoryRepository requestResponseRepository;
private PredictionMemoryRepository requestResponseRepository;
@BeforeSuite
public void setup() {
WebServer.start();
ResponseFinder responseFinder = WebServer.instance.getBean(ResponseFinder.class);
requestResponseRepository = new RequestResponseMemoryRepository();
responseFinder.setRequestResponseRepository(requestResponseRepository);
requestResponseRepository = new PredictionMemoryRepository();
responseFinder.setPredictionRepository(requestResponseRepository);
}
@AfterMethod
@ -41,7 +41,7 @@ public class MockingServletTests {
record.setResponse("get successful");
record.setResponseStatus(200);
requestResponseRepository.save(record);
assertEquals(get("/testget"), "200:get successful");
assertEquals(httpGet("/testget"), "200:get successful");
}
@Test
@ -53,7 +53,7 @@ public class MockingServletTests {
record.setResponse("getWithHeader successful");
record.setResponseStatus(200);
requestResponseRepository.save(record);
assertEquals(get("/testget", singletonMap("Content-Type", "application/json")), "200:getWithHeader successful");
assertEquals(httpGet("/testget", singletonMap("Content-Type", "application/json")), "200:getWithHeader successful");
}
@Test
@ -65,7 +65,7 @@ public class MockingServletTests {
record.setResponse("getWithHeader successful");
record.setResponseStatus(200);
requestResponseRepository.save(record);
assertEquals(get("/testget", singletonMap("Content-Type", "application/json")), "404:Not found");
assertEquals(httpGet("/testget", singletonMap("Content-Type", "application/json")), "404:Not found");
}
@Test
@ -76,7 +76,7 @@ public class MockingServletTests {
record.setResponse("get wildcard successful");
record.setResponseStatus(200);
requestResponseRepository.save(record);
assertEquals(get("/testget/foo"), "200:get wildcard successful");
assertEquals(httpGet("/testget/foo"), "200:get wildcard successful");
}
@Test
@ -87,6 +87,6 @@ public class MockingServletTests {
record.setResponse("post successful");
record.setResponseStatus(200);
requestResponseRepository.save(record);
assertEquals(post("/testpost", "body"), "200:post successful");
assertEquals(httpPost("/testpost", "body"), "200:post successful");
}
}

View file

@ -0,0 +1,42 @@
package nl.wehkamp.everest.web;
import static java.util.Collections.singletonMap;
import static nl.wehkamp.everest.util.FileLoader.load;
import static nl.wehkamp.everest.util.TestClient.httpPost;
import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertTrue;
import java.util.Optional;
import nl.wehkamp.everest.WebServer;
import nl.wehkamp.everest.dao.PredictionMemoryRepository;
import nl.wehkamp.everest.model.Prediction;
import nl.wehkamp.everest.service.ResponseFinder;
import org.testng.annotations.BeforeSuite;
import org.testng.annotations.Test;
public class UploadTests {
private PredictionMemoryRepository predictionMemoryRepository;
@BeforeSuite
public void setup() {
WebServer.start();
ResponseFinder responseFinder = WebServer.instance.getBean(ResponseFinder.class);
predictionMemoryRepository = new PredictionMemoryRepository();
responseFinder.setPredictionRepository(predictionMemoryRepository);
PredictableResponseServlet servlet = WebServer.instance.getBean(PredictableResponseServlet.class);
servlet.setPredictionRepository(predictionMemoryRepository);
predictionMemoryRepository.clear();
}
@Test
public void test() {
httpPost("/__api/upload", load("uploadtest.json"), singletonMap("Content-Type", "application/json"));
Optional<Prediction> prediction = predictionMemoryRepository.findByName("test.nl");
assertTrue(prediction.isPresent());
assertEquals(prediction.get().getUrl(), "/entry");
}
}

View file

@ -0,0 +1 @@
{"id":"91f83cd9-a0a5-49f5-b740-78ba8f504797","name":"wehkamp.nl","url":"http://www.wehkamp.nl","method":"GET","requestHeaders":{"Accept":["application/json"]},"response":"<html>","responseStatus":200,"responseHeaders":null}

View file

@ -0,0 +1 @@
{"id":"1","name":"test.nl","url":"/entry","method":"GET","requestHeaders":{"Accept":["application/json"]},"response":"<html>","responseStatus":200,"responseHeaders":null}