JAXB实现JavaBean与XML互相转换

一、简介

      JAXB(Java Architecture for XML Binding) 是一个业界的标准,是一项可以根据XML Schema产生Java类的技术。该过程中,JAXB也提供了将XML实例文档反向生成Java对象树的方法,并能将Java对象树的内容重新写到 XML实例文档。

      Jaxb 2.0是JDK 1.6的组成部分。我们不需要下载第三方jar包 即可做到轻松转换。Jaxb2使用了JDK的新特性,如:Annotation、GenericType等,需要在即将转换的JavaBean中添加annotation注解。

 

二、重要概念

  • JAXBContext类,是应用的入口,用于管理XML/Java绑定信息。
  • Marshaller接口,将Java对象序列化为XML数据。
  • Unmarshaller接口,将XML数据反序列化为Java对象。

 

  • @XmlType,将Java类或枚举类型映射到XML模式类型
  • @XmlAccessorType(XmlAccessType.FIELD) ,控制字段或属性的序列化。FIELD表示JAXB将自动绑定Java类中的每个非静态的(static)、非瞬态的(由@XmlTransient标 注)字段到XML。其他值还有XmlAccessType.PROPERTY和XmlAccessType.NONE。
  • @XmlAccessorOrder,控制JAXB 绑定类中属性和字段的排序。
  • @XmlJavaTypeAdapter,使用定制的适配器(即扩展抽象类XmlAdapter并覆盖marshal()和unmarshal()方法),以序列化Java类为XML。
  • @XmlElementWrapper ,对于数组或集合(即包含多个元素的成员变量),生成一个包装该数组或集合的XML元素(称为包装器)。
  • @XmlRootElement,将Java类或枚举类型映射到XML元素。
  • @XmlElement,将Java类的一个属性映射到与属性同名的一个XML元素。
  • @XmlAttribute,将Java类的一个属性映射到与属性同名的一个XML属性。

由@XmlTransient标 注的字段将不会被读取进xml之中,xml转obj的时候也不会赋值!!!


常见错误

单层结构 即类的属性不包含其他类

意外的元素 (uri:"", local:"Merchant")。所需元素为(none)

实体bean那里少了 @XmlRootElement(name="XXX") 了.加上这个注解就可以了

xml实体类 互转实体类定义

实体类 (多层结构 的外层)

@XmlRootElement(name = "Merchants") 
@XmlAccessorType(XmlAccessType.FIELD) 
public class MerchantList { 
     @XmlElement(name = "Merchant") 

         private List<Merchant> MerchantList;

实体类 (多层结构 的内层)

@XmlRootElement(name = "Merchant") --(作为内层时可要可不要,单层结构必须要!) 
  
 
  

    @XmlAccessorType(XmlAccessType.FIELD) 
  
 
  

    public class Merchant { 
  
 
  

         @XmlElement(name = "name") 
  
 
  

         private String name; 
  
 
  

         @XmlElement(name = "telenum") 
  
 
  

         private String telenum; 
  
 
  

         @XmlElementWrapper(name = "paytypes") 
  
 
  

         @XmlElement(name = "paytype") 
  
 
  

         private List<String> paytypes;

xml实体类互转 实现类


/** 
 
 
 

         * 读取 xml 并转换成 实体类 
 
 
 

         * @param clazz 
 
 
 

         * @param filepath 
 
 
 

         * @return 
 
 
 

         * @throws FileNotFoundException 
 
 
 

         */ 
 
 
 

        @SuppressWarnings("unchecked") 
 
 
 

        public static <T> T readString(Class<T> clazz, String filepath) 
 
 
 

                   throws FileNotFoundException { 
 
 
 

              JAXBContext jc; 
 
 
 

              try { 
 
 
 

                   jc = JAXBContext.newInstance(clazz); 
 
 
 

                   Unmarshaller um = jc.createUnmarshaller(); 
 
 
 

                   return (T) um.unmarshal(new FileReader(filepath)); 
 
 
 

              } catch (JAXBException e) { 
 
 
 

                   // TODO Auto-generated catch block 
 
 
 

                   e.printStackTrace(); 
 
 
 

              } 
 
 
 

              return null; 
 
 
 

        } 
 
 
 

        /** 
 
 
 

         * 解析bean 将xml转存到指定路径 
 
 
 

         * 
 
 
 

         * @param obj 
 
 
 

         * @param path 
 
 
 

         * @throws IOException 
 
 
 

         */ 
 
 
 

        @SuppressWarnings("unchecked") 
 
 
 

