`
shenyuc629
  • 浏览: 195406 次
  • 性别: Icon_minigender_1
  • 来自: 成都
社区版块
存档分类
最新评论

cxf使用JAXB数据绑定以及cxf对Map的支持

    博客分类:
  • CXF
阅读更多

由于篇幅有限,此处生出源代码,如有需要的在评论里面留下联系的方式,笔者到时联系你。转载请标明读者链接,谢谢。

        一.JAXB简介

JAXB CXF 一个默认的数据绑定,如果你不指定其他数据绑定在你的 Spring 配置中或者在 API ,你可以得到 JAXB 的数据绑定。自从 2.3.x 版本以后默认的使用 JAXB2.2 maven 使用者运行在 jdk6 之上将需要使用 java 认证的重写机制来使用 JAXB2.2 来替代 JAXB2.1

JAXB 使用 java 注解结合文件路径在 XML Java 之间构建映射。 JAXB 支持编码优先和架构优先编程。架构优先支持创建客户代理、动态、运行时。详解见 CXF DynamicClientFactory 类。

CXF 使用 JAXB 引用实现。为了学习更多关于注解类或者怎样把一个 schema 生成实体类,详见官网。

二. 解组和编组

解组: unmarshalling )把数据从存储媒介上转化到内存中的过程,正好与编组相反。因此需要把 xml 文档解组到 Java VM 中。这里的复杂性不是在扁平数据中,因为这不是必需的,而在于从正确的数据到正确 Java 代码变量的映射。如果映射是错误的,就不可能正确的访问数据。当然,如果再尝试重新编组还会造成更大的问题,并且问题传播的很快。

       编组:<!-- [if gte mso 9]><xml> <o:OfficeDocumentSettings> <o:AllowPNG/> </o:OfficeDocumentSettings> </xml><![endif]--> marshalling )是把内存中的数据转化到存储媒介上的过程。因此在 java XML 环境中,编组就是把一些 Java 对象转换成一个或多个 XML 文档。在数据库环境中,则是把 Java 表示的数据存入数据库。显然,编组的秘密在于把 Java 实例中的面向对象结构转化成适用于 XML 的扁平结构,或者 RDBMS 中的关系结构。

       三.代码以及分析

首先需要加入cxf所需要的包,在本次测试中,笔者添加了cxf的lib中全部的包。

下面直接上代码:

package com.syc.jaxb;

import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;


@XmlJavaTypeAdapter(UserAdapter.class)
public interface User {
	String getName();
	
}

此处注释的XmlJavaTypeAdapter是对自定义编组使用实现XmlAdapter的适配器,即UserAdapter这个类,该类实现了XmlAdapter适配器,因此要实现解组和编组两个方法。可能有的初学读者会提到:为什么我们要实现编组和解组呢?原因很简单,CXF不能直接支持List、Map等。

package com.syc.jaxb;

import javax.xml.bind.annotation.XmlType;

@XmlType(name="User")
public class UserImpl implements User{
	String name;
	public UserImpl(){}
	public UserImpl(String n){
		this.name =n;
	}
	@Override
	public String getName() {
		return name;
	}
	public void setName(String n){
		this.name = n ;
	}
}

  该类是实现了User接口,并且重写getName()方法,此类可以看成一个User实体类,其实也没有什么区别。这里注释的XmlType是将UserImpl映射到 XML 模式类型,即我们得到的客户端的时候显示的类的名字是User。

package com.syc.jaxb;

import java.util.Map;

import javax.jws.WebService;
import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;
@WebService
public interface HelloWorld {
	String sayHi(String text);
	String sayHiToUser(User user);
	@XmlJavaTypeAdapter(UserMapAdapter.class)
	Map<Integer,User> getUsers();
}

  该接口是暴露的服务,该服务有三个方法,暴露的服务必须使用@WebService注释,不然在发布服务的时候找不到不要发布的服务类。由于第三个方法返回的是一个Map类型, JAXB 不能将一些 Java 类型自然映射到 XML 表示形式,例如 ,HashMap 或者其他非 JavaBean 类。如参数类型为接口,以及 Map ,这需要特殊的 XmlAdapter 类进行处理。因此这里我们需要注释成让XmlAdapter适配器来处理。

package com.syc.jaxb;

import java.util.LinkedHashMap;
import java.util.Map;

import javax.jws.WebService;
@WebService(endpointInterface="com.syc.jaxb.HelloWorld",
				serviceName="HelloWorld")
public class HelloWorldImpl implements HelloWorld {
	Map<Integer,User> users = new LinkedHashMap<Integer, User>();
	
	@Override
	public String sayHi(String text) {
		System.out.println("sayHello called...");
		return "Hello " +text;
	}

	@Override
	public String sayHiToUser(User user) {
		System.out.println("sayUserHello called...");
		users.put(users.size()+1, user);
		return "Hello"+ user.getName();
	}

	@Override
	public Map<Integer, User> getUsers() {
		System.out.println("getMapUsers called...");
		
		return users;
	}

}

  该类是服务类的一个实现。

package com.syc.jaxb;

import javax.xml.bind.annotation.adapters.XmlAdapter;

public class UserAdapter extends XmlAdapter<UserImpl, User>{

	@Override
	public User unmarshal(UserImpl v) throws Exception {
		
		return v;
	}

	@Override
	public UserImpl marshal(User v) throws Exception {
		if(v instanceof UserImpl){
			return (UserImpl)v;
		}
		return new UserImpl(v.getName());
	}

}

  在这里,UserImpl是value类型,User是alue类型。UserAdapter类继承了XmlAdapter类,因此需要重写marshal()和unmarshal()方法,即编组和解组,在此处,编组就是将bound类型修改为value类型,然后将value类型编组为xml表示形式;解组就是JAXB绑定框架首先将XML表示形式解组为value类型,然后将value类型修改为bound类型。在这里我们可以这么理解,编组即bound->value->xml形式,解组即xml形式->value->bound。

package com.syc.jaxb;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlType;
@XmlType(name="UserMap")
@XmlAccessorType(XmlAccessType.FIELD)
public class UserMap {
	@XmlElement(nillable=false,name="entry")
	List<UserEntry> entries = new ArrayList<UserEntry>();
	public List<UserEntry> getEntries() {
		return entries;
	}
	public void addEntry(UserEntry entry){
		entries.add(entry);
		
	}
	@XmlAccessorType(XmlAccessType.FIELD)
	@XmlType(name="UserEntry")
	static class UserEntry{
		public UserEntry(){
			super();
		}
		
		public UserEntry(Map.Entry<Integer, User> entry){
			super();
			this.id = entry.getKey();
			this.user = entry.getValue();
		}
		public UserEntry(Integer id,User user){
			super();
			this.id = id;
			this.user = user;
		}
		@XmlElement(required=true,nillable=false)
		Integer id;
		User user;
		public Integer getId() {
			return id;
		}
		public void setId(Integer id) {
			this.id = id;
		}
		public User getUser() {
			return user;
		}
		public void setUser(User user) {
			this.user = user;
		}
		
	}
}

  UserMap类是让cxf支持MAP的关键,该类可以将map里面的key-value转换为User实体类,把key当作user的id值,把value当作user的name值,然后再把user保存到一个集合中,即实现了hash值到实体类的转换。

package com.syc.jaxb;

import java.util.LinkedHashMap;
import java.util.Map;

import javax.xml.bind.annotation.adapters.XmlAdapter;

public class UserMapAdapter extends XmlAdapter<UserMap, Map<Integer,User>>{

	@Override
	public Map<Integer, User> unmarshal(UserMap v) throws Exception {
		Map<Integer, User> map = new LinkedHashMap<Integer, User>();
		for(UserMap.UserEntry e : v.getEntries()){
			map.put(e.getId(), e.getUser());
		}
		return map;
	}

	@Override
	public UserMap marshal(Map<Integer, User> v) throws Exception {
		UserMap map = new UserMap();
		for(Map.Entry<Integer, User> e : v.entrySet()){
			UserMap.UserEntry u = new UserMap.UserEntry();
			u.setId(e.getKey());
			u.setUser(e.getValue());
			map.getEntries().add(u);
		}
		return map;
	}

}

  这里即对UserMap和Map对象的编组和解组。

package com.syc.jaxb;

import javax.xml.ws.Endpoint;

public class Server {
	public static void main(String[] args) {
		System.out.println("Starting Server... ");
		String address = "http://localhost:8899/hello";
		HelloWorldImpl implementor = new HelloWorldImpl();
		Endpoint.publish(address, implementor);
		try {
			Thread.sleep(5*60*1000);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		
		System.out.println("Exiting Server... ");
		System.exit(0);
	}
}

用WSDL2JAVA生成的客户端,调用服务端代码
 package com.syc.jaxb.client;


import java.util.List;

import org.apache.cxf.jaxws.JaxWsProxyFactoryBean;

public class HelloClient {
	public static void main(String[] args) {
		JaxWsProxyFactoryBean factoryBean = new JaxWsProxyFactoryBean();
		factoryBean.setAddress("http://localhost:8899/hello");
		factoryBean.setServiceClass(HelloWorld.class);
		HelloWorld h = (HelloWorld) factoryBean.create();
		System.out.println(h.sayHi("shenyc"));
		User u = new User();
		u.setName("syc");
		System.out.println(h.sayHiToUser(u));
		User u1 = new User();
		u1.setName("ssss");
		System.out.println(h.sayHiToUser(u1));
		User u2 = new User();
		u2.setName("aaaaa");
		System.out.println(h.sayHiToUser(u2));
		UserMap users = h.getUsers();
		List<UserEntry> list = users.getEntry();
		for(UserEntry ue : list){
			System.out.println(ue.getId()+":"+ue.getUser().getName());
		}
	}
}
  
分享到:
评论

相关推荐

    cxf-webservice复杂类型

    3. **使用`DataBinding`**:CXF还提供了数据绑定机制,允许开发者自定义XML到Java对象的转换规则。通过实现`Unmarshaller`和`Marshaller`接口,可以完全控制复杂类型的序列化和反序列化过程。 **三、CXF Web服务...

    CXF-JAXB包的处理问题

    而JAXB(Java Architecture for XML Binding)是Java平台的标准,用于将XML数据与Java对象之间进行绑定,使得开发者可以方便地在XML文档和Java对象之间转换。在处理CXF与JAXB的集成时,有时会遇到版本冲突的问题,...

    apache-cxf-3.1.18.zip

    - **强大的数据绑定**:CXF使用JAXB进行XML到Java对象的自动转换,简化了数据处理。 - **良好的社区支持**:由于是开源项目,Apache CXF拥有活跃的开发者社区,能及时解决用户遇到的问题。 总的来说,Apache CXF是...

    webservice实例 CXF的JAXWS和JAXRS实现 及JAXB标准接口实现带jar包

    在提供的压缩包“ws_test”中,很可能包含了使用CXF实现的Web服务示例,包括JAX-WS和JAX-RS的服务端点,以及使用JAXB进行数据交换的类。这个实例可能是全部手写的,意味着它提供了一整套从创建服务到处理请求和响应...

    Apache CXF之结合Spring配置发布WebServices(Aegis数据绑定)

    Aegis数据绑定支持基本的数据类型、集合、Map以及自定义的Java类,为开发者提供了一种灵活的方式来处理Java对象和服务之间的转换。 以下是使用Apache CXF结合Spring发布Web Services(Aegis数据绑定)的基本步骤: ...

    cxf-core-3.2.4_cxf_源码

    CXF支持JAXB、Aegis等多种数据绑定机制。 6. **Message**:CXF中的消息模型用于表示通信中的数据,包括请求和响应。 在源码`cxf-core-3.2.4`中,我们可以看到以下几个关键模块: 1. **spi**:服务提供接口,定义了...

    cxf 完整的服务端客户端

    - Aegis:CXF 内置的数据绑定引擎,支持非标准的 Java 对象序列化。 通过这个“cxf 完整的服务端客户端”示例,你可以深入理解 CXF 如何处理服务发布、服务消费、数据绑定、异常处理等核心功能,并能更好地掌握 Web...

    cxf-rt-databinding-jaxb-3.0.1-API文档-中文版.zip

    赠送jar包:cxf-rt-databinding-jaxb-3.0.1.jar; 赠送原API文档:cxf-rt-databinding-jaxb-3.0.1-javadoc.jar; 赠送源代码:cxf-rt-databinding-jaxb-3.0.1-sources.jar; 赠送Maven依赖信息文件:cxf-rt-...

    07.处理Map等CXF无法自动转换的复合数据类型的形参和返回值

    4. **数据绑定配置**:为了使CXF能够识别和使用我们的自定义JAXB类,我们需要在CXF的配置中指定数据绑定。这通常在服务的XML配置文件或者通过Java代码进行。 5. **使用CXF扩展**:CXF提供了许多扩展点,如...

    CXF2.6.4配java1.6版完整包和使用说明

    4. **数据绑定**:CXF支持多种数据绑定技术,如JAXB(Java Architecture for XML Binding)和XMLBeans,将XML数据自动映射为Java对象,简化了开发过程。 5. **安全机制**:CXF提供了丰富的安全特性,包括WS-...

    jaxb-api.jar.jaxws-api.zip_ jaxb-api.jar_cxf_jax-ws.jar_jaxb-api

    **JAXB(Java Architecture for XML Binding)** 是Java平台的一个标准,它允许开发者将XML文档和Java对象进行绑定,从而简化XML数据的处理。在Java 6中,JAXB是内置的API,但在更新的JDK版本中,它被移除了,转而...

    基于Apache CXF构建SOA应用 随书源代码

    覆盖以下内容:基于JAX-WS规范和CXF自身的前端模式实现,CXF支持的数据绑定(DataBindings),CXF支持的WSDL绑定,CXF支持的传输协议绑定。CXF的调式、配置、日志、发布和工具。CXF实现RESTful服务。CXF对WS-* 的...

    简单的webservice+Cxf+Spring数据对接实例以及jar.rar

    简单的webservice+Cxf+Spring数据对接实例以及jar.rar简单的webservice+Cxf+Spring数据对接实例以及jar.rar简单的webservice+Cxf+Spring数据对接实例以及jar.rar简单的webservice+Cxf+Spring数据对接实例以及jar.rar...

    cxf与axis2区别

    Axis2支持更多的数据绑定,包括XMLBeans、JiBX、JaxMe和JaxBRI,以及它原生的数据绑定(ADB)。Apache CXF目前仅支持JAXB和Aegis,默认是JAXB 2.0,但CXF 2.1版本中将支持XMLBeans、JiBX和Castor等数据绑定。 语言...

    apache-cxf2.7.18官方版最稳定版本

    5. **数据绑定**:CXF支持多种数据绑定技术,如JAXB(Java Architecture for XML Binding)用于XML到Java对象的映射,以及Aegis绑定,用于非JAXB对象的XML处理。 6. **安全功能**:CXF提供了全面的安全性支持,包括...

    cxf使用中编码问题

    总之,处理CXF中的编码问题需要对字符编码有深入的理解,并且熟悉CXF框架的配置和API。通过正确配置和使用各种工具,可以有效地避免和解决编码相关的问题,确保服务的正常运行和数据的准确传递。

    Cxf转换器示例

    3. **数据绑定**:CXF支持JAXB(Java Architecture for XML Binding)和其他数据绑定技术,允许对象模型与XML文档之间进行自动转换。在示例中,源码可能展示了如何利用这些绑定技术。 4. **测试用例**:为了验证...

    cxf-2.4.2 jar包

    4. **数据绑定**:CXF支持多种数据绑定技术,如JAXB(Java Architecture for XML Binding),用于将XML数据与Java对象之间进行自动转换。 5. **WS-Security**:CXF提供了对Web服务安全标准(如WS-Security、WS-...

    apache-cxf-2.7.7以及cxf客户端所需要的jar包

    2. **Data Binding**:CXF支持多种数据绑定机制,如JAXB(Java Architecture for XML Binding)用于将XML与Java对象相互转换,简化了Web服务的处理。 3. **WS-* Stack**:提供了对各种Web服务规范的支持,如WS-...

    CXF-3.1.11jar包

    6. **数据绑定**:CXF支持JAXB(Java Architecture for XML Binding)和XMLBeans,用于将XML数据与Java对象之间进行自动转换。 7. **安全特性**:CXF提供了WS-Security和其他安全标准的实现,确保服务的安全性,如...

Global site tag (gtag.js) - Google Analytics