CXF旨在为服务创建必要的基础设施,它的整体架构主要由以下几个部分组成:
1.Bus
它是C X F架构的主干,为共享资源提供了一个可配置的场所,作用非常类似于S p r i n gApplicationContext。这些共享资源包括WSDL管理器、绑定工厂等。通过对Bus进行扩展,可以方便地容纳自己的资源,或替换现有的资源。默认Bus实现是基于Spring的,通过依赖注入,将运行时组件串起来。Bus的创建由BusFactory负责,默认是 SpringBusFactory,对应于默认Bus实现。在构造过程中,SpringBusFactory会搜索META-INF/cxf(就包含在 CXFJar中)下的所有Bean配置文件,根据它们构建一个ApplicationContext。开发者也可提供自己的配置文件来定制Bus
2.消息传递和(Interceptor
CXF建立于一个通用的消息层之上,主要由消息、和链(InterceptorChain)组成。CXF是以消息处理为中心的,熟悉 JSP/Servlet的开发者可以将视为CXF架构中的Filter”,链也与FilterChain”类似。通过,开发者可以方便地在消息传递、处
理的整个过程中对CXF进行扩展。的方法主要有两个:handleMessagehandleFault,分别对应消息处理和错误处理。在开发的时候需要注意两点:
不是线程安全的,不建议在中定义实例变量并使用它。这一点跟JSP/Servlet中对于Filter的处理是一样的;
不要调用下一个的handleMessagehandleFault,这个工作由InterceptorChain来完成。
3.前端(Front End
它为CXF提供了创建服务的编程模型,当前主要的前端就是JAX-WS
4.服务模型
CXF中的服务通过服务模型来表示。它主要有两部分:ServiceInfo和服务本身。ServiceInfo作用类似WSDL,包含接口信息、绑定、端点(EndPoint)等信息;服务则包含了ServiceInfo、数据绑定、和服务属性等信息。可使用Java类和WSDL来创建服务。一般是由前端负责服务的创建,它通过ServiceFactory来完成。
5.绑定(Binding
绑定提供了在传输之上映射具体格式和协议的方法,主要的两个类是BindingBindingFactoryBindingFactory负责创建Binding
6.传输(Transport
为了向绑定和前端屏蔽传输细节,CXF提供了自己的传输抽象。其中主要有两个对象:ConduitDestination。前者是消息发送的基础,后者则对应消息接收。开发者还可以给ConduitDestination注册MessageObserver,以便在消息发送和接收时获得通知。
开发方法
CXF 可以创建的Web 服务应用有两种:服务提供者和服务消费者。这种结构可类比客户端/ 服务器结构,服务消费者类似于客户端,服务提供者类似于服务器。使用CXF 创建应用时,服务提供者和服务消费者并不需要同时出现,因为有可能应用只是作为服务提供者或服务消费者单独出现。
为了说明使用CXF 如何创建这两种类型的应用,本教程将同时给出它们的例子。另外,由于GroovyJava 世界中变得越来越流行,本教程会给出使用Groovy CXF 插件GroovyWS 的实现例子。例子使用JDK 1.5.X Groovy 1.0 完成,包含以下几部分:
1.User,用户对象,在消费者和提供者之间传递;
2.UserService,用户管理服务,它提供增加和获取所有用户的功能;
3.Client,服务消费者,它向UserService发起服务请求。
Java 实现的步骤包括以下几点。
服务端包含UserServiceUserServiceImplUser。其中,UserService是接口定义,UserServiceImpl是它的实现,并负责服务的发布,服务只有发布之后才能被消费。例子使用了JAX-WS,它们的主要内容如下:
UserService
package server;
import javax.jws.WebService;
@WebService
public interface UserService {
void add(User user);
User[] findAllUsers();
}
@WebService 指明接口是Web 服务
UserServiceImpl
import java.util.List;
import java.util.Vector;
import javax.jws.WebService;
l.ws.Endpoint;
@WebService(endpointInterface = "server.UserService",
serviceName = "UserService",
portName="UserServicePort")
public class UserServiceImpl implements UserService {编程入门先学js
static List<User> UserRepository= new Vector<User>();
public void add(User user) {
UserRepository.add(user);
}
public User[] findAllUsers() {
User[] users= new User[UserRepository.size()];
Array(users);
return users;
}
public static void main(String[] args){
UserServiceImpl userService= new UserServiceImpl();
Endpoint.publish("localhost:9000/userService
", userService);
}
}
@ WebService中的serviceNameportName,分别指定了其产生的WSDL中的服务名和端口名。endpointInterface为接口的类名。服务发布代码也可以放在另一个类中。
User
package server;
public class User {
String first;
String last;
public String getFirst() {
return first;
}
public void setFirst(String first) {
this.first = first;
}
public String getLast() {
return last;
}
public void setLast(String last) {
this.last = last;
}
}
2.客户端只有一个类:Client,其他的UserUserService引用server包中的对象。
package client;
l.namespace.QName;
l.ws.Service;
l.ws.soap.SOAPBinding;
import server.User;
import server.UserService;
public class Client {
public static void main(String[] arg){
Service service = ate(
new QName("server/
", "UserService"));
service.addPort(new QName("server/
", "UserServicePort")
, SOAPBinding.SOAP11HTTP_BINDING
, "localhost:9000/userService
");
UserService userService= Port(UserService.class);
User user= new User();
user.setFirst("James");
user.setLast("Bond");
userService.add(user);
User[] users= userService.findAllUsers();
for(User u : users){
System.out.First()+"."+u.getLast());
}
}
}
注意,QName 的第一个参数指明了WSDL 的目标名字空间,可以通过服务地址?wsdl”方式获取服务的WSDL,来查看服务的目标名字空间。对于由CXF 创建的服务,目标名字空间的默认构造规则是: 包名的倒序/。即如果包名是a.b.c,那么名字空间就为c.b.a/ GroovyWS 的实现步骤包括以下几点。
1.服务端包括:UserUserServicel。由于Groovy类包含一个metaClass属性,该属性不应该被序列化在服务端和客户端之间传递,l用来指定将该属性忽略掉。
User
package server;
class User {
String first
String last
}
UserService
package server;
import groovyx.ws.WSServer
class UserService {
private static List users= new Vector()
void add(User user){
users.add(user)
}
User[] findAllUsers(){
User[] u= new User[users.size()]
Array(u)
return u
}
static void main(args) {
def server = new WSServer()
server.setNode("server.UserService",
"localhost:9000/UserService
")
}
}
注意它的发布。
l
<?xml version="1.0" encoding="UTF-8"?>
<mappings xmlns:sample="DefaultNamespace
">
<mapping name="sample:User">
<property name="metaClass" ignore="true"/>
</mapping>
</mappings>
2.客户端包含:Clientll的内容和服务端的一样。Client的内容如下:

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。