        public static void beanToXmlFile(Object obj, String path) throws IOException { 
 
 
 

              JAXBContext jc; 
 
 
 

              try { 
 
 
 

                   jc = JAXBContext.newInstance(obj.getClass()); 
 
 
 

                   Marshaller mu = jc.createMarshaller(); 
 
 
 

                   File file = new File(path); 
 
 
 

                   if (!file.exists()) { 
 
 
 

                        file.createNewFile(); 
 
 
 

                   } 
 
 
 

                   //JAXB_FORMATTED_OUTPUT 表示输出时 是否将xml格式化 
 
 
 

                   mu.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); 
 
 
 

                   //JAXB_ENCODING 表示输出时 xml的字符集 
 
 
 

                   //mu.setProperty(Marshaller.JAXB_ENCODING, encoding); 
 
 
 

                   mu.marshal(obj, file); 
 
 
 

              } catch (JAXBException e) { 
 
 
 

                   e.printStackTrace(); 
 
 
 

              } 
 
 
 

        } 
 
 
 

        /** 
 
 
 

         * 解析bean 将xml 直接输出 
 
 
 

         * 
 
 
 

         * @param obj 
 
 
 

         * @param path 
 
 
 

         * @throws IOException 
 
 
 

         */ 
 
 
 

        @SuppressWarnings("unchecked") 
 
 
 

        public static String beanToXmlStr(Object obj) throws IOException { 
 
 
 

              JAXBContext jc; 
 
 
 

              String result=null; 
 
 
 

              try { 
 
 
 

                   jc = JAXBContext.newInstance(obj.getClass()); 
 
 
 

                   Marshaller mu = jc.createMarshaller(); 
 
 
 

                   StringWriter writer=new StringWriter(); 
 
 
 

                   mu.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); 
 
 
 

                   mu.marshal(obj, writer); 
 
 
 

                   result=writer.toString(); 
 
 
 

              } catch (JAXBException e) { 
 
 
 

                   e.printStackTrace(); 
 
 
 

              } 
 
 
 

              return  result; 
 
 
 

        } 
 
 
 
 
 
 
  
 
 

    public static void main(String[] args) throws IOException { 
  
 
  

               MerchantList mer = XmlToEntity.readString(MerchantList.class, 
  
 
  

                         "src/Merchant.xml"); 
  
 
  

               System.out.println(mer.toString()); 
  
 
  

               System.out.println(); 
  
 
  

               System.out.println(XmlToEntity.beanToXmlStr(mer)); 
  
 
  

               XmlToEntity.beanToXmlFile(mer, "d:\\tmp\\wtf.xml"); 
  
 
  

         }

待转换的XML文件:

<?xml version="1.0" encoding="UTF-8"?> 
   
 
   

     <Merchants> 
   
 
   

            <Merchant> 
   
 
   

                   <name>好奇而已</name> 
   
 
   

                   <telenum>13144445555</telenum> 
   
 
   

                   <paytypes> 
   
 
   

                          <paytype>alipay</paytype> 
   
 
   

                          <paytype>wechat</paytype> 
   
 
   

                          <paytype>baidu</paytype> 
   
 
   

                   </paytypes> 
   
 
   

            </Merchant> 
   
 
   

            <Merchant> 
   
 
   

                   <name>烤冷面</name> 
   
 
   

                   <telenum>13233335555</telenum> 
   
 
   

                   <paytypes> 
   
 
   

                          <paytype>alipay</paytype> 
   
 
   

                          <paytype>wechat</paytype> 
   
 
   

                          <paytype>baidu</paytype> 
   
 
   

                   </paytypes> 
   
 
   

            </Merchant> 
   
 
   

     </Merchants>

测试结果:

MerchantList [MerchantList=[Merchant [name=好奇而已, telenum=13144445555, paytypes=[alipay, wechat, baidu]], 
  
 
  

    Merchant [name=烤冷面, telenum=13233335555, paytypes=[alipay, wechat, baidu]]]] 
  
 
  
 
   
 
  

    <?xml version="1.0" encoding="UTF-8" standalone="yes"?> 
  
 
  

    <Merchants> 
  
 
  

        <Merchant> 
  
 
  

            <name>好奇而已</name> 
  
 
  

            <telenum>13144445555</telenum> 
  
 
  

            <paytypes> 
  
 
  

                <paytype>alipay</paytype> 
  
 
  

                <paytype>wechat</paytype> 
  
 
  

                <paytype>baidu</paytype> 
  
 
  

            </paytypes> 
  
 
  

        </Merchant> 
  
 
  

        <Merchant> 
  
 
  

            <name>烤冷面</name> 
  
 
  

            <telenum>13233335555</telenum> 
  
 
  

            <paytypes> 
  
 
  

                <paytype>alipay</paytype> 
  
 
  

                <paytype>wechat</paytype> 
  
 
  

                <paytype>baidu</paytype> 
  
 
  

            </paytypes> 
  
 
  

        </Merchant> 
  
 
  

    </Merchants>