@XmlElement有多个名字
我有一个情况,试图充当两个API之间的网关。 我需要做的是:
- 向APIa提出要求;
- 将XML响应解析(编组)到java对象中;
- 对它做一些改变;
- 然后以XML(unmarshal)向另一端(APIb)发出响应。
问题是我使用相同的对象来解析API响应并将响应发送到另一端。
public class ResponseAPI{ @XmlElement(name="ResponseCode") //I receive but I need to send private String responseCode; //getter and setter }
正如评论所说:我收到但我需要发送
有没有办法在不必创建另一个携带ResultCode的额外类的情况下完成这项工作?
提前致谢!
注意:
Ilya给出的答案有效,但不能保证在JAXB的所有实现中工作,甚至不能在单个JAXB实现的各个版本中工作。 当决定哪个元素编组取决于值的类型时,@ @XmlElements
注释很有用(参见: http : //blog.bdoughan.com/2010/10/jaxb-and-xsd-choice-xmlelements.html ) 。 在您的用例中, ResponseCode
和ResultCode
元素都对应于String
类型,unmarshalling将始终正常工作,但是选择要输出的元素是任意的。 一些JAXB Impls可能最后指定了胜利,但其他人可能很容易获得第一场胜利。
您可以通过利用@XmlElementRef
来执行以下操作。
Java模型
ResponseAPI
我们将responseCode
属性从String
类型更改为JAXBElement
。 JAXBElement
允许我们存储元素名称和值。
import javax.xml.bind.JAXBElement; import javax.xml.bind.annotation.*; @XmlRootElement @XmlAccessorType(XmlAccessType.FIELD) public class ResponseAPI{ @XmlElementRefs({ @XmlElementRef(name = "ResponseCode"), @XmlElementRef(name = "ResultCode") }) private JAXBElement responseCode; public JAXBElement getResponseCode() { return responseCode; } public void setResponseCode(JAXBElement responseCode) { this.responseCode = responseCode; } }
的ObjectFactory
我们在ResponseAPI
类上使用的@XmlElementRef
注释对应于使用@XmlRegistry
注释的类上的@XmlElementDecl
注释。 传统上这个类叫做ObjectFactory
但你可以把它叫做任何你想要的东西。
import javax.xml.bind.JAXBElement; import javax.xml.bind.annotation.*; import javax.xml.namespace.QName; @XmlRegistry public class ObjectFactory { @XmlElementDecl(name="ResponseCode") public JAXBElement createResponseCode(String string) { return new JAXBElement (new QName("ResponseCode"), String.class, string); } @XmlElementDecl(name="ResultCode") public JAXBElement createResultCode(String string) { return new JAXBElement (new QName("ResultCode"), String.class, string); } }
演示代码
input.xml中
ABC
演示
在创建JAXBContext
我们需要确保包含包含@XmlElementDecl
注释的类。
import java.io.File; import javax.xml.bind.*; public class Demo { public static void main(String[] args) throws Exception { JAXBContext jc = JAXBContext.newInstance(ResponseAPI.class, ObjectFactory.class); Unmarshaller unmarshaller = jc.createUnmarshaller(); File xml = new File("Scratch/src2/forum24554789/input.xml"); ResponseAPI responseAPI = (ResponseAPI) unmarshaller.unmarshal(xml); ObjectFactory objectFactory = new ObjectFactory(); String responseCode = responseAPI.getResponseCode().getValue(); JAXBElement resultCodeJAXBElement = objectFactory.createResultCode(responseCode); responseAPI.setResponseCode(resultCodeJAXBElement); Marshaller marshaller = jc.createMarshaller(); marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); marshaller.marshal(responseAPI, System.out); } }
产量
ABC
您可以使用@XmlElements annotaion尝试下一个解决方案
@XmlAccessorType(XmlAccessType.FIELD) public class ResponseAPI { @XmlElements( { @XmlElement(name = "ResponseCode"), @XmlElement(name = "ResultCode") }) private String responseCode; // ... }
在这种情况下,在解组(xml – >对象)期间将使用ResponseCode
和ResultCode
在编组期间(object – > xml)仅使用ResultCode
。
所以你可以解密XML
404
编组后的对象看起来像
404