Python更新XML节点值时如何保留原有XML注释与版本声明?
问题根因
你现在用的Python内置xml.etree.ElementTree(ET模块)默认的解析和写回逻辑,天生就会丢你要的内容:
- 解析XML时会直接跳过所有注释节点,不放进DOM树结构里
- 写回文件时默认不输出
<?xml version="1.0" encoding="UTF-8"?>这类声明 - 写回时会把空节点强制改成
<xxx />的自闭合简写,和你原文件<xxx></xxx>的写法不一样
修正后的可运行代码
不需要改你原来找节点、改值的逻辑,只要换解析器、补全写文件的参数就行:
import xml.etree.ElementTree as ET # 自定义解析器,关闭默认的注释过滤 class KeepCommentParser(ET.XMLParser): def _start_doc(self, *args): super()._start_doc(*args) # 把注释处理逻辑绑定到ET的Comment类,注释会作为正常节点保留 self._parser.CommentHandler = lambda text: ET.Comment(text) # 解析文件时用自定义解析器,别用默认的 tree = ET.parse('test.xml', parser=KeepCommentParser()) root = tree.getroot() # 你原来的修改逻辑原样保留就行 parent = root.find('.//NAME[@property="Name"]') change = parent.find('VALUE[@type="string"]') change.text = 'new value' # 写文件时补全参数,匹配原文件格式 tree.write( "test.xml", encoding="UTF-8", xml_declaration=True, # 强制输出XML版本声明 short_empty_elements=False # 空节点不转成自闭合格式,和原文件写法一致 )
最终效果
- 所有原位置的注释(包括开头的
<!-- Data System -->、每个业务块上方的说明注释)都会原封不动保留,位置和缩进完全和原文件一致 - 输出文件开头会带上和原文件完全一样的XML版本声明
- 空值节点不会被强制改成自闭合的
<VALUE type="None" />,保持原文件的<VALUE type="None"></VALUE>写法 - 只有你要改的那个
VALUE type="string"节点会被改成new value,其他内容完全不动
内容的提问来源于stack exchange,提问作者Cheries
相关产品推荐
相关产品推荐

