运用JAXB实现xml实体的按需注入

本文介绍了如何使用JAXB简化Java对象与XML之间的转换过程。通过具体案例展示了如何定义Java类来映射XML结构,利用@XmlElements等注解实现多态效果,并提供了通用方法以减少代码重复。

使用场景:最近做一个项目,项目中请求和相应报文均是xml格式的,然后报文头都是一样的,只是body会不同,JAXB是一个很好的解决java对象和xml的工具,我们需要在不用的接口返回不同的body体,但是又不想代码冗余每一个都写一个JAXB配置,最好是搞一个通用的,于是下面的代码就产生了。

 

一、简介

1、概念是什么:(Java Architecture for XML Binding) 是一个业界的标准,即是一项可以根据XML Schema产生Java类的技术。该过程中,JAXB也提供了将XML实例文档反向生成Java对象树的方法,并能将Java对象树的内容重新写到XML实例文档。有多种实现。

2、JAXB中有什么:包含“xjc”工具和一个“schemagen”工具。 

“xjc”工具可以用来将XML模式或其他类型模式文件(Java 1.6试验性地支持RELAX NG,DTD以及WSDL)转换为Java类。Java类使用javax.xml.bind.annotation包下的Java 标注,例如@XmlRootElement和@XmlElement。XML列表序列表示为java.util.List类型的属性, 通过JAXBContext可以创建Marshallers(将Java对象转换成XML)和Unmarshallers(将XML解析为Java对象)。

另外的“schemagen”工具,能够执行“xjc”的反向操作,通过一组标注的Java类创建一个XML模式。

二、依赖

JDK5以下开发需要的jar包:activation.jar、jaxb-api.jar、 jaxb-impl.jar、 jsr173-api.jar;

如果是基于JDK6以上版本已经集成JAXB2的JAR,在目录{JDK_HOME}/jre/lib/rt.jar中。

三、应用

第一步:创建要转化的java对象,该对象需要使用相关注解注释各字段

(标注在get方法上,标注在别的地方运行时会报错)

import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlElementWrapper;
import javax.xml.bind.annotation.XmlElements;
import javax.xml.bind.annotation.XmlRootElement;
import java.io.Serializable;

/**
 *
 * @author Zhaky
 */
@XmlRootElement(name = "merchant")
public class Merchant implements Serializable {
    private CommonHead head;
    private BaseBody body;

    @XmlElement(name = "head")
    public CommonHead getHead() {
        return head;
    }

    public Merchant() {
        super();
    }

    public void setHead(CommonHead head) {
        this.head = head;
    }
    @XmlElements({//重要:
            @XmlElement(name="body",type=Cancel.class),//这里的Cancel与下面类的@XmlType(name="Cancel")相对应,生成xml时节点名字为body
            @XmlElement(name="body",type=Refund.class),
            @XmlElement(name="body",type=Pay.class)
    })
    public BaseBody getBody() {
        return body;
    }

    public void setBody(BaseBody body) {
        this.body = body;
    }
}

@XmlElements 重要说明:网上资料对这个参数介绍不多也不详细,简单来说就是通过这个参数实现按需加载实体

import javax.xml.bind.annotation.XmlTransient;

import java.io.Serializable;


/**

* Created by Zhaky

*/

@XmlTransient

public abstract class BaseBody implements Serializable {

public BaseBody() {

super();

}

}

//此处必须要有无参数的构造方法

 


import org.hibernate.validator.constraints.Length;


import javax.validation.constraints.NotNull;

import javax.xml.bind.annotation.XmlType;


/**

*/

@XmlType(name="Cancel")

public class Cancel extends BaseBody {

//这里参数校验和xml实体公用了一个pojo

@NotNull(message = "{common.oriReqMsgId.not.empty}")

@Length(min = 0, max = 32, message = "{common.oriReqMsgId.length.error}")

private String oriReqMsgId;//原交易流水号

//扩展字段

@Length(min = 0, max = 128, message = "{common.extend1.length.error}")

private String extend1;//备用

@Length(min = 0, max = 128, message = "{common.extend2.length.error}")

private String extend2;//备用

@Length(min = 0, max = 128, message = "{common.extend3.length.error}")

private String extend3;//备用·

.....

//省略get set方法

}

 

配置完成开始使用!!

通用方法

public class XMLParaUtil{
public static String getRequestParamsXmlString(@Valid BaseBody requestVO) throws JAXBException {
        Merchant message = new Merchant();
        CommonHead head = new CommonHead();
        head.init(DateFormatUtils.format(new Date(), "yyyyMMddHHmmss"));
        message.setHead(head);
        message.setBody(requestVO);
        JAXBContext context = JAXBContext.newInstance(Merchant.class);
        Marshaller marshaller = context.createMarshaller();
        StringWriter sw = new StringWriter();
        marshaller.marshal(message, sw);
        return sw.toString();
}
}

 

外部使用时根据不同的场景引入不同的实现类即可

Cancel requestVO =new Cancel();

String plainXML = CmbcCore.getRequestParamsXmlString(requestVO);

 

转载于:https://my.oschina.net/zhaky/blog/852498

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值