开发者

@PayloadRoot value when using Objects and not schema xml

I'm using Objects as messages from client to service server. How should the endpoint be configured so that the service would be found? @PayloadRoot seems unfitting here because i don't use xml schema but Objects annotated with @XmlRootElement (i.e. Street)

my code:

the spring-ws-servlet.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xmlns:context="http://www.springframework.org/schema/context"
   xmlns:sws="http://www.springframework.org/schema/web-services"
   xmlns:oxm="http://www.springframework.org/schema/oxm"
   xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
   http://www.springframework.org/schema/web-services http://www.springframework.org/schema/web-services/web-services-2.0.xsd
   http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd
   http://www.springframework.org/schema/oxm http://www.springframework.org/schema/oxm/spring-oxm-3.0.xsd">

<context:component-scan base-package="com.coral.project.endpoints"/>

<sws:annotation-driven />

<sws:dynamic-wsdl id="test" portTypeName="TestCase" locationUri="/testService/"
                  targetNamespace="http://www.example.org/schemasDef/test/definitions">
    <sws:xsd location="/WEB-INF/schemasDef开发者_Python百科/test.xsd"/>
</sws:dynamic-wsdl>

<bean id="springWSClient" class="com.coral.project.endpoints.SpringWSClient">
    <property name="defaultUri" value="http://localhost:8080/parking/springServices/testService/"/>
    <property name="marshaller" ref="marshaller" />
    <property name="unmarshaller" ref="marshaller" />
</bean>

<oxm:jaxb2-marshaller id="marshaller">
    <oxm:class-to-be-bound name="com.coral.project.entity.Street"/>
</oxm:jaxb2-marshaller>
</beans>

the client:

public class SpringWSClient extends WebServiceGatewaySupport {

public void getSum() throws SOAPException, IOException, TransformerException {
    StreetDao streetDao = SpringUtils.getBean(StreetDao.class);
    Street street = streetDao.findById(1);

    getWebServiceTemplate().marshalSendAndReceive(street);

}
}

the endpoint:

@Endpoint
public class SpringWsEndpoint {

@Inject
private SpringWebService springWebService;

@PayloadRoot(localPart = "street", namespace = "http://blahblah")
@ResponsePayload
public Element handleTestRequest(@RequestPayload SAXSource testRequest) throws Exception {

    String fisrt = firstNum.valueOf(testRequest);
    String second = secondNum.valueOf(testRequest);

    String sum = springWebService.sum(Integer.parseInt(fisrt), Integer.parseInt(second)).toString();

    Element responseElement = new Element("TestRequest");
    Element sumElement = new Element("sum");
    sumElement.setText(sum);
    responseElement.setContent(sumElement);

    return responseElement;
}

}


Found out how to do it. Had to make several fixes. Most importantly @XmlRootElement name and namespace attributes are required in my case. So the working code is:

test.xsd

<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns:test="http://www.example.org/schemasDef/test/schemas" 
    elementFormDefault="qualified"
    targetNamespace="http://www.example.org/schemasDef/test/schemas">

    <xs:element name="TestRequest">
        <xs:complexType>
            <xs:all>
                <xs:element name="firstNum" type="xs:integer" />
                <xs:element name="secondNum" type="xs:integer" />
                <xs:element name="sum" type="xs:integer" />
            </xs:all>
        </xs:complexType>
    </xs:element>

</xs:schema>

TestRequest.java

package com.coral.project.entity;

import javax.xml.bind.annotation.XmlRootElement;

@XmlRootElement(name="TestRequest",namespace="http://www.example.org/schemasDef/test/schemas")
public class TestRequest {

private Integer firstNum;
private Integer secondNum;
private Integer sum;

public Integer getFirstNum() {
    return firstNum;
}
public void setFirstNum(Integer firstNum) {
    this.firstNum = firstNum;
}
public Integer getSecondNum() {
    return secondNum;
}
public void setSecondNum(Integer secondNum) {
    this.secondNum = secondNum;
}
public Integer getSum() {
    return sum;
}
public void setSum(Integer sum) {
    this.sum = sum;
}

}

spring-ws-servlet.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xmlns:context="http://www.springframework.org/schema/context"
   xmlns:sws="http://www.springframework.org/schema/web-services"
   xmlns:oxm="http://www.springframework.org/schema/oxm"
   xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
   http://www.springframework.org/schema/web-services http://www.springframework.org/schema/web-services/web-services-2.0.xsd
   http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd
   http://www.springframework.org/schema/oxm http://www.springframework.org/schema/oxm/spring-oxm-3.0.xsd">

