JAX-WS简写为Java Api For Xml Web Service。JAX-WS是使用XML构建Web Service与Client进行交流通信的技术。
在JAX-WS中,Web Service操作调用表现为以XML为基础的协议如SOAP协议。SOAP定义了封装架构,编码规则以及Web Service中调用和回应表现的规则。这些调用和回应在HTTP基础上以SOAP规范的消息进行传递。
尽管SOAP协议是很复杂的,但是JAX-WS隐藏了开发人员面对的复杂性。在服务器端,开发者可以通过在使用java语言接口中定义方法来制定Web Service。开发者可以编写一个或者多个类来实现这些方法。客户端程序也很容易编写。客户端会创建一个代理(表现服务器端的本地对象)并且简单的调用代理中的方法即可。在JAX-WS中,开发者不必去创建和解析SOAP消息。JAX-WS运行系统会自动完成调用和回应之间SAOP消息的转换。
使用JAX-WS,客户端和服务器端都有一个很大的优势:java编程语言的平台独立性。此外,JAX-WS并不限制:JAX-WS客户端程序可以访问不运行在java平台上的Web Servicce。这种灵活性是由于Web Service采用了W3C定义的技术规范:Http,SOAP,WSDL。
如何创建一个Web Service和Client并将他们部署。
开发一个JAX-WS Web Service首先是要定义一个类标示了javax.jws.WebService注释。@WebService注释定义了一个Web Service终端。
Service终端接口或者Service终端实现(SEI)是一个java接口和类,其中定义了客户端可以调用的方法。建立一个JAX-WS终端时接口并不是必须的。Web Service实现类定义了SEI。
你也可以通过向实现类的WebService注释中添加endpointInterface 元素来指定外部接口。之后你必须定义一个接口并且将其中需要实现的方法声明为public。
创建Web Service和Client的步骤
1. 编写实现类
2. 编译实现类
3. 添加部署Web Service必须的文件
4. 打包成WAR
5. 部署WAR文件
6. 编写Client类
7. 产生和编译连接到Service需要的文件
8. 编译Client类
9. 运行Client
JAX-WS终端要求
实现类必须注释为javax.jws.WebService或者javax.jws.WebServiceProvider。
实现类可以参考通过WebService注释中的endpointInterface元素。但是这不是必须的。如果WebService注释中没有endpointInterface元素的话,SEI会默认的为实现类定义一个。
实现类的方法必须是public,不能使final或者static。
被暴露给Web Service Client的方法必须被注释为javax.jws.WebMethod。
实现类不能使final和abstract。
实现类必须有一个默认的构造函数。
实现类不能定义finalize方法。
实现类必须在他生命周期回调函数中必须用javax.annotation.PostConstruct或者javax.annotation.PreDestroy注释。
PostConstruct方法由容器在实现类开始向Web Service Client做出反应之前调用。
PreDestroy方法由容器在终端移出操作之前调用。
编写Service终端实现类
在这个例子中,实现类Hello通过@WebService注释被定义为Service终端。Hello中有一个sayHello方法,被注释为@WebMethod。@WebMethod注释向Web Service Client暴露了被注释的方法。sayHello方法向客户段返回一通过参数name进行组装的问候字符串。这个实现类必须有一个默认的声明为public,无参数的构造函数。
- package helloservice.endpoint;
- import javax.jws.WebService;
- @WebService
- public class Hello {
- private String message = new String("Hello, ");
- public void Hello() {}
- @WebMethod
- public String sayHello(String name) {
- return message + name + ".";
- }
- }
package helloservice.endpoint;
import javax.jws.WebService;
@WebService
public class Hello {
private String message = new String("Hello, ");
public void Hello() {}
@WebMethod
public String sayHello(String name) {
return message + name + ".";
}
}
简单的JAX-WS客户端
HelloClient是一个可以访问Hello对象的sayHello方法的独立的客户端程序。这个调用是通过一个本地对象port实现的,当然这个本地对象port是远程Service对象的一个代理。
编写客户端程序
1. 使用javax.xml.ws.WebServiceRef注释可以声明一个Web Service的参考。@WebServiceRef注释使用wsdlLocation元素指定一个已经部署的Service的wsdl的URI
@WebServiceRef(wsdlLocation=http://localhost:8080/helloservice/hello?wsdl)
2. 找回Service的代理,看作一个port,这是通过调用Service的一个函数getHelloPort实现的
Hello port = service.getHelloPort();
Port实现了被service定义的SEI
3. 调用port的sayHello方法,并传入一个参数name。
String response = port.sayHello(name);
类的实现如下
- package simpleclient;
- import javax.xml.ws.WebServiceRef;
- import helloservice.endpoint.HelloService;
- import helloservice.endpoint.Hello;
- public class HelloClient {
- @WebServiceRef(wsdlLocation = "http://localhost:8080/helloservice/hello?wsdl")
- static HelloService service;
- /**
- * @param args the command line arguments
- */
- public static void main(String[] args) {
- try {
- HelloClient client = new HelloClient();
- client.doTest(args);
- } catch (Exception ex) {
- ex.printStackTrace();
- }
- }
- public void doTest(String[] args) {
- try { // Call Web Service Operation
- System.out.println(
- "Retrieving the port from the following service: "
- + service);
- Hello port = service.getHelloPort();
- System.out.println("Invoking the sayHello operation on the port.");
- String name;
- if (args.length > 0) {
- name = args[0];
- } else {
- name = "No Name";
- }
- String response = port.sayHello(name);
- System.out.println(response);
- } catch (Exception ex) {
- ex.printStackTrace();
- }
- }
- }
package simpleclient;
import javax.xml.ws.WebServiceRef;
import helloservice.endpoint.HelloService;
import helloservice.endpoint.Hello;
public class HelloClient {
@WebServiceRef(wsdlLocation = "http://localhost:8080/helloservice/hello?wsdl")
static HelloService service;
/**
* @param args the command line arguments
*/
public static void main(String[] args) {
try {
HelloClient client = new HelloClient();
client.doTest(args);
} catch (Exception ex) {
ex.printStackTrace();
}
}
public void doTest(String[] args) {
try { // Call Web Service Operation
System.out.println(
"Retrieving the port from the following service: "
+ service);
Hello port = service.getHelloPort();
System.out.println("Invoking the sayHello operation on the port.");
String name;
if (args.length > 0) {
name = args[0];
} else {
name = "No Name";
}
String response = port.sayHello(name);
System.out.println(response);
} catch (Exception ex) {
ex.printStackTrace();
}
}
}