title: Using Wss4jSecurityInterceptor throws a WRONG_DOCUMENT_ERR: A node is used in a different document than the one that created it
body: <p>I am upgrading my application to Java 11 and Spring boot 2.1.2 and running into following error when trying to communicate over SOAP to an external partner. It is the Wss4jSecurityInterceptor that causes this issue. It work before when running java 8 and Spring Boot 1</p>
  
  <pre><code>REQUEST: ExampleSoapClient.sendRequest([javax.xml.bind.JAXBElement@5bba179f]). 
  ERROR: WRONG_DOCUMENT_ERR: A node is used in a different document than the one that created it.
  org.w3c.dom.DOMException: WRONG_DOCUMENT_ERR: A node is used in a different document than the one that created it.
  at java.xml/com.sun.org.apache.xerces.internal.dom.ParentNode.internalInsertBefore(ParentNode.java:356)
  at java.xml/com.sun.org.apache.xerces.internal.dom.ParentNode.insertBefore(ParentNode.java:287)
  at java.xml/com.sun.org.apache.xerces.internal.dom.NodeImpl.appendChild(NodeImpl.java:237)
  at org.apache.wss4j.dom.util.WSSecurityUtil.prependChildElement(WSSecurityUtil.java:314)
  at org.apache.wss4j.dom.util.WSSecurityUtil.findWsseSecurityHeaderBlock(WSSecurityUtil.java:435)
  at org.apache.wss4j.dom.message.WSSecHeader.insertSecurityHeader(WSSecHeader.java:165)
  at org.apache.wss4j.dom.handler.WSHandler.doSenderAction(WSHandler.java:117)
  at org.springframework.ws.soap.security.wss4j2.Wss4jHandler.doSenderAction(Wss4jHandler.java:63)
  at org.springframework.ws.soap.security.wss4j2.Wss4jSecurityInterceptor.secureMessage(Wss4jSecurityInterceptor.java:574)
  at org.springframework.ws.soap.security.AbstractWsSecurityInterceptor.handleRequest(AbstractWsSecurityInterceptor.java:210)
  at org.springframework.ws.client.core.WebServiceTemplate.doSendAndReceive(WebServiceTemplate.java:597)
  at org.springframework.ws.client.core.WebServiceTemplate.sendAndReceive(WebServiceTemplate.java:555)
  at org.springframework.ws.client.core.WebServiceTemplate.marshalSendAndReceive(WebServiceTemplate.java:390)
  at org.springframework.ws.client.core.WebServiceTemplate.marshalSendAndReceive(WebServiceTemplate.java:378)
  at com.example.domain.integration.provider.ExampleSoapClient.sendRequest(ExampleportSoapClient.java:61)
  </code></pre>
  
  <p>java 11 and Spring boot 2.1.2 upgrade</p>
  
  <pre><code>import com.sun.xml.wss.impl.callback.PasswordCallback;
  import com.sun.xml.wss.impl.callback.UsernameCallback;
  import org.apache.wss4j.dom.WSConstants;
  import org.apache.wss4j.dom.handler.WSHandlerConstants;
  import org.springframework.http.client.SimpleClientHttpRequestFactory;
  import org.springframework.ws.client.core.WebServiceTemplate;
  import org.springframework.ws.client.core.support.WebServiceGatewaySupport;
  import org.springframework.ws.client.support.interceptor.ClientInterceptor;
  import org.springframework.ws.soap.security.wss4j2.Wss4jSecurityInterceptor;
  import org.springframework.ws.transport.http.ClientHttpRequestMessageSender;
  
  import javax.security.auth.callback.Callback;
  import javax.security.auth.callback.CallbackHandler;
  import javax.security.auth.callback.UnsupportedCallbackException;
  import java.io.IOException;
  
  public class ExampleSoapClient extends WebServiceGatewaySupport {
  
  private Wss4jSecurityInterceptor wss4jSecurityInterceptor;
  
  public ExampleSoapClient(Wss4jSecurityInterceptor wss4jSecurityInterceptor) {
      wss4jSecurityInterceptor = new Wss4jSecurityInterceptor();
      wss4jSecurityInterceptor.setValidationCallbackHandler(new ExampleCredentialsCallbackHandler());
      wss4jSecurityInterceptor.setSecurementActions(WSHandlerConstants.TIMESTAMP + " " + WSHandlerConstants.USERNAME_TOKEN);
      /* Default Password encoding is digest, that is not supported by EP hence need to set need to set following password type. */
      wss4jSecurityInterceptor.setSecurementPasswordType(WSConstants.PASSWORD_TEXT);
      wss4jSecurityInterceptor.setSecurementUsernameTokenNonce(false);
      wss4jSecurityInterceptor.setSecurementUsername("username");
      wss4jSecurityInterceptor.setSecurementPassword("password");
      //Note! this will help our external mock to not need any security implementation
      wss4jSecurityInterceptor.setSecurementMustUnderstand(false);
  
      SimpleClientHttpRequestFactory requestFactory = new SimpleClientHttpRequestFactory();
      requestFactory.setConnectTimeout(40000);
      requestFactory.setReadTimeout(40000);
      setMessageSender(new ClientHttpRequestMessageSender(requestFactory));
  }
  
  public Object sendRequest(Object request) {
  
      final WebServiceTemplate webServiceTemplate = getWebServiceTemplate();
      ClientInterceptor[] interceptors = new ClientInterceptor[1];
  
      interceptors[0] = wss4jSecurityInterceptor;
      webServiceTemplate.setInterceptors((interceptors));
  
      final SubmitDocument submitDocument = createRequest(request);
  
      final SubmitDocumentResponse submitDocumentResponse = (SubmitDocumentResponse) webServiceTemplate.marshalSendAndReceive(endpoint, submitDocument);
      return response;
  }
  
  }
  class ExampleCredentialsCallbackHandler implements CallbackHandler {
  
  public ExampleCredentialsCallbackHandler() {
  }
  
  @Override
  public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
  
      for (Callback callback : callbacks) {
  
          if (callback instanceof UsernameCallback) {
              handleUsernameCallback((UsernameCallback) callback);
          } else if (callback instanceof PasswordCallback) {
              handlePasswordCallback((PasswordCallback) callback);
          } else {
              throw new UnsupportedCallbackException(callback);
          }
      }
  }
  
  private void handleUsernameCallback(UsernameCallback callback) {
      callback.setUsername("username");
  }
  
  private void handlePasswordCallback(PasswordCallback callback) {
      callback.setPassword("password");
  }
  </code></pre>
  
  <p>}</p>