用于从XML文件中提取键值对的命令行工具

时间:2014-01-31 00:58:22

标签: xml unix xml-parsing utilities

我经常需要从XML文件中提取键值对。是否有一个易于使用的UNIX(-style)命令行工具可用于此?

示例案例

XML文件如下所示:

<array>
    <dict>
        <key>BlackPointCompensation</key>
        <false/>
        <key>Name</key>
        <string>Export A</string>
        <key>WatermarkSettings</key>
        <dict>
            <key>DGOperationClassName</key>
            <string>DGImageCompositeScaledOperation</string>
            <key>inputKeys</key>
            <dict>
                <key>inputCompositeImagePath</key>
                <string>/Users/me/imageA.psd</string>
                <key>inputOpacity</key>
                <real>0.94999999999999996</real>
            </dict>
        </dict>
    </dict>
    <dict>
        <key>BlackPointCompensation</key>
        <false/>
        <key>Name</key>
        <string>Export B</string>
        <key>WatermarkSettings</key>
        <dict>
            <key>DGOperationClassName</key>
            <string>DGImageCompositeScaledOperation</string>
            <key>inputKeys</key>
            <dict>
                <key>inputCompositeImagePath</key>
                <string>/Users/me/imageB.psd</string>
                <key>inputOpacity</key>
                <real>0.70</real>
            </dict>
        </dict>
    </dict>
</array>

对于这个文件,我想构造一个命令行命令,其中包含(&#34; key&#34; tag)参数"inputCompositeImagePath",它打印(&#34; string&#34; tag)值{{ 1}}和/Users/me/imageA.psd

什么是这种操作的好工具?我简要介绍了/Users/me/imageB.psd,但它似乎并不适合这个用例。

1 个答案:

答案 0 :(得分:0)

通过另一个stackoverflow答案(Extracting values from XML file...),我来了一个命令行工具xmlstarlet(在xmlstar.sourceforge.net下载,www.geekfarm.org上的教程),它可以做到工作:

比如说,XML文件保存为预设preset-test.xml。然后在你的shell中使用

xml el preset-test.xml

了解XML结构。然后输入

xml sel -t -c "(//string[preceding-sibling::key[1] = 'inputCompositeImagePath'])/text()" preset-test.xml
# (blank line for firefox rendering of stackoverflow code class)

提取想要的信息。它按预期打印:

/Users/me/imageA.psd
/Users/me/imageB.psd

注意:魔术显然在XPath表达式(//string[preceding-sibling::key[1] = 'inputCompositeImagePath'])/text()中。它的工作原理如下:

  1. //string[...]选择名称为string的所有代码,但

  2. preceding-sibling::key[1] = 'inputCompositeImagePath'将此选择限制为第一个前一个兄弟的值为'inputCompositeImagePath'的标签。

  3. /text(),而不是从此选择中选择文字内容。

  4. xmlstarlet工具可能不像我希望的那样容易使用,但由于其完整的XPath功能非常强大。