Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
756 views
in Technique[技术] by (71.8m points)

java - JAXWS Soap Handler Large MTOM Attachments

The JAXWS implementation within IBM WebSphere 7 and 8 appears to have some problems when it comes to soap handlers and large MTOM attachments. It appears that the entire message, including all attachment binary content, is read into memory when getMessage() is invoked on the SOAPMessageContext object. This can very easily cause the JVM to run out of available memory.

@Override
public boolean handleMessage(SOAPMessageContext context) {
    SOAPMessage soapMsg = context.getMessage();

    ...
}

In the above code snippet, context.getMessage() can result in out of memory exceptions if the incoming request attachments are larger than the amount of free memory available in the JVM.

How can I get access to the SoapHeader elements without triggering this undesired functionality? I see that the SOAPMessageContext class has a getHeaders(...) method but I'm not sure how to use it exactly. I'm specifically unsure what to pass in for the JAXBContext. Can anybody provide an example or explanation how to use this method?

Here's another related stackoverflow article : JAX-WS SoapHandler with large messages: OutOfMemoryError

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Here is how to access the headers without reading the entire message using the WebSphere built-in JAX-WS implementation.

public boolean handleMessage(SOAPMessageContext context) {

    AttributedURI messageIdURI = (AttributedURI)context.get("com.ibm.wsspi.wsaddressing.inbound.MessageID");
    String messageId = "";
    if (messageIdURI != null && messageIdURI.getURI() != null) {
        messageId = messageIdURI.getURI().toString();
    }
    EndpointReference fromApplicationEPR = (EndpointReference)context.get("com.ibm.wsspi.wsaddressing.inbound.FromEPR");
    String fromApplication = "";
    if (fromApplicationEPR != null && fromApplicationEPR.getAddress() != null &&
        fromApplicationEPR.getAddress().getURI() != null) {
        fromApplication = fromApplicationEPR.getAddress().getURI().toString();
    }

    ...

    return true;
}

Note that this differs based on the precise JAX-WS implementation. I'll post how to do this via Apache CXF when I get a chance. Here are the needed imports for the above code:

import com.ibm.ws.wsaddressing.AttributedURI;
import com.ibm.ws.wsaddressing.EndpointReference;

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...