如何使用Jackson 2.13.3在XML属性中保留未转义的&符号
解决Jackson XML属性中&不转义的问题
Jackson XML模块默认会对XML属性值中的特殊字符(如&、<、>等)进行转义,这是符合XML规范的行为,但如果需要强制输出未转义的&,可以通过以下两种方式实现:
方法一:全局禁用XML字符转义
通过配置XmlMapper关闭ToXmlGenerator.Feature.ESCAPE_XML_CHARACTERS特性,这样所有属性和元素的特殊字符都不会被转义。注意:这会破坏XML的合法性,仅在特殊场景下使用。
修改Main.java代码如下:
import com.fasterxml.jackson.dataformat.xml.XmlMapper; import com.fasterxml.jackson.dataformat.xml.ser.ToXmlGenerator; public class Main { public static void main(String[] args) throws Exception { XmlMapper xmlMapper = XmlMapper.builder() .configure(ToXmlGenerator.Feature.ESCAPE_XML_CHARACTERS, false) .build(); Property property = new Property(); property.setName("11&22"); property.setTest("11&22"); String xml = xmlMapper.writeValueAsString(property); System.out.println(xml); } }
方法二:针对单个属性定制序列化器
如果只想让特定属性不转义,其他属性保持默认转义行为,可以自定义序列化器并绑定到目标属性上:
1. 实现自定义序列化器
import com.fasterxml.jackson.core.JsonGenerator; import com.fasterxml.jackson.databind.SerializerProvider; import com.fasterxml.jackson.databind.ser.std.StdSerializer; import com.fasterxml.jackson.dataformat.xml.ser.ToXmlGenerator; import java.io.IOException; public class UnescapedXmlAttributeSerializer extends StdSerializer<String> { public UnescapedXmlAttributeSerializer() { super(String.class); } @Override public void serialize(String value, JsonGenerator gen, SerializerProvider provider) throws IOException { if (gen instanceof ToXmlGenerator xmlGen) { // 直接写入属性值,跳过转义逻辑 xmlGen.writeRawAttributeValue(value); } else { gen.writeString(value); } } }
2. 修改Property.java绑定序列化器
import com.fasterxml.jackson.databind.annotation.JsonSerialize; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement; @JacksonXmlRootElement(localName = "Property") public class Property { @JacksonXmlProperty(isAttribute = true) @JsonSerialize(using = UnescapedXmlAttributeSerializer.class) private String name; private String test; // Getter、Setter方法 public String getName() { return name; } public void setName(String name) { this.name = name; } public String getTest() { return test; } public void setTest(String test) { this.test = test; } }
3. Main.java保持原有基础配置
import com.fasterxml.jackson.dataformat.xml.XmlMapper; public class Main { public static void main(String[] args) throws Exception { XmlMapper xmlMapper = new XmlMapper(); Property property = new Property(); property.setName("11&22"); property.setTest("11&22"); String xml = xmlMapper.writeValueAsString(property); System.out.println(xml); } }
附:pom.xml依赖配置
<dependencies> <dependency> <groupId>com.fasterxml.jackson.dataformat</groupId> <artifactId>jackson-dataformat-xml</artifactId> <version>2.13.3</version> </dependency> </dependencies>
注意事项
- 未转义的&会导致生成的XML不符合W3C规范,无法被标准XML解析器正常解析,仅在明确不需要兼容标准XML的场景下使用。
- 方法二的自定义序列化器仅对目标属性生效,元素内的&仍会保持原有输出行为。
内容的提问来源于stack exchange,提问作者micpog90
相关产品推荐
相关产品推荐

