Tracing XML request/responses with JAX-WS when error occurs
Asked Answered
U

8

33

I want to log raw soap post requests if there are any errors , I am using JAX-WS. Any help will be appreciated.

Is there an easy way (aka: not using a proxy) to get access to the raw request/response XML for a webservice published with JAX-WS reference implementation (the one included in JDK 1.5 and better) only when exception occurs in response? I want to log raw SOAP reuest so that I can test it thorugh any webservice client at a later stage

Ulcerative answered 18/3, 2011 at 10:9 Comment(0)
S
36

Use

com.sun.xml.internal.ws.transport.http.client.HttpTransportPipe.dump=true

and

com.sun.xml.internal.ws.transport.http.HttpAdapter.dump=true

instead (note the "internal" in the package name), this did the trick for me.

Cheers, Torsten

Snowbird answered 13/4, 2011 at 10:28 Comment(3)
changed catalina.sh file , included 'internal' but still cant see any changes in logs/catalina.yyyy-MM-dd.log filesUlcerative
.internal. is required when you are using the JAX WS version contained in the JRE, whereas the non ".internal." version is used, when you are explicitly using a JAX WS libraryLingcod
how to add timestamp, at what time a particular request reached to server and at what time server responded back ?Shavonneshaw
M
31

Just thought I would mention this:

The question when to use the property name with the internal in it and when not ?

If you read the Metro Guide it will tell you to use:

on client:

com.sun.xml.ws.transport.http.client.HttpTransportPipe.dump=true

on server:

com.sun.xml.ws.transport.http.HttpAdapter.dump=true

However: It seems to me that when JAX-WS RI library got included as standard with the JDK (this was with Java 6) then Sun had to rename the property name to include 'internal'. So if you are using JAX-WS RI as it comes bundled with the JDK, then you must be sure to add the internal to the property name. Otherwise it will not work. In other words you need to use:

on client:

com.sun.xml.internal.ws.transport.http.client.HttpTransportPipe.dump=true

on server:

com.sun.xml.internal.ws.transport.http.HttpAdapter.dump=true

On the other hand if you are using a standalone version of JAX-WS RI (or of Metro as a whole) then I would guess you should use the property name without the internal.

I'll be glad if someone has inside knowledge on this and can say if this is true or not.

Monstrosity answered 13/6, 2013 at 10:49 Comment(0)
D
10

It is OK to go with system properties (here is Gradle DSL for test task):

systemProperty "com.sun.xml.ws.transport.http.client.HttpTransportPipe.dump", "true"
systemProperty "com.sun.xml.internal.ws.transport.http.client.HttpTransportPipe.dump", "true"
systemProperty "com.sun.xml.ws.transport.http.HttpAdapter.dump", "true"
systemProperty "com.sun.xml.internal.ws.transport.http.HttpAdapter.dump", "true"
systemProperty "com.sun.xml.ws.transport.http.HttpAdapter.dumpTreshold", "99999"
systemProperty "com.sun.xml.internal.ws.transport.http.HttpAdapter.dumpTreshold", "99999"

but those settings are global and may have high volume to enable them on PROD... It is not fun to add filters to your logging framework bound to business logic if you want to reduce volume of XML logging.

Details on capturing req/rsp bodies in WS handlers are in my answer How can I pass data back from a SOAP handler to a webservice client?

Here is an important part:

public class MsgLogger implements SOAPHandler<SOAPMessageContext> {

    public static String REQEST_BODY = "com.evil.request";
    public static String RESPONSE_BODY = "com.evil.response";

    @Override
    public Set<QName> getHeaders() {
        return null;
    }

    @Override
    public boolean handleMessage(SOAPMessageContext context) {
        SOAPMessage msg = context.getMessage();
        Boolean beforeRequest = (Boolean) context.get(MessageContext.MESSAGE_OUTBOUND_PROPERTY);
        try {
            ByteArrayOutputStream baos = new ByteArrayOutputStream(32_000);
            context.getMessage().writeTo(baos);
            String key = beforeRequest ? REQEST_BODY : RESPONSE_BODY;
            context.put(key, baos.toString("UTF-8"));
            context.setScope(key, MessageContext.Scope.APPLICATION);
        } catch (SOAPException | IOException e) { }
        return true;
    }

    @Override
    public boolean handleFault(SOAPMessageContext context) {
        return handleMessage(context);
    }

    @Override
    public void close(MessageContext context) { }
}

To register handler and use preserved properties:

BindingProvider provider = (BindingProvider) port;
List<Handler> handlerChain = provider.getBinding().getHandlerChain();
handlerChain.add(new MsgLogger());
provider.getBinding().setHandlerChain(handlerChain);

Req req = ...;
Rsp rsp = port.serviceCall(req); // call WS Port

// Access saved message bodies:
Map<String, Object> responseContext = provider.getResponseContext();
String reqBody = (String) responseContext.get(MsgLogger.REQEST_BODY);
String rspBody = (String) responseContext.get(MsgLogger.RESPONSE_BODY);

With this solution (it is only the skeleton, proper error handling / edge cases is up to you) you decide to log later when you've got response.

Dharna answered 13/3, 2019 at 12:21 Comment(1)
This answer is based on The Java API for XML-Based Web Services (JAX-WS) 2.3 spec so should work for any JAX WS implementation.Dharna
J
4

In addition to Torsten's answer

com.sun.xml.internal.ws.transport.http.client.HttpTransportPipe.dump=true

Make sure that you set this before instantiating the WebServiceClient object (the one that extends Service)

Jaenicke answered 23/11, 2011 at 10:54 Comment(0)
S
3

The first thing you might want to try is using one, or both, of the following system properties:

Client:

com.sun.xml.ws.transport.http.client.HttpTransportPipe.dump=true

Server:

com.sun.xml.ws.transport.http.HttpAdapter.dump=true
Sideboard answered 18/3, 2011 at 18:56 Comment(7)
I added above properties in my catalina.properties file in my tomcat server, but cant see any logs updated, please adviseUlcerative
added to my catalina.sh on JAVA_OPTS but cant see any changesUlcerative
Don't change catalina.properties. How are you setting JAVA_OPTS? The logging should be output via System.out.Sideboard
Following is the JAVA_OPTS line in my catalina.sh file JAVA_OPTS="-Dcom.sun.xml.ws.fault.SOAPFaultBuilder.disableCaptureStackTrace = false -Djava.awt.headless=true -Dfile.encoding=UTF-8 -server -Xms512m -Xmx1024m -XX:NewSize=256m -XX:MaxNewSize=256m -XX:PermSize=256m -XX:MaxPermSize=256m -XX:+DisableExplicitGC -Dcom.sun.xml.ws.transport.http.client.HttpTransportPipe.dump = true -Dcom.sun.xml.ws.transport.http.HttpAdapter.dump = true"Ulcerative
...and nothing's showing up in logs/catalina.out? I suppose it would be good to know what JDK and Tomcat versions you're using...Sideboard
TOMCAT 6.0.24 , jdk 1.6.0_18, cant see any changes in logs/catalina.yyyy-MM-dd.log filesUlcerative
set NO_SOAP_STACKTRACE=-Dcom.sun.xml.ws.fault.SOAPFaultBuilder.disableCaptureStackTrace=false set JAVA_OPTS=%JAVA_OPTS% %NO_SOAP_STACKTRACE% echo NO_SOAP_STACKTRACE This works, just (I'm editing the bat version of catalina) be sure to REMOVE every space (the text you showed us contains a space before the "=" char and one after)Tuddor
H
2

If you working with Jboss 6.1 and you want to print the logs for the JAX-WS generated classes request to the SOAP web service, open the file /home/oracle/jboss-eap-6.1/bin/standalone.sh note: please go where you have installed jboss

You will find something like this

JAVA_OPTS="$JAVA_OPTS -agentlib:jdwp=transport=dt_socket,address=$DEBUG_PORT,server=y,suspend=n"

Change it to the one shown below

JAVA_OPTS="$JAVA_OPTS -Dcom.sun.xml.ws.transport.http.client.HttpTransportPipe.dump=true -agentlib:jdwp=transport=dt_socket,address=$DEBUG_PORT,server=y,suspend=n"

Also make sure you enable debug

DEBUG_MODE=true
Higa answered 14/4, 2015 at 20:32 Comment(0)
C
1

I think that what you need is an handler, see: http://jax-ws.java.net/articles/handlers_introduction.html
With handler you can intercept web service call, and have access to all the SOAP message.

Christopherchristopherso answered 30/3, 2011 at 9:4 Comment(0)
L
1

This worked for me:

-Dcom.sun.xml.ws.transport.http.client.HttpTransportPipe.dump=true
Locris answered 27/10, 2014 at 12:13 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.