
com.sun.enterprise.admin.util.HttpConnectorAddress Maven / Gradle / Ivy
The newest version!
/*
* Copyright (c) 2024 Contributors to the Eclipse Foundation.
* Copyright (c) 1997, 2018 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0, which is available at
* http://www.eclipse.org/legal/epl-2.0.
*
* This Source Code may also be made available under the following Secondary
* Licenses when the conditions for such availability set forth in the
* Eclipse Public License v. 2.0 are satisfied: GNU General Public License,
* version 2 with the GNU Classpath Exception, which is available at
* https://www.gnu.org/software/classpath/license.html.
*
* SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
*/
package com.sun.enterprise.admin.util;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.util.Base64;
import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.HttpsURLConnection;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSession;
import javax.net.ssl.SSLSocketFactory;
import javax.net.ssl.TrustManager;
import static java.nio.charset.StandardCharsets.UTF_8;
public final class HttpConnectorAddress {
static final String HTTP_CONNECTOR = "http";
static final String HTTPS_CONNECTOR = "https";
public static final String AUTHORIZATION_KEY = "Authorization";
private static final String AUTHORIZATION_TYPE = "Basic ";
private String host;
private int port;
private String path;
private boolean secure;
private AuthenticationInfo authInfo;
private boolean interactive = true;
private SSLSocketFactory sslSocketFactory;
public HttpConnectorAddress() {
}
public HttpConnectorAddress(String host, int port) {
this(host, port, false);
}
/**
* construct an address which indicates the host, port and security attributes desired.
*
* @param host a host address
* @param port a port number
* @param secure a boolean indication of whether the connection should be secure (i.e. confidential) or not
*/
public HttpConnectorAddress(String host, int port, boolean secure) {
this(host, port, secure, null);
}
public HttpConnectorAddress(String host, int port, boolean secure, String path) {
this(host, port, secure, path, null);
}
public HttpConnectorAddress(String host, int port, SSLSocketFactory sslSocketFactory) {
this(host, port, true /* secure */, null /* path */, sslSocketFactory);
}
public HttpConnectorAddress(String host, int port, boolean secure, String path, SSLSocketFactory sslSocketFactory) {
this.host = host;
this.port = port;
this.secure = secure;
this.path = path;
this.sslSocketFactory = sslSocketFactory;
}
/**
* Open a connection using the reciever and the given path
*
* @param path the path to the required resource (path here is the portion after the hostname:port
portion
* of a URL)
* @return a connection to the required resource. The connection returned may be a sub-class of
* URLConnection
including HttpsURLConnection
. If the sub-class is a
* HttpsURLConnection
then this connection will accept any certificate from any server where the server's
* name matches the host name of this object. Specifically we allows the certificate not to contain the name of
* the server. This is a potential security hole, but is also a usability enhancement.
* @throws IOException if there's a problem in connecting to the resource
*/
public URLConnection openConnection(String path) throws IOException {
if (path == null || path.isBlank()) {
path = this.path;
}
final URLConnection cnx = this.openConnection(this.toURL(path));
if (!(cnx instanceof HttpsURLConnection)) {
return cnx;
}
configureSSL((HttpsURLConnection) cnx);
return cnx;
}
private void configureSSL(final HttpsURLConnection httpsCnx) throws IOException {
httpsCnx.setHostnameVerifier(new BasicHostnameVerifier(this.host));
httpsCnx.setSSLSocketFactory(getOrCreateSSLSocketFactory());
}
private synchronized SSLSocketFactory getOrCreateSSLSocketFactory() throws IOException {
/*
* The SSL socket factory will have been assigned a value if this
* connection was made from the DAS or an instance...that code would have
* used the constructor which accepts an SSLSocketFactory as an argument.
* (That socket factory should provide client authentication.)
*
* If that value is null then this connection is originating from
* somewhere else - such as asadmin - and the socket factory should be
* the one which uses SSL but does not provide client auth.
*/
if (sslSocketFactory == null) {
sslSocketFactory = createAdminSSLSocketFactory(null, null);
}
return sslSocketFactory;
}
private SSLSocketFactory createAdminSSLSocketFactory(String alias, String protocol) {
try {
if (protocol == null) {
protocol = "TLS";
}
SSLContext cntxt = SSLContext.getInstance(protocol);
/*
* Pass null for the array of KeyManagers. That uses the default
* ones, so if the user has loaded client keys into the standard
* Java SE keystore they will be found.
*/
AsadminTrustManager atm = new AsadminTrustManager();
atm.setInteractive(interactive);
cntxt.init(null, new TrustManager[] { atm }, null);
return cntxt.getSocketFactory();
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* get the protocol prefix to be used for a connection for the receiver
*
* @return the protocol prefix - one of http
or https
depending upon the security setting.
*/
public String getConnectorType() {
return this.isSecure() ? HTTPS_CONNECTOR : HTTP_CONNECTOR;
}
public String getHost() {
return host;
}
public void setHost(String host) {
this.host = host;
}
public int getPort() {
return port;
}
public void setPort(int port) {
this.port = port;
}
public String getPath() {
return path == null ? "/" : path;
}
public void setPath(String path) {
this.path = path;
}
public AuthenticationInfo getAuthenticationInfo() {
return authInfo;
}
public void setAuthenticationInfo(AuthenticationInfo authInfo) {
this.authInfo = authInfo;
}
/**
* Set the security attribute
*/
public void setSecure(boolean secure) {
this.secure = secure;
}
/**
* Indicate if the receiver represents a secure address
*/
public boolean isSecure() {
return secure;
}
/**
* Set the interactive mode for the connection.
*/
public void setInteractive(boolean mode) {
interactive = mode;
}
public URL toURL(String path) throws MalformedURLException {
return new URL(getConnectorType(), getHost(), getPort(), path == null ? "" : path);
}
public synchronized SSLSocketFactory getSSLSocketFactory() {
return sslSocketFactory;
}
private String getUser() {
return authInfo != null ? authInfo.getUser() : "";
}
private char[] getPassword() {
return authInfo != null ? authInfo.getPassword() : "".toCharArray();
}
private URLConnection openConnection(URL url) throws IOException {
return this.setOptions(this.makeConnection(url));
}
private URLConnection makeConnection(URL url) throws IOException {
return (url.openConnection());
}
private URLConnection setOptions(URLConnection uc) {
uc.setDoOutput(true);
uc.setUseCaches(false);
//uc.setRequestProperty("Content-type", "application/octet-stream");
uc.setRequestProperty("Connection", "Keep-Alive");
return this.setAuthentication(uc);
}
private URLConnection setAuthentication(URLConnection uc) {
if (authInfo != null) {
uc.setRequestProperty(AUTHORIZATION_KEY, this.getBasicAuthString());
}
return uc;
}
public String getBasicAuthString() {
String user = this.getUser();
String pass = this.getPassword() == null ? null : new String(this.getPassword());
String up = user == null ? "" : user;
String pp = pass == null ? "" : pass;
String cs = up + ":" + pp;
String enc = Base64.getEncoder().encodeToString(cs.getBytes(UTF_8));
return AUTHORIZATION_TYPE + enc;
}
public static class BasicHostnameVerifier implements HostnameVerifier {
private final String host;
public BasicHostnameVerifier(String host) {
if (host == null) {
throw new IllegalArgumentException("null host");
}
this.host = host;
}
@Override
public boolean verify(String s, SSLSession sslSession) {
return host.equals(s);
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy