Adding HTTPS support for UCS, refactored code for o.a.c.httpclient.contrib

CLOUDSTACK-3285
UCS: Need support for HTTP redirects and HTTPS Certificate handling
This commit is contained in:
Amogh Vasekar 2013-07-23 12:47:44 -07:00 committed by frank
parent 28855b4987
commit a47faa9d28
3 changed files with 45 additions and 17 deletions

View File

@ -5,9 +5,9 @@
// 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
@ -17,26 +17,50 @@
//
package com.cloud.ucs.manager;
import org.apache.commons.httpclient.Header;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.URI;
import org.apache.commons.httpclient.contrib.ssl.EasySSLProtocolSocketFactory;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.methods.StringRequestEntity;
import org.apache.commons.httpclient.protocol.Protocol;
import com.cloud.utils.exception.CloudRuntimeException;
public class UcsHttpClient {
private static HttpClient client = new HttpClient();
private String url;
private static Protocol ucsHttpsProtocol = new org.apache.commons.httpclient.protocol.Protocol("https", new EasySSLProtocolSocketFactory(), 443);
private final String url;
public UcsHttpClient(String ip) {
this.url = String.format("http://%s/nuova", ip);
url = String.format("http://%s/nuova", ip);
Protocol.registerProtocol("https", ucsHttpsProtocol);
}
public String call(String xml) {
PostMethod post = new PostMethod(url);
post.setRequestEntity(new StringRequestEntity(xml));
post.setRequestHeader("Content-type", "text/xml");
//post.setFollowRedirects(true);
try {
int result = client.executeMethod(post);
if (result == 302) {
// Handle HTTPS redirect
// Ideal way might be to configure from add manager API
// for using either HTTP / HTTPS
// Allow only one level of redirect
String redirectLocation;
Header locationHeader = post.getResponseHeader("location");
if (locationHeader != null) {
redirectLocation = locationHeader.getValue();
}
else {
throw new CloudRuntimeException("Call failed: Bad redirect from UCS Manager");
}
post.setURI(new URI(redirectLocation));
result = client.executeMethod(post);
}
// Check for errors
if (result != 200) {
throw new CloudRuntimeException("Call failed: " + post.getResponseBodyAsString());
}

View File

@ -32,21 +32,22 @@ import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import javax.net.ssl.TrustManagerFactory;
import javax.net.ssl.TrustManager;
import javax.net.ssl.TrustManagerFactory;
import javax.net.ssl.X509TrustManager;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
/**
* <p>
* EasyX509TrustManager unlike default {@link X509TrustManager} accepts
* self-signed certificates.
* EasyX509TrustManager unlike default {@link X509TrustManager} accepts
* self-signed certificates.
* </p>
* <p>
* This trust manager SHOULD NOT be used for productive systems
* due to security reasons, unless it is a concious decision and
* you are perfectly aware of security implications of accepting
* This trust manager SHOULD NOT be used for productive systems
* due to security reasons, unless it is a concious decision and
* you are perfectly aware of security implications of accepting
* self-signed certificates
* </p>
*
@ -78,20 +79,22 @@ public class EasyX509TrustManager implements X509TrustManager
if (trustmanagers.length == 0) {
throw new NoSuchAlgorithmException("no trust manager found");
}
this.standardTrustManager = (X509TrustManager)trustmanagers[0];
standardTrustManager = (X509TrustManager)trustmanagers[0];
}
/**
* @see javax.net.ssl.X509TrustManager#checkClientTrusted(X509Certificate[],String authType)
*/
public void checkClientTrusted(X509Certificate[] certificates,String authType) throws CertificateException {
standardTrustManager.checkClientTrusted(certificates,authType);
@Override
public void checkClientTrusted(X509Certificate[] certificates, String authType) throws CertificateException {
standardTrustManager.checkClientTrusted(certificates, authType);
}
/**
* @see javax.net.ssl.X509TrustManager#checkServerTrusted(X509Certificate[],String authType)
*/
public void checkServerTrusted(X509Certificate[] certificates,String authType) throws CertificateException {
@Override
public void checkServerTrusted(X509Certificate[] certificates, String authType) throws CertificateException {
if ((certificates != null) && LOG.isDebugEnabled()) {
LOG.debug("Server certificate chain:");
for (int i = 0; i < certificates.length; i++) {
@ -101,14 +104,15 @@ public class EasyX509TrustManager implements X509TrustManager
if ((certificates != null) && (certificates.length == 1)) {
certificates[0].checkValidity();
} else {
standardTrustManager.checkServerTrusted(certificates,authType);
standardTrustManager.checkServerTrusted(certificates, authType);
}
}
/**
* @see javax.net.ssl.X509TrustManager#getAcceptedIssuers()
*/
@Override
public X509Certificate[] getAcceptedIssuers() {
return this.standardTrustManager.getAcceptedIssuers();
return standardTrustManager.getAcceptedIssuers();
}
}