简体   繁体   English

Java CXF Restful Web服务

[英]Java CXF restful webservices

My webservice class is as following: 我的网络服务类如下:

package com.siemens.rest;
import java.io.ByteArrayInputStream;
import java.math.BigDecimal;

import javax.annotation.Resource;
import javax.servlet.ServletRequest;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.Source;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamSource;
import javax.xml.ws.BindingType;
import javax.xml.ws.Provider;
import javax.xml.ws.WebServiceContext;
import javax.xml.ws.WebServiceProvider;
import javax.xml.ws.handler.MessageContext;
import javax.xml.ws.http.HTTPBinding;
import javax.xml.ws.http.HTTPException;

import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xml.sax.InputSource;

@WebServiceProvider
@BindingType(value = HTTPBinding.HTTP_BINDING)
public class ConverterService implements Provider<Source> {

    /**
     * 
     */
    private static final long serialVersionUID = 1L;

    @Resource
    protected WebServiceContext wsContext;

    private BigDecimal rupeeRate = new BigDecimal("40.58");
    private BigDecimal euroRate = new BigDecimal("0.018368");

    public Source invoke(Source source) {
        try {
            String amount = null;

            if (source == null) {
                System.out.println("Getting input from query string");
                MessageContext mc = wsContext.getMessageContext();
                String query = (String) mc.get(MessageContext.QUERY_STRING);
                System.out.println("Query String = " + query);
                ServletRequest req = (ServletRequest) mc
                        .get(MessageContext.SERVLET_REQUEST);
                amount = req.getParameter("amount");
            } else {
                System.out.println("Getting input from input message");
                Node n = null;
                if (source instanceof DOMSource) {
                    n = ((DOMSource) source).getNode();
                } else if (source instanceof StreamSource) {
                    StreamSource streamSource = (StreamSource) source;
                    DocumentBuilderFactory dbf = DocumentBuilderFactory
                            .newInstance();
                    DocumentBuilder db = dbf.newDocumentBuilder();
                    InputSource inputSource = null;
                    if (streamSource.getInputStream() != null) {
                        inputSource = new InputSource(
                                streamSource.getInputStream());
                    } else if (streamSource.getReader() != null) {
                        inputSource = new InputSource(streamSource.getReader());
                    }
                    n = db.parse(inputSource);
                } else {
                    throw new RuntimeException("Unsupported source: " + source);
                }
                NodeList children = n.getChildNodes();
                for (int i = 0; i < children.getLength(); i++) {
                    Node child = children.item(i);
                    if (child.getNodeName().equals("dollars")) {
                        amount = child.getAttributes().getNamedItem("amount")
                                .getNodeValue();
                        break;
                    }
                }
            }
            BigDecimal dollars = new BigDecimal(amount);
            BigDecimal rupees = dollarToRupees(dollars);
            BigDecimal euros = rupeesToEuro(rupees);
            return createResultSource(rupees, euros);
        } catch (Exception e) {
            e.printStackTrace();
            throw new HTTPException(500);
        }
    }

    public BigDecimal dollarToRupees(BigDecimal dollars) {
        BigDecimal result = dollars.multiply(rupeeRate);
        return result.setScale(2, BigDecimal.ROUND_UP);
    }

    public BigDecimal rupeesToEuro(BigDecimal rupees) {
        BigDecimal result = rupees.multiply(euroRate);
        return result.setScale(2, BigDecimal.ROUND_UP);
    }

    private Source createResultSource(BigDecimal rupees, BigDecimal euros) {
        String body = "<ns:return xmlns:ns=\"http://rest.jaxws.samples.geronimo.apache.org\">"
                + "<ns:dollarToRupeesResponse>"
                + rupees
                + "</ns:dollarToRupeesResponse><ns:rupeesToEurosResponse>"
                + euros + "</ns:rupeesToEurosResponse></ns:return>";
        Source source = new StreamSource(new ByteArrayInputStream(
                body.getBytes()));
        return source;
    }
}

and the web.xml as follows: 和web.xml如下:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
  xmlns="http://java.sun.com/xml/ns/javaee"
  xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" 
  xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
  id="WebApp_ID" version="2.5">
  <display-name>jaxws-rest-converter</display-name>
  <servlet>
    <servlet-name>ConverterService</servlet-name>
    <servlet-class> com.siemens.rest.ConverterService </servlet-class>
    <load-on-startup>0</load-on-startup>
  </servlet>
  <servlet-mapping>
    <servlet-name>ConverterService</servlet-name>
    <url-pattern>/converter</url-pattern>
  </servlet-mapping>
</web-app>

While deploying it in tomcat 6.0, iam getting the following exception: 在tomcat 6.0中部署它时,iam收到以下异常:

