如何在使用 jaxb 进行编组时删除额外的转义字符

Posted

技术标签:

【中文标题】如何在使用 jaxb 进行编组时删除额外的转义字符【英文标题】:How to remove extra escape character while doing marshling using jaxb 【发布时间】:2021-11-01 16:54:31 【问题描述】:

原始 XML 放大器;由 JAXB 添加,需要忽略:-

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
 <emp>
 <address>7 stret &amp; new </address>
 <name>Naveenqq</name>
</emp>

预计没有 amp;(实际价值想要):

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
 <emp>
  <address>7 stret & new </address>
  <name>Naveenqq</name>
</emp>

我试过下面的代码:

  private static void jaxbObjectToXML(Emp employee) throws IOException, SAXException, ParserConfigurationException 

    try
     

        JAXBContext jaxbContext = JAXBContext.newInstance(Emp.class);
        Marshaller jaxbMarshaller = jaxbContext.createMarshaller();
        //jaxbMarshaller.setProperty("jaxb.encoding", "US-ASCII"); 
        jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); 
        //jaxbMarshaller.setProperty(OutputKeys.ENCODING, "ASCII");
        //jaxbMarshaller.setProperty(CharacterEscapeHandler.class.getName(), new CustomCharacterEscapeHandler());
        //          jaxbMarshaller.setProperty(CharacterEscapeHandler.class.getName(), new CharacterEscapeHandler() 
        //            
        //              @Override
        //              public void escape(char[] ch, int start, int length, boolean isAttVal, Writer out) throws IOException 
        //                  out.write( ch, start, length ); 
        //                  
        //              
        //          ); 
        //          
        //          StringWriter writer = new StringWriter();
        File file = new File("employee1.xml");
        jaxbMarshaller.marshal(employee, file); 
        //          
        //          DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
        //          DocumentBuilder builder = factory.newDocumentBuilder();
        //          InputSource is = new InputSource( new StringReader( writer.toString() ) );
        //          Document doc = builder.parse( is );
        System.out.println("done::");


     
    catch (JAXBException e) 
    
        e.printStackTrace();
    

请帮忙解决一下,所有的编码类型我都试过了

【问题讨论】:

【参考方案1】:

问题是 XML 中的 &amp;amp; 无效,如果您尝试使用 &amp;amp; 验证 XML,它将失败。 JAXB 非常聪明,因此它会尝试用它们的字符实体替换特殊字符。类似的事情也发生在 html 中。你可以refer here.

但如果您观察JAXB Unmarshalling 之后的值,则它已被&amp;amp; 取代,而不是&amp;amp;。因此您不必担心它在 XML 中的存在。我想如果你走你想要的路线,那么它会导致很多复杂性,并且你的 XML 本身将是无效的。

XML:

<emp>
   <address>7 stret &amp; new</address>
   <name>Naveenqq</name>
</emp>

根:

@Data
@XmlRootElement(name = "emp")
@XmlAccessorType(XmlAccessType.FIELD)
public class Root 
    private String address;
    private String name;


主要:

public class Main 
    public static void main(String[] args) throws JAXBException, XMLStreamException 
        final InputStream inputStream = Main.class.getClassLoader().getResourceAsStream("test.xml");
        final XMLStreamReader xmlStreamReader = XMLInputFactory.newInstance().createXMLStreamReader(inputStream);
        final Unmarshaller unmarshaller = JAXBContext.newInstance(Root.class).createUnmarshaller();
        final Root root = unmarshaller.unmarshal(xmlStreamReader, Root.class).getValue();
        System.out.println(root.toString());

        Marshaller marshaller = JAXBContext.newInstance(Root.class).createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
        marshaller.setProperty(Marshaller.JAXB_ENCODING, "US-ASCII");
        //marshaller.setProperty("com.sun.xml.internal.bind.xmlHeaders", new XmlCharacterHandler());
        marshaller.marshal(root, System.out);
    

输出:

Root(address=7 stret & new, name=Naveenqq)
<?xml version="1.0" encoding="US-ASCII"?>
<emp>
   <address>7 stret &amp; new</address>
   <name>Naveenqq</name>
</emp>

正如您在输出中看到的 Root(address=7 stret &amp; new, name=Naveenqq) 它已被 &amp;amp; 替换,因此您可以继续使用它。

希望解释有所帮助。

【讨论】:

【参考方案2】:

您的期望值不是有效的 XML,因此您无法说服任何支持 XML 的工具生成它。

您为什么要尝试生成无效的 XML?

【讨论】:

以上是关于如何在使用 jaxb 进行编组时删除额外的转义字符的主要内容,如果未能解决你的问题,请参考以下文章

在 JaxB 编组没有 @XmlRootElement 注释的元素时删除 ns2 前缀

在 JaxB 编组期间将字符串截断到最大限制

如何使用 JAXB2 用动态元素编组 XML

JAXB - 如何在没有标题的情况下编组java对象

JAXB 继承,解组到编组类的子类

使用 eclipselink 在 JPA 对象上进行 jaxb 编组期间的日期对话错误