1

Currently I get the following error when I am attempt to attach an org.w3c.dom.Element to an existing SOAPHeader in a javax.xml.ws.handler.soap.SOAPHandler during an outgoing client side message:

org.w3c.dom.DOMException: WRONG_DOCUMENT_ERR: A node is used in a different document than the one that created it

This problem only occurs if I make a seperate jax-ws client call to another webservice from within the handleMessage() function. To answer some questions, I am properly importing and cloning the Element object when attempting to attach it and can successfully do so as long as I don't make a subsequent webservice call as I stated above. Both my client side call and webservice are running on JBoss EAP 5.1. Thoughts? Suggestions? Example usage has been depicted below:

public boolean handleMessage(SOAPMessageContext ctx) {
    Boolean outbound = (Boolean) msgContext.get(MessageContext.MESSAGE_OUTBOUND_PROPERTY);
    if(!outbound)
    {
       SOAPPart document = ctx.getMessage().getSOAPPart();          
       SOAPHeaderElement wsse = getSecurityHeaderElement(document.getEnvelope());

       //Extra Webservice call
       Service service=Service.create(wsdlUrl,qname);
       WebserviceInterface ws=service.getPort(WebserviceInterface.class);
       ws.helloWorld();
       //End of other webservice call

       DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
       DocumentBuilder docBuilder= factory.newDocumentBuilder();
       Document doc=docBuilder.newDocument();
       //Insert appending nodes here
       Element xmlElement=doc.getDocumentElement();

       Node node = document.importNode(xmlElement.cloneNode(true),true);    
       wsse.appendChild(node);
    }
}   

What baffles me most is that this other webservice call should have 0 effect on the originating webservices SOAPHeader, but again if I remove the webservice call the problem goes away.

dsutherland
  • 792
  • 6
  • 15
  • Please show the code you're using. You *say* you're properly importing the element - but without seeing the code, we can't tell whether or not that's true, and it's the obvious thing that could be going wrong. – Jon Skeet May 29 '13 at 20:50
  • I can do that but if I wasn't importing it properly how would removing the extra webservice call allow the import to work? – dsutherland May 30 '13 at 13:21
  • @JonSkeet - I've added some code to show the import occuring. Again though, I don't know how that would make a difference as removing the webservice call allows the import to occur without a problem. It's very strange. – dsutherland May 30 '13 at 13:29
  • @JonSkeet - Furthermore, if I move the webservice call back to the first action in the function, the handler fails to even retrieve the SecurityHeaderElement with the same error. – dsutherland May 30 '13 at 13:43
  • Is `getSecurityHeaderElement` your own method? If so, what does it do? If not, where is it from? While I can't see why the other web service call would cause a problem either, the more we know the more we may be able to help you. – Jon Skeet May 30 '13 at 17:09
  • @JonSkeet - Yes it is my method. It simply retrieves the SOAPHeader from the Envelope and checks if it currently contains an element labeled "wsse". If it does not, it creates the element using the envelope and appends it to the SOAPHeader. – dsutherland May 30 '13 at 23:51
  • Out of interest, what happens if you move the first two lines (extracting the document etc) to *after* the webservice call? – Jon Skeet May 31 '13 at 06:52
  • @JonSkeet - Sorry for the delayed response (didn't realize you responded). If the web service call is the first thing that happens, I will get a WRONG_DOCUMENT_ERR as soon as I try to append anything to the SOAP document. Even if the element I am appending was created with the SOAP documents .createElement method where the SOAP Document by default is the elements Document... It seriously is baffling. – dsutherland Jun 04 '13 at 17:22
  • @JonSkeet - Any thoughts on how I should move forward? This is extremely important and seems like it shouldn't be an issue. – dsutherland Jun 12 '13 at 18:41
  • No, I'm afraid not - unless you can come up with a short but complete program demonstrating the problem, so that I (and others) can reproduce it ourselves. – Jon Skeet Jun 12 '13 at 22:02
  • I could do that but where would I upload it to? And obviously your environment would have to be the same "JBoss EAP 5.1" – dsutherland Jun 14 '13 at 16:14
  • Well not *necessarily*. We don't know how much is environmental at the moment. As it is, I'm afraid I don't think I can help :( – Jon Skeet Jun 14 '13 at 17:30
  • :'( ugh... i don't know how to move forward. If you want me to put it online somewhere, would github be sufficient? Or is there something particular I need to use for stackoverflow? – dsutherland Jun 18 '13 at 18:03
  • Nothing specific for SO - but if it really required running JBoss, I think you may find it hard to get help :( – Jon Skeet Jun 18 '13 at 18:04
  • That's true, but I guess the question is i'm not sure if it is a jboss issue, an apache xerces issue (since tomcat and jboss both use xerces), etc. I mean this should work regardless of what server instance your running it on but I've only tested it on JBoss 5.1 and it's clearly not working on that lol – dsutherland Jun 19 '13 at 15:32
  • @JonSkeet - So I posted an answer to this. It turns out that the webservice call itself isn't the issue but the instantiating a new instance of the webservice was the problem. Still no idea why that's an issue but just thought you should know. Must be a bug in XERCES or JBOSS – dsutherland Sep 30 '13 at 14:34

1 Answers1

1

So after further analysis, it turns out calling a webservice from within the handleMessage() method isn't the issue; however, specifically instantiating a new instance of any webservice during the handleMessage() phase is what causes the problem. Still not sure why this is an issue (guessing it's a bug with APACHE XERCES or JBoss 5.1) but here is an example of how it can work.

private WebserviceInterface ws;

//Assuming this method is only called when not handling a message
public void init()
{
     Service service=Service.create(wsdlUrl,qname);
     ws=service.getPort(WebserviceInterface.class);
}
public boolean handleMessage(SOAPMessageContext ctx)
{
     Boolean outbound = (Boolean)msgContext.get(MessageContext.MESSAGE_OUTBOUND_PROPERTY);
     if(!outbound)
     {
          SOAPPart document = ctx.getMessage().getSOAPPart();          
          SOAPHeaderElement wsse = getSecurityHeaderElement(document.getEnvelope());

          //Extra Webservice call
          Element xmlElement=ws.helloWorld();

          Node node = document.importNode(xmlElement.cloneNode(true),true);    
          wsse.appendChild(node);
      }
}   
dsutherland
  • 792
  • 6
  • 15