Commit 7d53d531 authored by Roeland Luykx's avatar Roeland Luykx

Output from the EPD Projectathon 2018:

Idp user authentication with artifact binding now also supported with ehc. please see XuaDemo custom protocol handler.

git-svn-id: https://svn.code.sf.net/p/ehealthconnector/code/trunk@1721 e99adb7c-5e35-42fd-8d1b-cdb378af05e8
parent 86dcefa6
......@@ -25,8 +25,12 @@ import org.ehealth_connector.security.ch.ppq.PrivacyPolicyFeedResponse;
import org.ehealth_connector.security.ch.ppq.PrivacyPolicyQueryResponse;
import org.ehealth_connector.security.communication.xua.XUserAssertionRequest;
import org.ehealth_connector.security.communication.xua.XUserAssertionResponse;
import org.ehealth_connector.security.saml2.ArtifactResolve;
import org.ehealth_connector.security.saml2.ArtifactResponse;
import org.ehealth_connector.security.saml2.Base;
import org.ehealth_connector.security.saml2.Response;
import org.ehealth_connector.security.serialization.impl.ArtifactResolveSerializerImpl;
import org.ehealth_connector.security.serialization.impl.ArtifactResponseSerializerImpl;
import org.ehealth_connector.security.serialization.impl.AuthnRequestSerializerImpl;
import org.ehealth_connector.security.serialization.impl.BaseSerializerImpl;
import org.ehealth_connector.security.serialization.impl.PrivacyPolicyFeedResponseSerializerImpl;
......@@ -43,8 +47,7 @@ import org.slf4j.LoggerFactory;
public class DemoXuaOutputLogger {
/**
* The fn extension (_Java here and _Dotnet in the .Net demo allows
* efficient comparison in the test scripts).
* The fn extension (_Java here and _Dotnet in the .Net demo allows efficient comparison in the test scripts).
*/
private static String FN_EXT = "_Java.xml";
......@@ -52,8 +55,7 @@ public class DemoXuaOutputLogger {
protected Logger log = LoggerFactory.getLogger(DemoXuaOutputLogger.class);
/**
* Gets the Path to the given file and creates the directory structure if it
* does not exist.
* Gets the Path to the given file and creates the directory structure if it does not exist.
*
* @param aOutputFile
* the filename of the output file
......@@ -133,6 +135,28 @@ public class DemoXuaOutputLogger {
}
}
public void logOut(ArtifactResolve artifactResolve) {
try {
final ArtifactResolveSerializerImpl serializer = new ArtifactResolveSerializerImpl();
final String xmlString = serializer.toXmlString(artifactResolve);
System.out.print(xmlString + "\n");
} catch (final Throwable t) {
log.trace("Error", t);
}
}
public void logOut(ArtifactResponse artifactResponse) {
try {
final ArtifactResponseSerializerImpl serializer = new ArtifactResponseSerializerImpl();
final String xmlString = serializer.toXmlString(artifactResponse);
System.out.print(xmlString + "\n");
} catch (final Throwable t) {
log.trace("Error", t);
}
}
/**
* Logs the given request to the configured output
*
......@@ -178,8 +202,7 @@ public class DemoXuaOutputLogger {
final BaseSerializerImpl serializer = new BaseSerializerImpl();
final byte[] xmlArray = serializer.toXmlByteArray(baseElement);
final File outputFile = new File(getPathDir(aOutputFile),
baseElement.getClass().getSimpleName() + FN_EXT);
final File outputFile = new File(getPathDir(aOutputFile), baseElement.getClass().getSimpleName() + FN_EXT);
System.out.print("Write to file " + outputFile.getAbsolutePath() + "\n");
final FileOutputStream os = new FileOutputStream(outputFile);
......@@ -290,8 +313,7 @@ public class DemoXuaOutputLogger {
while (outputFile.exists()) {
++counter;
outputFile = new File(getPathDir(aOutputPath),
aXUserAssertionResponse.getClass().getSimpleName() + "_" + counter
+ FN_EXT);
aXUserAssertionResponse.getClass().getSimpleName() + "_" + counter + FN_EXT);
}
System.out.print("Write to file " + outputFile.getAbsolutePath() + "\n");
......
......@@ -43,5 +43,5 @@ java -jar ehealthconnectorDemo.jar DemoXua --ChPpqEhs -m=query -i=rsc/demoXua/pp
java -jar ehealthconnectorDemo.jar DemoXua --ChPpqEhs -m=add -n=rsc/demoXua/ppf/ehs_addpolicy.xml -i=rsc/demoXua/ppq/ehs_ppqrequest_input.xml -o=xuademo-output/ppf
java -jar ehealthconnectorDemo.jar DemoXua --ChPpqEhs -m=update -n=rsc/demoXua/ppf/ehs_updatepolicy.xml -i=rsc/demoXua/ppq/ehs_ppqrequest_input.xml -o=xuademo-output/ppf
java -jar ehealthconnectorDemo.jar DemoXua --ChPpqEhs -m=delete -n=rsc/demoXua/ppf/ehs_addpolicy.xml -i=rsc/demoXua/ppq/ehs_ppqrequest_input.xml -o=xuademo-output/ppf
java -jar ehealthconnectorDemo.jar DemoXua --IdpProtoHin -y=ehcdemo -k=<keystore stuff> -o=xuademo-output/idp
java -jar ehealthconnectorDemo.jar DemoXua --IdpProtoHin -y=ehcdemo -k=rsc/demoXua/security/ehs_gazelle.p12:testit:pkcs12:"ehs gazelle xua demo" -o=test-files
java -jar ehealthconnectorDemo.jar DemoXua --IdpProtoSoe -y=ehcdemo -k=<keystore stuff> -o=xuademo-output/idp
\ No newline at end of file
......@@ -15,21 +15,6 @@
<artifactId>ehealth_connector-fhir-structures-gen</artifactId>
<version>1.7-SNAPSHOT</version>
</dependency>
<!--
<dependency>
<groupId>org.ehealth_connector.cda.ch</groupId>
<artifactId>ehealth_connector-cda-ch</artifactId>
<version>1.6-SNAPSHOT</version>
</dependency>
-->
<!-- open health tools mdht cda-ch -->
<!--
<dependency>
<groupId>org.openhealthtools.mdht.uml.cda.ch</groupId>
<artifactId>org.openhealthtools.mdht.uml.cda.ch</artifactId>
<version>1.6-SNAPSHOT</version>
</dependency>
-->
<!-- test stuff -->
<dependency>
<groupId>junit</groupId>
......@@ -115,4 +100,4 @@
</profiles>
<name>eHealthConnector FHIR Structures CH</name>
</project>
\ No newline at end of file
</project>
......@@ -19,7 +19,6 @@ package org.ehealth_connector.security.authentication;
import org.ehealth_connector.security.communication.config.IdpClientConfig;
import org.ehealth_connector.security.exceptions.ClientSendException;
import org.ehealth_connector.security.saml2.Response;
/**
* <!-- @formatter:off -->
......@@ -52,14 +51,14 @@ public interface AuthenticationModule {
* <div class="it"></div>
*
* @return
* <div class="en">The response to the AuthnRequest from IdP service.</div>
* <div class="en">The response to the AuthnRequest from IdP service. Response or Artifact String</div>
* <div class="de">Die Antwort auf eine AuthnRequest des IdP Services.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
* @throws ClientSendException
*/
Response invokeUserAuthentication(AuthnRequest aAuthnRequest,
IdpClientConfig clientConfiguration) throws ClientSendException;
Object invokeUserAuthentication(AuthnRequest aAuthnRequest, IdpClientConfig clientConfiguration)
throws ClientSendException;
}
/*
*
* The authorship of this project and accompanying materials is held by medshare GmbH, Switzerland.
* All rights reserved. https://medshare.net
*
* Source code, documentation and other resources have been contributed by various people.
* Project Team: https://sourceforge.net/p/ehealthconnector/wiki/Team/
* For exact developer information, please refer to the commit history of the forge.
*
* This code is made available under the terms of the Eclipse Public License v1.0.
*
* Accompanying materials are made available under the terms of the Creative Commons
* Attribution-ShareAlike 4.0 License.
*
* This line is intended for UTF-8 encoding checks, do not modify/delete: äöüéè
*
*/
package org.ehealth_connector.security.communication.clients;
import org.ehealth_connector.security.exceptions.ClientSendException;
import org.ehealth_connector.security.saml2.ArtifactResolve;
import org.ehealth_connector.security.saml2.ArtifactResponse;
/**
* <!-- @formatter:off -->
* <div class="en">HEREISENGLISH</div>
* <div class="de">HIERISTDEUTSCH</div>
* <div class="fr">VOICIFRANCAIS</div>
* <div class="it">ITALIANO</div>
*
* <!-- @formatter:on -->
*/
public interface ArtifactResolveClient {
/**
* <!-- @formatter:off -->
* <div class="en">Method to send an ArtifactResolve.</div>
* <div class="de">Methode um einen ArtifactResolve zu senden.</div>
* <div class="fr"></div>
* <div class="it"></div>
*
* @param aArtifactResolve
* <div class="en">the AuthnRequest to be sent.</div>
* <div class="de">Der AuthnRequest welcher geschickt werden soll.</div>
* <div class="fr"></div>
* <div class="it"></div>
* @return
* <div class="en">the ArtifactResponse</div>
* <div class="de">Die ArtifactResponse.</div>
* <div class="fr"></div>
* <div class="it"></div>
* @throws ClientSendException
* <div class="en">will be thrown if an error occoures</div>
* <div class="de">wird geworfen wenn ein Fehler auftritt.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
ArtifactResponse send(ArtifactResolve aArtifactResolve) throws ClientSendException;
}
......@@ -19,7 +19,6 @@ package org.ehealth_connector.security.communication.clients;
import org.ehealth_connector.security.authentication.AuthnRequest;
import org.ehealth_connector.security.exceptions.ClientSendException;
import org.ehealth_connector.security.saml2.Response;
/**
* <!-- @formatter:off -->
......@@ -55,5 +54,5 @@ public interface IdpClient {
* <div class="it"></div>
* <!-- @formatter:on -->
*/
Response send(AuthnRequest aAuthnRequest) throws ClientSendException;
Object send(AuthnRequest aAuthnRequest) throws ClientSendException;
}
......@@ -21,6 +21,7 @@ import java.security.KeyStore;
import org.ehealth_connector.security.authentication.AuthnRequest;
import org.ehealth_connector.security.exceptions.SigningException;
import org.ehealth_connector.security.saml2.ArtifactResolve;
/**
*
......@@ -64,8 +65,7 @@ public interface SignCryptModule {
* <div class="it"></div>
* <!-- @formatter:on -->
*/
void setPki(KeyStore keyStore, String aKeyStorePassword, KeyStore trustStore,
String aTrustStorePassword);
void setPki(KeyStore keyStore, String aKeyStorePassword, KeyStore trustStore, String aTrustStorePassword);
/**
*
......@@ -94,4 +94,6 @@ public interface SignCryptModule {
*/
void signAuthnRequest(AuthnRequest aAuthnRequest, String aSigningAlias) throws SigningException;
void signArtifactResolve(ArtifactResolve artifactResolve, String aSigningAlias) throws SigningException;
}
/*
*
* The authorship of this project and accompanying materials is held by medshare GmbH, Switzerland.
* All rights reserved. https://medshare.net
*
* Source code, documentation and other resources have been contributed by various people.
* Project Team: https://sourceforge.net/p/ehealthconnector/wiki/Team/
* For exact developer information, please refer to the commit history of the forge.
*
* This code is made available under the terms of the Eclipse Public License v1.0.
*
* Accompanying materials are made available under the terms of the Creative Commons
* Attribution-ShareAlike 4.0 License.
*
* This line is intended for UTF-8 encoding checks, do not modify/delete: äöüéè
*
*/
package org.ehealth_connector.security.saml2;
/**
* <!-- @formatter:off -->
* <div class="en">Interface describing the methods of ArtifactResolve. </div>
* <div class="de">Interface welches die Methoden von ArtifactResolve beschreibt.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
public interface ArtifactResolve extends Base {
/**
* <!-- @formatter:off -->
* <div class="en">Method to get the Artifact.</div>
* <div class="de">Methode um das Artifact zu holen.</div>
* <div class="fr"></div>
* <div class="it"></div>
*
* @return
* <div class="en">the Artifact as {@link java.lang.String}</div>
* <div class="de">der Artifact als {@link java.lang.String}</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
String getArtifact();
}
/*
*
* The authorship of this project and accompanying materials is held by medshare GmbH, Switzerland.
* All rights reserved. https://medshare.net
*
* Source code, documentation and other resources have been contributed by various people.
* Project Team: https://sourceforge.net/p/ehealthconnector/wiki/Team/
* For exact developer information, please refer to the commit history of the forge.
*
* This code is made available under the terms of the Eclipse Public License v1.0.
*
* Accompanying materials are made available under the terms of the Creative Commons
* Attribution-ShareAlike 4.0 License.
*
* This line is intended for UTF-8 encoding checks, do not modify/delete: äöüéè
*
*/
package org.ehealth_connector.security.saml2;
/**
* <!-- @formatter:off -->
* <div class="en">Interface describing the methods of the AssertionBuilder. </div>
* <div class="de">Interface welches die Methoden des AssertionBuilders beschreibt.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
public interface ArtifactResolveBuilder extends BaseBuilder<ArtifactResolveBuilder> {
/**
* <!-- @formatter:off -->
* <div class="en">Method to add an Artifact to the ArtifactResolve to be build.</div>
* <div class="de">Methode um ein Artifact dem ArtifactResolve hinzuzufügen.</div>
* <div class="fr"></div>
* <div class="it"></div>
*
* @param aArtifact
* <div class="en">the Artifact to be added.</div>
* <div class="de">das Artifact welches hinzugefügt werden soll.</div>
* <div class="fr"></div>
* <div class="it"></div>
* @return
* <div class="en">the actual instance of this builder</div>
* <div class="de">die aktuelle Instanz des Builders</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
public ArtifactResolveBuilder artifact(String aArtifact);
}
/*
*
* The authorship of this project and accompanying materials is held by medshare GmbH, Switzerland.
* All rights reserved. https://medshare.net
*
* Source code, documentation and other resources have been contributed by various people.
* Project Team: https://sourceforge.net/p/ehealthconnector/wiki/Team/
* For exact developer information, please refer to the commit history of the forge.
*
* This code is made available under the terms of the Eclipse Public License v1.0.
*
* Accompanying materials are made available under the terms of the Creative Commons
* Attribution-ShareAlike 4.0 License.
*
* This line is intended for UTF-8 encoding checks, do not modify/delete: äöüéè
*
*/
package org.ehealth_connector.security.saml2;
import java.util.List;
/**
* <!-- @formatter:off -->
* <div class="en">Interface describing the methods of ArtifactResponse. </div>
* <div class="de">Interface welches die Methoden von ArtifactResponse beschreibt.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
public interface ArtifactResponse extends Base {
/**
*
* <!-- @formatter:off -->
*<div class="en">Method to get Consent value.</div>
* <div class="de">Methode um den Consent wert zu erhalten.</div>
* <div class="fr"></div>
* <div class="it"></div>
*
* @return
* <div class="en">the Destination value as {@link java.lang.String}.</div>
* <div class="de">der Destination Wert als {@link java.lang.String}.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
String getConsent();
/**
*
* <!-- @formatter:off -->
* <div class="en">Method to get Destination value.</div>
* <div class="de">Methode um den Inhalt der Destination zu erhalten.</div>
* <div class="fr"></div>
* <div class="it"></div>
*
* @return
* <div class="en">the Destination value as {@link java.lang.String}.</div>
* <div class="de">der Inhalt der Destination als {@link java.lang.String}.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
String getDestination();
/**
* <!-- @formatter:off -->
* <div class="en">Method to get InResponseTo value.</div>
* <div class="de">Methode um den InResponseTo zu erhalten.</div>
* <div class="fr"></div>
* <div class="it"></div>
*
* @return
* <div class="en">the InResponseTo value as {@link java.lang.String}.</div>
* <div class="de">der InResponseTo Wert als {@link java.lang.String}.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
String getInResponseTo();
/**
*
* <!-- @formatter:off -->
* <div class="en">Method to get the Status.</div>
* <div class="de">Methode um den Status zu holen.</div>
* <div class="fr"></div>
* <div class="it"></div>
*
* @return
* <div class="en">the Status value as {@link org.ehealth_connector.security.saml2.Status}.</div>
* <div class="de">der Status als {@link org.ehealth_connector.security.saml2.Status}.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
Status getStatus();
/**
*
* <!-- @formatter:off -->
* <div class="en">Method to get a list of Response.</div>
* <div class="de">Methode um die Liste von Responses zu holen.</div>
* <div class="fr"></div>
* <div class="it"></div>
*
*@return
* <div class="en">a {@link java.util.List} of {@link org.ehealth_connector.security.saml2.Response}.</div>
* <div class="de">eine {@link java.util.List} von {@link org.ehealth_connector.security.saml2.Response}.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
List<Response> getResponses();
}
/*
*
* The authorship of this project and accompanying materials is held by medshare GmbH, Switzerland.
* All rights reserved. https://medshare.net
*
* Source code, documentation and other resources have been contributed by various people.
* Project Team: https://sourceforge.net/p/ehealthconnector/wiki/Team/
* For exact developer information, please refer to the commit history of the forge.
*
* This code is made available under the terms of the Eclipse Public License v1.0.
*
* Accompanying materials are made available under the terms of the Creative Commons
* Attribution-ShareAlike 4.0 License.
*
* This line is intended for UTF-8 encoding checks, do not modify/delete: äöüéè
*
*/
package org.ehealth_connector.security.saml2;
/**
* <!-- @formatter:off -->
* <div class="en">Interface describing the methods of the ResponseBuilder.</div>
* <div class="de">Interface welches die Methoden des ResponseBuilders beschreibt.</div>
* <div class="fr"></div>
* <div class="it"></div>
* <!-- @formatter:on -->
*/
public interface ArtifactResponseBuilder extends SimpleBuilder<ArtifactResponse> {
// There are no special methods defined, but the interface has to be
// declared for selection reasons.
}
......@@ -95,11 +95,9 @@ public abstract class AbstractSoapClient<T> {
private Logger logger = LoggerFactory.getLogger(getClass());
protected void createBody(Element aBodyElement, Element envelopElement)
throws SerializeException {
protected void createBody(Element aBodyElement, Element envelopElement) throws SerializeException {
// create soap body
final Element soapBody = envelopElement.getOwnerDocument().createElementNS(getSoapNs(),
"Body");
final Element soapBody = envelopElement.getOwnerDocument().createElementNS(getSoapNs(), "Body");
envelopElement.appendChild(soapBody);
// add authnrequest to soap body
......@@ -132,12 +130,11 @@ public abstract class AbstractSoapClient<T> {
}
protected void createHeader(Element aSecurityHeaderElement, WsaHeaderValue wsHeaders,
Element envelopElement) throws SerializeException {
protected void createHeader(Element aSecurityHeaderElement, WsaHeaderValue wsHeaders, Element envelopElement)
throws SerializeException {
// create soap header
final Element headerElement = envelopElement.getOwnerDocument().createElementNS(getSoapNs(),
"Header");
final Element headerElement = envelopElement.getOwnerDocument().createElementNS(getSoapNs(), "Header");
envelopElement.appendChild(headerElement);
final Element headerWsaAction = envelopElement.getOwnerDocument()
......@@ -151,14 +148,14 @@ public abstract class AbstractSoapClient<T> {
headerElement.appendChild(headerWsaMessageID);
final Element headerSecurityElement = envelopElement.getOwnerDocument().createElementNS(
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd",
"Security");
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd", "Security");
headerElement.appendChild(headerSecurityElement);
// add security header element (assertion) to the headers
final Node importedHeaderNode = envelopElement.getOwnerDocument()
.importNode(aSecurityHeaderElement, true);
headerSecurityElement.appendChild(importedHeaderNode);
if (aSecurityHeaderElement != null) {
final Node importedHeaderNode = envelopElement.getOwnerDocument().importNode(aSecurityHeaderElement, true);
headerSecurityElement.appendChild(importedHeaderNode);
}
}
protected String createXmlString(Element aEnvelope) throws TransformerException {// transform
......@@ -168,22 +165,19 @@ public abstract class AbstractSoapClient<T> {
final Transformer transformer = tf.newTransformer();
transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes");
final StringWriter writer = new StringWriter();
transformer.transform(new DOMSource(aEnvelope.getOwnerDocument()),
new StreamResult(writer));
transformer.transform(new DOMSource(aEnvelope.getOwnerDocument()), new StreamResult(writer));
return writer.toString();
}
protected T execute(HttpPost post)
throws ClientSendException, ClientProtocolException, IOException {
protected T execute(HttpPost post) throws ClientSendException, ClientProtocolException, IOException {
final CloseableHttpClient httpclient = getHttpClient();
final CloseableHttpResponse response = httpclient.execute(post);
final HttpEntity errorEntity = response.getEntity();
final String content = EntityUtils.toString(errorEntity);
logger.debug("SOAP Message\n" + content);
if ((response.getStatusLine() != null)
&& (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK)) {
if ((response.getStatusLine() != null) && (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK)) {
return parseResponse(content);
} else {
......@@ -202,15 +196,14 @@ public abstract class AbstractSoapClient<T> {
final KeyStore keyStore = pki.loadStore(new FileInputStream(config.getKeyStore()),
config.getKeyStorePassword(), config.getKeyStoreType());
final TrustStrategy acceptingTrustStrategy = (X509Certificate[] chain,
String authType) -> true;
final TrustStrategy acceptingTrustStrategy = (X509Certificate[] chain, String authType) -> true;
final SSLContext sslcontext = SSLContexts.custom()//
.loadKeyMaterial(keyStore, config.getKeyStorePassword().toCharArray())//
.loadTrustMaterial(keyStore, acceptingTrustStrategy)//
.build();
return HttpClients.custom().setSslcontext(sslcontext).build();
} catch (KeyStoreException | KeyManagementException | UnrecoverableKeyException
| NoSuchAlgorithmException | IOException e) {
} catch (KeyStoreException | KeyManagementException | UnrecoverableKeyException | NoSuchAlgorithmException
| IOException e) {
throw new ClientSendException(e);
}
}
......@@ -230,8 +223,7 @@ public abstract class AbstractSoapClient<T> {
return logger;
}
protected Node getNode(Element element, String xPathExpression)
throws XPathExpressionException {
protected Node getNode(Element element, String xPathExpression) throws XPathExpressionException {
final XPath xPath = XPathFactory.newInstance().newXPath();
xPath.setNamespaceContext(new NamespaceContext() {
......@@ -270,21 +262,19 @@ public abstract class AbstractSoapClient<T> {
}
protected Element getResponseElement(String content, String nameSpaceUri, String localName)
throws ParserConfigurationException, UnsupportedOperationException, SAXException,
IOException, XPathExpressionException {
throws ParserConfigurationException, UnsupportedOperationException, SAXException, IOException,
XPathExpressionException {
final DocumentBuilderFactory docFactory = DocumentBuilderFactory.newInstance();
docFactory.setNamespaceAware(true);
final DocumentBuilder docBuilder = docFactory.newDocumentBuilder();
final Document soapDocument = docBuilder
.parse(new ByteArrayInputStream(content.getBytes()));
final Document soapDocument = docBuilder.parse(new ByteArrayInputStream(content.getBytes()));
String prefix = soapDocument.getDocumentElement().getPrefix();
if (!StringUtils.isEmpty(prefix)) {
prefix += ":";
}
final Node bodyNode = getNode(soapDocument.getDocumentElement(),
"/" + prefix + "Envelope/" + prefix + "Body");
final Node b