【问题标题】:payload source of response with spring ws MockWebServiceClient使用 spring ws MockWebServiceClient 响应的有效负载源
【发布时间】:2011-06-06 23:28:05
【问题描述】:

我正在使用 spring-ws 2.0.2 和 spring-ws-test 来运行我的 SOAP 服务器的集成测试。我正在使用与 http://static.springsource.org/spring-ws/site/apidocs/org/springframework/ws/test/server/MockWebServiceClient.html

完全相同的方法

这是我正在运行的代码,为简洁起见省略了预期的响应 XML,因为它与问题无关。

我希望能够在响应负载中看到 xml,但不知道如何访问它。如果我在设置响应后设置断点并检查它,我可以看到它有一个 SaajSoapMessage 类型的私有 messageContext.response 但我不知道如何访问它,或者是否有更好的方法来查看响应 XML。

package com.example.integration;                                                                     

import static org.springframework.ws.test.server.RequestCreators.*;                                 
import static org.springframework.ws.test.server.ResponseMatchers.*;                                
import static org.testng.AssertJUnit.*;                                                             

import javax.xml.transform.Source;                                                                  

import org.springframework.beans.factory.annotation.Autowired;                                      
import org.springframework.context.ApplicationContext;                                              
import org.springframework.ws.test.server.MockWebServiceClient;                                     
import org.springframework.ws.test.server.ResponseActions;                                          
import org.springframework.xml.transform.StringSource;                                              
import org.testng.annotations.BeforeClass;                                                          
import org.testng.annotations.Test;                                                                 

@ContextConfiguration(locations={"/transaction-test-context.xml", "/spring-web-services-servlet.xml"})
public class BaseWebServiceIntegrationTest {                          

    @Autowired
    private ApplicationContext applicationContext;

    private MockWebServiceClient mockClient;

    @BeforeClass(groups="integration")
    public void createClient() {
        assertNotNull("expected applicationContext to be non-null", applicationContext);
        mockClient = MockWebServiceClient.createClient(applicationContext);
    }

    @Test(groups="integration")
    public void proofOfConcept() {

        assertNotNull("expected mockClient to be non-null", mockClient);

        Source requestPayload = new StringSource(
                "<s0:ListDevicesRequest " +
                "xmlns:soapenc='http://schemas.xmlsoap.org/soap/encoding/' " +
                "xmlns:xs='http://www.w3.org/2001/XMLSchema' " +
                "xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance' " +
                "xmlns:s0='urn:com:example:xmlschema:service:v1.1:DeviceManager.xsd'>" +
                    "<s0:MacID>66:bb:be:ee:00:00:01:00</s0:MacID>" +
                "</s0:ListDevicesRequest>"
                );

        Source responsePayload = new StringSource("<!-- response omitted for the post, not relevant -->");

        ResponseActions response = mockClient.sendRequest(withPayload(requestPayload));
        response.andExpect(noFault())
                .andExpect(payload(responsePayload));

    }
}

已按要求添加应用程序上下文文件。我们有一些,但下面的一个是肥皂专用的。

