XML学习笔记六:Jaxb负责xml与javaBean映射

前言:

1、两套标准:Jax-ws(web service)和 Jax-rs(restful)。

2、在JAVA EE 5\6中,jaxb可以很方便的与jax-rs、jax-ws集成,极大的简化了web service接口的开发工作量。jaxb负责xml与javaBean的映射。

3、cxf等架构的使用,ws中不需要手动写映射,而restfu则需要手动书写注解。(也可以使用JAXB的XJC工具,通过定义schema的方式实现Java对象与XML的绑定)。

4、jaxb除了在ws与restful中广泛使用,也可以作为解析xml的一种日常技术。


一、web service中的jaxb

1、在使用cxf的客户端时,一般使用 wsdl2java 命令生成,所以不需要自己写jaxb的代码。如:

@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "cat",propOrder = {
    "color","id","name"
})
public class Cat {

    protected String color;
    protected Integer id;
    protected String name;
//......
}

2、其实这边映射的就是 soap消息,与访问的 wsdl 具有一致性。


二、jaxb详解。

(一)实例

1、javaBean实例:

package cn.rest.bean;

import java.util.List;

import javax.xml.bind.annotation.XmlAttribute;
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlElementWrapper;
import javax.xml.bind.annotation.XmlRootElement;

/**
 * 
 * UserBean.java
 *
 * @title User的传输数据类
 * @description
 * @author SAM-SHO 
 * @Date 2014-11-25
 */

@XmlRootElement(name = "USER")
//@XmlAccessorType(XmlAccessType.FIELD ) //写这个注解,就不需要@XmlElement注解,一般和XmlType一起使用,指定名称。
//@XmlType(propOrder = { "name","age","userAddress","phoneList"})
public class UserBean {
	private String name;
	private String key;
	private String age;
	private UserAddress userAddress;//地址
	private List<UserPhone> phoneList ;//手机

	@XmlElement(name="NAME")
	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	@XmlElement(name = "AGE")
	public String getAge() {
		return age;
	}

	public void setAge(String age) {
		this.age = age;
	}

	@XmlElement(name = "UserAddress")
	public UserAddress getUserAddress() {
		return userAddress;
	}

	public void setUserAddress(UserAddress userAddress) {
		this.userAddress = userAddress;
	}

	@XmlElementWrapper(name = "PhoneList")//标注集合
	@XmlElement(name = "UserPhone")
	public List<UserPhone> getPhoneList() {
		return phoneList;
	}

	public void setPhoneList(List<UserPhone> phoneList) {
		this.phoneList = phoneList;
	}

	@XmlAttribute(name="key")//属性
	public String getKey() {
		return key;
	}

	public void setKey(String key) {
		this.key = key;
	}
	
}
package cn.rest.bean;

public class UserPhone {
	
	private String type;//电话号码类型
	private String num;//电话号码
	
	public String getType() {
		return type;
	}
	public void setType(String type) {
		this.type = type;
	}
	public String getNum() {
		return num;
	}
	public void setNum(String num) {
		this.num = num;
	}
	
}
package cn.rest.bean;

import javax.xml.bind.annotation.XmlElement;

public class UserAddress {
	
	private String homeAddress;//家庭地址
	private String workAddress;//公司地址
	
	@XmlElement(name = "HomeAddress")
	public String getHomeAddress() {
		return homeAddress;
	}
	public void setHomeAddress(String homeAddress) {
		this.homeAddress = homeAddress;
	}

	@XmlElement(name = "WorkAddress")
	public String getWorkAddress() {
		return workAddress;
	}
	public void setWorkAddress(String workAddress) {
		this.workAddress = workAddress;
	}

}

2、解析工具。

1)javaBean 映射成 xml,使用Marshaller 。

	/**
	 * Objext 转成 XML
	 * 
	 * @param object
	 */
	public static void Object2Xml(Object object) {
		// FileWriter writer = null;
		try {
			JAXBContext context = JAXBContext.newInstance(object.getClass());
			Marshaller marshal = context.createMarshaller();
			marshal.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT,true); // 格式化输出
			marshal.setProperty(Marshaller.JAXB_ENCODING,"utf-8");// 编码格式,默认为utf-8
			marshal.setProperty(Marshaller.JAXB_FRAGMENT,false);// 是否省略xml头信息
			marshal.marshal(object,System.out);

			// writer = new FileWriter("shop.xml");
			// marshal.marshal(object,writer);
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

2)xml 映射成 javaBean,使用 Unmarshaller

	/**
	 * xml 转成特定的Bean
	 * 
	 * @param xml
	 * @return
	 */
	public static UserBean parseXml2UserBean(String xml) {
		try {
			JAXBContext context = JAXBContext.newInstance(UserBean.class);
			InputSource is = new InputSource();
			StringReader xmlStr = new StringReader(xml);
			is.setCharacterStream(xmlStr);
			Unmarshaller unmarshaller = context.createUnmarshaller();
			UserBean user = (UserBean) unmarshaller.unmarshal(is);
			return user;

		} catch (JAXBException e) {
			e.printStackTrace();
			return null;
		}
	}

