你们如何在某些标签后向一堆 XML 文件添加一行?解决方案可以基于 unix 工具的使用,或者命名一个可以让我快速轻松地完成此操作的文本编辑器或实用程序。我有 60 多个文件需要编辑。
例如我有以下 XML:
<Node disablePersistence="true">
<Name>Mapper</Name>
<Action>
<Class-Name>com.test.component.Mapper</Class-Name>
<Param name="output_url" value="constant:file:///output.xml"/>
<Param name="xml_url" value="constant:file:///input.xml"/>
<Param name="xsl_url" value="constant:file:///template.xsl"/>
</Action>
<Next-Node>ComposeMessage</Next-Node>
</Node>
首先,我需要搜索标签 Node。然后,我需要搜索标签 Name = Mapper。然后搜索标签 Action。然后搜索标签 Param。在所有 Param 标签所在的位置,我们需要插入新行:
<Param name="new_parameter" value="constant:true"/>
这可能吗?或者要求太多,手动编辑所有文件会更快吗?
答案1
这是使用xmlstarlet
XPath 的解决方案。我扩展了 XML 以证明我们可以挑选出特定节点:
解决方案
xmlstarlet edit \
--subnode '//Node[Name/text()="Mapper"]/Action' --type elem --name 'Param' \
--var nap '$prev' \
--insert '$nap' --type attr --name 'name' --value 'new_parameter' \
--insert '$nap' --type attr --name 'constant:true'
我们创建一个新的子节点,Node/Action
其中还有一个Name
具有文本值的元素Mapper
。我们将这个新节点分配给 XPath 变量,nap
以便我们可以轻松引用它。最后,我们向其中插入两个属性。
示例 XML
<root>
<Node disablePersistence="true">
<Name>Mapper</Name>
<Action>
<Class-Name>com.test.component.Mapper</Class-Name>
<Param name="output_url" value="constant:file:///output.xml"/>
<Param name="xml_url" value="constant:file:///input.xml"/>
<Param name="xsl_url" value="constant:file:///template.xsl"/>
</Action>
<Next-Node>ComposeMessage</Next-Node>
</Node>
<Node disablePersistence="true">
<Name>DoNotTouchMe</Name>
<Action>
<Class-Name>com.test.component.Mapper</Class-Name>
<Param name="output_url" value="constant:file:///output.xml"/>
<Param name="xml_url" value="constant:file:///input.xml"/>
<Param name="xsl_url" value="constant:file:///template.xsl"/>
</Action>
<Next-Node>ComposeMessage</Next-Node>
</Node>
</root>
结果
<root>
<Node disablePersistence="true">
<Name>Mapper</Name>
<Action>
<Class-Name>com.test.component.Mapper</Class-Name>
<Param name="output_url" value="constant:file:///output.xml"/>
<Param name="xml_url" value="constant:file:///input.xml"/>
<Param name="xsl_url" value="constant:file:///template.xsl"/>
<Param name="new_parameter" constant:true=""/>
</Action>
<Next-Node>ComposeMessage</Next-Node>
</Node>
<Node disablePersistence="true">
<Name>DoNotTouchMe</Name>
<Action>
<Class-Name>com.test.component.Mapper</Class-Name>
<Param name="output_url" value="constant:file:///output.xml"/>
<Param name="xml_url" value="constant:file:///input.xml"/>
<Param name="xsl_url" value="constant:file:///template.xsl"/>
</Action>
<Next-Node>ComposeMessage</Next-Node>
</Node>
</root>