Avoid the usage of remote services, replace with local server Remote service echo.jsontest.com has low quota leading to failing tests when exceeded. Replace with a local server, returning the same repsonse. As a bonus the test can be run as a unit test. Also remove code duplication, move common code to TestHttpServer.
Project: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/repo Commit: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/commit/9b4f84e8 Tree: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/tree/9b4f84e8 Diff: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/diff/9b4f84e8 Branch: refs/heads/master Commit: 9b4f84e8aaf2f1af5281b14e3c00871982a5abae Parents: fcaa205 Author: Svetoslav Neykov <[email protected]> Authored: Thu Jun 25 23:48:37 2015 +0300 Committer: Svetoslav Neykov <[email protected]> Committed: Thu Jun 25 23:48:37 2015 +0300 ---------------------------------------------------------------------- .../brooklyn/test/TestHttpRequestHandler.java | 73 ++++++++++ .../test/java/brooklyn/test/TestHttpServer.java | 144 +++++++++++++++++++ .../brooklyn/util/ResourceUtilsHttpTest.java | 84 +++-------- .../software/http/HttpRequestSensorTest.java | 20 ++- .../rest/resources/CatalogResetTest.java | 83 ++--------- 5 files changed, 261 insertions(+), 143 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/9b4f84e8/core/src/test/java/brooklyn/test/TestHttpRequestHandler.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/brooklyn/test/TestHttpRequestHandler.java b/core/src/test/java/brooklyn/test/TestHttpRequestHandler.java new file mode 100644 index 0000000..1a6c766 --- /dev/null +++ b/core/src/test/java/brooklyn/test/TestHttpRequestHandler.java @@ -0,0 +1,73 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package brooklyn.test; + +import java.io.IOException; +import java.io.UnsupportedEncodingException; +import java.util.ArrayList; +import java.util.Collection; + +import org.apache.http.Header; +import org.apache.http.HttpEntity; +import org.apache.http.HttpException; +import org.apache.http.HttpRequest; +import org.apache.http.HttpResponse; +import org.apache.http.HttpStatus; +import org.apache.http.entity.StringEntity; +import org.apache.http.message.BasicHeader; +import org.apache.http.protocol.HttpContext; +import org.apache.http.protocol.HttpRequestHandler; + +import brooklyn.util.exceptions.Exceptions; + +public class TestHttpRequestHandler implements HttpRequestHandler { + private HttpEntity entity; + private int responseCode = HttpStatus.SC_OK; + private Collection<Header> headers = new ArrayList<Header>(); + + public TestHttpRequestHandler response(String response) { + try { + this.entity = new StringEntity(response); + } catch (UnsupportedEncodingException e) { + throw Exceptions.propagate(e); + } + return this; + } + + public TestHttpRequestHandler code(int responseCode) { + this.responseCode = responseCode; + return this; + } + + public TestHttpRequestHandler header(String name, String value) { + headers.add(new BasicHeader(name, value)); + return this; + } + + @Override + public void handle(HttpRequest request, HttpResponse response, HttpContext context) throws HttpException, IOException { + for (Header h : headers) { + response.setHeader(h); + } + + response.setStatusCode(responseCode); + response.setEntity(entity); + } + +} http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/9b4f84e8/core/src/test/java/brooklyn/test/TestHttpServer.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/brooklyn/test/TestHttpServer.java b/core/src/test/java/brooklyn/test/TestHttpServer.java new file mode 100644 index 0000000..51e827c --- /dev/null +++ b/core/src/test/java/brooklyn/test/TestHttpServer.java @@ -0,0 +1,144 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package brooklyn.test; + +import java.io.IOException; +import java.net.InetAddress; +import java.net.MalformedURLException; +import java.net.URL; +import java.net.UnknownHostException; +import java.util.Collection; +import java.util.List; + +import org.apache.http.HttpRequestInterceptor; +import org.apache.http.HttpResponseInterceptor; +import org.apache.http.impl.bootstrap.HttpServer; +import org.apache.http.impl.bootstrap.ServerBootstrap; +import org.apache.http.protocol.HttpProcessor; +import org.apache.http.protocol.HttpRequestHandler; +import org.apache.http.protocol.ImmutableHttpProcessor; +import org.apache.http.protocol.ResponseConnControl; +import org.apache.http.protocol.ResponseContent; + +import brooklyn.util.collections.MutableList; +import brooklyn.util.exceptions.Exceptions; +import brooklyn.util.net.Networking; + +public class TestHttpServer { + private static class HandlerTuple { + String path; + HttpRequestHandler handler; + public HandlerTuple(String path, HttpRequestHandler handler) { + this.path = path; + this.handler = handler; + } + } + private HttpServer server; + private List<HttpRequestInterceptor> requestInterceptors = MutableList.of(); + private List<HttpResponseInterceptor> responseInterceptors = MutableList.of(new ResponseContent(), new ResponseConnControl()); + private int basePort = 50505; + private Collection<HandlerTuple> handlers = MutableList.of(); + + public TestHttpServer interceptor(HttpResponseInterceptor interceptor) { + checkNotStarted(); + responseInterceptors.add(interceptor); + return this; + } + + public TestHttpServer requestInterceptors(List<HttpResponseInterceptor> interceptors) { + checkNotStarted(); + this.responseInterceptors = interceptors; + return this; + } + + public TestHttpServer interceptor(HttpRequestInterceptor interceptor) { + checkNotStarted(); + requestInterceptors.add(interceptor); + return this; + } + + public TestHttpServer responseInterceptors(List<HttpRequestInterceptor> interceptors) { + checkNotStarted(); + this.requestInterceptors = interceptors; + return this; + } + + public TestHttpServer basePort(int basePort) { + checkNotStarted(); + this.basePort = basePort; + return this; + } + + public TestHttpServer handler(String path, HttpRequestHandler handler) { + checkNotStarted(); + handlers.add(new HandlerTuple(path, handler)); + return this; + } + + public TestHttpServer start() { + checkNotStarted(); + + HttpProcessor httpProcessor = new ImmutableHttpProcessor(requestInterceptors, responseInterceptors); + int port = Networking.nextAvailablePort(basePort); + ServerBootstrap bootstrap = ServerBootstrap.bootstrap() + .setListenerPort(port) + .setLocalAddress(getLocalAddress()) + .setHttpProcessor(httpProcessor); + + for (HandlerTuple tuple : handlers) { + bootstrap.registerHandler(tuple.path, tuple.handler); + } + server = bootstrap.create(); + + try { + server.start(); + } catch (IOException e) { + throw Exceptions.propagate(e); + } + + return this; + } + + public void stop() { + server.stop(); + } + + private void checkNotStarted() { + if (server != null) { + throw new IllegalStateException("Server already started"); + } + } + + private InetAddress getLocalAddress() { + try { + return InetAddress.getLocalHost(); + } catch (UnknownHostException e) { + throw Exceptions.propagate(e); + } + } + + public String getUrl() { + try { + return new URL("http", server.getInetAddress().getHostAddress(), server.getLocalPort(), "").toExternalForm(); + } catch (MalformedURLException e) { + throw Exceptions.propagate(e); + } + } + +} http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/9b4f84e8/core/src/test/java/brooklyn/util/ResourceUtilsHttpTest.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/brooklyn/util/ResourceUtilsHttpTest.java b/core/src/test/java/brooklyn/util/ResourceUtilsHttpTest.java index 2c5da32..daac00a 100644 --- a/core/src/test/java/brooklyn/util/ResourceUtilsHttpTest.java +++ b/core/src/test/java/brooklyn/util/ResourceUtilsHttpTest.java @@ -24,62 +24,49 @@ import static org.testng.Assert.assertFalse; import java.io.IOException; import java.io.InputStream; -import org.apache.http.Header; import org.apache.http.HttpException; import org.apache.http.HttpRequest; import org.apache.http.HttpResponse; import org.apache.http.HttpStatus; import org.apache.http.entity.StringEntity; -import org.apache.http.impl.bootstrap.HttpServer; -import org.apache.http.impl.bootstrap.ServerBootstrap; import org.apache.http.localserver.RequestBasicAuth; import org.apache.http.localserver.ResponseBasicUnauthorized; -import org.apache.http.message.BasicHeader; -import org.apache.http.protocol.BasicHttpProcessor; import org.apache.http.protocol.HttpContext; import org.apache.http.protocol.HttpRequestHandler; -import org.apache.http.protocol.ResponseConnControl; -import org.apache.http.protocol.ResponseContent; import org.apache.http.protocol.ResponseServer; import org.testng.annotations.AfterClass; import org.testng.annotations.BeforeClass; import org.testng.annotations.Test; +import brooklyn.test.TestHttpRequestHandler; +import brooklyn.test.TestHttpServer; import brooklyn.util.stream.Streams; import brooklyn.util.text.Strings; public class ResourceUtilsHttpTest { private ResourceUtils utils; - private HttpServer server; + private TestHttpServer server; private String baseUrl; @BeforeClass(alwaysRun=true) public void setUp() throws Exception { utils = ResourceUtils.create(this, "mycontext"); - - BasicHttpProcessor httpProcessor = new BasicHttpProcessor(); - httpProcessor.addInterceptor(new ResponseServer()); - httpProcessor.addInterceptor(new ResponseContent()); - httpProcessor.addInterceptor(new ResponseConnControl()); - httpProcessor.addInterceptor(new RequestBasicAuth()); - httpProcessor.addInterceptor(new ResponseBasicUnauthorized()); - - server = ServerBootstrap.bootstrap() - .setListenerPort(24266) - .setHttpProcessor(httpProcessor) - .registerHandler("/simple", new SimpleResponseHandler("OK")) - .registerHandler("/empty", new SimpleResponseHandler(HttpStatus.SC_NO_CONTENT, "")) - .registerHandler("/missing", new SimpleResponseHandler(HttpStatus.SC_NOT_FOUND, "Missing")) - .registerHandler("/redirect", new SimpleResponseHandler(HttpStatus.SC_MOVED_TEMPORARILY, "Redirect", new BasicHeader("Location", "/simple"))) - .registerHandler("/cycle", new SimpleResponseHandler(HttpStatus.SC_MOVED_TEMPORARILY, "Redirect", new BasicHeader("Location", "/cycle"))) - .registerHandler("/secure", new SimpleResponseHandler(HttpStatus.SC_MOVED_TEMPORARILY, "Redirect", new BasicHeader("Location", "https://0.0.0.0/"))) - .registerHandler("/auth", new AuthHandler("test", "test", "OK")) - .registerHandler("/auth_escape", new AuthHandler("test@me:/", "test", "OK")) - .registerHandler("/auth_escape2", new AuthHandler("test@me:test", "", "OK")) - .registerHandler("/no_credentials", new CheckNoCredentials()) - .create(); - server.start(); - baseUrl = "http://" + server.getInetAddress().getHostName() + ":" + server.getLocalPort(); + server = new TestHttpServer() + .interceptor(new ResponseServer()) + .interceptor(new ResponseBasicUnauthorized()) + .interceptor(new RequestBasicAuth()) + .handler("/simple", new TestHttpRequestHandler().response("OK")) + .handler("/empty", new TestHttpRequestHandler().code(HttpStatus.SC_NO_CONTENT)) + .handler("/missing", new TestHttpRequestHandler().code(HttpStatus.SC_NOT_FOUND).response("Missing")) + .handler("/redirect", new TestHttpRequestHandler().code(HttpStatus.SC_MOVED_TEMPORARILY).response("Redirect").header("Location", "/simple")) + .handler("/cycle", new TestHttpRequestHandler().code(HttpStatus.SC_MOVED_TEMPORARILY).response("Redirect").header("Location", "/cycle")) + .handler("/secure", new TestHttpRequestHandler().code(HttpStatus.SC_MOVED_TEMPORARILY).response("Redirect").header("Location", "https://0.0.0.0/")) + .handler("/auth", new AuthHandler("test", "test", "OK")) + .handler("/auth_escape", new AuthHandler("test@me:/", "test", "OK")) + .handler("/auth_escape2", new AuthHandler("test@me:test", "", "OK")) + .handler("/no_credentials", new CheckNoCredentials()) + .start(); + baseUrl = server.getUrl(); } @AfterClass(alwaysRun=true) @@ -161,38 +148,6 @@ public class ResourceUtilsHttpTest { assertFalse(contents.contains("bit.ly"), "contents="+contents); } - private static class SimpleResponseHandler implements HttpRequestHandler { - private int statusCode = HttpStatus.SC_OK; - private String responseBody = ""; - private Header[] headers; - - protected SimpleResponseHandler(String response) { - this.responseBody = response; - } - - protected SimpleResponseHandler(int status, String response) { - this.statusCode = status; - this.responseBody = response; - } - - protected SimpleResponseHandler(int status, String response, Header... headers) { - this.statusCode = status; - this.responseBody = response; - this.headers = headers; - } - - @Override - public void handle(HttpRequest request, HttpResponse response, HttpContext context) throws HttpException, IOException { - response.setStatusCode(statusCode); - response.setEntity(new StringEntity(responseBody)); - if (headers != null) { - for (Header header : headers) { - response.setHeader(header); - } - } - } - } - private static class AuthHandler implements HttpRequestHandler { private String username; private String password; @@ -204,6 +159,7 @@ public class ResourceUtilsHttpTest { this.responseBody = response; } + @Override public void handle(HttpRequest request, HttpResponse response, HttpContext context) throws HttpException, IOException { String creds = (String) context.getAttribute("creds"); if (creds == null || !creds.equals(getExpectedCredentials())) { http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/9b4f84e8/software/base/src/test/java/brooklyn/entity/software/http/HttpRequestSensorTest.java ---------------------------------------------------------------------- diff --git a/software/base/src/test/java/brooklyn/entity/software/http/HttpRequestSensorTest.java b/software/base/src/test/java/brooklyn/entity/software/http/HttpRequestSensorTest.java index db26223..de60fb1 100644 --- a/software/base/src/test/java/brooklyn/entity/software/http/HttpRequestSensorTest.java +++ b/software/base/src/test/java/brooklyn/entity/software/http/HttpRequestSensorTest.java @@ -19,7 +19,7 @@ package brooklyn.entity.software.http; import org.testng.annotations.AfterMethod; -import org.testng.annotations.BeforeMethod; +import org.testng.annotations.BeforeClass; import org.testng.annotations.Test; import brooklyn.entity.basic.Attributes; @@ -30,6 +30,8 @@ import brooklyn.event.AttributeSensor; import brooklyn.event.basic.Sensors; import brooklyn.location.Location; import brooklyn.test.EntityTestUtils; +import brooklyn.test.TestHttpRequestHandler; +import brooklyn.test.TestHttpServer; import brooklyn.test.entity.TestApplication; import brooklyn.test.entity.TestEntity; import brooklyn.util.config.ConfigBag; @@ -44,8 +46,16 @@ public class HttpRequestSensorTest { private TestApplication app; private EntityLocal entity; - @BeforeMethod(alwaysRun=true) + private TestHttpServer server; + private String serverUrl; + + @BeforeClass(alwaysRun=true) public void setUp() throws Exception { + server = new TestHttpServer() + .handler("/myKey/myValue", new TestHttpRequestHandler().header("Content-Type", "application/json").response("{\"myKey\":\"myValue\"}")) + .start(); + serverUrl = server.getUrl(); + app = TestApplication.Factory.newManagedInstanceForTests(); entity = app.createAndManageChild(EntitySpec.create(TestEntity.class) .location(app.newLocalhostProvisioningLocation().obtain())); @@ -55,19 +65,21 @@ public class HttpRequestSensorTest { @AfterMethod(alwaysRun=true) public void tearDown() throws Exception { if (app != null) Entities.destroyAll(app.getManagementContext()); + server.stop(); } - @Test(groups="Integration") + @Test public void testHttpSensor() throws Exception { HttpRequestSensor<Integer> sensor = new HttpRequestSensor<Integer>(ConfigBag.newInstance() .configure(HttpRequestSensor.SENSOR_PERIOD, Duration.millis(100)) .configure(HttpRequestSensor.SENSOR_NAME, SENSOR_STRING.getName()) .configure(HttpRequestSensor.SENSOR_TYPE, TARGET_TYPE) .configure(HttpRequestSensor.JSON_PATH, "$.myKey") - .configure(HttpRequestSensor.SENSOR_URI, "http://echo.jsontest.com/myKey/myValue")); + .configure(HttpRequestSensor.SENSOR_URI, serverUrl + "/myKey/myValue")); sensor.apply(entity); entity.setAttribute(Attributes.SERVICE_UP, true); EntityTestUtils.assertAttributeEqualsEventually(entity, SENSOR_STRING, "myValue"); } + } http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/9b4f84e8/usage/rest-server/src/test/java/brooklyn/rest/resources/CatalogResetTest.java ---------------------------------------------------------------------- diff --git a/usage/rest-server/src/test/java/brooklyn/rest/resources/CatalogResetTest.java b/usage/rest-server/src/test/java/brooklyn/rest/resources/CatalogResetTest.java index 1c4f6ff..e4cc015 100644 --- a/usage/rest-server/src/test/java/brooklyn/rest/resources/CatalogResetTest.java +++ b/usage/rest-server/src/test/java/brooklyn/rest/resources/CatalogResetTest.java @@ -20,46 +20,24 @@ package brooklyn.rest.resources; import static org.testng.Assert.assertNotNull; -import java.io.IOException; -import java.io.UnsupportedEncodingException; -import java.net.InetAddress; -import java.net.URL; -import java.util.ArrayList; -import java.util.Collection; - import javax.ws.rs.core.MediaType; -import org.apache.http.Header; -import org.apache.http.HttpEntity; -import org.apache.http.HttpException; -import org.apache.http.HttpRequest; -import org.apache.http.HttpResponse; import org.apache.http.HttpStatus; -import org.apache.http.entity.StringEntity; -import org.apache.http.impl.bootstrap.HttpServer; -import org.apache.http.impl.bootstrap.ServerBootstrap; -import org.apache.http.message.BasicHeader; -import org.apache.http.protocol.HttpContext; -import org.apache.http.protocol.HttpProcessor; -import org.apache.http.protocol.HttpRequestHandler; -import org.apache.http.protocol.ImmutableHttpProcessor; -import org.apache.http.protocol.ResponseConnControl; -import org.apache.http.protocol.ResponseContent; import org.testng.annotations.AfterClass; import org.testng.annotations.BeforeClass; import org.testng.annotations.Test; import brooklyn.catalog.BrooklynCatalog; import brooklyn.rest.testing.BrooklynRestResourceTest; +import brooklyn.test.TestHttpRequestHandler; +import brooklyn.test.TestHttpServer; import brooklyn.util.ResourceUtils; -import brooklyn.util.exceptions.Exceptions; -import brooklyn.util.net.Networking; import com.sun.jersey.api.client.UniformInterfaceException; public class CatalogResetTest extends BrooklynRestResourceTest { - private HttpServer server; + private TestHttpServer server; private String serverUrl; @BeforeClass(alwaysRun=true) @@ -67,20 +45,11 @@ public class CatalogResetTest extends BrooklynRestResourceTest { public void setUp() throws Exception { useLocalScannedCatalog(); super.setUp(); - HttpProcessor httpProcessor = new ImmutableHttpProcessor( - new ResponseContent(), - new ResponseConnControl()); - - int port = Networking.nextAvailablePort(50505); - server = ServerBootstrap.bootstrap() - .setListenerPort(port) - .setLocalAddress(InetAddress.getLocalHost()) - .setHttpProcessor(httpProcessor) - .registerHandler("/404", new ResponseHandler().code(HttpStatus.SC_NOT_FOUND).response("Not Found")) - .registerHandler("/200", new ResponseHandler().response("OK")) - .create(); - server.start(); - serverUrl = new URL("http", server.getInetAddress().getHostAddress(), server.getLocalPort(), "").toExternalForm(); + server = new TestHttpServer() + .handler("/404", new TestHttpRequestHandler().code(HttpStatus.SC_NOT_FOUND).response("Not Found")) + .handler("/200", new TestHttpRequestHandler().response("OK")) + .start(); + serverUrl = server.getUrl(); } @Override @@ -141,40 +110,4 @@ public class CatalogResetTest extends BrooklynRestResourceTest { assertNotNull(catalog.getCatalogItem("brooklyn.osgi.tests.SimpleApplication", BrooklynCatalog.DEFAULT_VERSION)); } - private static class ResponseHandler implements HttpRequestHandler { - private HttpEntity entity; - private int responseCode = HttpStatus.SC_OK; - private Collection<Header> headers = new ArrayList<Header>(); - - public ResponseHandler response(String response) { - try { - this.entity = new StringEntity(response); - } catch (UnsupportedEncodingException e) { - throw Exceptions.propagate(e); - } - return this; - } - - public ResponseHandler code(int responseCode) { - this.responseCode = responseCode; - return this; - } - - @SuppressWarnings("unused") - public ResponseHandler header(String name, String value) { - headers.add(new BasicHeader(name, value)); - return this; - } - - @Override - public void handle(HttpRequest request, HttpResponse response, HttpContext context) throws HttpException, IOException { - for (Header h : headers) { - response.setHeader(h); - } - - response.setStatusCode(responseCode); - response.setEntity(entity); - } - - } }
