[Web Service]Web Service学习与工作原理研究|用IDEA开发Web Service
>简介
利用IDEA简单定义了一个WebService,以此作为一个实例。
采用的方式为Axis,发布的URL路径为:http://localhost:8080/WS2/services/HelloWorld。
接着利用IDEA打包成war包(WS2),放置在TOMCAT目录下的./Tomcat8.0/webapps/WS2。
在浏览器输入地址http://localhost:8080/WS2/services/HelloWorld可见:
发布成功。具体发布过程略,基本一路默认。可以参考本文文末:来自CSDN身披白袍的博客。
在这个基础上,来试着分析它的工作过程。
---------------------------------
>Web Service的三元素
(图片取自百度搜索)
Web Service(以下简称ws)的三个要素分别是UDDI、WSDL、SOAP。
- WSDL(网络服务描述语言,Web Services Description Language)
- SOAP (简单对象访问协议,Simple Object Access Protocol)
- UDDI(通用描述、发现与集成服务,Universal Description Discovery and Integration)
- WSDL定义在一个ws里,描述了这个ws的访问方法和提供内容,换句话说就是告诉用户怎么调用这个ws以及这个ws能用来做什么;
- SOAP则简单得多,说白了就是个数据载体,在ws和用户之间通过WSDL定义的接口进行数据转发;
- UDDI是对于企业而言的,参考上图,服务提供商发布了一个ws,要让所有人都能找到这个ws,就可以利用UDDI标记到服务市场,这有点像在商品身上贴个标签,告诉别人这个商品多少钱、在哪里可以买到。
---------------------------------
>WSDL
作为个人用户,一个开发者,我们着重关心的是一个ws要如何实现。而这就需要去学习有关WSDL的内容。
一个标准的WSDL主要包含四个部分:
这里有一个我在简介中提到的WSDL文档实例,可以到这里查看完全的源码,比较容易分析,或者,可以参考我经过折叠得到的下图:
已知,我提供的ws是:
package example;
public class HelloWorld {
public String sayHelloWorldFrom(String from) {//注意输入的请求值名为from
String result = "Hello, world, from " + from;
System.out.println(result);
return result;//反馈的值为sayHelloWorldFromReturn
}
}
先看<types>:
<wsdl:types>
<schema elementFormDefault="qualified" targetNamespace="http://example" xmlns="http://www.w3.org/2001/XMLSchema">
<element name="from" type="xsd:string"/><!--标记了客户端发来的数据所用的数据类型string-->
<element name="sayHelloWorldFromReturn" type="xsd:string"/><!--标记了服务返回的数据类型string-->
</schema>
</wsdl:types>
再看<message>:
<wsdl:message name="sayHelloWorldFromResponse">
<!--一个请求,名字为from,和<types>里标记的值是相同的,表示这个message:part对应的数据类型在types被定义为string,下同-->
<wsdl:part element="impl:sayHelloWorldFromReturn" name="sayHelloWorldFromReturn"/>
</wsdl:message>
<wsdl:message name="sayHelloWorldFromRequest">
<wsdl:part element="impl:from" name="from"/>
</wsdl:message>
接着是<portType>,定义了端口的操作类型。一共有四种,只接收(One-Way)、请求反馈(Request-response)、请求等待(Solicit-response)、提示(Notification)。
这四种模式,执行方式分别为:只接收请求但不反馈、接受请求后并反馈、发送一个请求并等待反馈、只发送请求。
最常用的是——请求反馈(Request-response):
<wsdl:portType name="HelloWorld"><!--端口名为HelloWorld,也就是http://localhost:8080/WS2/services/HelloWorld所标示的端口名-->
<wsdl:operation name="sayHelloWorldFrom" parameterOrder="from">
<!--一个请求,对应的Name为sayHelloWorldFromRequest,也就是指对name相同的<messege>执行接受请求-->
<wsdl:input message="impl:sayHelloWorldFromRequest" name="sayHelloWorldFromRequest"/>
<!--一个反馈,...同上。去掉反馈output,就是one-way模式-->
<wsdl:output message="impl:sayHelloWorldFromResponse" name="sayHelloWorldFromResponse"/>
</wsdl:operation>
</wsdl:portType>
接着,是绑定一种SOAP,可以假象为绑定一个信使,这个邮箱(ws)的消息均由此类信使(SOAP)传送。<bind>:
<wsdl:binding name="HelloWorldSoapBinding" type="impl:HelloWorld"><!--type是指绑定了HelloWorld端口-->
<wsdlsoap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/><!--表示用http和document框架-->
<wsdl:operation name="sayHelloWorldFrom"><!--定义了一个操作符-->
<wsdlsoap:operation soapAction=""/><!--类似html中form的action内容-->
<wsdl:input name="sayHelloWorldFromRequest"><!--一个请求,对应的消息<message>的name-->
<wsdlsoap:body use="literal"/><!--用literal方式对SOAP的body内容编码-->
</wsdl:input>
<wsdl:output name="sayHelloWorldFromResponse">
<wsdlsoap:body use="literal"/>
</wsdl:output>
</wsdl:operation>
</wsdl:binding>
最后,其实还有一小段:
<wsdl:service name="HelloWorldService"><!--定义了这个ws的name-->
<wsdl:port binding="impl:HelloWorldSoapBinding" name="HelloWorld"><!--把这个ws绑定了一个SOAP,并给出端口-->
<wsdlsoap:address location="http://localhost:8080//services/example/HelloWorld"/><!--ws的url地址-->
</wsdl:port>
</wsdl:service>
再来回顾一下WSDL的内容:
- types标记了输入输出的message的内容类型,如string;
- message标记了这个ws支持哪几种message,并按照types中的定义严格控制自己的数据类型;
- portType标记了这个端口名,并把这个端口名支持的操作方式、操作方式所接受的meaage进行了说明;
- bind标记了这个端口绑定了哪种信使SOAP,并对SOAP消息体进行编码,再把对应的body映射到对应的portType上。
一个前提:SOAP体内的body中,放置了数据,并传到了这个ws的某个端口上。首先这个端口bind的SOAP先检查自己是不是到了自己要去的端口,是的话,把自己体内的body数据编码,转交给这个端口的定义类型,也就是portType标明的操作方法;操作方法会继续把这个数据“封装”成该方法绑定的message,message用types中定义的数据类型装填,接着交给ws。发送反馈时,步骤相反。
>SOAP
如果只是单纯的开发者,其实SOAP不需要太关心,基本上现有的框架或是开发环境基本会自动填充。
在SOAP中,只有四种元素:<Envelope><Header><Body><Fault>,其中第一、第三中元素时必需的。它看着就像这个样子:
<?xml version="1.0"?><!--Envelope必选,告诉别人这是一个SOAP,但我们不需要关心它-->
<soap:Envelope xmlns:soap="http://www.w3.org/2001/12/soap-envelope" soap:encodingStyle="http://www.w3.org/2001/12/soap-encoding">
<!--可选的消息头-->
<soap:Header>
...
...
</soap:Header>
<!--必须有的消息体,也就是数据区-->
<soap:Body>
...
...
<!--可选的出错处理-->
<soap:Fault>
...
...
</soap:Fault>
</soap:Body>
</soap:Envelope>
重点主要在于<body>:
<soap:Body>
<m:GetMsg xmlns:m="http://blog.csdn.net/shenpibaipao">
<m:Word>Hello</m:Word>
</m:GetMsg>
</soap:Body>
其中的<m:xx>都来自规定好的命名空间,这个主要取决于WSDL绑定的SOAP。只要知道它里面是数据就好了。>如何开发一个Web Service
为什么要用IDEA?因为它的很多概念和Maven很像,就是仓库的管理和module式的开发。它的每个Project都是一个Module,随时插拔,同时对于依赖库(jar包)可以自动获取并管理。(换句话说,免去了到各个网站自己手动下jar包然后添加到工程里的烦恼)
一、创建一个WebService工程:
File - New - Project -
这里选的是JDK1.8和Tomcat8,不过随意吧,不影响。但我这里选择了Axis,这个和之后编写客户端有关。同时建议默认选dowload,会自动帮你下缺失的jar包。
二、生成WSDL
建立新工程后,目录下会是这样的:
默认生成了一个HelloWorld:
package example;
public class HelloWorld {
public String sayHelloWorldFrom(String from) {
String result = "Hello, world, from " + from;
System.out.println(result);
return result;
}
}
假设这个文件就是我们编写的ws应用(我们拿它举例,事实上任何一个类都可以利用这个方法做成ws),右键这个文件,选择:然后输入地址(看心情输吧,不过建议跟教程保持一致,方便之后的步骤):
然后会发现目录下生成了一个HelloWorld.wsdl文件。文件打开,和我上文中举例的内容是一样的。
三、配置Tomcat和发布到Tomcat上
实际上这一步是要在IDE中运行才需要做的(且你直接没配置TOMCAT)。如果你在服务器上有一个TOMCAT,你直接发布这个包到TOMCAT就好了。
打包发布到Tomcat的步骤也很简单,点击Build - Build Arifacts - Build,到工程目录下\.out\artifacts会有个WStest2_war_exploded文件夹(你可以随意改名,比如WS2),直接拖到Tomcat的webapps文件下,启动Tomcat,这个ws就被布置到网络服务器上了。
你可以输入http://localhost:8080/WS2/services/HelloWorld进行查看:
那如果想在IDEA中先配置Tomcat调试这个ws呢?按照图操作就好了:
选择你的Tomcat安装路径:(到这里下载对应位数的bin版本就好:https://tomcat.apache.org/download-80.cgi)
然后在这个界面切到Deployment 标签,看看有没有一个war(如下图),如果没有,就手动按绿色加号添加。如果这时候右下角弹出一个Fix按钮,直接就Fix,会自动帮你补上所有需要的jar包。
最后运行Tomcat即可。
四、编写客户端
点中工程栏里的HelloWorld.wsdl,然后点选Tools - Web Service -Build Java code from wsdl:
看图选,其中rul路径,看心情吧反正待会还能改,比如我用了上文提到的WS2,这样可以很方便地布置到Tomcat上去:
于是目录下会生成一大堆东西:
Client是我们待会儿自己要建立的,稍后再说。而其他由wsdl自动生成的文件里,在HelloWorlServiceLocator中,会有个final量:
private java.lang.String HelloWorld_address = "http://localhost:8080/WS2/services/HelloWorld";//身披白袍的博客
这个地址显然就是待会儿客户端要访问的地址了。如果只是在IDEA中开启TOMCAT测试,就把WS2/去掉:http://localhost:8080/WS2/services/HelloWorld
创建一个java class,也就是客户端的测试类:
代码点击此处直接复制。
然后右键这个文件,点Run.xxxxx,就可以看到控制台回信了:
或是到这里下载Demo:http://download.csdn.net/download/shenpibaipao/10020499
还可以参考这里:http://blog.csdn.net/qq_33546747/article/details/53304097