<context:component-scan base-package="com.coral.project.endpoints"/>

<sws:annotation-driven marshaller="marshaller" unmarshaller="marshaller"/>

<sws:dynamic-wsdl id="test" portTypeName="TestCase" locationUri="/testService/"
                  targetNamespace="http://www.example.org/schemasDef/test/definitions">
    <sws:xsd location="/WEB-INF/schemasDef/test.xsd"/>
</sws:dynamic-wsdl>

<bean id="springWSClient" class="com.coral.project.endpoints.SpringWSClient">
    <property name="defaultUri" value="http://localhost:8080/parking/springServices/testService"/>
    <property name="marshaller" ref="marshaller" />
    <property name="unmarshaller" ref="marshaller" />
</bean>

<oxm:jaxb2-marshaller id="marshaller">
    <oxm:class-to-be-bound name="com.coral.project.entity.TestRequest"/>
</oxm:jaxb2-marshaller>
</beans>

SpringWsEndpoint.java

package com.coral.project.endpoints;

import javax.inject.Inject;

import org.springframework.ws.server.endpoint.annotation.Endpoint;
import org.springframework.ws.server.endpoint.annotation.PayloadRoot;
import org.springframework.ws.server.endpoint.annotation.RequestPayload;
import org.springframework.ws.server.endpoint.annotation.ResponsePayload;

import com.coral.project.entity.TestRequest;
import com.coral.project.services.ifc.SpringWebService;

@Endpoint
public class SpringWsEndpoint {

private static final String NAMESPACE_URI = "http://www.example.org/schemasDef/test/schemas";

@Inject
private SpringWebService springWebService;


@PayloadRoot(namespace = NAMESPACE_URI, localPart = "TestRequest")
@ResponsePayload
public TestRequest handleTestRequestObj(@RequestPayload TestRequest testRequest) throws Exception {

    Integer sum = springWebService.sum(testRequest.getFirstNum(), testRequest.getSecondNum());
    testRequest.setSum(sum);
    return testRequest;

}


}

SpringWsClient.java

package com.coral.project.endpoints;

import java.io.IOException;

import javax.xml.soap.SOAPException;
import javax.xml.transform.TransformerException;

import org.springframework.ws.client.core.support.WebServiceGatewaySupport;

import com.coral.project.entity.TestRequest;

public class SpringWSClient extends WebServiceGatewaySupport {

public TestRequest getTestRequest() throws SOAPException, IOException, TransformerException {
    TestRequest testRequest = new TestRequest();
    testRequest.setFirstNum(6);
    testRequest.setSecondNum(9);

    TestRequest testResponse = (TestRequest)getWebServiceTemplate().marshalSendAndReceive(testRequest);
    return testResponse;
}
}


Thanks a bunch, I had to make a similar trick for my own needs and your solution was the last bit I needed to get it working. I'll summarize the differences here for reference.

I was working on an endpoint that gets arbitrary XML and returns arbitrary XML. No marshalling or unmarshalling because the data is said to be huge. The receiving end is documented here.

A simple String container:

package our.site.etc;

import javax.xml.bind.annotation.XmlRootElement;

@XmlRootElement(name="StringResponse",namespace="http://link.to.our/schemas/service/endpoint/yyyy/mm/dd")
public class StringResponse {
private String responseData;

public StringResponse() {
    ;
}

public StringResponse(String data) {
    this.responseData = data;
}

public String getResponseData() {
    return responseData;
}

public void setResponseData(String data) {
    this.responseData = data;
}

}

The endpoint method:

@PayloadRoot(localPart = LOCALPART, namespace = NAMESPACE)
@ResponsePayload
public @ResponseBody StringResponse receiveMessage(MessageContext messageContext) throws Exception {
    // do our thing:
    return new StringResponse(super.handleMessage(messageContext));
}

And the final touch was to omit the WSClient part, just to define the jaxb2 marshaller:

<oxm:jaxb2-marshaller id="marshaller">
    <oxm:class-to-be-bound name="our.site.etc.StringResponse"/>
</oxm:jaxb2-marshaller>

And now my endpoint returns the response String inside CDATA. Practically it just passes data around, doing minimal things to it.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