http://elf8848.iteye.com/blog/1048707
作者:赵磊
博客:http://elf8848.iteye.com
?
一、WebService应用场景简述
WebService的主要目标是跨平台的可互操作性。为了达到这一目标,WebService完全基于XML(可扩展标记语言)、XSD(XMLSchema)等独立于平台、独立于软件供应商的标准,是创建可互操作的、分布式应用程序的新平台。
1、跨防火墙的通信,基本HTTP协议,走80端口,多公司,多机房通信时不用为防火墙烦恼
2、应用程序集成,把用不同语言写成的、在不同平台上运行的各种程序集成起来,也就是异构系统的系统。比如服务端是java的webService实现XFire做的服务端,客户端是.net的?webService实现或C++的?webService实现都可以。
?不适合使用WebService的场景
1、单机应用程序
2、局域网的同构应用程序
总之,只要从应用程序结构的角度看,有别的方法比WebService更有效、更可行,那就不要用WebService,WebService的性能是多种通信协议中最慢的.
二、XFire简介
?XFire是新一代的Java WebService引擎,XFire使得在JavaEE应用中发布Web服务变得轻而易举。和其他Web服务引擎相比,XFire的配置非常简单,可以非常容易地和Spring集成,它使得Java开发人员终于可以获得和.Net开发人员一样的开发效率。
?XFire是codeHaus组织提供的一个开源框架,它构建了POJO和SOA之间的桥梁,主要特性就是支持将POJO通过非常简单的方式发布成Web服务,这种处理方式不仅充分发挥了POJO的作用,简化了Java应用转化为Web服务的步骤和过程,也直接降低了SOA的实现难度,为企业转向SOA架构提供了一种简单可行的方式。
?XFire?支持将Web服务绑定到POJO、XMLBeans、JAXB1.1、JAXB2.0和Castor;
支持基于HTTP、JMS、XMPP等多种协议访问Web服务;
支持多种Web服务业界重要标准如SOAP、WSDL、Web服务寻址(WS-Addressing)、Web服务安全(WS-Security)等;
支持JSR181,可以通过JDK5配置Web服务;
高性能的SOAP实现;
服务器端、客户端代码辅助生成;
对Spring、Pico、Plexus等项目的支持等。
?XFire是一种基于Servlet技术的SOA应用开发框架,需要Servlet容器的支持。XFire支持在多种Servlet容器中运行,包括Websphere、Weblogic、TOMCAT等。支持JDK 1.4以上(含1.4).
?XFire框架目前的最新版本是1.2.6,可以访问http://xfire.codehaus.org?下载XFire框架的安装包,下载时请选择“全部二进制发布包”,而不仅仅是“XFirejar文件".下载地址:http://xfire.codehaus.org/Download
三、快速发布WebService接口:
1.下载XFire
2.用Eclipse创建一个Web项目,
3.导入xfire-distribution-1.2.6xfire-1.2.6lib中的所以jar包
4.导入xfire-distribution-1.2.6xfire-1.2.6xfire-all-1.2.6.jar包
5.创建实体类User类,这个类将被通过SOAP协议传输.
- package?webService;??
- import?java.util.Date;??
- public?class?User?{??
- ????private?static?final?long?serialVersionUID?=?6517808321041980976L;??
- private?Long?userId;??
- private?String?accountId;??
- private?String?userName;??
- private?Date?lastLogin;??
- ??
- public?String?getAccountId()?{??
- ????????return?accountId;??
- ????}??
- void?setAccountId(String?accountId)?{??
- this.accountId?=?accountId;??
- public?Date?getLastLogin()?{??
- return?lastLogin;??
- void?setLastLogin(Date?lastLogin)?{??
- this.lastLogin?=?lastLogin;??
- public?Long?getUserId()?{??
- return?userId;??
- void?setUserId(Long?userId)?{??
- this.userId?=?userId;??
- public?String?getUserName()?{??
- return?userName;??
- void?setUserName(String?userName)?{??
- this.userName?=?userName;??
- }??
?
6.编写接口UserService,这个接口暴露两个方法
package?webService.server;??
import?webService.User;??
interface?UserService?{??
public?User?queryUserByAccoutId(String?accountId);??
void?createUser(User?user);??
7.实现接口UserServiceImpl,实现接口UserService.
import?java.rmi.RemoteException;??
import?org.apache.commons.logging.Log;??
import?org.apache.commons.logging.LogFactory;??
class?UserServiceImpl?implements?UserService?{??
final?Log?log?=?LogFactory.getLog(UserServiceImpl.class);??
void?createUser(User?user)?{??
????????log.debug("createUser?user="?+?user);??
public?User?queryUserByAccoutId(String?key)?{??
????????log.info("key="?+?key);??
????????User?user?=?new?User();??
????????user.setAccountId("testAccount");??
????????user.setLastLogin(new?Date());??
????????user.setUserId(new?Long(123L));??
????????user.setUserName("用户名");??
return?user;??
8.修改web.xml文件,目的是注册servlet,发布暴露WSDL.
<?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">??
- ??context-param ????param-name>contextConfigLocation</param-value>classpath:applicationContext.xml>??这是spring的配置文件??
- listenerlistener-class>org.springframework.web.context.ContextLoaderListenerservletservlet-name>xfireservlet-class>org.codehaus.xfire.spring.XFireSpringServletservlet-mappingurl-pattern>/service/*>??注意这个地址,一会要访问这个地址,查看wsdl??
- web-app>??
9.修改spring配置文件applicationContext.xml
?>???
<!DOCTYPE?beans?PUBLIC?"-//SPRING//DTD?BEAN//EN"?"http://www.springframework.org/dtd/spring-beans.dtd"beansimport?resource="classpath:org/codehaus/xfire/spring/xfire.xml"?/>??
bean?id="baseWebService"?class="org.codehaus.xfire.spring.remoting.XFireExporter"??
????????lazy-init="false"?abstract="true" ????????property?name="serviceFactory"?ref="xfire.serviceFactory"?property?name="xfire"?ref="xfire"?beanbean?id="userWS"?class="webService.server.UserServiceImpl">>??这是接口实现类??
bean?id="userService"?parent="baseWebService">????
property?name="serviceBean"?ref="userWS"?property?name="serviceClass"?value="webService.server.UserService"?/>??这是接口??
10. 启动TOMCAT,?
访问地址:?? http://localhost:8080/应用根/service?? 查看wsdl
如果能查看到wsdl,服务端就OK了
也可以使用Eclipse中的WTP中的Web Service Explore测试SOAP方式,具体操作方法,看最后面下载中的PDF文件.
下面生成客户端
11.通过Ant自动生成客户端,在web目录 (你可能是WebRoot)创建build.xml文件,并运行这个文件生成代码,注意根据你的情况修改哦.
xml?
version=
"1.0"project?
name=
"wsgen"?
default=
"wsgen"?
basedir=
"."path?
id=
"classpathId"fileset?
dir=
"./WEB-INF/lib" ????????????include?name="*.jar"?filesetpathtaskdef?classpathref="classpathId"?name="wsgen"?classname="org.codehaus.xfire.gen.WsGenTask"taskdeftarget?name="wsgen"?description="generate?client"wsgen?outputDirectory="../src/"?wsdl="http://127.0.0.1:8080/RR_Test/service/UserService?wsdl"?binding="xmlbeans"?package="webService.client"?overwrite="true"? ????????????????????????请自行修改这几个参数,outputDirectory是src目录位置,????wsdl是wsdl的url改成你自己的地址,????package是生成的代码存放的包名??
?targetproject 12. 编写测试类WebServiceClientTest
package?webService.client;??
import?java.net.MalformedURLException;??
import?java.util.concurrent.ExecutorService;??
import?java.util.concurrent.Executors;??
import?org.apache.log4j.Logger;??
import?org.apache.xmlbeans.XmlObject;??
import?org.codehaus.xfire.client.Client;??
import?org.codehaus.xfire.client.XFireProxyFactory;??
import?org.codehaus.xfire.service.binding.ObjectServiceFactory;??
import?org.codehaus.xfire.transport.http.HttpTransport;??
import?webService.server.UserService;??
import?org.codehaus.xfire.service.Service;??
?
?*?说明:?WebService客户端,?是测试工具类?
?*??
?*?如何查看测试所用时间??
?*?请看log4j.properties文件,出输出日志到d:mina.log,?
?*?log4j记录每一次请求响应的日志,包括时间.?
?*?请使用结束的时间减去开始的时间,得到总用时.???
?*/??
class?WebServiceClientTest?{??
static?Logger?logger?=?Logger.getLogger(WebServiceClientTest. ??????
static?String?baseUrl?=?"http://127.0.0.1:8080/RR_Test";??
??????
//服务器返回的数据量大小,请根据需要修改?,有三个值可选?4k,15k,50k??
static?String?key="15k";??
//?这里修改并发数??
int?threadSize=100;??
//?这里修改重复次数??
int?count=?????*?主测试方法?
?????*??
?????*?@throws?MalformedURLException?
?????*/??
void?main(String[]?args)?{??
??????????
????????test1();??
//??????ExecutorService?exec?=?Executors.newFixedThreadPool(500);??
//??????logger.info("WebService?client说:开始测试");??
//??????for?(int?i?=?0;?i?<?threadSize;?i++)?{??
//??????????exec.execute(new?Runnable()?{??
//??????????????public?void?run()?{??
//??????????????????for?(int?j?=?0;?j?<?count;?j++)?{??
//??????????????????????test2();??
//??????????????????}??
//??????????????}??
//??????????});??
//??????}??
//??????exec.shutdown();??
?????*?测试1?
void?test1()?{??
????????UserServiceClient?client?=?new?UserServiceClient();??
????????String?url?=?baseUrl?+?"/service/UserService";??
????????XmlObject?xmlObject?=?client.getUserServiceHttpPort(url).queryUserByAccoutId("CN20106195184");??
????????System.out.println(xmlObject);??
?????*?测试2?
void?test2()?{??
try?{??
????????????Service?serviceModel?=?new?ObjectServiceFactory().create(UserService. ????????????UserService?service?=?(UserService)?new?XFireProxyFactory().create(serviceModel,?baseUrl??
????????????????????+?"/service/UserService");??
????????????Client?client?=?Client.getInstance(service);??
????????????client.setProperty("mtom-enabled",?"true");??
????????????client.setProperty(HttpTransport.CHUNKING_ENABLED,250); line-height:18px"> ????????????User?user?=?service.queryUserByAccoutId(key);??
????????????logger.info("userId="?+?user.getUserId()?+?",?userName长度="?+?user.getUserName().length()??
????????????????????+?",?lastLogin="?+?user.getLastLogin());??
????????}?catch?(MalformedURLException?e)?{??
????????????e.printStackTrace();??
????????}??
13.注意修改测试类中的URL,要与你的程序发布情况一致,主要是 IP,端口,应用根
这里log4j的东西,省略了,你自己加上吧.
运行main()方法,看结果吧
四、常见异常解决方法:
ps:如果出现class path resource [META-INF/xfire/services.xml] cannot be opened because it does not exist
修改方法:把META-INF文件夹copy到工程的build的classes目录下。
出现异常org.springframework.beans.factory.BeanDefinitionStoreException: Unrecognized xbean namespace mapping:http://XFire.codehaus.org/config/1.0?
查阅官方文档,发现 xmlns="http://xfire.codehaus.org/config/1.0?"> 是全部小写,立即替换,解决!
下面有电子书下载
(编辑:李大同)
【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!