3)测试:

		UserBean tUserBean = new UserBean();
		tUserBean.setName("SAM-SHO");
		tUserBean.setAge("27");
		tUserBean.setKey("属性111");

		UserAddress tUserAddress = new UserAddress();
		tUserAddress.setWorkAddress("苏州园区");
		tUserAddress.setHomeAddress("苏州高新区");
		tUserBean.setUserAddress(tUserAddress);

		List<UserPhone> phoneList = new ArrayList<UserPhone>();
		UserPhone tUserPhone = new UserPhone();
		tUserPhone.setType("移动");
		tUserPhone.setNum("13612345678");
		phoneList.add(tUserPhone);

		tUserPhone = new UserPhone();
		tUserPhone.setType("联通");
		tUserPhone.setNum("13798765432");
		phoneList.add(tUserPhone);
		tUserBean.setPhoneList(phoneList);

		ObjectAndXmlHandle.Object2Xml(tUserBean);

【输出】

<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<USER key="属性111">
    <AGE>27</AGE>
    <NAME>SAM-SHO</NAME>
    <PhoneList>
        <UserPhone>
            <num>13612345678</num>
            <type>移动</type>
        </UserPhone>
        <UserPhone>
            <num>13798765432</num>
            <type>联通</type>
        </UserPhone>
    </PhoneList>
    <UserAddress>
        <HomeAddress>苏州高新区</HomeAddress>
        <WorkAddress>苏州园区</WorkAddress>
    </UserAddress>
</USER>



(二)jaxb 注解详解:

1、@XmlRootElement 将一个Java类映射为一段XML的根节点。参数:

name 定义这个根节点的名称

namespace 定义这个根节点命名空间


2、@XmlAccessorType 定义映射这个类中的何种类型需要映射到XML。可接收四个参数,分别是:

XmlAccessType.FIELD:映射这个类中的所有字段到XML

XmlAccessType.PROPERTY:映射这个类中的属性(get/set方法)到XML

XmlAccessType.PUBLIC_MEMBER:将这个类中的所有public的field或property同时映射到XML(默认)

XmlAccessType.NONE:不映射


3、@XmlElement 指定一个字段或get/set方法映射到XML的节点。如,当一个类的XmlAccessorType 被标注为

PROPERTY时,在某一个没有get/set方法的字段上标注此注解,即可将该字段映射到XML。参数:

defaultValue 指定节点默认值

name 指定节点名称

namespace 指定节点命名空间

required 是否必须(默认为false)

nillable 该字段是否包含 nillable="true" 属性(默认为false)

type 定义该字段或属性的关联类型


4、@XmlAttribute 指定一个字段或get/set方法映射到XML的属性。参数:

name 指定属性名称

namespace 指定属性命名空间

required 是否必须(默认为false)



5、@XmlTransient 定义某一字段或属性不需要被映射为XML。如,当一个类的XmlAccessorType 被标注为PROPERTY时,在某一get/set方法的字段上标注此注解,那么该属性则不会被映射。


6、@XmlType 定义映射的一些相关规则。参数:

propOrder 指定映射XML时的节点顺序

actoryClass 指定UnMarshal时生成映射类实例所需的工厂类,默认为这个类本身

factoryMethod 指定工厂类的工厂方法

name 定义XML Schema中type的名称

namespace 指定Schema中的命名空间


7、@XmlElementWrapper 为数组元素或集合元素定义一个父节点。如,类中有一元素为List items,若不加此注解,该元素将被映射为
    <items>...</items>


    <items>...</items>

这种形式,此注解可将这个元素进行包装,如:
    @XmlElementWrapper(name="items")
    @XmlElement(name="item")
    public List items;

将会生成这样的XML样式:

    <items>
        <item>...</item>
        <item>...</item>
    </items>

8、@XmlJavaTypeAdapter 自定义某一字段或属性映射到XML的适配器。如,类中包含一个接口,我们可以定义一个适配器(继承自 javax.xml.bind.annotation.adapters.XmlAdapter类),指定这个接口如何映射到XML。 9、@XmlSchema 配置整个包的namespace,这个注解需放在package-info.java文件中。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


php输出xml格式字符串
J2ME Mobile 3D入门教程系列文章之一
XML轻松学习手册
XML入门的常见问题(一)
XML入门的常见问题(三)
XML轻松学习手册(2)XML概念
xml文件介绍及使用
xml编程(一)-xml语法
XML文件结构和基本语法
第2章 包装类
XML入门的常见问题(二)
Java对象的强、软、弱和虚引用
JS解析XML文件和XML字符串详解
java中枚举的详细使用介绍
了解Xml格式
XML入门的常见问题(四)
深入SQLite多线程的使用总结详解
PlayFramework完整实现一个APP(一)
XML和YAML的使用方法
XML轻松学习总节篇