How can I make Spring WebServices log all SOAP requests?

113,370

Solution 1

For Spring Boot project adding below in application.properties worked for me:

logging.level.org.springframework.web=DEBUG
logging.level.org.springframework.ws.client.MessageTracing.sent=DEBUG
logging.level.org.springframework.ws.server.MessageTracing.sent=DEBUG
logging.level.org.springframework.ws.client.MessageTracing.received=TRACE
logging.level.org.springframework.ws.server.MessageTracing.received=TRACE

Solution 2

You can use this to log the raw paylod of incoming and outgoing web service calls.. I'm not sure how to log how long the webservice communication took.

   <!-- Spring Web Service Payload Logging-->
   <logger name="org.springframework.ws.client.MessageTracing">
    <level value="TRACE"/> 
   </logger>
   <logger name="org.springframework.ws.server.MessageTracing">
    <level value="TRACE"/> 
   </logger>

Additional details can be found at http://static.springsource.org/spring-ws/site/reference/html/common.html#logging

Solution 3

This worked for me. It logs the request message sent and the response received. You could work out the total time taken from the log.

log4j.logger.org.springframework.ws.client.MessageTracing.sent=TRACE
log4j.logger.org.springframework.ws.client.MessageTracing.received=TRACE

Solution 4

If you have your own Logging system the following interceptor can be an alternative to log the SOAP messages.

    setInterceptors(new ClientInterceptor[]{new ClientInterceptor() {

        @Override
        public boolean handleResponse(MessageContext messageContext) throws WebServiceClientException {
            System.out.println("### SOAP RESPONSE ###");
            try {
                ByteArrayOutputStream buffer = new ByteArrayOutputStream();
                messageContext.getResponse().writeTo(buffer);
                String payload = buffer.toString(java.nio.charset.StandardCharsets.UTF_8.name());
                System.out.println(payload);
            } catch (IOException e) {
                throw new WebServiceClientException("Can not write the SOAP response into the out stream", e) {
                    private static final long serialVersionUID = -7118480620416458069L;
                };
            }

            return true;
        }

        @Override
        public boolean handleRequest(MessageContext messageContext) throws WebServiceClientException {

            System.out.println("### SOAP REQUEST ###");
            try {
                ByteArrayOutputStream buffer = new ByteArrayOutputStream();
                messageContext.getRequest().writeTo(buffer);
                String payload = buffer.toString(java.nio.charset.StandardCharsets.UTF_8.name());
                System.out.println(payload);
            } catch (IOException e) {
                throw new WebServiceClientException("Can not write the SOAP request into the out stream", e) {
                    private static final long serialVersionUID = -7118480620416458069L;
                };
            }

            return true;
        }

        @Override
        public boolean handleFault(MessageContext messageContext) throws WebServiceClientException {
            System.out.println("### SOAP FAULT ###");
            try {
                ByteArrayOutputStream buffer = new ByteArrayOutputStream();
                messageContext.getResponse().writeTo(buffer);
                String payload = buffer.toString(java.nio.charset.StandardCharsets.UTF_8.name());
                System.out.println(payload);
            } catch (IOException e) {
                throw new WebServiceClientException("Can not write the SOAP fault into the out stream", e) {
                    private static final long serialVersionUID = 3538336091916808141L;
                };
            }

            return true;
        }
    }});

In each handle method you can easily use payload to obtain raw soap messages.

Solution 5

First, SLF4J is just a simple facade. It means you still need a logging framework(e.g. java.util.logging, logback, log4j).

Second, Spring-ws uses Commons Logging interface that is another simple facade like SLF4J.

Finally, you can use below setting to enable Spring-ws message logging functionality.

log4j.logger.org.springframework.ws.client.MessageTracing.sent=DEBUG
log4j.logger.org.springframework.ws.client.MessageTracing.received=TRACE

