如何使用Groovy MarkupBuilder生成不带引号的数值属性?
如何用Groovy的MarkupBuilder生成不带引号的属性
默认情况下Groovy的MarkupBuilder会给所有XML属性值添加引号,无论类型。要实现部分属性不带引号,需要借助更灵活的处理方式,以下是可行方案:
方案1:使用StreamingMarkupBuilder(推荐)
StreamingMarkupBuilder允许直接嵌入原始XML片段,能精准控制属性的引号状态:
def writer = new StringWriter() def xml = new groovy.xml.StreamingMarkupBuilder().bind { consolidate( // 直接编写不带引号的属性 'amount=220.36', date: "2023-01-06", invoiceId: "123456XXX", currency: 'EUR' ) } writer << xml println writer.toString()
执行后生成的结果符合预期:
<consolidate amount=220.36 date="2023-01-06" invoiceId="123456XXX" currency="EUR"/>
方案2:自定义MarkupBuilder的属性渲染逻辑
如果坚持使用MarkupBuilder,可以通过继承并重写属性处理方法实现,但相对繁琐:
class CustomMarkupBuilder extends groovy.xml.MarkupBuilder { CustomMarkupBuilder(Writer writer) { super(writer) } @Override protected void printAttributes(Map attrs) { attrs.each { key, value -> writer.write(" $key") if (value != null) { // 指定amount属性不加引号,其他属性保留默认引号逻辑 if (key == 'amount') { writer.write("=$value") } else { writer.write("=\"${encodeAttribute(value.toString())}\"") } } } } } // 使用自定义Builder生成XML def writer = new StringWriter() def xml = new CustomMarkupBuilder(writer) xml.setDoubleQuotes(true) def invoiceId = "123456XXX" def date = "2023-01-06" def amount = 220.36 xml.consolidate( amount: amount.toDouble(), date: date, invoiceId: invoiceId, currency: 'EUR' ) println writer.toString()
⚠️ 注意:XML规范中属性值必须加引号,虽然多数解析器能兼容不带引号的数值,但这种写法不符合标准语法,可能在严格解析场景下出现问题,建议谨慎使用。
内容的提问来源于stack exchange,提问作者laloune
相关产品推荐
相关产品推荐

