//JAXB support Collection(List,Set),does not support Map(not Collection).
//XmlAdapter<ValueType,BoundType> : !use List to implement Map's feature,like (List students)!!!
//<ValueType> : to be persisted format, The type that JAXB knows how to handle out of the box
//<BoundType> : memory format, The type that JAXB doesn't know how to handle
public class MapAdapter extends XmlAdapter<MapAdapter.AdaptedMap, Map<String, String>>
/**
* @author timeriver.wang
* @date 2013-01-09 8:07:01 PM
*/
@XmlRootElement
@XmlAccessorType(XmlAccessType.PROPERTY)
public class Student {
private String id;
private String name;
public String getId() {
return id;
}
@XmlElement(name = "id")
public void setId(String id) {
this.id = id;
}
@XmlElement(name = "name")
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
/**
* @author timeriver.wang
* @date 2013-01-09 8:08:15 PM
*/
public class Test {
private static String filePath = "D:/teacher.xml";
public static void main( String[] args )throws Exception {
toXml();
toObj();
}
private static void toXml()throws Exception {
Teacher teacher = initTeacher();
//
JAXBContext jaxbContext = JAXBContext.newInstance( Teacher.class );
// marshal 整理,编列,元帅的意思
Marshaller jaxbMarshaller = jaxbContext.createMarshaller();
// format, make every element keep a separate line.
jaxbMarshaller.setProperty( Marshaller.JAXB_FORMATTED_OUTPUT, true );
//output --> file
File file = new File( filePath );
jaxbMarshaller.marshal( teacher, file );
//output --> console
jaxbMarshaller.marshal( teacher, System.out );
}
private static void toObj()throws Exception {
File file = new File( filePath );
JAXBContext jaxbContext = JAXBContext.newInstance( Teacher.class );
Unmarshaller jaxbUnmarshaller = jaxbContext.createUnmarshaller();
Teacher teacher = (Teacher) jaxbUnmarshaller.unmarshal( file );
System.out.println( teacher.getName() );
}
private static Teacher initTeacher(){
// organize Object(to be saved/persisted)
Teacher teacher = new Teacher();
teacher.setId( "101" );
teacher.setName( "DAO SHI" );
Address address = new Address();
address.setArea( "bei jing, hai dian qu" );
address.setStreet( "shang di 8 jie 88 hao" );
teacher.setAddress( address );
Student stu1 = new Student();
stu1.setId( "007" );
stu1.setName( "ZHOU XING XING" );
Student stu2 = new Student();
stu2.setId( "008" );
stu2.setName( "DA WEN XI" );
List<Student>students = new ArrayList<Student>();
students.add( stu1 );
students.add( stu2 );
teacher.setStudents( students );
Set<String> interests = new HashSet<String>();
interests.add( "play dota" );
interests.add( "smoke" );
teacher.setInterests( interests );
Map<String,String> phones = new HashMap<String,String>();
phones.put( "workPhoe", "18612345678" );
phones.put( "homePhoe", "01012345678" );
teacher.setPhones( phones );
return teacher;
}
}
/**
* @author timeriver.wang
* @date 2013-01-09 8:07:09 PM
*/
// @XmlRootElement(namespace ="NAMESPACE" )
@XmlRootElement
@XmlType(propOrder = {"id","name","address","students","interests","phones"})
public class Teacher {
private String id;
private String name;
private Address address;
private List<Student> students;
private Set<String> interests;
private Map<String, String> phones;
@XmlAttribute(name = "tid")
public String getId() {
return id;
}
public void setId( String id ) {
this.id = id;
}
@XmlElement(name = "tname")
public String getName() {
return name;
}
public void setName( String name ) {
this.name = name;
}
@XmlElement(name = "address")
public Address getAddress() {
return address;
}
public void setAddress( Address address ) {
this.address = address;
}
@XmlElementWrapper(name = "students")
@XmlElement(name = "student")
public List<Student> getStudents() {
return students;
}
public void setStudents( List<Student> students ) {
this.students = students;
}
@XmlElementWrapper(name = "interests")
@XmlElement(name = "interest")
public Set<String> getInterests() {
return interests;
}
public void setInterests( Set<String> interests ) {
this.interests = interests;
}
// can not use XmlElementWrapper, because "Map" is not a "Collection"
// @XmlElementWrapper(name = "phones")
// @XmlElement(name = "phone")
// 也可以不加任何注解,JAXB,会提供一个默认的注解
@XmlJavaTypeAdapter(MapAdapter.class)
@XmlElement(name = "phones")
public Map<String, String> getPhones() {
return phones;
}
public void setPhones( Map<String, String> phones ) {
this.phones = phones;
}
}
//JAXB support Collection(List,Set),does not support Map(not Collection).
//XmlAdapter<ValueType,BoundType> : !use List to implement Map's feature,like (List students)!!!
//<ValueType> : to be persisted format, The type that JAXB knows how to handle out of the box
//<BoundType> : memory format, The type that JAXB doesn't know how to handle
public class MapAdapter extends XmlAdapter<MapAdapter.AdaptedMap, Map<String, String>> {
public static class AdaptedMap {
public List<Entry> entry = new ArrayList<Entry>();
}
public static class Entry {
public String key;
public String value;
}
@Override
public Map<String, String> unmarshal(AdaptedMap adaptedMap) throws Exception {
Map<String, String> map = new HashMap<String, String>();
for(Entry entry : adaptedMap.entry) {
map.put(entry.key, entry.value);
}
return map;
}
//use List to implement Map's feature,like (List students)!
@Override
public AdaptedMap marshal(Map<String, String> map) throws Exception {
AdaptedMap adaptedMap = new AdaptedMap();
for(Map.Entry<String, String> mapEntry : map.entrySet()) {
Entry entry = new Entry();
entry.key = mapEntry.getKey();
entry.value = mapEntry.getValue();
adaptedMap.entry.add(entry);
}
return adaptedMap;
}
}
@XmlRootElement
public class Address {
private String area;
private String street;
@XmlElement(name = "area")
public String getArea() {
return area;
}
public void setArea( String area ) {
this.area = area;
}
@XmlElement(name = "street")
public String getStreet() {
return street;
}
public void setStreet(String street) {
this.street = street;
}
}