log4j.logger.org.springframework.ws.server.MessageTracing.sent=DEBUG
log4j.logger.org.springframework.ws.server.MessageTracing.received=TRACE
Share:
113,370
Nate Reed
Author by

Nate Reed

Updated on July 05, 2022

Comments

  • Nate Reed
    Nate Reed almost 2 years

    I need all SOAP requests logged in the CommonLogFormat (see http://en.wikipedia.org/wiki/Common_Log_Format), plus the duration (the amount of time it takes to process the request).

    What's the best way to do this? It looks like it's possible to configure log4j for Spring WebServices but will it log all the values I'm interested in? http://pijava.wordpress.com/2009/12/04/spring-webservice-soap-requestresponse-logging-with-log4j/

    EDIT: We're actually using SLF4J, not Log4j. Also, it looks like it's possible to do this by configuring the PayloadLoggingInterceptor: http://static.springsource.org/spring-ws/site/reference/html/server.html#server-endpoint-interceptor

    But I am not sure where the log messages will go. I added that interceptor to our interceptors and I don't see any log messages.

  • wytten
    wytten over 11 years
    I can't find these classes in spring-ws 1.5.9
  • JustinKSU
    JustinKSU over 11 years
    They aren't classes, they are categories that are logged to. See documentation at static.springsource.org/spring-ws/site/reference/html/…
  • JustinKSU
    JustinKSU over 11 years
    PayloadLoggingInterceptor might also be helpful. Original poster added a link to it.
  • aram063
    aram063 almost 11 years
    Obviously, that should be added to your log4j.properties file.
  • JustinKSU
    JustinKSU over 8 years
    I would think so. Try it out and let us know!
  • theINtoy
    theINtoy over 8 years
    This worked for me. Thanks. Does anybody know how to pretty print the SOAP in the logs?
  • Ondrej Burkert
    Ondrej Burkert over 7 years
    Just a bit more concise syntax: <logger name="org.springframework.ws.client.MessageTracing" level="TRACE" />
  • hudi
    hudi about 7 years
    this just log message with http status 200 (OK). Is these some way to log message which end with other status like 400 ?
  • JustinKSU
    JustinKSU about 7 years
    @hudi it depends. Some things logged like 404 may not make it down to the Spring level. It's a 500 error thrown by the application, I think it should get logged. I would suggest asking a separate question with a little more detail.
  • Mukhamedali  Zhadigerov
    Mukhamedali Zhadigerov over 4 years
    I've added <appender> and now it logs to the file as well as console. How to make it log to the file only?
  • PeterS
    PeterS over 4 years
    Finally an answer that isn't using hard coded property files or spring XML!
  • mkane
    mkane over 4 years
    Link not valid anymore
  • Olgun Kaya
    Olgun Kaya about 4 years
    Below is where the logger's set. protected static final Log sentMessageTracingLogger = LogFactory.getLog("org.springframework.ws.client.MessageTrac‌​ing.sent"); protected static final Log receivedMessageTracingLogger = LogFactory.getLog("org.springframework.ws.client.MessageTrac‌​ing.received");
  • firstpostcommenter
    firstpostcommenter over 3 years
    Nice. Initially I was confused because Sent code flow was only using DEBUG and not TRACE so it did not print the complete SOAP message details for Request. But then I realised that the received message is in TRACE mode so it displays both the response and also the complete request message body to which the response is about
  • pdem
    pdem over 2 years
    Precisions, it could be obvious for some, but the method is exactly : org.springframework.ws.client.core.support.WebServiceGateway‌​Support#setIntercept‌​ors and the implemented interface is org.springframework.ws.client.support.interceptor.ClientInte‌​rceptor for which you also need to implment an empty afterCompletion method.
  • Procrastinator
    Procrastinator over 2 years
    If you have a new question, please ask it by clicking the Ask Question button. Include a link to this question if it helps provide context. - From Review
  • Anurag Yadav
    Anurag Yadav about 2 years
    Anyways ...just call your method MySoapClient() before client call