From 1048f0508ffdb1cb996509f9ff10596527fdb03b Mon Sep 17 00:00:00 2001 From: Keith Armstrong Date: Wed, 18 Dec 2024 16:12:28 +0000 Subject: [PATCH] Initial commit --- .gitignore | 29 ++ .idea/.gitignore | 3 + .idea/artifacts/soapClient_jar.xml | 9 + .idea/libraries/jcommander_1_27.xml | 9 + .idea/misc.xml | 6 + .idea/modules.xml | 8 + .idea/vcs.xml | 6 + lib/jcommander-1.27.jar | Bin 0 -> 55585 bytes soapClient.iml | 12 + src/META-INF/MANIFEST.MF | 3 + src/com/belkast/soap/Base64.java | 396 ++++++++++++++++++ src/com/belkast/soap/Parser.java | 30 ++ src/com/belkast/soap/Protector.java | 39 ++ .../belkast/soap/SpaceParameterSplitter.java | 14 + src/com/belkast/soap/Webservice.java | 386 +++++++++++++++++ 15 files changed, 950 insertions(+) create mode 100644 .gitignore create mode 100644 .idea/.gitignore create mode 100644 .idea/artifacts/soapClient_jar.xml create mode 100644 .idea/libraries/jcommander_1_27.xml create mode 100644 .idea/misc.xml create mode 100644 .idea/modules.xml create mode 100644 .idea/vcs.xml create mode 100644 lib/jcommander-1.27.jar create mode 100644 soapClient.iml create mode 100644 src/META-INF/MANIFEST.MF create mode 100644 src/com/belkast/soap/Base64.java create mode 100644 src/com/belkast/soap/Parser.java create mode 100644 src/com/belkast/soap/Protector.java create mode 100644 src/com/belkast/soap/SpaceParameterSplitter.java create mode 100644 src/com/belkast/soap/Webservice.java diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..f68d109 --- /dev/null +++ b/.gitignore @@ -0,0 +1,29 @@ +### IntelliJ IDEA ### +out/ +!**/src/main/**/out/ +!**/src/test/**/out/ + +### Eclipse ### +.apt_generated +.classpath +.factorypath +.project +.settings +.springBeans +.sts4-cache +bin/ +!**/src/main/**/bin/ +!**/src/test/**/bin/ + +### NetBeans ### +/nbproject/private/ +/nbbuild/ +/dist/ +/nbdist/ +/.nb-gradle/ + +### VS Code ### +.vscode/ + +### Mac OS ### +.DS_Store \ No newline at end of file diff --git a/.idea/.gitignore b/.idea/.gitignore new file mode 100644 index 0000000..26d3352 --- /dev/null +++ b/.idea/.gitignore @@ -0,0 +1,3 @@ +# Default ignored files +/shelf/ +/workspace.xml diff --git a/.idea/artifacts/soapClient_jar.xml b/.idea/artifacts/soapClient_jar.xml new file mode 100644 index 0000000..893c068 --- /dev/null +++ b/.idea/artifacts/soapClient_jar.xml @@ -0,0 +1,9 @@ + + + $PROJECT_DIR$/out/artifacts/soapClient_jar + + + + + + \ No newline at end of file diff --git a/.idea/libraries/jcommander_1_27.xml b/.idea/libraries/jcommander_1_27.xml new file mode 100644 index 0000000..435c5f6 --- /dev/null +++ b/.idea/libraries/jcommander_1_27.xml @@ -0,0 +1,9 @@ + + + + + + + + + \ No newline at end of file diff --git a/.idea/misc.xml b/.idea/misc.xml new file mode 100644 index 0000000..03f397c --- /dev/null +++ b/.idea/misc.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/.idea/modules.xml b/.idea/modules.xml new file mode 100644 index 0000000..eb791b6 --- /dev/null +++ b/.idea/modules.xml @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/.idea/vcs.xml b/.idea/vcs.xml new file mode 100644 index 0000000..94a25f7 --- /dev/null +++ b/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/lib/jcommander-1.27.jar b/lib/jcommander-1.27.jar new file mode 100644 index 0000000000000000000000000000000000000000..f94909022a9ed96c16f8c15a165d0aa045394fa5 GIT binary patch literal 55585 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 + + + + + + + + + + + \ No newline at end of file diff --git a/src/META-INF/MANIFEST.MF b/src/META-INF/MANIFEST.MF new file mode 100644 index 0000000..3375b0c --- /dev/null +++ b/src/META-INF/MANIFEST.MF @@ -0,0 +1,3 @@ +Manifest-Version: 1.0 +Main-Class: com.belkast.soap.Webservice + diff --git a/src/com/belkast/soap/Base64.java b/src/com/belkast/soap/Base64.java new file mode 100644 index 0000000..8c820de --- /dev/null +++ b/src/com/belkast/soap/Base64.java @@ -0,0 +1,396 @@ +/* + * To change this template, choose Tools | Templates + * and open the template in the editor. + */ +package com.belkast.soap; + +/** + * + * @author Keith + */ +public class Base64 { + + +//The line separator string of the operating system. + +private static final String systemLineSeparator = System.getProperty("line.separator"); + + + +//Mapping table from 6-bit nibbles to Base64 characters. + +private static char[] map1 = new char[64]; + +static { + + int i=0; + + for (char c='A'; c<='Z'; c++) map1[i++] = c; + + for (char c='a'; c<='z'; c++) map1[i++] = c; + + for (char c='0'; c<='9'; c++) map1[i++] = c; + + map1[i++] = '+'; map1[i++] = '/'; } + + + +//Mapping table from Base64 characters to 6-bit nibbles. + +private static byte[] map2 = new byte[128]; + +static { + + for (int i=0; isun.misc.BASE64Encoder.encodeBuffer(byte[]). + +* @param in An array containing the data bytes to be encoded. + +* @return A String containing the Base64 encoded data, broken into lines. + +*/ + +public static String encodeLines (byte[] in) { + +return encodeLines(in, 0, in.length, 76, systemLineSeparator); } + + + +/** + +* Encodes a byte array into Base 64 format and breaks the output into lines. + +* @param in An array containing the data bytes to be encoded. + +* @param iOff Offset of the first byte in in to be processed. + +* @param iLen Number of bytes to be processed in in, starting at iOff. + +* @param lineLen Line length for the output data. Should be a multiple of 4. + +* @param lineSeparator The line separator to be used to separate the output lines. + +* @return A String containing the Base64 encoded data, broken into lines. + +*/ + +public static String encodeLines (byte[] in, int iOff, int iLen, int lineLen, String lineSeparator) { + +int blockLen = (lineLen*3) / 4; + +if (blockLen <= 0) throw new IllegalArgumentException(); + +int lines = (iLen+blockLen-1) / blockLen; + +int bufLen = ((iLen+2)/3)*4 + lines*lineSeparator.length(); + +StringBuilder buf = new StringBuilder(bufLen); + +int ip = 0; + +while (ip < iLen) { + + int l = Math.min(iLen-ip, blockLen); + + buf.append (encode(in, iOff+ip, l)); + + buf.append (lineSeparator); + + ip += l; } + +return buf.toString(); } + + + +/** + +* Encodes a byte array into Base64 format. + +* No blanks or line breaks are inserted in the output. + +* @param in An array containing the data bytes to be encoded. + +* @return A character array containing the Base64 encoded data. + +*/ + +public static char[] encode (byte[] in) { + +return encode(in, 0, in.length); } + + + +/** + +* Encodes a byte array into Base64 format. + +* No blanks or line breaks are inserted in the output. + +* @param in An array containing the data bytes to be encoded. + +* @param iLen Number of bytes to process in in. + +* @return A character array containing the Base64 encoded data. + +*/ + +public static char[] encode (byte[] in, int iLen) { + +return encode(in, 0, iLen); } + + + +/** + +* Encodes a byte array into Base64 format. + +* No blanks or line breaks are inserted in the output. + +* @param in An array containing the data bytes to be encoded. + +* @param iOff Offset of the first byte in in to be processed. + +* @param iLen Number of bytes to process in in, starting at iOff. + +* @return A character array containing the Base64 encoded data. + +*/ + +public static char[] encode (byte[] in, int iOff, int iLen) { + +int oDataLen = (iLen*4+2)/3; // output length without padding + +int oLen = ((iLen+2)/3)*4; // output length including padding + +char[] out = new char[oLen]; + +int ip = iOff; + +int iEnd = iOff + iLen; + +int op = 0; + +while (ip < iEnd) { + + int i0 = in[ip++] & 0xff; + + int i1 = ip < iEnd ? in[ip++] & 0xff : 0; + + int i2 = ip < iEnd ? in[ip++] & 0xff : 0; + + int o0 = i0 >>> 2; + + int o1 = ((i0 & 3) << 4) | (i1 >>> 4); + + int o2 = ((i1 & 0xf) << 2) | (i2 >>> 6); + + int o3 = i2 & 0x3F; + + out[op++] = map1[o0]; + + out[op++] = map1[o1]; + + out[op] = op < oDataLen ? map1[o2] : '='; op++; + + out[op] = op < oDataLen ? map1[o3] : '='; op++; } + +return out; } + + + +/** + +* Decodes a string from Base64 format. + +* No blanks or line breaks are allowed within the Base64 encoded input data. + +* @param s A Base64 String to be decoded. + +* @return A String containing the decoded data. + +* @throws IllegalArgumentException If the input is not valid Base64 encoded data. + +*/ + +public static String decodeString (String s) { + +return new String(decode(s)); } + + + +/** + +* Decodes a byte array from Base64 format and ignores line separators, tabs and blanks. + +* CR, LF, Tab and Space characters are ignored in the input data. + +* This method is compatible with sun.misc.BASE64Decoder.decodeBuffer(String). + +* @param s A Base64 String to be decoded. + +* @return An array containing the decoded data bytes. + +* @throws IllegalArgumentException If the input is not valid Base64 encoded data. + +*/ + +public static byte[] decodeLines (String s) { + +char[] buf = new char[s.length()]; + +int p = 0; + +for (int ip = 0; ip < s.length(); ip++) { + + char c = s.charAt(ip); + + if (c != ' ' && c != '\r' && c != '\n' && c != '\t') + + buf[p++] = c; } + +return decode(buf, 0, p); } + + + +/** + +* Decodes a byte array from Base64 format. + +* No blanks or line breaks are allowed within the Base64 encoded input data. + +* @param s A Base64 String to be decoded. + +* @return An array containing the decoded data bytes. + +* @throws IllegalArgumentException If the input is not valid Base64 encoded data. + +*/ + +public static byte[] decode (String s) { + +return decode(s.toCharArray()); } + + + +/** + +* Decodes a byte array from Base64 format. + +* No blanks or line breaks are allowed within the Base64 encoded input data. + +* @param in A character array containing the Base64 encoded data. + +* @return An array containing the decoded data bytes. + +* @throws IllegalArgumentException If the input is not valid Base64 encoded data. + +*/ + +public static byte[] decode (char[] in) { + +return decode(in, 0, in.length); } + + + +/** + +* Decodes a byte array from Base64 format. + +* No blanks or line breaks are allowed within the Base64 encoded input data. + +* @param in A character array containing the Base64 encoded data. + +* @param iOff Offset of the first character in in to be processed. + +* @param iLen Number of characters to process in in, starting at iOff. + +* @return An array containing the decoded data bytes. + +* @throws IllegalArgumentException If the input is not valid Base64 encoded data. + +*/ + +public static byte[] decode (char[] in, int iOff, int iLen) { + +if (iLen%4 != 0) throw new IllegalArgumentException ("Length of Base64 encoded input string is not a multiple of 4."); + +while (iLen > 0 && in[iOff+iLen-1] == '=') iLen--; + +int oLen = (iLen*3) / 4; + +byte[] out = new byte[oLen]; + +int ip = iOff; + +int iEnd = iOff + iLen; + +int op = 0; + +while (ip < iEnd) { + + int i0 = in[ip++]; + + int i1 = in[ip++]; + + int i2 = ip < iEnd ? in[ip++] : 'A'; + + int i3 = ip < iEnd ? in[ip++] : 'A'; + + if (i0 > 127 || i1 > 127 || i2 > 127 || i3 > 127) + + throw new IllegalArgumentException ("Illegal character in Base64 encoded data."); + + int b0 = map2[i0]; + + int b1 = map2[i1]; + + int b2 = map2[i2]; + + int b3 = map2[i3]; + + if (b0 < 0 || b1 < 0 || b2 < 0 || b3 < 0) + + throw new IllegalArgumentException ("Illegal character in Base64 encoded data."); + + int o0 = ( b0 <<2) | (b1>>>4); + + int o1 = ((b1 & 0xf)<<4) | (b2>>>2); + + int o2 = ((b2 & 3)<<6) | b3; + + out[op++] = (byte)o0; + + if (op parameters = new ArrayList(); + + @Parameter(names = "--props" , description = "Location of the Properties file") + public String varPropertiesFile; + + @Parameter(names = "--key" , description = "Key used for encryption", required = true) + public String varKey; + + @Parameter(names = "--encrypt", description = "Encrypt this value using the Key") + public String varEncrypt; + + @Parameter(names = "--replace", description = "Tokens for which to search", variableArity = true, splitter = SpaceParameterSplitter.class) + public List varTokens = new ArrayList(); + + @Parameter(names = "--help", description = "print this message", help = true) + public boolean help; + + @Parameter(names = "--debug", description = "Used to debug the program") + public String debug; +} diff --git a/src/com/belkast/soap/Protector.java b/src/com/belkast/soap/Protector.java new file mode 100644 index 0000000..d4df7c5 --- /dev/null +++ b/src/com/belkast/soap/Protector.java @@ -0,0 +1,39 @@ +package com.belkast.soap; + +import java.security.Key; +import javax.crypto.Cipher; +import javax.crypto.spec.SecretKeySpec; + +public class Protector + { + private static final String ALGORITHM = "AES"; + + public static char[] encrypt(byte[] varKey, String valueToEnc) throws Exception + { + System.out.println("## Encrypting password ##"); + Key key = generateKey(varKey); + Cipher c = Cipher.getInstance("AES"); + c.init(1, key); + byte[] encValue = c.doFinal(valueToEnc.getBytes()); + char[] encryptedValue = Base64.encode(encValue); + return encryptedValue; + } + + public static String decrypt(byte[] varKey, String encryptedValue) throws Exception + { + System.out.println("## Decrypting password ##"); + Key key = generateKey(varKey); + Cipher c = Cipher.getInstance("AES"); + c.init(2, key); + byte[] decordedValue = Base64.decode(encryptedValue); + byte[] decValue = c.doFinal(decordedValue); + String decryptedValue = new String(decValue); + return decryptedValue; + } + + private static Key generateKey(byte[] varKey) throws Exception + { + Key key = new SecretKeySpec(varKey, "AES"); + return key; + } + } \ No newline at end of file diff --git a/src/com/belkast/soap/SpaceParameterSplitter.java b/src/com/belkast/soap/SpaceParameterSplitter.java new file mode 100644 index 0000000..2ef5a9f --- /dev/null +++ b/src/com/belkast/soap/SpaceParameterSplitter.java @@ -0,0 +1,14 @@ +package com.belkast.soap; + +import com.beust.jcommander.converters.*; + +import java.util.Arrays; +import java.util.List; + +public class SpaceParameterSplitter implements IParameterSplitter + { + public List split(String value) + { + return Arrays.asList(value.split("###")); + } + } diff --git a/src/com/belkast/soap/Webservice.java b/src/com/belkast/soap/Webservice.java new file mode 100644 index 0000000..8362c76 --- /dev/null +++ b/src/com/belkast/soap/Webservice.java @@ -0,0 +1,386 @@ + package com.belkast.soap; + + import java.io.BufferedReader; + import java.io.ByteArrayOutputStream; + import java.io.File; + import java.io.FileInputStream; + import java.io.FileReader; + import java.io.IOException; + import java.io.InputStreamReader; + import java.io.OutputStream; + import java.io.PrintStream; + import java.io.BufferedWriter; + import java.io.FileWriter; + import java.net.HttpURLConnection; + import java.net.URL; + import java.net.URLConnection; + import java.text.SimpleDateFormat; + import java.util.*; + import java.util.Map.Entry; + import javax.net.ssl.HostnameVerifier; + import javax.net.ssl.HttpsURLConnection; + import javax.net.ssl.SSLSession; + + import com.beust.jcommander.*; + + public class Webservice + { + private static Boolean varDebug; + + private static String varDebugToFile = "false"; + + private static String varPassword; + private static String programStatus; + + private static String NEW_STATUS = null; + + public static void main(String[] args) throws Exception + { + try + { + soapResponse(args); + } + catch(Exception ex) + { + throw new RuntimeException(ex); + } + } + + public static String soapResponse(String[] args) throws Exception + { + + SimpleDateFormat varFormat = new SimpleDateFormat("HH:mm:ss.SSS"); + + Date dateStart = new Date(); + + System.out.println("\nStart Time: " + varFormat.format(dateStart) + ""); + + Parser commandLine = new Parser(); + JCommander jct = new JCommander (commandLine); + File configFilePath = new File(""); + try + { + jct.parse(args); + } + catch (ParameterException ex) + { + System.out.println(ex.getMessage()); + jct.usage(); + } + + if (commandLine.varKey != null && commandLine.varEncrypt != null) + { + varPassword = encryptPassword(commandLine.varKey, commandLine.varEncrypt); + return ""; + } + + if (commandLine.varPropertiesFile == null) + { + programStatus = "Properties file not valid"; + return programStatus; + } + + varDebug = Boolean.parseBoolean(commandLine.debug); + + System.out.println("Debug is: " + varDebug.toString() + ""); + + try + { + configFilePath = new File(commandLine.varPropertiesFile); + FileReader fileReader = new FileReader(configFilePath); + } + catch (IOException e) + { + programStatus = e.toString(); + return programStatus; + } + + String varDelimiter = readProperty(varDebug, configFilePath, "ARGUMENT_DELIMITER"); + varDebugToFile = readProperty(varDebug, configFilePath, "DEBUG_TO_FILE"); + + debugMessage(varDebug, "==================== START ====================", varDebugToFile); + debugMessage(varDebug, "Start Time: " + varFormat.format(dateStart), varDebugToFile); + + HashMap hashMap = generateHashMap(commandLine.varTokens.size(), varDelimiter, commandLine.varTokens); + + System.out.println(); + String varURL = readProperty(varDebug, configFilePath, "SHIM_URL"); + String varInputFile = readProperty(varDebug, configFilePath, "INPUT_FILE"); + String varUsername = readProperty(varDebug, configFilePath, "USERNAME"); + String varPasswordTemp = readProperty(varDebug, configFilePath, "PASSWORD"); + + String varUseSSL = readProperty(varDebug, configFilePath, "SSL"); + + String varKeystore_LOC = readProperty(varDebug, configFilePath, "JAVA_KS_LOCATION"); + String varKeystore_PW = readProperty(varDebug, configFilePath, "JAVA_KS_PASSWORD"); + + try + { + varPassword = Protector.decrypt(commandLine.varKey.getBytes(), varPasswordTemp); + } + catch (Exception e) + { + programStatus = e.toString(); + return programStatus; + } + + if ((varURL.equalsIgnoreCase("")) || (varInputFile.equalsIgnoreCase(""))) + { + programStatus = "Properties file " + configFilePath.toString() + " is not valid"; + return programStatus; + } + + System.out.println(); + + String varDocument = readTextFile(varInputFile, hashMap); + if (varDocument.length() > 0) + { + String response = writeMessage(varUsername, varPassword, varURL, varInputFile, varUseSSL, varKeystore_LOC, varKeystore_PW, hashMap, varDocument.getBytes()); + System.out.println(); + System.out.println("SOAP Document received: " + response + ""); + + debugMessage(varDebug, "SOAP Document received: " + response, varDebugToFile); + + Date dateEnd = new Date(); + + System.out.println("\nEnd Time: " + varFormat.format(dateEnd) + ""); + debugMessage(varDebug, "End Time: " + varFormat.format(dateEnd), varDebugToFile); + debugMessage(varDebug, "==================== FINISH ====================", varDebugToFile); + + if (programStatus == null) + { + return "WS response: " + response; + } + } + + return programStatus; + + } + + private static String debugMessage(Boolean varLevel, String varMessage, String varDebugToFile) + { +// System.out.println("I AM HERE [" + varMessage + "]"); + + if (varLevel.booleanValue() == true) + { + System.out.println(varMessage); + } + + if (varDebugToFile.equalsIgnoreCase("true")) + { + File file = new File("debug.log"); + try + { + //if file doesnt exists, then create it + if (!file.exists()) + { + System.out.println("Creating a new file!"); + file.createNewFile(); + } + + BufferedWriter bw = null; + bw = new BufferedWriter(new FileWriter(file, true)); + bw.write(varMessage); + bw.newLine(); + bw.flush(); + bw.close(); + } + catch (IOException e) + { + return programStatus; + } + } + + return "OK"; + } + + private static HashMap generateHashMap(Integer size, String delimiter, List tokens) throws Exception + { + + System.out.println("\n## Generating a HashMap based on " + tokens.toString() + " ##"); + String[] argumentsArray = new String[size]; + HashMap hashMap = new HashMap(); + + System.out.println("Token size " + size.toString() + ""); + + + for (int i = 0; i < size; i++) + { + argumentsArray[i] = tokens.get(i); + System.out.println("Token [" + i + "]: " + argumentsArray[i] + ""); + + String words[] = argumentsArray[i].split(delimiter); + + if (words.length != 2) + continue; + System.out.println("hashMap: " + words[0] + " and " + words[1] + ""); + hashMap.put(words[0], words[1]); + } + debugMessage(varDebug, "Array Size " + argumentsArray.length + "", varDebugToFile); + debugMessage(varDebug, "HashMap contains " + hashMap.size() + " key value pairs", varDebugToFile); + + return hashMap; + } + + private static String encryptPassword(String tempKey, String varPassword) throws Exception + { + char[] varPasswordIn = new char[0]; + Integer validKeyLength = 15; + + System.out.println("\n## Generating an encrypted password ##"); + try + { + tempKey.charAt(validKeyLength); + byte[] thisKey = tempKey.getBytes(); + System.out.println("Key to use: " + new String(thisKey)); + System.out.println("Value to encrypt: " + varPassword); + varPasswordIn = Protector.encrypt(thisKey, varPassword); + System.out.println("Encrypted value: " + new String(varPasswordIn)); + String varPasswordOut = Protector.decrypt(thisKey, new String(varPasswordIn)); + System.out.println("Test Decrypted value: " + varPasswordOut); + } + catch(Exception e) + { + e.printStackTrace(); + } + + return varPasswordIn.toString(); + } + + public static String readProperty(Boolean varDebug, File MyFile, String varProperty) throws Exception + { + Properties props = new Properties(); + String propertyValue = ""; + + if (varProperty.equals("SHOW_DEBUG")) + { + varDebug = true; + } + try + { + props.load(new FileInputStream(MyFile)); + propertyValue = props.getProperty(varProperty); + if (propertyValue == null) + { + propertyValue = ""; + } + debugMessage(varDebug, "Reading properties file for " + varProperty + ", got " + propertyValue + "", varDebugToFile); + } + catch (Exception e) + { + e.printStackTrace(); + } + return propertyValue; + } + + public static String readTextFile(String fullPathFilename, HashMap hashMap) throws IOException + { + System.out.println("## Preparing the SOAP document ##"); + StringBuilder sb = new StringBuilder(43); + try + { + File myFile = new File(fullPathFilename); + FileReader fileReader = new FileReader(myFile); + BufferedReader reader = new BufferedReader(fileReader); + String line; + while ((line = reader.readLine()) != null) + { + sb.append(line); + } + reader.close(); + } + catch (IOException e) + { + e.printStackTrace(); + return (""); + } + + String returnString = sb.toString(); + + Set set = hashMap.entrySet(); + Iterator i = set.iterator(); + while (i.hasNext()) + { + Map.Entry me = (Map.Entry)i.next(); + System.out.println("Replacing " + me.getKey().toString() + " with " + me.getValue().toString() + ""); + + debugMessage(varDebug, "Replacing " + me.getKey().toString() + " with " + me.getValue().toString(), varDebugToFile); + + returnString = returnString.replaceAll(me.getKey().toString(), me.getValue().toString()); + } + + System.out.println("SOAP Document to send: " + returnString + ""); + + debugMessage(varDebug, "SOAP Document to send: " + returnString, varDebugToFile); + + return returnString; + } + + public static String writeMessage(String username, String password, String varURL, String varInputFile, String varUseSSL, String thisKeystore, String thisPassword, HashMap hashMap, byte[] document) throws Exception + { + programStatus = NEW_STATUS; + + StringBuilder response = new StringBuilder(500); + String login = username + ":" + password; + String encoding = Base64.encodeString(login); + + URL url = new URL(varURL); + + try { + System.out.println("\n## Sending SOAP Document ##"); + + if ( Boolean.parseBoolean(varUseSSL) ) + { + System.setProperty("javax.net.ssl.trustStore", thisKeystore); + System.setProperty("javax.net.ssl.trustStorePassword", thisPassword); + } + + URLConnection connection = url.openConnection(); + connection.setRequestProperty("Authorization", "Basic " + encoding); + HttpURLConnection httpConn = (HttpURLConnection)connection; + ByteArrayOutputStream outstr = new ByteArrayOutputStream(); + + httpConn.setRequestProperty("Content-Length", String.valueOf(document.length)); + httpConn.setRequestProperty("Content-Type", "text/xml; charset=utf-8"); + httpConn.setRequestMethod("POST"); + httpConn.setDoOutput(true); + httpConn.setDoInput(true); + + OutputStream out = httpConn.getOutputStream(); + out.write(document); + out.close(); + + InputStreamReader ireader = new InputStreamReader(httpConn.getInputStream()); + + BufferedReader in = new BufferedReader(ireader); + String inputLine; + while ((inputLine = in.readLine()) != null) + { + response.append(inputLine); + } + + in.close(); + httpConn.disconnect(); + } + catch (Exception e) + { + e.printStackTrace(); + programStatus = e.toString(); + return programStatus; + } + + return response.toString(); + } + + static + { + HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier() + { + public boolean verify(String hostname, SSLSession sslSession) + { + System.out.println("Hostname: " + hostname + ""); + return true; + } + }); + } +} \ No newline at end of file