import java.io.FileReader; import java.io.FileWriter; import java.math.BigDecimal; import java.util.Date; import java.util.HashSet; import java.util.Set; import javax.xml.bind.JAXBContext; import javax.xml.bind.Marshaller; import javax.xml.bind.Unmarshaller; import javax.xml.bind.annotation.XmlAccessType; import javax.xml.bind.annotation.XmlAccessorOrder; import javax.xml.bind.annotation.XmlAccessOrder; import javax.xml.bind.annotation.XmlAccessorType; import javax.xml.bind.annotation.XmlAttribute; import javax.xml.bind.annotation.XmlElement; import javax.xml.bind.annotation.XmlElementWrapper; import javax.xml.bind.annotation.XmlRootElement; import javax.xml.bind.annotation.XmlType; //设置生成的xml的根节点的名称 @XmlRootElement(name = "shop") //设置根据字段还是方法生成 @XmlAccessorType(XmlAccessType.FIELD) @XmlAccessorOrder(XmlAccessOrder.ALPHABETICAL) @XmlType(name = "shop", propOrder = { "name", "number", "describer", "address","orders" }) public class Shop { public static void main(String[] args) { Set<Order> orders = new HashSet<Order>(); Address address1 = new Address("China", "ShangHai", "ShangHai", "Huang", "200000"); Customer customer1 = new Customer("Jim", "male", "13699990000", address1); Order order1 = new Order("Mart", "LH59900", new Date(), new BigDecimal(60), 1); order1.setCustomer(customer1); Address address2 = new Address("China", "JiangSu", "NanJing", "ZhongYangLu", "210000"); Customer customer2 = new Customer("David", "male", "13699991000", address2); Order order2 = new Order("Mart", "LH59800", new Date(), new BigDecimal(80), 1); order2.setCustomer(customer2); orders.add(order1); orders.add(order2); Address address3 = new Address("China", "ZheJiang", "HangZhou", "XiHuRoad", "310000"); Shop shop = new Shop("CHMart", "100000", "EveryThing",address3); shop.setOrders(orders); FileWriter writer = null; try { JAXBContext context = JAXBContext.newInstance(Shop.class); Marshaller marshal = context.createMarshaller(); marshal.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); marshal.marshal(shop, System.out); writer = new FileWriter("shop.xml"); marshal.marshal(shop, writer); Unmarshaller unmarshal = context.createUnmarshaller(); FileReader reader = new FileReader("shop.xml") ; Shop shop1 = (Shop)unmarshal.unmarshal(reader); Set<Order> orders1 = shop1.getOrders(); for(Order order : orders1){ System.out.println("***************************"); System.out.println(order.getOrderNumber()); System.out.println(order.getCustomer().getName()); System.out.println("***************************"); } } catch (Exception e) { e.printStackTrace(); } } @XmlAttribute private String name; // @XmlElement private String number; @XmlElement private String describer; @XmlElementWrapper(name = "orders") @XmlElement(name = "order") private Set<Order> orders; @XmlElement private Address address; public Shop() { } public Shop(String name, String number, String describer, Address address) { this.name = name; this.number = number; this.describer = describer; this.address = address; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getNumber() { return number; } public void setNumber(String number) { this.number = number; } public String getDescriber() { return describer; } public void setDescriber(String describer) { this.describer = describer; } public Set<Order> getOrders() { return orders; } public void setOrders(Set<Order> orders) { this.orders = orders; } public Address getAddress() { return address; } public void setAddress(Address address) { this.address = address; } }
Order.java
import java.math.BigDecimal; import java.util.Date; import javax.xml.bind.annotation.XmlAccessorType; import javax.xml.bind.annotation.XmlAccessType; import javax.xml.bind.annotation.XmlAttribute; import javax.xml.bind.annotation.XmlRootElement; import javax.xml.bind.annotation.XmlType; import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter; @XmlType(name="order",propOrder={"shopName","orderNumber","price","amount","purDate","customer"}) @XmlAccessorType(XmlAccessType.FIELD) @XmlRootElement public class Order { private String shopName; @XmlAttribute private String orderNumber; @XmlJavaTypeAdapter(value=DateAdapter.class) private Date purDate; private BigDecimal price; private int amount; private Customer customer; public Order() { } public Order(String shopName, String orderNumber, Date purDate, BigDecimal price, int amount) { this.shopName = shopName; this.orderNumber = orderNumber; this.purDate = purDate; this.price = price; this.amount = amount; } public String getShopName() { return shopName; } public void setShopName(String shopName) { this.shopName = shopName; } public String getOrderNumber() { return orderNumber; } public void setOrderNumber(String orderNumber) { this.orderNumber = orderNumber; } public Date getPurDate() { return purDate; } public void setPurDate(Date purDate) { this.purDate = purDate; } public BigDecimal getPrice() { return price; } public void setPrice(BigDecimal price) { this.price = price; } public int getAmount() { return amount; } public void setAmount(int amount) { this.amount = amount; } public Customer getCustomer() { return customer; } public void setCustomer(Customer customer) { this.customer = customer; } }
Customer.java
import java.util.Set; import javax.xml.bind.annotation.XmlAccessorType; import javax.xml.bind.annotation.XmlAccessType; import javax.xml.bind.annotation.XmlAttribute; import javax.xml.bind.annotation.XmlRootElement; import javax.xml.bind.annotation.XmlType; @XmlType @XmlAccessorType(XmlAccessType.FIELD) @XmlRootElement public class Customer { @XmlAttribute private String name; private String gender; private String phoneNo; private Address address; private Set<Order> orders; public Customer() { } public Customer(String name, String gender, String phoneNo, Address address) { this.name = name; this.gender = gender; this.phoneNo = phoneNo; this.address = address; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getGender() { return gender; } public void setGender(String gender) { this.gender = gender; } public String getPhoneNo() { return phoneNo; } public void setPhoneNo(String phoneNo) { this.phoneNo = phoneNo; } public Address getAddress() { return address; } public void setAddress(Address address) { this.address = address; } public Set<Order> getOrders() { return orders; } public void setOrders(Set<Order> orders) { this.orders = orders; } }
Address.java
import javax.xml.bind.annotation.XmlAccessorOrder; import javax.xml.bind.annotation.XmlAccessOrder; import javax.xml.bind.annotation.XmlAccessorType; import javax.xml.bind.annotation.XmlAccessType; import javax.xml.bind.annotation.XmlAttribute; import javax.xml.bind.annotation.XmlElement; import javax.xml.bind.annotation.XmlRootElement; import javax.xml.bind.annotation.XmlType; @XmlType(propOrder = { "state", "province", "city", "street", "zip" }) @XmlAccessorOrder(XmlAccessOrder.ALPHABETICAL) @XmlAccessorType(XmlAccessType.NONE) @XmlRootElement public class Address { @XmlAttribute private String state; @XmlElement private String province; @XmlElement private String city; @XmlElement private String street; @XmlElement private String zip; public Address() { super(); } public Address(String state, String province, String city, String street, String zip) { super(); this.state = state; this.province = province; this.city = city; this.street = street; this.zip = zip; } public String getState() { return state; } public void setState(String state) { this.state = state; } public String getProvince() { return province; } public void setProvince(String province) { this.province = province; } public String getCity() { return city; } public void setCity(String city) { this.city = city; } public String getStreet() { return street; } public void setStreet(String street) { this.street = street; } public String getZip() { return zip; } public void setZip(String zip) { this.zip = zip; } }
输出:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?> <shop name="CHMart"> <number>100000</number> <describer>EveryThing</describer> <address state="China"> <province>ZheJiang</province> <city>HangZhou</city> <street>XiHuRoad</street> <zip>310000</zip> </address> <orders> <order orderNumber="LH59900"> <shopName>Mart</shopName> <price>60</price> <amount>1</amount> <purDate>2016-11-23 14:51:40</purDate> <customer name="Jim"> <gender>male</gender> <phoneNo>13699990000</phoneNo> <address state="China"> <province>ShangHai</province> <city>ShangHai</city> <street>Huang</street> <zip>200000</zip> </address> </customer> </order> <order orderNumber="LH59800"> <shopName>Mart</shopName> <price>80</price> <amount>1</amount> <purDate>2016-11-23 14:51:40</purDate> <customer name="David"> <gender>male</gender> <phoneNo>13699991000</phoneNo> <address state="China"> <province>JiangSu</province> <city>NanJing</city> <street>ZhongYangLu</street> <zip>210000</zip> </address> </customer> </order> </orders> </shop> *************************** LH59900 Jim *************************** *************************** LH59800 David **************************
工具类JaxbUtil.java:
import java.io.StringReader; import java.io.StringWriter; import java.util.Collection; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentMap; import javax.xml.bind.JAXBContext; import javax.xml.bind.JAXBElement; import javax.xml.bind.JAXBException; import javax.xml.bind.Marshaller; import javax.xml.bind.Unmarshaller; import javax.xml.bind.annotation.XmlAnyElement; import javax.xml.namespace.QName; import org.apache.commons.lang3.Validate; import com.thinkgem.jeesite.common.utils.Exceptions; import com.thinkgem.jeesite.common.utils.Reflections; import com.thinkgem.jeesite.common.utils.StringUtils; /** * 使用Jaxb2.0实现XML<->Java Object的Mapper. * 在创建时需要设定所有需要序列化的Root对象的Class. * 特别支持Root对象是Collection的情形. */ public class JaxbUtil { private static ConcurrentMap<Class, JAXBContext> jaxbContexts = new ConcurrentHashMap<Class, JAXBContext>(); /** * Java Object->Xml without encoding. */ @SuppressWarnings("rawtypes") public static String toXml(Object root) { Class clazz = Reflections.getUserClass(root); return toXml(root, clazz, null); } /** * Java Object->Xml with encoding. */ @SuppressWarnings("rawtypes") public static String toXml(Object root, String encoding) { Class clazz = Reflections.getUserClass(root); return toXml(root, clazz, encoding); } /** * Java Object->Xml with encoding. */ @SuppressWarnings("rawtypes") public static String toXml(Object root, Class clazz, String encoding) { try { StringWriter writer = new StringWriter(); createMarshaller(clazz, encoding).marshal(root, writer); return writer.toString(); } catch (JAXBException e) { throw Exceptions.unchecked(e); } } /** * Java Collection->Xml without encoding, 特别支持Root Element是Collection的情形. */ @SuppressWarnings("rawtypes") public static String toXml(Collection<?> root, String rootName, Class clazz) { return toXml(root, rootName, clazz, null); } /** * Java Collection->Xml with encoding, 特别支持Root Element是Collection的情形. */ @SuppressWarnings("rawtypes") public static String toXml(Collection<?> root, String rootName, Class clazz, String encoding) { try { CollectionWrapper wrapper = new CollectionWrapper(); wrapper.collection = root; JAXBElement<CollectionWrapper> wrapperElement = new JAXBElement<CollectionWrapper>(new QName(rootName), CollectionWrapper.class, wrapper); StringWriter writer = new StringWriter(); createMarshaller(clazz, encoding).marshal(wrapperElement, writer); return writer.toString(); } catch (JAXBException e) { throw Exceptions.unchecked(e); } } /** * Xml->Java Object. */ @SuppressWarnings("unchecked") public static <T> T fromXml(String xml, Class<T> clazz) { try { StringReader reader = new StringReader(xml); return (T) createUnmarshaller(clazz).unmarshal(reader); } catch (JAXBException e) { throw Exceptions.unchecked(e); } } /** * 创建Marshaller并设定encoding(可为null). * 线程不安全,需要每次创建或pooling。 */ @SuppressWarnings("rawtypes") public static Marshaller createMarshaller(Class clazz, String encoding) { try { JAXBContext jaxbContext = getJaxbContext(clazz); Marshaller marshaller = jaxbContext.createMarshaller(); marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); if (StringUtils.isNotBlank(encoding)) { marshaller.setProperty(Marshaller.JAXB_ENCODING, encoding); } return marshaller; } catch (JAXBException e) { throw Exceptions.unchecked(e); } } /** * 创建UnMarshaller. * 线程不安全,需要每次创建或pooling。 */ @SuppressWarnings("rawtypes") public static Unmarshaller createUnmarshaller(Class clazz) { try { JAXBContext jaxbContext = getJaxbContext(clazz); return jaxbContext.createUnmarshaller(); } catch (JAXBException e) { throw Exceptions.unchecked(e); } } @SuppressWarnings("rawtypes") protected static JAXBContext getJaxbContext(Class clazz) { Validate.notNull(clazz, "'clazz' must not be null"); JAXBContext jaxbContext = jaxbContexts.get(clazz); if (jaxbContext == null) { try { jaxbContext = JAXBContext.newInstance(clazz, CollectionWrapper.class); jaxbContexts.putIfAbsent(clazz, jaxbContext); } catch (JAXBException ex) { throw new RuntimeException("Could not instantiate JAXBContext for class [" + clazz + "]: " + ex.getMessage(), ex); } } return jaxbContext; } /** * 封装Root Element 是 Collection的情况. */ public static class CollectionWrapper { @XmlAnyElement protected Collection<?> collection; } }
测试:
String s = JaxbUtil.toXml(shop);
System.out.println(s);
输出:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?> <shop name="CHMart"> <number>100000</number> <describer>EveryThing</describer> <address state="China"> <province>ZheJiang</province> <city>HangZhou</city> <street>XiHuRoad</street> <zip>310000</zip> </address> <orders> <order orderNumber="LH59800"> <shopName>Mart</shopName> <price>80</price> <amount>1</amount> <purDate>2016-11-23 14:54:39</purDate> <customer name="David"> <gender>male</gender> <phoneNo>13699991000</phoneNo> <address state="China"> <province>JiangSu</province> <city>NanJing</city> <street>ZhongYangLu</street> <zip>210000</zip> </address> </customer> </order> <order orderNumber="LH59900"> <shopName>Mart</shopName> <price>60</price> <amount>1</amount> <purDate>2016-11-23 14:54:39</purDate> <customer name="Jim"> <gender>male</gender> <phoneNo>13699990000</phoneNo> <address state="China"> <province>ShangHai</province> <city>ShangHai</city> <street>Huang</street> <zip>200000</zip> </address> </customer> </order> </orders> </shop>