Java JAXB更改默认命名转换器

Java JAXB更改默认命名转换器,java,xml,jaxb,Java,Xml,Jaxb,在JAXB的帮助下,我想通过重用一些没有JAXB类型/元素注释的现有XML/类来进行封送和解封送 是否可以将默认的JAXB命名映射配置更改为映射所有标记/字段,如“firstName->firstName”,而不引入任何注释 我指的是这些类字段(注意:它们以小写字母开头) 要映射到该XML(注意:它们以大写字母开头): 约翰 雌鹿 Jesper建议使用MOXy的另一种方法是使用StreamReaderDelegate和DelegatingXMLStreamWriter过滤输入和输出xml 对于

在JAXB的帮助下,我想通过重用一些没有JAXB类型/元素注释的现有XML/类来进行封送和解封送

是否可以将默认的JAXB命名映射配置更改为映射所有标记/字段,如“firstName->firstName”,而不引入任何注释

我指的是这些类字段(注意:它们以小写字母开头)

要映射到该XML(注意:它们以大写字母开头):


约翰
雌鹿

Jesper建议使用MOXy的另一种方法是使用
StreamReaderDelegate
DelegatingXMLStreamWriter
过滤输入和输出xml

对于解组,您可以执行以下操作:

String xml = "<Person><FirstName>John</FirstName><LastName>Doe</LastName></Person>";

XMLStreamReader xsr = XMLInputFactory.newInstance().createXMLStreamReader(new StringReader(xml));
xsr = new StreamReaderDelegate(xsr) {
    @Override
    public String getLocalName() {
        String s = super.getLocalName(); 
        return Character.toLowerCase(s.charAt(0)) + s.substring(1); 
    }
};

JAXBContext jc = JAXBContext.newInstance(Person.class);
Unmarshaller u = jc.createUnmarshaller();
Person person = u.unmarshal(xsr, Person.class).getValue();
stringxml=“JohnDoe”;
XMLStreamReader xsr=XMLInputFactory.newInstance().createXMLStreamReader(新StringReader(xml));
xsr=新StreamReaderDelegate(xsr){
@凌驾
公共字符串getLocalName(){
字符串s=super.getLocalName();
返回字符.toLowerCase(s.charAt(0))+s.substring(1);
}
};
JAXBContext jc=JAXBContext.newInstance(Person.class);
解组器u=jc.createUnmarshaller();
Person=u.unmarshal(xsr,Person.class).getValue();
类似于沼泽化:

StringWriter sw = new StringWriter();
XMLStreamWriter xsw = XMLOutputFactory.newInstance().createXMLStreamWriter(sw);
xsw = new DelegatingXMLStreamWriter(xsw) {
    @Override
    public void writeStartElement(String prefix, String localName, String namespaceURI) throws XMLStreamException {
        String s = localName;
        super.writeStartElement(prefix, Character.toUpperCase(s.charAt(0)) + s.substring(1), namespaceURI);
    }
};

Marshaller m = jc.createMarshaller();
JAXBElement<Person> jaxbElement = new JAXBElement<Person>(new QName(Person.class.getSimpleName()), Person.class, person);
m.marshal(jaxbElement, xsw);
StringWriter sw=新建StringWriter();
XMLStreamWriter xsw=XMLOutputFactory.newInstance().createXMLStreamWriter(sw);
xsw=新的DelegatingXMLStreamWriter(xsw){
@凌驾
public void writeStarteElement(字符串前缀、字符串localName、字符串namespaceURI)引发XMLStreamException{
字符串s=localName;
super.writeStart元素(前缀,Character.toUpperCase(s.charAt(0))+s.substring(1),namespaceURI);
}
};
Marshaller m=jc.createMarshaller();
JAXBElement=newjaxbelement(新的QName(Person.class.getSimpleName()),Person.class,Person);
m、 元帅(jaxbElement,xsw);
DelegatingXMLStreamWriter
出于某种原因是包私有的,但它是一个简单的类,您可以从中复制源代码


此解决方案基于。

我认为JDK中的JAXB实现无法做到这一点。如果您使用诸如EclipseLink MOXy之类的替代实现,这可能是可能的。见:谢谢,杰斯珀。我看到这个注释
XMLNameTransformer
可以完成这项工作,但不想引入新的库依赖项。谢谢,@Oleg。工作起来很有魅力。我认为某种xml预处理/转换可以完成这项工作,但这是更好的解决方案。
String xml = "<Person><FirstName>John</FirstName><LastName>Doe</LastName></Person>";

XMLStreamReader xsr = XMLInputFactory.newInstance().createXMLStreamReader(new StringReader(xml));
xsr = new StreamReaderDelegate(xsr) {
    @Override
    public String getLocalName() {
        String s = super.getLocalName(); 
        return Character.toLowerCase(s.charAt(0)) + s.substring(1); 
    }
};

JAXBContext jc = JAXBContext.newInstance(Person.class);
Unmarshaller u = jc.createUnmarshaller();
Person person = u.unmarshal(xsr, Person.class).getValue();
StringWriter sw = new StringWriter();
XMLStreamWriter xsw = XMLOutputFactory.newInstance().createXMLStreamWriter(sw);
xsw = new DelegatingXMLStreamWriter(xsw) {
    @Override
    public void writeStartElement(String prefix, String localName, String namespaceURI) throws XMLStreamException {
        String s = localName;
        super.writeStartElement(prefix, Character.toUpperCase(s.charAt(0)) + s.substring(1), namespaceURI);
    }
};

Marshaller m = jc.createMarshaller();
JAXBElement<Person> jaxbElement = new JAXBElement<Person>(new QName(Person.class.getSimpleName()), Person.class, person);
m.marshal(jaxbElement, xsw);