SEVERE: Servlet /jaxws-rest-converter threw load() exception java.lang.ClassCastException: com.siemens.rest.ConverterService cannot be cast to javax.servlet.Servlet at org.apache.catalina.core.StandardWrapper.loadServlet(StandardWrapper.java:1116) at org.apache.catalina.core.StandardWrapper.load(StandardWrapper.java:993) at org.apache.catalina.core.StandardContext.loadOnStartup(StandardContext.java:4420) at org.apache.catalina.core.StandardContext.start(StandardContext.java:4733) at org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1053) at org.apache.catalina.core.StandardHost.start(StandardHost.java:840) at org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1053) at org.apache.catalina.core.StandardEngine.start(StandardEngine.java:463) at org.apache.catalina.core.StandardService.start(StandardService.java:525) at org.apache.catalina.core.StandardServer.start(StandardServer.java:754) at org.apache.catalina.startup.Catalina.start(Catalina.java:595) at sun.ref 严重:Servlet / jaxws-rest-converter抛出load()异常java.lang.ClassCastException:com.siemens.rest.ConverterService无法在org.apache.catalina.core.StandardWrapper.loadServlet(StandardWrapper)上转换为javax.servlet.Servlet。 .java:1116),位于org.apache.catalina.core.StandardContext.loadOnStartup(StandardContext.java:4420),位于org.apache.catalina.core.StandardWrapper.load(StandardWrapper.java:993)。 org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1053)的core.StandardContext.start(StandardContext.java:4733)org.apache.catalina.core.StandardHost.start(StandardHost.java:840)的core.StandardContext.start(StandardContext.java:4733)在org.apache.catalina.core.StandardEngine.start(StandardEngine.java:463)在org.apache.catalina.core.StandardEngine.start(ContainerBase.java:1053)在org.apache.catalina.core.StandardService.start (StandardService.java:525),位于org.apache.catalina.core.StandardServer.start(StandardServer.java:754),位于org.apache.catalina.startup.Catalina.start(Catalina.java:595),位于sun.ref lect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) at java.lang.reflect.Method.invoke(Unknown Source) at org.apache.catalina.startup.Bootstrap.start(Bootstrap.java:289) at org.apache.catalina.startup.Bootstrap.main(Bootstrap.java:414) org的lect.NativeMethodAccessorImpl.invoke0(本地方法),sun.reflect.NativeMethodAccessorImpl.invoke(未知源),org.java.lang.reflect.Method.invoke(未知的源)。 apache.catalina.startup.Bootstrap.start(Bootstrap.java:289)在org.apache.catalina.startup.Bootstrap.main(Bootstrap.java:414)

I think the web.xml is wrong, can anyone pls help me in this. 我认为web.xml是错误的,任何人都可以在这方面帮助我。 Iam trying to implement restful webservices in CXF . Iam试图在CXF实现静态的Web服务。

I think that you have several things wrong in your implementation. 我认为您在执行中有几处错误。

First of all your web.xml is indeed wrong. 首先,您的web.xml确实是错误的。 This file is meant to declare servlets, filters, etc, but never webservices providers. 该文件用于声明servlet,过滤器等,但不能声明webservices提供程序。 You are getting the ClassCastException because you are telling that your ConverterService is a servlet. 之所以得到ClassCastException是因为您告诉您ConverterService是一个servlet。

So, what you need to do is to declare the Apache CXF servlet in you web.xml to let him anwser some request. 因此,您需要做的是在web.xml中声明Apache CXF servlet,以使他处理一些请求。 Check this example: 检查以下示例:

   <!-- 
       Web service Front Controller. It will receive all the web service request and then it 
       delegates the request to the web services configured in the CXF config file
    -->
    <servlet>
        <servlet-name>CXFServlet</servlet-name>
        <servlet-class>org.apache.cxf.transport.servlet.CXFServlet</servlet-class>
        <load-on-startup>1</load-on-startup>
    </servlet>

    <!-- 
       Every request that start with this will be handled by the CXF servlet 
    -->
    <servlet-mapping>
      <servlet-name>CXFServlet</servlet-name>
      <url-pattern>/ctx/authbasic/ws/*</url-pattern>
    </servlet-mapping>

After this, you need to declare correctly each one of your webservices. 此后,您需要正确声明每个Web服务。 I use Spring to config my Apache CXF services, so here you can check an example. 我使用Spring来配置Apache CXF服务,因此您可以在此处查看示例。

    <jaxws:endpoint id="dataService"
        implementor="some.package.DataSIB"
        address="/DataService" wsdlLocation="classpath:wsdls/DataService.wsdl">
        <jaxws:properties>
            <!-- jaxws properties binding config -->
        </jaxws:properties>
        <jaxws:dataBinding>
          <!-- data binding config -->
        </jaxws:dataBinding>
    </jaxws:endpoint>

With this configuration, you any request to /ctx/authbasic/ws/DataService will be handled by the web services implementation. 使用此配置,您对/ctx/authbasic/ws/DataService任何请求都将由Web服务实现处理。 Here the example of a web service declaration (SEI) and its implementation (SIB): 以下是Web服务声明(SEI)及其实现(SIB)的示例:

@WebService(name = "dataService", targetNamespace = "http://some-domain/dataservice/definition")
@SOAPBinding(style = Style.DOCUMENT, use = Use.LITERAL, parameterStyle = ParameterStyle.WRAPPED)
public interface DataSEI {
    // You methods here
}

@WebService(endpointInterface = "some.package.DataSEI",
serviceName = "dataServiceService",
portName = "dataServicePort",
targetNamespace = "http://some-domain/dataservice/definition")
public class DataSIB implements DataSEI {
   // Your methods here
}

NOTE: This is an example of a SOAP web services, but this might help you to understand the framework 注意:这是SOAP Web服务的示例,但这可能有助于您了解框架。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM