将 xml 转换为键值对表示法

2023-12-31

I use xmlstarlet el -v显示 xml 文件的结构,包括所有属性和值。我想将其输出转换为某种键值对,即每个属性及其值位于单独的行上(包括 XPath);每行必须是唯一的。

<?xml version=1.0 encoding=UTF-8?>
<topRoot>
  <topSystem>
    <commSvcEp>
      <commSyslog descr="Syslog Service" name="syslog" policyOwner="local" severity="critical">
        <commSyslogClient adminState="disabled" forwardingFacility="local7" hostname="none" name="secondary" severity="critical"></commSyslogClient>
        <commSyslogClient adminState="disabled" forwardingFacility="local7" hostname="none" name="tertiary" severity="critical"></commSyslogClient>
        <commSyslogClient adminState="disabled" forwardingFacility="local7" hostname="none" name="primary" severity="critical"></commSyslogClient>
      </commSyslog>
    </commSvcEp>
  </topSystem>
</topRoot>

当前结果:

topRoot/topSystem/commSvcEp/commSyslog[@descr='Syslog Service' and @name='syslog' and @policyOwner='local' and @severity='critical']
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[@adminState='disabled' and @forwardingFacility='local7' and @hostname='none' and @name='secondary' and @severity='critical']
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[@adminState='disabled' and @forwardingFacility='local7' and @hostname='none' and @name='tertiary' and @severity='critical']
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[@adminState='disabled' and @forwardingFacility='local7' and @hostname='none' and @name='primary' and @severity='critical']

期望的结果(可能是任何类似的结果;索引只是一个想法):

topRoot/topSystem/commSvcEp/commSyslog@descr='Syslog Service'
topRoot/topSystem/commSvcEp/commSyslog@name='syslog'
topRoot/topSystem/commSvcEp/commSyslog@policyOwner='local'
topRoot/topSystem/commSvcEp/commSyslog@severity='critical'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[0]@adminState='disabled'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[0]@forwardingFacility='local7'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[0]@hostname='none'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[0]@name='secondary'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[0]@severity='critical'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[1]@adminState='disabled'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[1]@forwardingFacility='local7'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[1]@hostname='none'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[1]@name='tertiary'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[1]@severity='critical'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[2]@adminState='disabled'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[2]@forwardingFacility='local7'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[2]@hostname='none'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[2]@name='primary'
topRoot/topSystem/commSvcEp/commSyslog/commSyslogClient[2]@severity='critical'

我想要实现的目标是能够跑步diff超过两个这样的文件或使用grep过滤匹配模式。我确信有一种方法可以创建这样的输出,而不使用sed, awk或除此之外的其他任何东西xmlstarlet itself.

对于 xmlstarlet 和整个 xml 世界,我几乎是一个新手(不仅仅是因为我不喜欢 xml,因为它的复杂性和解析开销等),所以我非常感谢您的帮助。谢谢!


既然你已经在使用xmlstarlet,您也可以使用 XSLT。

XSLT 1.0(可以通过使用 xmlstarlet 来运行tr命令)

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="text"/>
    <xsl:strip-space elements="*"/>

    <xsl:param name="sep" select="'.'"/>

    <xsl:template match="text()"/>

    <xsl:template match="*">
        <xsl:variable name="path">
            <xsl:for-each select="ancestor-or-self::*">
                <xsl:variable name="predicate">
                    <xsl:call-template name="genPredicate"/>
                </xsl:variable>
                <xsl:if test="ancestor::*">
                    <xsl:value-of select="$sep"/>
                </xsl:if>
                <xsl:value-of select="concat(local-name(),$predicate)"/>
            </xsl:for-each>
        </xsl:variable>
        <xsl:for-each select="@*">
            <xsl:value-of select="concat($path,$sep,name(),'=',.)"/>
            <xsl:text>&#xA;</xsl:text>
        </xsl:for-each>
        <xsl:if test="not(@*)">
            <xsl:text>&#xA;</xsl:text>          
        </xsl:if>
        <xsl:apply-templates select="node()"/>
    </xsl:template>

    <xsl:template name="genPredicate">
        <xsl:if test="preceding-sibling::*[local-name()=local-name(current())] or following-sibling::*[local-name()=local-name(current())]">
            <xsl:value-of select="concat('[',count(preceding-sibling::*[local-name()=local-name(current())])+1,']')"/>          
        </xsl:if>
    </xsl:template>

</xsl:stylesheet>

注意:有一个参数名为sep所以你可以从命令行更改分隔符(使用-p sep="/"或任何你想要的分隔符)。当前设置为您首选的“.”。

Output

commSyslog.descr=Syslog Service
commSyslog.name=syslog
commSyslog.policyOwner=local
commSyslog.severity=critical
commSyslog.commSyslogClient[1].adminState=disabled
commSyslog.commSyslogClient[1].forwardingFacility=local7
commSyslog.commSyslogClient[1].hostname=none
commSyslog.commSyslogClient[1].name=secondary
commSyslog.commSyslogClient[1].severity=critical
commSyslog.commSyslogClient[2].adminState=disabled
commSyslog.commSyslogClient[2].forwardingFacility=local7
commSyslog.commSyslogClient[2].hostname=none
commSyslog.commSyslogClient[2].name=tertiary
commSyslog.commSyslogClient[2].severity=critical
commSyslog.commSyslogClient[3].adminState=disabled
commSyslog.commSyslogClient[3].forwardingFacility=local7
commSyslog.commSyslogClient[3].hostname=none
commSyslog.commSyslogClient[3].name=primary
commSyslog.commSyslogClient[3].severity=critical
commSyslog.commSyslogMonitor.adminState=disabled
commSyslog.commSyslogMonitor.descr=
commSyslog.commSyslogMonitor.name=
commSyslog.commSyslogMonitor.severity=critical
commSyslog.commSyslogConsole.adminState=disabled
commSyslog.commSyslogConsole.descr=
commSyslog.commSyslogConsole.name=
commSyslog.commSyslogConsole.severity=critical
commSyslog.commSyslogSource.audits=disabled
commSyslog.commSyslogSource.descr=
commSyslog.commSyslogSource.events=disabled
commSyslog.commSyslogSource.faults=enabled
commSyslog.commSyslogSource.name=
commSyslog.commSyslogFile.adminState=enabled
commSyslog.commSyslogFile.descr=
commSyslog.commSyslogFile.name=messages
commSyslog.commSyslogFile.severity=critical
commSyslog.commSyslogFile.size=4194304
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

将 xml 转换为键值对表示法 的相关文章

随机推荐

  • 在 javascript 中获取推荐 url

    我想看看我从各种 URL 缩短服务 例如 bit ly tinyurl com 但由于它们使用 301 重定向 因此不会出现在我的分析中 如何找出谁在重定向流量 Or 更准确地说 我如何在 javascript 中获取不同类型重定向的推荐
  • std::unique_ptr 如何没有大小开销?

    如果空类的大小不能为 0 那么 std tuple 有何魔力 使得 unique ptr 的 sizeof 在 64 位机器中返回 8 在 unique ptr 中 成员定义为 typedef std tuple
  • 实体框架:在没有导航属性的情况下映射外键?

    动机 我的 EF4 1 DbContext 以错误的顺序保存实体 原因 我的模型缺乏导航属性 我想如何解决它 我想在 DbContext 中设置外键关系 问题是我的实体对象没有导航属性 我使用它来填充 Web 服务 然后将 DTO 对象触发
  • tweepy.errors.Forbidden:403 Forbidden - 使用 Tweepy 的 Twitter API 身份验证问题

    我正在遇到 tweepy errors Forbidden 403 Forbidden When authenticating requests to the Twitter API v2 endpoints you must use ke
  • df.duplicated() 误报?

    我有一个数据框 包含 2 865 044 个条目 具有 3 级多重索引 MultiIndex levels names year country productcode 我正在尝试重塑数据框以生成宽数据框 但出现错误 ReshapeErro
  • Xamarin iOS - 以编程方式加载故事板参考

    我有 2 个故事板 Activities storyboard and Contacts storyboard On Contacts storyboard我有一个视图控制器 ContactDetails On Activities sto
  • CSS 转换未触发

    我正在创建一个 DOM 元素 一个 div 将其添加到 DOM 然后在 javascript 中快速更改其宽度 理论上 这应该会触发 CSS3 转换 但结果是直接从 A 到 B 而没有中间的转换 如果我通过单独的测试单击事件更改宽度 一切都
  • 显示任意大小的位图而不会耗尽内存

    如何在不出现 OOMing 或缩小图像尺寸的情况下显示任意大小的图像 我不想因为缩放和拖动图片而缩小尺寸 如果无法显示任意大小的图像 如何确定要显示的图像的最大可能大小 而不导致 ROOM 位图数据分配在 Native 堆中 而不是 VM
  • react-native-image-picker launchCamera 在 android 中不起作用

    我在用着 react native image picker 3 0 1 在本机反应中捕获图像 但我在 android 9 中打开相机时出错 我收到错误 errorCode others errorMessage This library
  • SQL合并语句

    我正在尝试使用 SQL Server 2008 中新的 MERGE 语句 该语句将从临时表中获取记录 并在其他表中更新相同的记录 该语句如下 create table TempTable ProcPOAmdDel ProcessAmendm
  • Ionic:管理多个 iOS 版本

    我有一个离子应用程序 用于为不同组织构建同一应用程序的多个版本 gulp 脚本为我交换了所有的 asset config xml 这对于 Android 来说效果很好 因为我在签名时将 apk 输出到单独的文件夹中 但我不确定如何在 iOS
  • 为什么枚举常量必须在枚举类型中的任何其他变量和方法声明之前声明?

    如果我在声明枚举常量之前或没有以这种方式声明变量 enum MyEnum int i 90 它显示以下编译错误 MyEnum java 3
  • Android向项目添加外部库

    我有一个项目 我想添加外部库 并将它们与应用程序打包在一起 但我不确定它是否发生 我在这个链接上读到 https developer android com guide appendix faq commontasks html https
  • NSPopUpButton、NSComboBox 类似菜单

    我正在尝试创建一个带有下拉菜单的菜单 每个单元格都有自定义背景 首先 我尝试改编 NSPopUpButton 但我找不到更改单元格背景图像的方法 使用 setImage 会将文本滑动到背景的右侧 接下来我停在 NSComboBox 但我找不
  • 如何将 rune 转换为 unicode-style-string,如 Golang 中的 `\u554a`?

    如果你跑fmt Println u554a 显示 啊 但是如何获取 unicode style string u554a来自符文 啊 package main import fmt import strconv func main quot
  • “MKS 源完整性”有责备/注释吗?

    我正在通过 MKS Source Integrity 专有的 VCS MKS Integrity 的前身 访问 Windows 上控制的一些源代码 如何找出源代码的特定行最后更改的版本 根据 VCS 该功能被称为 责备 或 注释 更新 20
  • 将列值从 VARCHAR(n) 转换为 DECIMAL 时出现问题

    我有一个 SQL Server 2000 数据库 其中有一列类型为 VARCHAR 255 所有数据要么为 NULL 要么为最多两点精度的数字数据 例如 11 85 我尝试运行以下 T SQL 查询 但收到错误 将数据类型 varchar
  • 机器人在网格中移动

    机器人位于 4x4 网格的左上角 机器人可以上下左右移动 但不能两次访问同一地点 机器人正在尝试到达网格的右下角 它可以到达网格右下角的方法有多少种 现在我知道 如果机器人只能向下或向右移动 那么答案将是 8C4 因为它必须以任何顺序向右移
  • bootstrap-vue 改变 的位置

    默认情况下
  • 将 xml 转换为键值对表示法

    I use xmlstarlet el v显示 xml 文件的结构 包括所有属性和值 我想将其输出转换为某种键值对 即每个属性及其值位于单独的行上 包括 XPath 每行必须是唯一的