<?xml version="1.0"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:p="http://www.springframework.org/schema/p"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:tx="http://www.springframework.org/schema/tx"
       xmlns:sec="http://www.springframework.org/schema/security"
       xsi:schemaLocation="
        http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
        http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security-3.0.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd">

    <sec:global-method-security pre-post-annotations="disabled" jsr250-annotations="disabled" />

    <tx:annotation-driven/>
    <context:component-scan base-package="com.example.integration"/>
    <context:component-scan base-package="com.example.signal"/>

    <bean id="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean"/>

    <bean id="faultService" class="com.example.webservice.fault.FaultService"/>

    <bean id="soapDeviceService" class="com.example.webservice.device.SoapDeviceServiceImpl"/>


    <!-- 1.1 Endpoints -->
    <bean id="deviceManagerEndpoint_v1_1" class="com.example.webservice.spring.DeviceManagerEndpoint">
        <property name="soapDeviceService" ref="soapDeviceService"/>
    </bean>



    <bean class="com.example.webservice.spring.PayloadMethodMarshallingEndpointAdapter">
        <property name="marshaller" ref="marshaller"/>
        <property name="unmarshaller" ref="marshaller"/>
    </bean>
    <bean id="marshaller" class="org.springframework.oxm.jaxb.Jaxb2Marshaller">
        <property name="mtomEnabled" value="false"/>
        <property name="contextPath" value="com.example.xmlschema.service.v1_0.devicemanager"/>
    </bean>

    <bean class="org.springframework.ws.server.endpoint.mapping.PayloadRootAnnotationMethodEndpointMapping">
        <property name="interceptors">
            <list>
                <bean class="com.example.webservice.interceptor.LoggingInterceptor"/>
                <ref bean="validatingInterceptor"/>
            </list>
        </property>
    </bean>

    <bean id="validatingInterceptor" class="org.springframework.ws.soap.server.endpoint.interceptor.PayloadValidatingInterceptor">
        <property name="schemas">
            <list>
                <value>/WEB-INF/wsdl/*Types_v*.xsd</value>
            </list>
        </property>
        <property name="validateRequest" value="true"/>
        <property name="validateResponse" value="true"/>
    </bean>

    <bean class="com.example.webservice.spring.SpringWebserviceFaultMappingExceptionResolver">
        <property name="order" value="1"/>
        <property name="marshaller" ref="marshaller"/>
    </bean>

</beans>

【问题讨论】:

  • 我们可以看看spring-web-services-servlet.xml吗?

标签: integration-testing spring-ws


【解决方案1】:

好吧,晚了 4 年,但这是我的答案,我为之感到骄傲和羞愧:-

.andExpect(
    new ResponseMatcher()
    {
        @Override
        public void match(WebServiceMessage request, WebServiceMessage response)
            throws IOException, AssertionError
        {
            response.writeTo(System.out);
        }
    })

从 Java 8 开始:

.andExpect((request, response) -> response.writeTo(System.out))

【讨论】:

  • 这在 eclipse 中作为代码 sn-p 模板太棒了!
  • 3 年后又是一个更好的等效解决方案,这要归功于 Java 8!
  • 发送请求时如何指定url?
【解决方案2】:

您可以在您的 spring-ws 上下文中安装一个 PayloadLoggingInterceptor,默认情况下它将记录所有请求和响应负载。像这样配置它:

<sws:interceptors>
  <bean class="org.springframework.ws.server.endpoint.interceptor.PayloadLoggingInterceptor"/>
</sws:interceptors>

查看 springsource 文档了解更多信息 here

【讨论】:

    【解决方案3】:

    配置 log4j 并在 log4j 中添加配置以显示 spring 类日志。日志将显示调用 Spring 类的顺序以及发送的请求和响应。

    <logger name="org.springframework.ws" additivity="false">
       <level value="DEBUG#org.tiaa.infra.logging.TiaaLevel" />
       <appender-ref ref="DailyRollingFileAppender"/>
    </logger>
    

    【讨论】:

      【解决方案4】:

      +1 @NeilStevens 解决方案...永远不会太晚!。谢谢 :-) 这是一个轻微的重构,可以将内容打印到 sf4j 记录器并使用静态导入的魔力...:

      import static SomeTestClass.ResponseOutputMatcher.printResponse;
      
      
      public class SomeTestClass {
          private static final Logger LOG = LoggerFactory.getLogger(SomeTestClass.class);
      
          @Test
          public void someTest() {
      
              mockClient.sendRequest(...)
                .andExpect(printResponse(LOG))
                .andExpect(noFault());
          }
      
          @RequiredArgsConstructor
          public static class ResponseOutputMatcher implements ResponseMatcher {
              private final Logger logger;
      
              public ResponseOutputMatcher() {
                  this(LoggerFactory.getLogger(ResponseOutputMatcher.class));
              }
      
              @Override
              public void match(WebServiceMessage request, WebServiceMessage response) throws IOException, AssertionError {
                  ByteArrayOutputStream out = new ByteArrayOutputStream();
                  response.writeTo(out);
                  logger.info(format("Received payload response:\n%s\n%s\n%s", repeat(">", 80), out.toString(), repeat("_", 80)));
              }
      
              public static ResponseMatcher printResponse(Logger logger) {
                  return new ResponseOutputMatcher(logger);
              }
          }
      

      【讨论】:

      • 发送请求时如何指定url
      猜你喜欢
      • 2019-04-03
      • 2011-09-19
      • 2017-11-30
      • 2017-05-04
      • 1970-01-01
      • 2020-04-05
      • 1970-01-01
      • 2016-11-26
      • 1970-01-01
      相关资源
      最近更新 更多