在項目中突然要想使用xml ,又涉及到java對象轉爲xml ,於是就學習了XStream,並封裝了Xml工具類,於是就編寫本博客作爲記錄。
具體使用可以看這篇文章: XStream 簡介
不多說,直接上代碼 ,如下所示:
javabean代碼如下:
@XStreamAlias("bank")
public class Bank {
private String name;
private String address;
private Map<String, String> map;
private List<Account> accounts;
//省略 setter 和getter
}
封裝工具類如下:
import com.thoughtworks.xstream.XStream;
import com.thoughtworks.xstream.converters.Converter;
import com.thoughtworks.xstream.converters.MarshallingContext;
import com.thoughtworks.xstream.converters.UnmarshallingContext;
import com.thoughtworks.xstream.io.HierarchicalStreamReader;
import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
import com.thoughtworks.xstream.io.xml.DomDriver;
import java.util.AbstractMap;
import java.util.HashMap;
import java.util.Map;
public class XmlUtils {
public static Boolean useConverter = true; // 是否使用map轉換器。
private static Converter converter = new MapEntryConverter(); //轉換器
public static Converter getConverter() {
return converter;
}
private static <T> XStream getXStream(Class<T> t) {
//創建解析XML對象
XStream xStream = new XStream(new DomDriver());
//處理註解
xStream.processAnnotations(t);
if (useConverter)
xStream.registerConverter(converter);
return xStream;
}
/**
* XML轉對象
*
* @param clazz 對象類
* @param xml xml字符串
* @param <T> T
* @return
*/
public static <T> T parseFromXml(Class<T> clazz, String xml) {
XStream xStream = getXStream(clazz);
@SuppressWarnings("unchecked")
T t = (T) xStream.fromXML(xml);//將XML字符串轉爲bean對象
return t;
}
/**
* 對象轉xml
*
* @param obj 對象
* @return
*/
public static String toXml(Object obj) {
XStream xStream = getXStream(obj.getClass());
return xStream.toXML(obj);
}
private static class MapEntryConverter implements Converter {
public boolean canConvert(Class clazz) {
return AbstractMap.class.isAssignableFrom(clazz);
}
public void marshal(Object value, HierarchicalStreamWriter writer, MarshallingContext context) {
AbstractMap map = (AbstractMap) value;
for (Object obj : map.entrySet()) {
Map.Entry entry = (Map.Entry) obj;
writer.startNode(entry.getKey().toString());
writer.setValue(entry.getValue().toString());
writer.endNode();
}
}
public Object unmarshal(HierarchicalStreamReader reader, UnmarshallingContext context) {
Map<String, String> map = new HashMap<String, String>();
while (reader.hasMoreChildren()) {
reader.moveDown();
map.put(reader.getNodeName(), reader.getValue());
reader.moveUp();
}
return map;
}
}
}
考慮到項目中的javaBean中也可能存在map集合,於是我在工具類上又自定義了一個轉換器,用於對map集合進行處理。
測試代碼如下:
private static void test2() {
// XmlUtils.useConverter = true;
Bank bank = getBank();
String result = XmlUtils.toXml(bank);
System.out.println(result);
System.out.println("-------------------轉換結束-------");
Bank newBank = XmlUtils.parseFromXml(Bank.class, result);
System.out.println(newBank);
}
private static Bank getBank() {
Bank bank = new Bank();
Account account1 = new Account();
Account account2 = new Account();
account1.setAccoutId(1);
account1.setAccountName("aaa");
account1.setAccountMoeny(100);
account1.setTelNum("1333333333");
account2.setAccoutId(2);
account2.setAccountName("sunli");
account2.setAccountMoeny(200);
account2.setTelNum("14444444");
List<Account> accounts = new ArrayList<Account>();
accounts.add(account1);
accounts.add(account2);
Map<String, String> map = new HashMap<>();
map.put("test", "111");
map.put("test2", "1001");
map.put("test3", "000");
bank.setMap(map);
bank.setName("中國人民銀行");
bank.setAddress("地球");
bank.setAccounts(accounts);
return bank;
}
控制檯輸出如下:
請注意看, 打印出的xml 中的map節點,如果使用XStream默認的轉換器打印出來的map下的節點數據並不是這樣。