浏览代码

根据JAXB官方文档改进JAXBContext的使用

master
Daniel Qian 10 年前
父节点
当前提交
457a9809db
共有 2 个文件被更改,包括 39 次插入34 次删除
  1. +38
    -31
      src/main/java/me/chanjar/weixin/util/xml/XmlTransformer.java
  2. +1
    -3
      src/test/java/me/chanjar/weixin/bean/WxXmlMessageTest.java

+ 38
- 31
src/main/java/me/chanjar/weixin/util/xml/XmlTransformer.java 查看文件

@@ -8,84 +8,91 @@ import java.io.Writer;
import java.util.HashMap; import java.util.HashMap;
import java.util.Map; import java.util.Map;


import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Marshaller;
import javax.xml.bind.Unmarshaller;
import javax.xml.bind.*;


import me.chanjar.weixin.bean.*;
import org.xml.sax.InputSource; import org.xml.sax.InputSource;


import com.sun.xml.bind.marshaller.CharacterEscapeHandler; import com.sun.xml.bind.marshaller.CharacterEscapeHandler;


public class XmlTransformer { public class XmlTransformer {


protected static final JAXBContext jaxbContext = initJAXBContext();

/** /**
* xml -> pojo * xml -> pojo
*
* @param clazz * @param clazz
* @param object
* @param xml
* @return * @return
* @throws JAXBException
* @throws JAXBException
*/ */
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public static <T> T fromXml(Class<T> clazz, String xml) throws JAXBException { public static <T> T fromXml(Class<T> clazz, String xml) throws JAXBException {
JAXBContext context = getJAXBContext(clazz);
JAXBContext context = jaxbContext;
Unmarshaller um = context.createUnmarshaller(); Unmarshaller um = context.createUnmarshaller();
T object = (T) um.unmarshal(new StringReader(xml)); T object = (T) um.unmarshal(new StringReader(xml));
return object; return object;
} }
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public static <T> T fromXml(Class<T> clazz, InputStream is) throws JAXBException { public static <T> T fromXml(Class<T> clazz, InputStream is) throws JAXBException {
JAXBContext context = getJAXBContext(clazz);
JAXBContext context = jaxbContext;
Unmarshaller um = context.createUnmarshaller(); Unmarshaller um = context.createUnmarshaller();
InputSource inputSource = new InputSource(is); InputSource inputSource = new InputSource(is);
inputSource.setEncoding("utf-8"); inputSource.setEncoding("utf-8");
T object = (T) um.unmarshal(inputSource); T object = (T) um.unmarshal(inputSource);
return object; return object;
} }
/** /**
* pojo -> xml * pojo -> xml
*
* @param clazz * @param clazz
* @param object
* @return * @return
* @throws JAXBException
* @throws JAXBException
*/ */
public static <T> String toXml(Class<T> clazz, T object) throws JAXBException { public static <T> String toXml(Class<T> clazz, T object) throws JAXBException {
StringWriter stringWriter = new StringWriter(); StringWriter stringWriter = new StringWriter();
toXml(clazz, object, stringWriter); toXml(clazz, object, stringWriter);
return stringWriter.getBuffer().toString(); return stringWriter.getBuffer().toString();
} }
public static <T> void toXml(Class<T> clazz, T object, Writer writer) throws JAXBException { public static <T> void toXml(Class<T> clazz, T object, Writer writer) throws JAXBException {
JAXBContext context = getJAXBContext(clazz);
JAXBContext context = jaxbContext;
Marshaller m = context.createMarshaller(); Marshaller m = context.createMarshaller();
m.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); m.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
m.setProperty(CharacterEscapeHandler.class.getName(), characterUnescapeHandler); m.setProperty(CharacterEscapeHandler.class.getName(), characterUnescapeHandler);
m.marshal(object, writer); m.marshal(object, writer);
} }
protected static CharacterEscapeHandler characterUnescapeHandler = new CharacterUnescapeHandler(); protected static CharacterEscapeHandler characterUnescapeHandler = new CharacterUnescapeHandler();
protected static class CharacterUnescapeHandler implements CharacterEscapeHandler { protected static class CharacterUnescapeHandler implements CharacterEscapeHandler {
public void escape(char[] ac, int i, int j, boolean flag, Writer writer) throws IOException { public void escape(char[] ac, int i, int j, boolean flag, Writer writer) throws IOException {
writer.write(ac, i, j); writer.write(ac, i, j);
} }
} }
protected static Map<Class<?>, JAXBContext> jaxbContexts = new HashMap<Class<?>, JAXBContext>();
protected static JAXBContext getJAXBContext(Class<?> clazz){
//JAXBContext是线程安全的,且创建相对比较耗性能,使用map缓存,并发下多次创建没问题.
JAXBContext context = jaxbContexts.get(clazz);
if(context == null){
try {
context = JAXBContext.newInstance(clazz);
} catch (JAXBException e) {
throw new RuntimeException("创建JAXBContext实例失败:" + clazz.getName(), e);
}
jaxbContexts.put(clazz, context);
}
return context;

private static JAXBContext initJAXBContext() {
/*
* JAXBContext对象是线程安全的,根据官方文档的建议将对象作为全局实例
* https://jaxb.java.net/guide/Performance_and_thread_safety.html
*/
try {
return JAXBContext.newInstance(
WxXmlOutMessage.class,
WxXmlOutImageMessage.class,
WxXmlOutMewsMessage.class,
WxXmlOutMusicMessage.class,
WxXmlOutTextMessage.class,
WxXmlOutVideoMessage.class,
WxXmlOutVoiceMessage.class,
WxXmlMessage.class);
} catch (JAXBException e) {
throw new RuntimeException(e);
}
} }
} }

+ 1
- 3
src/test/java/me/chanjar/weixin/bean/WxXmlMessageTest.java 查看文件

@@ -1,11 +1,9 @@
package me.chanjar.weixin.bean; package me.chanjar.weixin.bean;


import me.chanjar.weixin.bean.WxXmlMessage;
import me.chanjar.weixin.api.WxConsts;
import org.testng.Assert; import org.testng.Assert;
import org.testng.annotations.Test; import org.testng.annotations.Test;


import me.chanjar.weixin.api.WxConsts;

@Test @Test
public class WxXmlMessageTest { public class WxXmlMessageTest {




正在加载...
取消
保存