xml - xmlstarlet 默认命名空间
问题描述
我想使用 xmlstarlet 将第三方 xml 文件转换为 csv 文件。一些文件使用带有 xmlns 声明的默认命名空间,其他文件使用没有 xmlns 声明的默认命名空间,而其他文件在最精确的解释中使用严格的默认命名空间。
这是一些较小的文件,应该可以澄清我的问题。
foo1.xml
<?xml version="1.0"?>
<root xmlns="http://my.namespace" xmlns:fooNS="http://foo.namespace" xmlns:barNS="http://bar.namespace">
<fooNS:foo id="1">FOO 1</fooNS:foo>
<fooNS:foo id="2">FOO 2</fooNS:foo>
<barNS:bar ref="2" unitRef="Unit1">2000</barNS:bar>
<unit id="Unit1">
<measure>bars</measure>
</unit>
</root>
foo2.xml:
<?xml version="1.0"?>
<root xmlns:fooNS="http://foo.namesapece" xmlns:barNS="http://bar.namespace">
<fooNS:foo id="1">FOO 1</fooNS:foo>
<fooNS:foo id="2">FOO 2</fooNS:foo>
<barNS:bar ref="2" unitRef="Unit1">2000</barNS:bar>
<unit id="Unit1">
<measure>bars</measure>
</unit>
</root>
foo3.xml
<?xml version="1.0"?>
<myNS:root xmlns:myNS="http://my.namespace" xmlns:fooNS="http://foo.namesapece" xmlns:barNS="http://bar.namespace">
<fooNS:foo id="1">FOO 1</fooNS:foo>
<fooNS:foo id="2">FOO 2</fooNS:foo>
<barNS:bar ref="2" unitRef="Unit1">2000</barNS:bar>
<unit id="Unit1">
<measure>bars</measure>
</unit>
</myNS:root>
现在我想要一个文件"FOO 2 | 2000 | bars"
作为输出。属性“unitRef”在 xsd 中定义为 IDREF。
此命令适用于foo1.xml(但不适用于 foo2.xml 和 foo3.xml):
$> xmlstarlet sel -N xbrli="http://my.namespace" \
-t -m "//fooNS:foo[../barNS:bar/@ref = @id]"
-v . -o " | " \
-v "../barNS:bar[@ref=current()/@id]" -o " | " \
-v \
"//xbrli:unit[@id=current()/../barNS:bar[@ref=current()/@id]/@unitRef]/xbrli:measure" \
-n foo1.xml
此命令适用于foo2.xml 和 foo3.xml(但不适用于 foo1.xml):
$> xmlstarlet sel -N xmlns="http://my.namespace" \
-t -m "//fooNS:foo[../barNS:bar/@ref = @id]" \
-v . -o " | " \
-v "../barNS:bar[@ref=current()/@id]" -o " | " \
-v \
"//unit[@id=current()/../barNS:bar[@ref=current()/@id]/@unitRef]/measure" \
-n foo[23].xml
问题:是否有适用于所有三个第三方文件的语法?如果不使用 xmlstarlet,那么也许使用 xslt 文件?或者也许可以处理所有 xml 文件(使用 xmlstarlet 或 xslt),以便它们的行为相似?
谢谢。
解决方案
因为没有人提供更好的解决方案,所以我使用了#kjhughes 提出的解决方案。
所以(不推荐)答案:-v "// [local-name()='unit'][@id=current()/../barNS:bar[@ref=current()/@id]/ @unitRef]/ [local-name()='measure']"
另请参阅“ XPath 如何处理 XML 名称空间? ”以获得所有推荐解决方案的描述。但它们都不适用于我的所有情况。
推荐阅读
- vim - 如何在 vimscript 中插入文本
- javascript - Scrapy 飞溅响应不会返回完整的 html
- javascript - 如何制作一个 chrome 扩展程序,它将获取当前网页并通过 FTP 将其上传到我的自定义域,以便我可以在手机上查看它?
- vue.js - vue js和laravel护照中的权限用户
- javascript - CSS 和 Javascript 未加载
- mongodb - Spring data MongoDB匹配,查找和投影以从查找的文档中仅选择必填字段
- java - 列表视图中的 getItemIdAtPosition() 未显示
- javascript - 将模块范围的变量导入另一个模块
- javascript - 如何通过 UDP 发送图像(或其他大文件)
- dhcp - 无法通过 TFTP 的 python 脚本在路由器上执行配置