BartekS
BartekS

Reputation: 147

Spring Boot WS-Server - Custom Http Status

I published endpoints using Spring Boot WS-Server

When I use SoapUI I see:

HTTP/1.1 200 Accept: text/xml, text/html, image/gif, image/jpeg, *; q=.2, /; q=.2 SOAPAction: "" Content-Type: text/xml;charset=utf-8 Content-Length: 828 Date: Thu, 29 Apr 2021 14:04:54 GMT Keep-Alive: timeout=60 Connection: keep-alive

I would like to set custom HTTP Status in response (I know that it may be against the standard but it is an external requirement). I also read following topic:

Spring WS (DefaultWsdl11Definition) HTTP status code with void

But this solution failed

Spring Boot version: 2.2.7

Upvotes: 2

Views: 2160

Answers (1)

BartekS
BartekS

Reputation: 147

Problem was solved

As I said I wanted to set custom HTTP status in SOAP response.

I found this post: Spring WS (DefaultWsdl11Definition) HTTP status code with void

Author used EndpointInterceptor with TransportContext to get HttpServletResponse, then he changed status. The difference between my and his case is the fact, that he returned void from WebService method whereas I wanted to return some response.

In my situation following code in Spring WebServiceMessageReceiverObjectSupport class (method handleConnection) overrode servlet status previously set in interceptor:

if (response instanceof FaultAwareWebServiceMessage && connection instanceof FaultAwareWebServiceConnection) {
                    FaultAwareWebServiceMessage faultResponse = (FaultAwareWebServiceMessage)response;
                    FaultAwareWebServiceConnection faultConnection = (FaultAwareWebServiceConnection)connection;
                    faultConnection.setFaultCode(faultResponse.getFaultCode());
                }

In order to bypass this fragment of code I needed to define class with my own implementation of handleConnection method, which extended class WebServiceMessageReceiverHandlerAdapter

In my implementation I excluded change of status. Important thing is to pass WebMessageFactory bean in autowired constructor of this class, otherwise exception is raised during app's startup.

This class has to be marked with Spring stereotype (eg. @Component) and name of this bean has to be configured in Configuration class when configuring ServletRegistrationBean:

@Bean
    public ServletRegistrationBean<MessageDispatcherServlet> messageDispatcherServlet(ApplicationContext applicationContext){
        MessageDispatcherServlet servlet = new MessageDispatcherServlet();
        servlet.setApplicationContext(applicationContext);
        servlet.setTransformWsdlLocations(true);
        servlet.setMessageFactoryBeanName("webServiceMessageFactory");
        servlet.setMessageReceiverHandlerAdapterBeanName("myOwnMessageReceiverHandlerAdapter");
        return new ServletRegistrationBean<>(servlet,"/ws/*");
    }

Upvotes: 1

Related Questions