package com.brmoney.util.obj2xml; import java.util.Iterator; import java.util.List; import org.dom4j.Document; import org.dom4j.DocumentException; import org.dom4j.DocumentHelper; import org.dom4j.Element; import com.brmoney.flight.pojo.DomeTicketPsg; import com.brmoney.util.resource.FieldResourceBundle; import com.thoughtworks.xstream.XStream; import com.thoughtworks.xstream.io.xml.DomDriver; import com.thoughtworks.xstream.converters.Converter; public class Object2Xml { static DomDriver domDriver = null; static Converter xmlNullConverter = null; static { domDriver = new DomDriver(); xmlNullConverter = new XmlNullConverter(); } public static String compare2Object(Object obj1, Object obj2) throws DocumentException { XStream stream = new XStream(domDriver); stream.registerConverter(xmlNullConverter); String xml1 = stream.toXML(obj1); String xml2 = stream.toXML(obj2); Document doc1 = DocumentHelper.parseText(xml1); Document doc2 = DocumentHelper.parseText(xml2); StringBuffer buffer = new StringBuffer(); List<Element> elements = doc1.selectNodes(obj1.getClass().getName()); List<Element> unElements = doc2.selectNodes(obj1.getClass().getName()); for (int i = 0; i < elements.size(); i++) { Element rootElement = elements.get(i); Element unRootElement = unElements.get(i); if (rootElement != null && unRootElement != null) { Iterator eles = rootElement.elementIterator(); Iterator unEles = unRootElement.elementIterator(); while (eles.hasNext() && unEles.hasNext()) { Element e = (Element) eles.next(); Element ue = (Element) unEles.next(); if (e.getName().equals(ue.getName()) && !e.getTextTrim().equals(ue.getTextTrim())) { String[] config = FieldResourceBundle.getMessage( e.getName(), obj1.getClass().getSimpleName()) .split("[|]"); if (config[0] != null) { buffer.append(config[0]).append(":").append("由") .append(e.getTextTrim()).append( " 更改为: ") .append(ue.getTextTrim()).append(" "); } } } } } return buffer.toString(); } public static void main(String[] args) throws DocumentException { DomeTicketPsg psg1 = new DomeTicketPsg(); psg1.setPsgName("项羽"); DomeTicketPsg psg2 = new DomeTicketPsg(); psg2.setPsgName("刘备"); System.out.print(Object2Xml.compare2Object(psg1, psg2)); } }
package com.brmoney.util.obj2xml; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.text.DateFormat; import java.util.ArrayList; import java.util.Calendar; import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Locale; import java.util.Map; 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; /** * 自定义XStream转化器, * 使null值标签可以输出到XML */ @SuppressWarnings("unchecked") public class XmlNullConverter implements Converter { private Map<Class<?>, List<String>> attributes = null; public void regAttribute(Class<?> type, String attribute) { if (null == attributes) { attributes = new HashMap<Class<?>, List<String>>(); } List value = attributes.get(type); if (null == value) { value = new ArrayList<String>(); attributes.put(type, value); } value.add(attribute); } /** * 是否是属性(是属性的不用以单独标签实现) * @param type * @param attribute * @return */ private boolean isClassAttribute(Class<?> type, String attribute) { List<String> value = getAttributes(type); if (null == value) return false; if (value.contains(attribute)) { return true; } return false; } /** * 获取注册的属性 * @param type * @return */ private List<String> getAttributes(Class<?> type) { if (null != attributes) { return attributes.get(type); } return null; } /** * 输出对象的属性标签 * @param source * @param writer */ private void writerAttribute(Object source, HierarchicalStreamWriter writer) { Class cType = source.getClass(); List<String> value = getAttributes(cType); if ((null != value) && (value.size() > 0)) { Method[] methods = cType.getMethods(); for (Method method : methods) { String methodName = method.getName(); if (methodName.indexOf("get") != -1 && methodName != "getClass") { String name = methodName.substring(3); //首字母小写 name = name.substring(0, 1).toLowerCase()+name.substring(1); if (value.contains(name)) { Object o = null; try { o = method.invoke(source, null); } catch (Exception e) { e.printStackTrace(); } writer.addAttribute(name, o==null?"":o.toString()); } } } } } public void marshal(Object source, HierarchicalStreamWriter writer, MarshallingContext context) { if (null == source) return; if (isBaseType(source.getClass())) { return; } Class cType = source.getClass(); Method[] methods = cType.getMethods(); writerAttribute(source, writer); for(Method m : methods) { String methodName = m.getName(); if (methodName.indexOf("get") != -1 && methodName != "getClass") { if (source instanceof List) { List list = (List)source; for (Object obj: list) { String name = obj.getClass().toString(); name = name.substring(name.lastIndexOf(".") + 1); writer.startNode(name); marshal(obj, writer, context); writer.endNode(); } } else { boolean isBaseType = isBaseType(m.getReturnType()); String name = methodName.substring(3); if (isBaseType) { name = name.substring(0, 1).toLowerCase()+name.substring(1); } Object o = null; try { o = m.invoke(source, null); } catch (IllegalArgumentException e) { e.printStackTrace(); } catch (IllegalAccessException e) { e.printStackTrace(); } catch (InvocationTargetException e) { e.printStackTrace(); } //如果是基本类型调用toString,否则递归 if (isBaseType) { if (!isClassAttribute(cType, name)) { writer.startNode(name); if (m.getReturnType().equals(Date.class)&&o!=null&&!"".equals(o.toString())) { Date date = (Date)o; DateFormat formatter = DateFormat.getDateInstance(DateFormat.FULL,new Locale("zh", "CN")); writer.setValue(formatter.format(date)); }else{ writer.setValue(o==null?"":o.toString()); } writer.endNode(); } } else { writer.startNode(name); marshal(o, writer, context); writer.endNode(); } } } } } public Object unmarshal(HierarchicalStreamReader reader, UnmarshallingContext context) { return null; } public boolean canConvert(Class type) { return true; } private boolean isBaseType(Class<?> type) { if (type.equals(Integer.class) || type.equals(Double.class) || type.equals(String.class) || type.equals(Boolean.class) || type.equals(Long.class) ||type.equals(Short.class) ||type.equals(Byte.class) ||type.equals(Float.class) ||type.equals(Date.class)) { return true; } return false; } }
package com.brmoney.util.resource; import java.util.Locale; import java.util.ResourceBundle; public class FieldResourceBundle { private static String baseKey = "datafield/"; public static String getMessage(String key,String propName){ Locale locale = new Locale("zh", "CN"); ResourceBundle bundle = ResourceBundle.getBundle(baseKey+propName, locale); if(bundle.containsKey(key)){ return bundle.getString(key); } return ""; } }