XSLT 3.0迭代包含在XML

时间:2017-10-27 09:23:03

标签: json xslt xslt-3.0

我正在使用XSLT处理各种XML文件。在一个XML中,我找到了一个包装的JSON列表:

<list><![CDATA[[
    {
    "title": "Title 1",
    "value": "Value 1",
    "order": 1
    },
    {
    "title": "Title 2",
    "value": "Value 2",
    "order": 2
    }
]]]>
</list>

我的问题是我需要遍历列表。例如:

<xsl:variable name="listVar">
    <!-- do something with list -->
</xsl:variable>
<xsl:for-each select="$listVar">
    <!-- do something with objects in list e.g. -->
    <xsl:value-of select="title"/>
    <xsl:value-of select="value"/>
</xsl:for-each>

如何使用XSLT执行此操作?我使用的是XSLT 3.0和Saxon引擎,版本9.8 HE。

考虑的解决方案:

1。 使用parse-json功能:     

但是由于XPathException,我不能迭代结果:&#34;子轴的上下文项的必需项类型是node();提供的值(。)具有项类型数组(函数(*))&#34;或者&#34;地图不能被雾化&#34;。我发现有 可能我应该考虑的函数,如map:get,map:entry,但到目前为止,我还没有在我的案例中使用它们。

2。 Addidiotnal变换在上述之前:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
                version="3.0">
    <xsl:output method="xml" encoding="UTF-8" indent="no"/>
    <xsl:template match="@*|node()">
        <xsl:copy>
            <xsl:apply-templates select="@*|node()"/>
        </xsl:copy>
    </xsl:template>
    <xsl:template match="list">
        <list>
            <xsl:copy-of select="json-to-xml(.)"/>
        </list>
    </xsl:template>
</xsl:stylesheet>

然后:

<xsl:variable name="listVar" select="list/array/map"/>

但它不起作用 - 可能是由于添加了命名空间

<list>
    <array xmlns="http://www.w3.org/2005/xpath-functions">
        <map>
...

1 个答案:

答案 0 :(得分:1)

使用parse-json解析时,您的JSON结构为您提供了array maps lookup operator {{3}}的{{3}}处理单个数组项的最简单方法是使用{{ 1}} {{3}},然后您可以使用?*甚至for-each

apply-templates

在哪里访问地图值,您可以再次使用<?xml version="1.0" encoding="UTF-8"?> <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:math="http://www.w3.org/2005/xpath-functions/math" exclude-result-prefixes="xs math" version="3.0"> <xsl:template match="list"> <xsl:apply-templates select="parse-json(.)?*"/> </xsl:template> <xsl:template match=".[. instance of map(xs:string, item())]"> <xsl:value-of select="?title, ?value"/> </xsl:template> </xsl:stylesheet> ,如上所示。

至于使用?foo返回的XML,它返回XPath函数命名空间中的元素以便选择它们,就像命名空间中的任何其他元素一样,您需要确保使用例如命名空间来设置命名空间。 json-to-xml表示要处理该命名空间中元素的部分,或者您可以使用命名空间通配符,例如xpath-default-namespace