diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/APIMCertificateMGTException.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/APIMCertificateMGTException.java index 7c7b317537..89e7c38eb7 100644 --- a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/APIMCertificateMGTException.java +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/APIMCertificateMGTException.java @@ -26,37 +26,8 @@ public class APIMCertificateMGTException extends Exception{ private static final long serialVersionUID = -37676242646464497L; - private String errorMessage; - - public String getErrorMessage() { - return errorMessage; - } - - public void setErrorMessage(String errorMessage) { - this.errorMessage = errorMessage; - } - public APIMCertificateMGTException(String msg, Exception nestedEx) { super(msg, nestedEx); - setErrorMessage(msg); - } - - public APIMCertificateMGTException(String message, Throwable cause) { - super(message, cause); - setErrorMessage(message); - } - - public APIMCertificateMGTException(String msg) { - super(msg); - setErrorMessage(msg); - } - - public APIMCertificateMGTException() { - super(); - } - - public APIMCertificateMGTException(Throwable cause) { - super(cause); } } diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/AuthenticationHandler.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/AuthenticationHandler.java index 2891e06179..276380ce86 100644 --- a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/AuthenticationHandler.java +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/AuthenticationHandler.java @@ -19,7 +19,6 @@ package org.wso2.carbon.apimgt.handlers; import com.google.gson.Gson; import org.apache.axis2.context.MessageContext; -import org.apache.axis2.description.HandlerDescription; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.apache.synapse.core.axis2.Axis2MessageContext; @@ -51,8 +50,6 @@ import java.util.StringTokenizer; */ public class AuthenticationHandler extends AbstractHandler { private static final Log log = LogFactory.getLog(AuthenticationHandler.class); - private static HandlerDescription EMPTY_HANDLER_METADATA = new HandlerDescription("API Security Handler"); - private HandlerDescription handlerDesc; private RESTInvoker restInvoker; private static final String X_JWT_ASSERTION = "X-JWT-Assertion"; @@ -69,7 +66,6 @@ public class AuthenticationHandler extends AbstractHandler { public AuthenticationHandler() { log.info("Engaging API Security Handler.........."); restInvoker = new RESTInvoker(); - this.handlerDesc = EMPTY_HANDLER_METADATA; this.iotServerConfiguration = Utils.initConfig(); } @@ -94,13 +90,16 @@ public class AuthenticationHandler extends AbstractHandler { RESTResponse response; if (headers.containsKey(AuthConstants.MDM_SIGNATURE)) { - String mdmSignature = headers.get(AuthConstants.MDM_SIGNATURE).toString(); + String mdmSignature = headers.get(AuthConstants.MDM_SIGNATURE); if (log.isDebugEnabled()) { log.debug("Verify Cert:\n" + mdmSignature); } String deviceType = this.getDeviceType(messageContext.getTo().getAddress().trim()); + if (deviceType == null){ + return false; + } URI certVerifyUrl = new URI(iotServerConfiguration.getVerificationEndpoint() + deviceType); - Map certVerifyHeaders = this.setHeaders(); + Map certVerifyHeaders = this.setHeaders(this.restInvoker); Certificate certificate = new Certificate(); certificate.setPem(mdmSignature); @@ -125,7 +124,7 @@ public class AuthenticationHandler extends AbstractHandler { } } else if (headers.containsKey(AuthConstants.PROXY_MUTUAL_AUTH_HEADER)) { - String subjectDN = headers.get(AuthConstants.PROXY_MUTUAL_AUTH_HEADER).toString(); + String subjectDN = headers.get(AuthConstants.PROXY_MUTUAL_AUTH_HEADER); if (log.isDebugEnabled()) { log.debug("Verify subject DN: " + subjectDN); @@ -133,7 +132,7 @@ public class AuthenticationHandler extends AbstractHandler { String deviceType = this.getDeviceType(messageContext.getTo().getAddress().trim()); URI certVerifyUrl = new URI(iotServerConfiguration.getVerificationEndpoint() + deviceType); - Map certVerifyHeaders = this.setHeaders(); + Map certVerifyHeaders = this.setHeaders(this.restInvoker); Certificate certificate = new Certificate(); certificate.setPem(subjectDN); certificate.setTenantId(tenantId); @@ -152,9 +151,7 @@ public class AuthenticationHandler extends AbstractHandler { CertificateFactory cf = CertificateFactory.getInstance("X.509"); ByteArrayInputStream bais = new ByteArrayInputStream(certs[0].getEncoded()); X509Certificate x509 = (X509Certificate) cf.generateCertificate(bais); - if (bais != null) { - bais.close(); - } + bais.close(); if (x509 != null) { headers.put(AuthConstants.PROXY_MUTUAL_AUTH_HEADER, CertificateGenerator.getCommonName(x509)); return true; @@ -162,13 +159,13 @@ public class AuthenticationHandler extends AbstractHandler { response = null; } } else if (headers.containsKey(AuthConstants.ENCODED_PEM)) { - String encodedPem = headers.get(AuthConstants.ENCODED_PEM).toString(); + String encodedPem = headers.get(AuthConstants.ENCODED_PEM); if (log.isDebugEnabled()) { log.debug("Verify Cert:\n" + encodedPem); } String deviceType = this.getDeviceType(messageContext.getTo().getAddress().trim()); URI certVerifyUrl = new URI(iotServerConfiguration.getVerificationEndpoint() + deviceType); - Map certVerifyHeaders = this.setHeaders(); + Map certVerifyHeaders = this.setHeaders(this.restInvoker); Certificate certificate = new Certificate(); certificate.setPem(encodedPem); @@ -224,9 +221,9 @@ public class AuthenticationHandler extends AbstractHandler { return null; } - private Map setHeaders() throws APIMCertificateMGTException { + private Map setHeaders(RESTInvoker restInvoker) throws APIMCertificateMGTException { Map map = new HashMap<>(); - String accessToken = Utils.getAccessToken(iotServerConfiguration); + String accessToken = Utils.getAccessToken(iotServerConfiguration, restInvoker); map.put(AUTHORIZATION, BEARER + accessToken); map.put(CONTENT_TYPE, "application/json"); return map; diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/invoker/RESTInvoker.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/invoker/RESTInvoker.java index 107d754ff4..da182e325b 100644 --- a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/invoker/RESTInvoker.java +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/invoker/RESTInvoker.java @@ -34,39 +34,35 @@ import java.io.IOException; import java.net.URI; import java.nio.charset.StandardCharsets; import java.util.Map; +import java.util.Set; public class RESTInvoker { private static final Log log = LogFactory.getLog(RESTInvoker.class); - private int maxTotalConnections = 100; - private int maxTotalConnectionsPerRoute = 100; - private int connectionTimeout = 120000; - private int socketTimeout = 120000; - private CloseableHttpClient client = null; - private PoolingHttpClientConnectionManager connectionManager = null; public RESTInvoker() { configureHttpClient(); } private void configureHttpClient() { - + int connectionTimeout = 120000; + int socketTimeout = 120000; + int maxTotalConnectionsPerRoute = 100; + int maxTotalConnections = 100; RequestConfig defaultRequestConfig = RequestConfig.custom() .setExpectContinueEnabled(true) .setConnectTimeout(connectionTimeout) .setSocketTimeout(socketTimeout) .build(); - - connectionManager = new PoolingHttpClientConnectionManager(); + PoolingHttpClientConnectionManager connectionManager = new PoolingHttpClientConnectionManager(); connectionManager.setDefaultMaxPerRoute(maxTotalConnectionsPerRoute); connectionManager.setMaxTotal(maxTotalConnections); client = HttpClients.custom() .setConnectionManager(connectionManager) .setDefaultRequestConfig(defaultRequestConfig) .build(); - if(log.isDebugEnabled()){ log.debug("REST client initialized with " + "maxTotalConnection = " + maxTotalConnections + @@ -76,58 +72,6 @@ public class RESTInvoker { } - public void closeHttpClient() { - IOUtils.closeQuietly(client); - IOUtils.closeQuietly(connectionManager); - } - - /** - * Invokes the http GET method - * - * @param uri endpoint/service url - * @param requestHeaders header list - * @param username username for authentication - * @param password password for authentication - * @return RESTResponse of the GET request (can be the response body or the response status code) - * @throws Exception - */ - public RESTResponse invokeGET(URI uri, Map requestHeaders, String username, String password) throws IOException { - - HttpGet httpGet = null; - CloseableHttpResponse response = null; - Header[] headers; - int httpStatus; - String contentType; - String output; - try { - httpGet = new HttpGet(uri); - if (requestHeaders != null && !requestHeaders.isEmpty()) { - Object keys[] = requestHeaders.keySet().toArray(); - for (Object header : keys) { - httpGet.setHeader(header.toString(), requestHeaders.get(header).toString()); - } - } - response = sendReceiveRequest(httpGet, username, password); - output = IOUtils.toString(response.getEntity().getContent()); - headers = response.getAllHeaders(); - httpStatus = response.getStatusLine().getStatusCode(); - contentType = response.getEntity().getContentType().getValue(); - if (log.isDebugEnabled()) { - log.debug("Invoked GET " + uri.toString() + " - Response message: " + output); - } - EntityUtils.consume(response.getEntity()); - } finally { - if (response != null) { - IOUtils.closeQuietly(response); - } - if (httpGet != null) { - httpGet.releaseConnection(); - } - } - return new RESTResponse(contentType, output, headers, httpStatus); - } - - public RESTResponse invokePOST(URI uri, Map requestHeaders, String username, String password, String payload) throws IOException { @@ -141,9 +85,9 @@ public class RESTInvoker { httpPost = new HttpPost(uri); httpPost.setEntity(new StringEntity(payload)); if (requestHeaders != null && !requestHeaders.isEmpty()) { - Object keys[] = requestHeaders.keySet().toArray(); - for (Object header : keys) { - httpPost.setHeader(header.toString(), requestHeaders.get(header).toString()); + Set keys = requestHeaders.keySet(); + for (String header : keys) { + httpPost.setHeader(header, requestHeaders.get(header)); } } response = sendReceiveRequest(httpPost, username, password); @@ -167,101 +111,6 @@ public class RESTInvoker { return new RESTResponse(contentType, output, headers, httpStatus); } - /** - * Invokes the http PUT method - * - * @param uri endpoint/service url - * @param requestHeaders header list - * @param username username for authentication - * @param password password for authentication - * @param payload payload body passed - * @return RESTResponse of the PUT request (can be the response body or the response status code) - * @throws Exception - */ - public RESTResponse invokePUT(URI uri, Map requestHeaders, String username, String password, - String payload) throws IOException { - - HttpPut httpPut = null; - CloseableHttpResponse response = null; - Header[] headers; - int httpStatus; - String contentType; - String output; - try { - httpPut = new HttpPut(uri); - httpPut.setEntity(new StringEntity(payload)); - if (requestHeaders != null && !requestHeaders.isEmpty()) { - Object keys[] = requestHeaders.keySet().toArray(); - for (Object header : keys) { - httpPut.setHeader(header.toString(), requestHeaders.get(header).toString()); - } - } - response = sendReceiveRequest(httpPut, username, password); - output = IOUtils.toString(response.getEntity().getContent()); - headers = response.getAllHeaders(); - httpStatus = response.getStatusLine().getStatusCode(); - contentType = response.getEntity().getContentType().getValue(); - if (log.isDebugEnabled()) { - log.debug("Invoked PUT " + uri.toString() + " - Response message: " + output); - } - EntityUtils.consume(response.getEntity()); - } finally { - if (response != null) { - IOUtils.closeQuietly(response); - } - if (httpPut != null) { - httpPut.releaseConnection(); - } - } - return new RESTResponse(contentType, output, headers, httpStatus); - } - - /** - * Invokes the http DELETE method - * - * @param uri endpoint/service url - * @param requestHeaders header list - * @param username username for authentication - * @param password password for authentication - * @return RESTResponse of the DELETE (can be the response status code or the response body) - * @throws Exception - */ - public RESTResponse invokeDELETE(URI uri, Map requestHeaders, String username, String password) throws IOException { - - HttpDelete httpDelete = null; - CloseableHttpResponse response = null; - Header[] headers; - int httpStatus; - String contentType; - String output; - try { - httpDelete = new HttpDelete(uri); - if (requestHeaders != null && !requestHeaders.isEmpty()) { - Object keys[] = requestHeaders.keySet().toArray(); - for (Object header : keys) { - httpDelete.setHeader(header.toString(), requestHeaders.get(header).toString()); - } - } - response = sendReceiveRequest(httpDelete, username, password); - output = IOUtils.toString(response.getEntity().getContent()); - headers = response.getAllHeaders(); - httpStatus = response.getStatusLine().getStatusCode(); - contentType = response.getEntity().getContentType().getValue(); - if (log.isDebugEnabled()) { - log.debug("Invoked DELETE " + uri.toString() + " - Response message: " + output); - } - EntityUtils.consume(response.getEntity()); - } finally { - if (response != null) { - IOUtils.closeQuietly(response); - } - if (httpDelete != null) { - httpDelete.releaseConnection(); - } - } - return new RESTResponse(contentType, output, headers, httpStatus); - } - private CloseableHttpResponse sendReceiveRequest(HttpRequestBase requestBase, String username, String password) throws IOException { CloseableHttpResponse response; diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/invoker/RESTResponse.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/invoker/RESTResponse.java index 7ce0389baa..57b4d58f94 100644 --- a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/invoker/RESTResponse.java +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/invoker/RESTResponse.java @@ -36,7 +36,7 @@ public class RESTResponse { * @param headers from the REST invoke response * @param httpStatus from the REST invoke response */ - public RESTResponse(String contentType, String content, Header[] headers, int httpStatus) { + RESTResponse(String contentType, String content, Header[] headers, int httpStatus) { this.contentType = contentType; this.content = content; this.headers = headers; diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/utils/AuthConstants.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/utils/AuthConstants.java index 74870c131f..f2a9f7a42b 100644 --- a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/utils/AuthConstants.java +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/utils/AuthConstants.java @@ -21,18 +21,6 @@ package org.wso2.carbon.apimgt.handlers.utils; * This initializes the constance. */ public class AuthConstants { -// public static final String SEC_FAULT = "SECURITY_VALIDATION_FAILURE"; -// public static final String HTTPS = "https"; -// public static final String WSSE = "wsse"; -// public static final String AUTH_CONFIGURATION_FILE_NAME = "api-filter-config.xml"; -// public static final String API_FILTER_CONFIG_ELEMENT = "apiFilterConfig"; -// public static final String API_LIST_PROPERTY = "apiList"; -// public static final String HOST = "host"; -// public static final String HTTPS_PORT = "httpsPort"; -// public static final String USERNAME = "username"; -// public static final String PASSWORD = "password"; -// public static final String IOS_VERIFY_ENDPOINT = "ios-verify-endpoint"; -// public static final String ANDROID_VERIFY_ENDPOINT = "android-verify-endpoint"; public static final String MDM_SIGNATURE = "mdm-signature"; public static final String PROXY_MUTUAL_AUTH_HEADER = "proxy-mutual-auth-header"; public static final String MUTUAL_AUTH_HEADER = "mutual-auth-header"; diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/utils/Utils.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/utils/Utils.java index e7d239a1ee..1a2d7e5859 100644 --- a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/utils/Utils.java +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/main/java/org/wso2/carbon/apimgt/handlers/utils/Utils.java @@ -59,14 +59,20 @@ public class Utils { /** * This method initializes the iot-api-config.xml file. - * @return + * @return IoTServerConfiguration Object based on the configuration file. */ public static IOTServerConfiguration initConfig() { - try { + return initConfig(CarbonUtils.getCarbonConfigDirPath() + File.separator + IOT_APIS_CONFIG_FILE); + } - String IOTServerAPIConfigurationPath = CarbonUtils.getCarbonConfigDirPath() + File.separator - + IOT_APIS_CONFIG_FILE; - File file = new File(IOTServerAPIConfigurationPath); + /** + * This methods initialized the iot-api-config.xml from provided path. + * @param path The actual file path of iot-api-config.xml + * @return The instance of the IOTServerConfiguration based on the configuration. + */ + public static IOTServerConfiguration initConfig(String path){ + try { + File file = new File(path); Document doc = Utils.convertToDocument(file); JAXBContext fileContext = JAXBContext.newInstance(IOTServerConfiguration.class); @@ -91,7 +97,7 @@ public class Utils { /** * This method gets the values from system variables and sets to xml. */ - public static String replaceProperties(String text) { + private static String replaceProperties(String text) { String regex = "\\$\\{(.*?)\\}"; Pattern pattern = Pattern.compile(regex); Matcher matchPattern = pattern.matcher(text); @@ -107,11 +113,12 @@ public class Utils { /** * This class build the iot-api-config.xml file. - * @param file - * @return + * + * @param file The file object of iot-api-config.xml. + * @return Document instance of the file * @throws APIMCertificateMGTException */ - public static Document convertToDocument(File file) throws APIMCertificateMGTException { + private static Document convertToDocument(File file) throws APIMCertificateMGTException { DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); factory.setNamespaceAware(true); try { @@ -126,48 +133,45 @@ public class Utils { /** * This class get the access token from the key manager. - * @param iotServerConfiguration - * @return + * + * @param iotServerConfiguration Instance of the IoTsererConfiguration. + * @return Access token will be returned. * @throws APIMCertificateMGTException */ - public static String getAccessToken(IOTServerConfiguration iotServerConfiguration) + public static String getAccessToken(IOTServerConfiguration iotServerConfiguration, RESTInvoker restInvoker) throws APIMCertificateMGTException { try { if (clientId == null || clientSecret == null) { - getClientSecretes(iotServerConfiguration); + getClientSecretes(iotServerConfiguration, restInvoker); } URI tokenUrl = new URI(iotServerConfiguration.getOauthTokenEndpoint()); String tokenContent = "grant_type=password&username=" + iotServerConfiguration.getUsername()+ "&password=" + iotServerConfiguration.getPassword() + "&scope=activity-view"; String tokenBasicAuth = "Basic " + Base64.encode((clientId + ":" + clientSecret).getBytes()); - Map tokenHeaders = new HashMap(); + Map tokenHeaders = new HashMap<>(); tokenHeaders.put("Authorization", tokenBasicAuth); tokenHeaders.put("Content-Type", "application/x-www-form-urlencoded"); - RESTInvoker restInvoker = new RESTInvoker(); RESTResponse response = restInvoker.invokePOST(tokenUrl, tokenHeaders, null, null, tokenContent); if(log.isDebugEnabled()) { log.debug("Token response:" + response.getContent()); } JSONObject jsonResponse = new JSONObject(response.getContent()); - String accessToken = jsonResponse.getString("access_token"); - return accessToken; + return jsonResponse.getString("access_token"); - } catch (URISyntaxException e) { + } catch (URISyntaxException | IOException e) { throw new APIMCertificateMGTException("Error occurred while trying to call oauth token endpoint", e); } catch (JSONException e) { throw new APIMCertificateMGTException("Error occurred while converting the json to object", e); - } catch (IOException e) { - throw new APIMCertificateMGTException("Error occurred while trying to call oauth token endpoint", e); } } /** * This method register an application to get the client key and secret. - * @param iotServerConfiguration + * @param iotServerConfiguration Instance of the IoTServerConfiguration. * @throws APIMCertificateMGTException */ - private static void getClientSecretes(IOTServerConfiguration iotServerConfiguration) + private static void getClientSecretes(IOTServerConfiguration iotServerConfiguration, RESTInvoker restInvoker) throws APIMCertificateMGTException { try { String username = iotServerConfiguration.getUsername(); @@ -180,12 +184,11 @@ public class Utils { dcr.setCallbackUrl(AuthConstants.CALLBACK_URL); dcr.setIsSaasApp(true); String dcrContent = dcr.toJSON(); - Map dcrHeaders = new HashMap(); + Map dcrHeaders = new HashMap<>(); String basicAuth = Base64.encode((username + ":" + password).getBytes()); dcrHeaders.put(AuthConstants.CONTENT_TYPE_HEADER, AuthConstants.CONTENT_TYPE); dcrHeaders.put(AuthConstants.AUTHORIZATION_HEADER, AuthConstants.BASIC_AUTH_PREFIX + basicAuth); URI dcrUrl = new URI(iotServerConfiguration.getDynamicClientRegistrationEndpoint()); - RESTInvoker restInvoker = new RESTInvoker(); RESTResponse response = restInvoker.invokePOST(dcrUrl, dcrHeaders, null, null, dcrContent); if (log.isDebugEnabled()) { log.debug("DCR response :" + response.getContent()); diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/AuthenticationHandlerTest.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/AuthenticationHandlerTest.java new file mode 100644 index 0000000000..f68a9bd973 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/AuthenticationHandlerTest.java @@ -0,0 +1,242 @@ +/* +* Copyright (c) 2017, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. +* WSO2 Inc. 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 org.wso2.carbon.apimgt.handlers; + +import com.google.gson.Gson; +import junit.framework.Assert; +import org.apache.axiom.om.OMAbstractFactory; +import org.apache.axiom.om.OMDocument; +import org.apache.axiom.soap.SOAPEnvelope; +import org.apache.axis2.addressing.EndpointReference; +import org.apache.axis2.context.ConfigurationContext; +import org.apache.axis2.engine.AxisConfiguration; +import org.apache.http.ProtocolVersion; +import org.apache.http.client.methods.CloseableHttpResponse; +import org.apache.http.entity.BasicHttpEntity; +import org.apache.http.message.BasicStatusLine; +import org.apache.synapse.MessageContext; +import org.apache.synapse.config.SynapseConfigUtils; +import org.apache.synapse.config.SynapseConfiguration; +import org.apache.synapse.core.SynapseEnvironment; +import org.apache.synapse.core.axis2.Axis2MessageContext; +import org.apache.synapse.core.axis2.Axis2SynapseEnvironment; +import org.testng.annotations.BeforeClass; +import org.testng.annotations.Test; +import org.wso2.carbon.apimgt.handlers.beans.ValidationResponce; +import org.wso2.carbon.apimgt.handlers.invoker.RESTInvoker; +import org.wso2.carbon.apimgt.handlers.mock.MockClient; +import org.wso2.carbon.apimgt.handlers.mock.MockHttpResponse; +import org.wso2.carbon.apimgt.handlers.utils.AuthConstants; + +import java.io.BufferedReader; +import java.io.ByteArrayInputStream; +import java.io.FileReader; +import java.io.IOException; +import java.io.UnsupportedEncodingException; +import java.lang.reflect.Field; +import java.nio.charset.StandardCharsets; +import java.util.HashMap; +import javax.security.cert.X509Certificate; + +/** + * This testcase will focus on covering the methods of {@link AuthenticationHandler} + */ +public class AuthenticationHandlerTest extends BaseAPIHandlerTest { + + private AuthenticationHandler handler; + private SynapseConfiguration synapseConfiguration; + private MockClient mockClient; + + @BeforeClass + public void initTest() { + TestUtils.setSystemProperties(); + this.handler = new AuthenticationHandler(); + this.synapseConfiguration = new SynapseConfiguration(); + } + + @Test(description = "Handle request with empty transport headers") + public void testHandleRequestWithEmptyTransportHeader() throws Exception { + boolean response = this.handler.handleRequest(createSynapseMessageContext("", this.synapseConfiguration, + new HashMap<>(), "https://test.com/testservice")); + Assert.assertFalse(response); + } + + @Test(description = "Handle request with without device type", + dependsOnMethods = "testHandleRequestWithEmptyTransportHeader") + public void testHandleRequestWithURISyntaxError() throws Exception { + HashMap transportHeaders = new HashMap<>(); + transportHeaders.put(AuthConstants.MDM_SIGNATURE, "some cert"); + boolean response = this.handler.handleRequest(createSynapseMessageContext("", this.synapseConfiguration, + transportHeaders, "https://test.com/testservice")); + Assert.assertFalse(response); + } + + @Test(description = "Handle request with device type URI with MDM ceritificate", + dependsOnMethods = "testHandleRequestWithURISyntaxError") + public void testHandleSuccessfulRequestMDMCertificate() throws Exception { + HashMap transportHeaders = new HashMap<>(); + transportHeaders.put(AuthConstants.MDM_SIGNATURE, "some cert"); + setMockClient(); + this.mockClient.setResponse(getDCRResponse()); + this.mockClient.setResponse(getAccessTokenReponse()); + this.mockClient.setResponse(getValidationResponse()); + boolean response = this.handler.handleRequest(createSynapseMessageContext("", this.synapseConfiguration, + transportHeaders, "https://test.com/testservice/api/testdevice")); + Assert.assertTrue(response); + this.mockClient.reset(); + } + + @Test(description = "Handle request with device type URI with Proxy Mutual Auth Header", + dependsOnMethods = "testHandleSuccessfulRequestMDMCertificate") + public void testHandleSuccessRequestProxyMutualAuthHeader() throws Exception { + HashMap transportHeaders = new HashMap<>(); + transportHeaders.put(AuthConstants.PROXY_MUTUAL_AUTH_HEADER, "Test Header"); + setMockClient(); + this.mockClient.setResponse(getAccessTokenReponse()); + this.mockClient.setResponse(getValidationResponse()); + boolean response = this.handler.handleRequest(createSynapseMessageContext("", this.synapseConfiguration, + transportHeaders, "https://test.com/testservice/api/testdevice")); + Assert.assertTrue(response); + this.mockClient.reset(); + } + + @Test(description = "Handle request with device type URI with Mutual Auth Header", + dependsOnMethods = "testHandleSuccessRequestProxyMutualAuthHeader") + public void testHandleSuccessRequestMutualAuthHeader() throws Exception { + HashMap transportHeaders = new HashMap<>(); + transportHeaders.put(AuthConstants.MUTUAL_AUTH_HEADER, "Test Header"); + setMockClient(); + this.mockClient.setResponse(getAccessTokenReponse()); + this.mockClient.setResponse(getValidationResponse()); + MessageContext messageContext = createSynapseMessageContext("", this.synapseConfiguration, + transportHeaders, "https://test.com/testservice/api/testdevice"); + org.apache.axis2.context.MessageContext axisMC = ((Axis2MessageContext) messageContext).getAxis2MessageContext(); + String certStr = getContent(TestUtils.getAbsolutePathOfConfig("ra_cert.pem")); + X509Certificate cert = X509Certificate.getInstance(new ByteArrayInputStream(certStr. + getBytes(StandardCharsets.UTF_8.name()))); + axisMC.setProperty(AuthConstants.CLIENT_CERTIFICATE, new X509Certificate[]{cert}); + boolean response = this.handler.handleRequest(messageContext); + Assert.assertTrue(response); + this.mockClient.reset(); + } + + @Test(description = "Handle request with device type URI with Encoded Pem", + dependsOnMethods = "testHandleSuccessRequestMutualAuthHeader") + public void testHandleSuccessRequestEncodedPem() throws Exception { + HashMap transportHeaders = new HashMap<>(); + transportHeaders.put(AuthConstants.ENCODED_PEM, "encoded pem"); + setMockClient(); + this.mockClient.setResponse(getAccessTokenReponse()); + this.mockClient.setResponse(getValidationResponse()); + MessageContext messageContext = createSynapseMessageContext("", this.synapseConfiguration, + transportHeaders, "https://test.com/testservice/api/testdevice"); + boolean response = this.handler.handleRequest(messageContext); + Assert.assertTrue(response); + this.mockClient.reset(); + } + + private static MessageContext createSynapseMessageContext( + String payload, SynapseConfiguration config, HashMap transportHeaders, + String address) throws Exception { + org.apache.axis2.context.MessageContext mc = + new org.apache.axis2.context.MessageContext(); + AxisConfiguration axisConfig = config.getAxisConfiguration(); + if (axisConfig == null) { + axisConfig = new AxisConfiguration(); + config.setAxisConfiguration(axisConfig); + } + ConfigurationContext cfgCtx = new ConfigurationContext(axisConfig); + SynapseEnvironment env = new Axis2SynapseEnvironment(cfgCtx, config); + MessageContext synMc = new Axis2MessageContext(mc, config, env); + SOAPEnvelope envelope = + OMAbstractFactory.getSOAP11Factory().getDefaultEnvelope(); + OMDocument omDoc = + OMAbstractFactory.getSOAP11Factory().createOMDocument(); + omDoc.addChild(envelope); + envelope.getBody().addChild(SynapseConfigUtils.stringToOM(payload)); + synMc.setEnvelope(envelope); + synMc.setTo(new EndpointReference(address)); + org.apache.axis2.context.MessageContext axis2MessageContext = + ((Axis2MessageContext) synMc).getAxis2MessageContext(); + axis2MessageContext.setProperty(org.apache.axis2.context.MessageContext.TRANSPORT_HEADERS, transportHeaders); + return synMc; + } + + private void setMockClient() throws NoSuchFieldException, IllegalAccessException { + Field restInvokerField = this.handler.getClass().getDeclaredField("restInvoker"); + restInvokerField.setAccessible(true); + RESTInvoker restInvoker = (RESTInvoker) restInvokerField.get(this.handler); + Field clientField = restInvoker.getClass().getDeclaredField("client"); + clientField.setAccessible(true); + this.mockClient = new MockClient(); + clientField.set(restInvoker, this.mockClient); + } + + private CloseableHttpResponse getDCRResponse() throws IOException { + CloseableHttpResponse mockDCRResponse = new MockHttpResponse(); + String dcrResponseFile = TestUtils.getAbsolutePathOfConfig("dcr-response.json"); + BasicHttpEntity responseEntity = new BasicHttpEntity(); + responseEntity.setContent(new ByteArrayInputStream(getContent(dcrResponseFile). + getBytes(StandardCharsets.UTF_8.name()))); + responseEntity.setContentType(TestUtils.CONTENT_TYPE); + mockDCRResponse.setEntity(responseEntity); + mockDCRResponse.setStatusLine(new BasicStatusLine(new ProtocolVersion("http", 1, 0), 200, "OK")); + return mockDCRResponse; + } + + private CloseableHttpResponse getAccessTokenReponse() throws IOException { + CloseableHttpResponse mockDCRResponse = new MockHttpResponse(); + String dcrResponseFile = TestUtils.getAbsolutePathOfConfig("accesstoken-response.json"); + BasicHttpEntity responseEntity = new BasicHttpEntity(); + responseEntity.setContent(new ByteArrayInputStream(getContent(dcrResponseFile). + getBytes(StandardCharsets.UTF_8.name()))); + responseEntity.setContentType(TestUtils.CONTENT_TYPE); + mockDCRResponse.setEntity(responseEntity); + mockDCRResponse.setStatusLine(new BasicStatusLine(new ProtocolVersion("http", 1, 0), 200, "OK")); + return mockDCRResponse; + } + + private CloseableHttpResponse getValidationResponse() throws UnsupportedEncodingException { + ValidationResponce response = new ValidationResponce(); + response.setDeviceId("1234"); + response.setDeviceType("testdevice"); + response.setJWTToken("1234567788888888"); + response.setTenantId(-1234); + Gson gson = new Gson(); + String jsonReponse = gson.toJson(response); + CloseableHttpResponse mockDCRResponse = new MockHttpResponse(); + BasicHttpEntity responseEntity = new BasicHttpEntity(); + responseEntity.setContent(new ByteArrayInputStream(jsonReponse.getBytes(StandardCharsets.UTF_8.name()))); + responseEntity.setContentType(TestUtils.CONTENT_TYPE); + mockDCRResponse.setEntity(responseEntity); + mockDCRResponse.setStatusLine(new BasicStatusLine(new ProtocolVersion("http", 1, 0), 200, "OK")); + return mockDCRResponse; + } + + private String getContent(String filePath) throws IOException { + FileReader fileReader = new FileReader(filePath); + BufferedReader bufferedReader = new BufferedReader(fileReader); + String content = ""; + String line; + while ((line = bufferedReader.readLine()) != null) { + content += line + "\n"; + } + bufferedReader.close(); + return content; + } +} diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/BaseAPIHandlerTest.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/BaseAPIHandlerTest.java new file mode 100644 index 0000000000..57a293e2eb --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/BaseAPIHandlerTest.java @@ -0,0 +1,60 @@ +/* +* Copyright (c) 2017, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. +* WSO2 Inc. 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 org.wso2.carbon.apimgt.handlers; + +import org.testng.annotations.BeforeSuite; +import org.wso2.carbon.base.MultitenantConstants; +import org.wso2.carbon.context.PrivilegedCarbonContext; + +import java.io.File; + +/** + * This is the base test case for API Handler tests. + */ +public class BaseAPIHandlerTest { + + @BeforeSuite + public void init() { + setUpCarbonHome(); + } + + private void setUpCarbonHome() { + if (System.getProperty("carbon.home") == null) { + File file = new File("src/test/resources/carbon-home"); + if (file.exists()) { + System.setProperty("carbon.home", file.getAbsolutePath()); + } + file = new File("carbon-home"); + if (file.exists()) { + System.setProperty("carbon.home", file.getAbsolutePath()); + } + file = new File("../../resources/carbon-home"); + if (file.exists()) { + System.setProperty("carbon.home", file.getAbsolutePath()); + } + file = new File("../../../resources/carbon-home"); + if (file.exists()) { + System.setProperty("carbon.home", file.getAbsolutePath()); + } + } + PrivilegedCarbonContext.getThreadLocalCarbonContext().setTenantDomain(MultitenantConstants + .SUPER_TENANT_DOMAIN_NAME); + PrivilegedCarbonContext.getThreadLocalCarbonContext().setTenantId(MultitenantConstants.SUPER_TENANT_ID); + } + +} diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/IOTServerConfigurationTest.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/IOTServerConfigurationTest.java new file mode 100644 index 0000000000..84ebc86365 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/IOTServerConfigurationTest.java @@ -0,0 +1,97 @@ +/* +* Copyright (c) 2017, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. +* WSO2 Inc. 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 org.wso2.carbon.apimgt.handlers; + +import org.testng.Assert; +import org.testng.annotations.BeforeClass; +import org.testng.annotations.Test; +import org.wso2.carbon.apimgt.handlers.config.IOTServerConfiguration; +import org.wso2.carbon.apimgt.handlers.utils.Utils; + +import java.io.File; + +/** + * This class validates the behaviour of {@link IOTServerConfiguration} + */ +public class IOTServerConfigurationTest extends BaseAPIHandlerTest { + private static final String CONFIG_DIR = "carbon-home" + File.separator + "repository" + File.separator + + "conf" + File.separator; + + @BeforeClass + public void initTest(){ + TestUtils.resetSystemProperties(); + } + + @Test(description = "Validating the IoT Server configuration initialization without system properties") + public void initConfigWithoutSystemProps() { + IOTServerConfiguration serverConfiguration = Utils.initConfig(); + Assert.assertTrue(serverConfiguration != null); + Assert.assertEquals(serverConfiguration.getHostname(), "https://${iot.core.host}:${iot.core.https.port}/"); + Assert.assertEquals(serverConfiguration.getVerificationEndpoint(), + "https://${iot.core.host}:${iot.core.https.port}/api/certificate-mgt/v1.0/admin/certificates/verify/"); + Assert.assertEquals(serverConfiguration.getUsername(), "testuser"); + Assert.assertEquals(serverConfiguration.getPassword(), "testuserpwd"); + Assert.assertEquals(serverConfiguration.getDynamicClientRegistrationEndpoint(), + "https://${iot.keymanager.host}:${iot.keymanager.https.port}/client-registration/v0.11/register"); + Assert.assertEquals(serverConfiguration.getOauthTokenEndpoint(), + "https://${iot.keymanager.host}:${iot.keymanager.https.port}/oauth2/token"); + Assert.assertEquals(serverConfiguration.getApis().size(), 1); + Assert.assertEquals(serverConfiguration.getApis().get(0).getContextPath(), "/services"); + } + + @Test(description = "Initializing IoT server config with invalid configuration", + dependsOnMethods = "initConfigWithoutSystemProps") + public void initConfigWithInvalidConfig() { + IOTServerConfiguration serverConfig = Utils.initConfig(TestUtils.getAbsolutePathOfConfig(CONFIG_DIR + + "iot-api-config-invalid.xml")); + Assert.assertEquals(serverConfig, null); + } + + @Test(description = "Initializing IoT server config with invalid xml", + dependsOnMethods = "initConfigWithInvalidConfig") + public void initConfigWithInvalidXMLConfig() { + IOTServerConfiguration serverConfig = Utils.initConfig(TestUtils.getAbsolutePathOfConfig(CONFIG_DIR + + "iot-api-config-invalid-xml.xml")); + Assert.assertEquals(serverConfig, null); + } + + @Test(description = "Initializing IoT server config with system configs", + dependsOnMethods = "initConfigWithInvalidXMLConfig") + public void initConfigWithSystemProps() { + TestUtils.setSystemProperties(); + IOTServerConfiguration serverConfiguration = Utils.initConfig(); + Assert.assertTrue(serverConfiguration != null); + Assert.assertEquals(serverConfiguration.getHostname(), "https://" + TestUtils.IOT_CORE_HOST + ":" + + TestUtils.IOT_CORE_HTTPS_PORT + + "/"); + Assert.assertEquals(serverConfiguration.getVerificationEndpoint(), + "https://" + TestUtils.IOT_CORE_HOST + ":" + TestUtils.IOT_CORE_HTTPS_PORT + + "/api/certificate-mgt/v1.0/admin/certificates/" + + "verify/"); + Assert.assertEquals(serverConfiguration.getUsername(), "testuser"); + Assert.assertEquals(serverConfiguration.getPassword(), "testuserpwd"); + Assert.assertEquals(serverConfiguration.getDynamicClientRegistrationEndpoint(), + "https://" + TestUtils.IOT_KEYMANAGER_HOST + ":" + TestUtils.IOT_KEYMANAGER_PORT + + "/client-registration/v0.11/register"); + Assert.assertEquals(serverConfiguration.getOauthTokenEndpoint(), + "https://" + TestUtils.IOT_KEYMANAGER_HOST + ":" + TestUtils.IOT_KEYMANAGER_PORT + + "/oauth2/token"); + Assert.assertEquals(serverConfiguration.getApis().size(), 1); + Assert.assertEquals(serverConfiguration.getApis().get(0).getContextPath(), "/services"); + } +} diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/TestUtils.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/TestUtils.java new file mode 100644 index 0000000000..5b22e1c5d9 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/TestUtils.java @@ -0,0 +1,61 @@ +/* +* Copyright (c) 2017, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. +* WSO2 Inc. 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 org.wso2.carbon.apimgt.handlers; + +import org.testng.Assert; + +import java.io.File; +import java.net.URL; + +/** + * Utils class which provides utility methods for other testcases. + */ +public class TestUtils { + static final String IOT_CORE_HOST = "iot.core.wso2.com"; + static final String IOT_CORE_HTTPS_PORT = "9443"; + static final String IOT_KEYMANAGER_HOST = "iot.keymanager.wso2.com"; + static final String IOT_KEYMANAGER_PORT = "9443"; + static final String CONTENT_TYPE = "application/json"; + + private static final String IOT_HOST_PROPERTY = "iot.core.host"; + private static final String IOT_PORT_PROPERTY = "iot.core.https.port"; + private static final String IOT_KEY_MANAGER_HOST_PROPERTY = "iot.keymanager.host"; + private static final String IOT_KEY_MANAGER_PORT_PROPERTY = "iot.keymanager.https.port"; + + static String getAbsolutePathOfConfig(String configFilePath) { + ClassLoader classLoader = TestUtils.class.getClassLoader(); + URL invalidConfig = classLoader.getResource(configFilePath); + Assert.assertTrue(invalidConfig != null); + File file = new File(invalidConfig.getFile()); + return file.getAbsolutePath(); + } + + static void setSystemProperties() { + System.setProperty(IOT_HOST_PROPERTY, IOT_CORE_HOST); + System.setProperty(IOT_PORT_PROPERTY, IOT_CORE_HTTPS_PORT); + System.setProperty(IOT_KEY_MANAGER_HOST_PROPERTY, IOT_KEYMANAGER_HOST); + System.setProperty(IOT_KEY_MANAGER_PORT_PROPERTY, IOT_KEYMANAGER_PORT); + } + + static void resetSystemProperties() { + System.clearProperty(IOT_HOST_PROPERTY); + System.clearProperty(IOT_PORT_PROPERTY); + System.clearProperty(IOT_KEY_MANAGER_HOST_PROPERTY); + System.clearProperty(IOT_KEY_MANAGER_PORT_PROPERTY); + } +} diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/mock/MockClient.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/mock/MockClient.java new file mode 100644 index 0000000000..6c36969026 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/mock/MockClient.java @@ -0,0 +1,72 @@ +/* +* Copyright (c) 2017, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. +* WSO2 Inc. 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 org.wso2.carbon.apimgt.handlers.mock; + +import org.apache.http.HttpHost; +import org.apache.http.HttpRequest; +import org.apache.http.client.methods.CloseableHttpResponse; +import org.apache.http.conn.ClientConnectionManager; +import org.apache.http.impl.client.CloseableHttpClient; +import org.apache.http.params.HttpParams; +import org.apache.http.protocol.HttpContext; + +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +/** + * Mock implementation for CloseableHttpClient to be used in test cases. + */ +public class MockClient extends CloseableHttpClient { + private List responses = new ArrayList<>(); + private int responseCount = 0; + + @Override + protected CloseableHttpResponse doExecute(HttpHost httpHost, HttpRequest httpRequest, HttpContext httpContext) + throws IOException { + if (this.responseCount < this.responses.size()) { + this.responseCount++; + return this.responses.get(this.responseCount - 1); + } else { + return new MockHttpResponse(); + } + } + + @Override + public void close() throws IOException { + } + + @Override + public HttpParams getParams() { + return null; + } + + @Override + public ClientConnectionManager getConnectionManager() { + return null; + } + + public void setResponse(CloseableHttpResponse reponse) { + this.responses.add(reponse); + } + + public void reset() { + this.responses.clear(); + this.responseCount = 0; + } +} diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/mock/MockHttpResponse.java b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/mock/MockHttpResponse.java new file mode 100644 index 0000000000..adfd7652c5 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/java/org/wso2/carbon/apimgt/handlers/mock/MockHttpResponse.java @@ -0,0 +1,178 @@ +/* +* Copyright (c) 2017, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. +* WSO2 Inc. 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 org.wso2.carbon.apimgt.handlers.mock; + +import org.apache.http.Header; +import org.apache.http.HeaderIterator; +import org.apache.http.HttpEntity; +import org.apache.http.ProtocolVersion; +import org.apache.http.StatusLine; +import org.apache.http.client.methods.CloseableHttpResponse; +import org.apache.http.params.HttpParams; + +import java.io.IOException; +import java.util.Locale; + +/** + * Mock http response to be used in the test cases. + * + */ +public class MockHttpResponse implements CloseableHttpResponse { + private HttpEntity httpEntity; + private StatusLine statusLine; + + @Override + public void close() throws IOException { + + } + + @Override + public StatusLine getStatusLine() { + return this.statusLine; + } + + @Override + public void setStatusLine(StatusLine statusLine) { + this.statusLine = statusLine; + } + + @Override + public void setStatusLine(ProtocolVersion protocolVersion, int i) { + + } + + @Override + public void setStatusLine(ProtocolVersion protocolVersion, int i, String s) { + + } + + @Override + public void setStatusCode(int i) throws IllegalStateException { + + } + + @Override + public void setReasonPhrase(String s) throws IllegalStateException { + + } + + @Override + public HttpEntity getEntity() { + return this.httpEntity; + } + + @Override + public void setEntity(HttpEntity httpEntity) { + this.httpEntity = httpEntity; + } + + @Override + public Locale getLocale() { + return null; + } + + @Override + public void setLocale(Locale locale) { + + } + + @Override + public ProtocolVersion getProtocolVersion() { + return null; + } + + @Override + public boolean containsHeader(String s) { + return false; + } + + @Override + public Header[] getHeaders(String s) { + return new Header[0]; + } + + @Override + public Header getFirstHeader(String s) { + return null; + } + + @Override + public Header getLastHeader(String s) { + return null; + } + + @Override + public Header[] getAllHeaders() { + return new Header[0]; + } + + @Override + public void addHeader(Header header) { + + } + + @Override + public void addHeader(String s, String s1) { + + } + + @Override + public void setHeader(Header header) { + + } + + @Override + public void setHeader(String s, String s1) { + + } + + @Override + public void setHeaders(Header[] headers) { + + } + + @Override + public void removeHeader(Header header) { + + } + + @Override + public void removeHeaders(String s) { + + } + + @Override + public HeaderIterator headerIterator() { + return null; + } + + @Override + public HeaderIterator headerIterator(String s) { + return null; + } + + @Override + public HttpParams getParams() { + return null; + } + + @Override + public void setParams(HttpParams httpParams) { + + } +} diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/accesstoken-response.json b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/accesstoken-response.json new file mode 100644 index 0000000000..11be1e29eb --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/accesstoken-response.json @@ -0,0 +1,7 @@ +{ + "scope": "API_SUBSCRIBER_SCOPE", + "token_type": "Bearer", + "expires_in": 3600, + "refresh_token": "33c3be152ebf0030b3fb76f2c1f80bf8", + "access_token": "292ff0fd256814536baca0926f483c8d" +} \ No newline at end of file diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/carbon.xml b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/carbon.xml new file mode 100644 index 0000000000..31752cf9b4 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/carbon.xml @@ -0,0 +1,656 @@ + + + + + + + + + ${product.name} + + + ${product.key} + + + ${product.version} + + + + + + + + + local:/${carbon.context}/services/ + + + + + + + ${default.server.role} + + + + + + + org.wso2.carbon + + + / + + + + + + + + + 15 + + + + + + + + + 0 + + + + + 9999 + + 11111 + + + + + + 10389 + + 8000 + + + + + + 10500 + + + + + + + org.wso2.carbon.tomcat.jndi.CarbonJavaURLContextFactory + + + + + + + + + java + + + + + + + + + + false + + + false + + + 600 + + + + false + + + + + + + + 30 + + + + + + + + + 15 + + + + + + ${carbon.home}/repository/deployment/server/ + + + 15 + + + ${carbon.home}/repository/conf/axis2/axis2.xml + + + 30000 + + + ${carbon.home}/repository/deployment/client/ + + ${carbon.home}/repository/conf/axis2/axis2_client.xml + + true + + + + + + + + + + admin + Default Administrator Role + + + user + Default User Role + + + + + + + + + + + + ${carbon.home}/repository/resources/security/wso2carbon.jks + + JKS + + wso2carbon + + wso2carbon + + wso2carbon + + + + + + ${carbon.home}/repository/resources/security/client-truststore.jks + + JKS + + wso2carbon + + + + + + + + + + + + + + + + + + + UserManager + + + false + + + + + + + ${carbon.home}/tmp/work + + + + + + true + + + 10 + + + 30 + + + + + + 100 + + + + keystore + certificate + * + + org.wso2.carbon.ui.transports.fileupload.AnyFileUploadExecutor + + + + + jarZip + + org.wso2.carbon.ui.transports.fileupload.JarZipUploadExecutor + + + + dbs + + org.wso2.carbon.ui.transports.fileupload.DBSFileUploadExecutor + + + + tools + + org.wso2.carbon.ui.transports.fileupload.ToolsFileUploadExecutor + + + + toolsAny + + org.wso2.carbon.ui.transports.fileupload.ToolsAnyFileUploadExecutor + + + + + + + info + org.wso2.carbon.core.transports.util.InfoProcessor + + + wsdl + org.wso2.carbon.core.transports.util.Wsdl11Processor + + + wsdl2 + org.wso2.carbon.core.transports.util.Wsdl20Processor + + + xsd + org.wso2.carbon.core.transports.util.XsdProcessor + + + + + + false + false + true + svn + http://svnrepo.example.com/repos/ + username + password + true + + + + + + + + + + + + + + + ${require.carbon.servlet} + + + + + true + + + + + + + default repository + ${p2.repo.url} + + + + + + + + true + + + + + + true + + diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/iot-api-config-invalid-xml.xml b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/iot-api-config-invalid-xml.xml new file mode 100644 index 0000000000..b7519e99ac --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/iot-api-config-invalid-xml.xml @@ -0,0 +1,40 @@ + + + + + + https://${iot.core.host}:${iot.core.https.port}/ + + + https://${iot.core.host}:${iot.core.https.port}/api/certificate-mgt/v1.0/admin/certificates/verify/ + + + testuser + testuserpwd + + + https://${iot.keymanager.host}:${iot.keymanager.https.port}/client-registration/v0.11/register + + + https://${iot.keymanager.host}:${iot.keymanager.https.port}/oauth2/token + + + /services + + + + + + + https://${iot.core.host}:${iot.core.https.port}/ + + + https://${iot.core.host}:${iot.core.https.port}/api/certificate-mgt/v1.0/admin/certificates/verify/ + + + testuser + testuserpwd + + + https://${iot.keymanager.host}:${iot.keymanager.https.port}/client-registration/v0.11/register + + + https://${iot.keymanager.host}:${iot.keymanager.https.port}/oauth2/token + + + /services + + \ No newline at end of file diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/iot-api-config.xml b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/iot-api-config.xml new file mode 100644 index 0000000000..fcb53bd009 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/iot-api-config.xml @@ -0,0 +1,40 @@ + + + + + + https://${iot.core.host}:${iot.core.https.port}/ + + + https://${iot.core.host}:${iot.core.https.port}/api/certificate-mgt/v1.0/admin/certificates/verify/ + + + testuser + testuserpwd + + + https://${iot.keymanager.host}:${iot.keymanager.https.port}/client-registration/v0.11/register + + + https://${iot.keymanager.host}:${iot.keymanager.https.port}/oauth2/token + + + /services + + \ No newline at end of file diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/registry.xml b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/registry.xml new file mode 100644 index 0000000000..a226ae80a8 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/carbon-home/repository/conf/registry.xml @@ -0,0 +1,50 @@ + + + + + + + + wso2registry + false + true + / + + + jdbc:h2:./target/databasetest/CARBON_TEST + + org.h2.Driver + 80 + 60000 + 5 + + + false + + + + true + true + true + true + + diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/dcr-response.json b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/dcr-response.json new file mode 100644 index 0000000000..1672f812d7 --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/dcr-response.json @@ -0,0 +1,6 @@ +{ + "callBackURL": "www.google.lk", + "clientName": null, + "clientId": "HfEl1jJPdg5tbtrxhAwybN05QGoa", + "clientSecret": "l6c0aoLcWR3fwezHhc7XoGOht5Aa" +} \ No newline at end of file diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/ra_cert.pem b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/ra_cert.pem new file mode 100644 index 0000000000..516b08ccee --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/ra_cert.pem @@ -0,0 +1,33 @@ +-----BEGIN CERTIFICATE----- +MIIFqDCCA5CgAwIBAgIBAjANBgkqhkiG9w0BAQUFADCBizELMAkGA1UEBhMCVVMx +DTALBgNVBAgTBFRlc3QxDTALBgNVBAcTBFRlc3QxETAPBgNVBAoTCFRlc3QgT3Jn +MRYwFAYDVQQLEw1UZXN0IG9yZyB1bml0MRUwEwYDVQQDEwxXU08yIFJvb3QgQ0Ex +HDAaBgkqhkiG9w0BCQEWDXJvb3RAd3NvMi5jb20wHhcNMTUwMTI3MTI1MzAxWhcN +MTcxMDIzMTI1MzAxWjCBgzELMAkGA1UEBhMCVVMxGTAXBgNVBAgTEFRlc3QgUkEg +UHJvdmluY2UxFTATBgNVBAcTDFRlc3QgUkEgQ2l0eTEUMBIGA1UEChMLVGVzdCBS +QSBPcmcxGTAXBgNVBAsTEFRlc3QgUkEgb3JnIHVuaXQxETAPBgNVBAMTCFdTTzIg +UkEgMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAtUMgUlYYU3/TPfEe +zNAvBaiOi/jUjfZ9IbxvMl7obDT17/5vU68TCGkZRjyfYUEiGNBisUEFWjSk/sGL +/ofYKUAxw33cd456FLMjaJX/4Zk4y8eYB1m1GGlHejoDyjPhq8S6GDmy+PXbJr8n +lSTROR2mQHkGwYrCreWeU4AYWzdctIFk7U2DKeIvZYSidIIjfSpDXURxrt9LPvig +fMzr5l/WkZfjvk5S+W7rgMtpllxlEPgyDc07pNAdNSq5FB990oaUsVX8o6l6wdCw +grYz83edPOKwZa04fsVztz2oF3ZYSGGjD3lwh0KS/jUL+awRyhMx5p/O1hySg6PP +pJjeqRuobNTuwSAXxp3nsNSY0DkGW04pSxWoDQqhnpaqBbAf71l6ya2e3so1SHm/ +jouWSYTHncq5bmGE4AN7ZGVGZvfx84+UR8fNxJxxLo+DFFE0oJNzpPGNxILpHxgT +V7IOII6mhfkrQk+AFQiW2Y5FXLVYv8r+SPXW8pYsjaWl971XZeM/HC3L9IZkCrrr +a0ID5oT6vt+xTmdo4yiBqIP5TBYm+1a9YzMAy7XGtPih9k6cufMLcfzvUZdOXw9x +3T05nM5ZtcDq0gHvUzQ7sfHTguWVnuHVEdb2ox4x2L5NzEA475fbSdXpMok9z/z7 +Xa71vIZi28InDAFBQehUlJnFtf0CAwEAAaMdMBswDAYDVR0TBAUwAwEB/zALBgNV +HQ8EBAMCBaAwDQYJKoZIhvcNAQEFBQADggIBAAO0TwnQBMJvL8wbfsnTqAGCCHM4 +x1cpW+KgTmflPEliYGOn/dJYDz/dUowCgoj5mrSxjQ3G1/qL+9Y7E33h0tyw37vH +YDL1p2Tn+fwmXRHrk+CHoPHNcImEfSIDWbbG7ehBR6erVfbQSZjmj4fwPkItp8rP +nyUtXHOLpfFYoAxYkNP9+C8vpC9W/H1pj3rzmQFA1z+EZAKVV7vDAxbe6sun84nf +YAaMSIzHx1B+XLHokgChmnZr3wV7EypBEmmKp4ITvJqK7WsIG9t1M6hI7OTPCURR +mdy+DJtIoIUbZxHyIyC9nPcVJFkdBusnfXq4uMb0KMaWYCU8ESqZPySukF2qZ5KA +acB+0ZhY+EGQ6QF/hB6iiUj96BlQ7XAPXFU6xUt6nRjDiJmb3vW1IEv0hpbs7PRl +UMlbOwQk37rXpFqQc6ZW7lsxI2RmfkD4DOkQIGH3q5foVr+PEp0uSPWrFX62eBet +1S4c/opVv6BcuUgilYABHTYxb45GfYwJAI9Qw2uQWT8DmhtVbcYu6GLYGlnRyaOC +EPzc0z0KQTjhsgHWzi60IYBBh+fy+Z7w5X1rTTvhFOoU5J7kedGEqiBatIZmhF5t +UFbT0u350ET5a0Kg83gu5aLwXdoIP9o7bp3XzLBMVNny2RX3tOHUA2HBe/p0h0OU +Ggt3G6oD0gBe9pZI +-----END CERTIFICATE----- diff --git a/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/testng.xml b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/testng.xml new file mode 100644 index 0000000000..2f9882254f --- /dev/null +++ b/components/apimgt-extensions/org.wso2.carbon.apimgt.handlers/src/test/resources/testng.xml @@ -0,0 +1,30 @@ + + + + + + + + + + + + + + diff --git a/components/device-mgt/org.wso2.carbon.device.mgt.analytics.data.publisher/src/test/java/org/wso2/carbon/device/mgt/analytics/data/publisher/DataPublisherConfigTest.java b/components/device-mgt/org.wso2.carbon.device.mgt.analytics.data.publisher/src/test/java/org/wso2/carbon/device/mgt/analytics/data/publisher/DataPublisherConfigTest.java index e5bcab9378..0e04de8a56 100644 --- a/components/device-mgt/org.wso2.carbon.device.mgt.analytics.data.publisher/src/test/java/org/wso2/carbon/device/mgt/analytics/data/publisher/DataPublisherConfigTest.java +++ b/components/device-mgt/org.wso2.carbon.device.mgt.analytics.data.publisher/src/test/java/org/wso2/carbon/device/mgt/analytics/data/publisher/DataPublisherConfigTest.java @@ -32,7 +32,7 @@ import java.net.URL; */ public class DataPublisherConfigTest extends BaseAnalyticsDataPublisherTest { - @Test(description = "Validating the behaviour od getInstance of the config before calling the init", + @Test(description = "Validating the behaviour of getInstance config before calling the init", expectedExceptions = InvalidConfigurationStateException.class) public void testGetInstanceWithoutInit() throws NoSuchFieldException, IllegalAccessException { Field configField = AnalyticsConfiguration.class.getDeclaredField("config"); @@ -41,7 +41,7 @@ public class DataPublisherConfigTest extends BaseAnalyticsDataPublisherTest { AnalyticsConfiguration.getInstance(); } - @Test(description = "Validating the behaviour od getInstance of the config before calling the init", + @Test(description = "Analytics configuration initialization with invalid config", expectedExceptions = DataPublisherConfigurationException.class, dependsOnMethods = "testGetInstanceWithoutInit") public void testInitWithInvalidConfig() throws DataPublisherConfigurationException { @@ -55,7 +55,7 @@ public class DataPublisherConfigTest extends BaseAnalyticsDataPublisherTest { } - @Test(description = "Validating the behaviour od getInstance of the config before calling the init", + @Test(description = "Analytics config initialization with invalid xml", expectedExceptions = DataPublisherConfigurationException.class, dependsOnMethods = "testInitWithInvalidConfig") public void testInitWithInvalidXML() throws DataPublisherConfigurationException { diff --git a/components/test-coverage/pom.xml b/components/test-coverage/pom.xml index bbf6c68d08..9adaf272a2 100644 --- a/components/test-coverage/pom.xml +++ b/components/test-coverage/pom.xml @@ -186,6 +186,9 @@ + + + diff --git a/pom.xml b/pom.xml index 3304b7b587..0b5533ee52 100644 --- a/pom.xml +++ b/pom.xml @@ -1163,7 +1163,12 @@ commons-codec ${version.commons.codec} - + + org.apache.httpcomponents + httpcore + ${apache.http.compnents.core} + test + commons-lang.wso2 commons-lang @@ -1973,6 +1978,9 @@ 2.3.2 + + 4.4.3 + 2.1.7-wso2v7 1.5.11.wso2v15