XSLT按属性查询节点

时间:2013-04-10 08:25:28

标签: xslt xml-parsing xslt-1.0

我需要查询一个大的XML文件,以提取只包含属性等于给定参数的所需节点的子XML树。

这是我的源文件

            <a:level1 xmlns:a="some:a" xmlns:b="some:b"
                      xmlns:c="some:c" xmlns:d="some:d">
                <a:level2>
                    <b:level3>
                        <b:date a:value="TODAY">
                            <c:level4>
                                <d:level5>
                                    <d:level6 a:value="AAA">
                                        <d:level7 a:value="AAA_AAA">
                                            <d:level8 a:value="XXX/123">
                                                <d:leaf a:value="150415">
                                                    <b:leaf1>100</b:leaf1>
                                                    <b:leaf2>100</b:leaf2>
                                                </d:leaf>
                                                <d:leaf a:value="200814">
                                                    <b:leaf1>1961</b:leaf1>
                                                    <b:leaf2>1961</b:leaf2>
                                                </d:leaf>
                                            </d:level8>
                                        </d:level7>
                                    </d:level6>
                                    <d:level6 a:value="BBB">
                                        <d:level7 a:value="BBB_BBB">
                                            <d:level8 a:value="XXX/123">
                                                <d:leaf a:value="1505">
                                                    <b:leaf1>0.42</b:leaf1>
                                                    <b:leaf2>0.42</b:leaf2>
                                                </d:leaf>
                                            </d:level8>
                                        </d:level7>
                                    </d:level6>
                                </d:level5>
                            </c:level4>
                        </b:date>
                    </b:level3>
                </a:level2>
            </a:level1>

这是我的样式表:

        <?xml version="1.0" encoding="UTF-8"?>
        <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
            xmlns:xs="http://www.w3.org/2001/XMLSchema"
            xmlns:a="xmlCache">
            <xsl:param name="myparam" as="xs:string" required="no"/>
            <xsl:output method="xml" omit-xml-declaration="yes" indent="yes"/>
            <xsl:strip-space  elements="*"/>

            <xsl:template match="node()|@*" name="identity">
                <xsl:copy>
                    <xsl:apply-templates select="node()|@*"/>
                </xsl:copy>
            </xsl:template>

            <xsl:template match="@*">
                <xsl:message><xsl:value-of select="@a:value"/></xsl:message>
                <xsl:if test="@a:value=$myparam">
                    <xsl:call-template name="identity"/>
                </xsl:if>
            </xsl:template>
        </xsl:stylesheet>

但似乎没有用。有人可以帮忙吗?

更新:抱歉没有明确问题。我想提取整个子集XML树。例如,如果参数是AAA,则输出为:

            <a:level1 xmlns:a="some:a" xmlns:b="some:b"
                      xmlns:c="some:c" xmlns:d="some:d">
                <a:level2>
                    <b:level3>
                        <b:date a:value="TODAY">
                            <c:level4>
                                <d:level5>
                                    <d:level6 a:value="AAA">
                                        <d:level7 a:value="AAA_AAA">
                                            <d:level8 a:value="XXX/123">
                                                <d:leaf a:value="150415">
                                                    <b:leaf1>100</b:leaf1>
                                                    <b:leaf2>100</b:leaf2>
                                                </d:leaf>
                                                <d:leaf a:value="200814">
                                                    <b:leaf1>1961</b:leaf1>
                                                    <b:leaf2>1961</b:leaf2>
                                                </d:leaf>
                                            </d:level8>
                                        </d:level7>
                                    </d:level6>
                                </d:level5>
                            </c:level4>
                        </b:date>
                    </b:level3>
                </a:level2>
            </a:level1>

1 个答案:

答案 0 :(得分:0)

通过猜测以下内容,您可以找到更多内容。

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    xmlns:a="xmlCache">
    <xsl:param name="myparam"/>
    <xsl:output method="xml" omit-xml-declaration="yes" indent="yes"/>
    <xsl:strip-space  elements="*"/>

    <xsl:template match="node()|@*" mode ="copy" >
        <xsl:copy>
            <xsl:apply-templates select="node()|@*" mode="copy"/>
        </xsl:copy>
    </xsl:template>

<xsl:template match ="node()|@*">
    <xsl:choose>
        <xsl:when test="@*[name()='a:value']=$myparam">
            <xsl:copy>
                <xsl:apply-templates select="@*|*" mode="copy"/>
            </xsl:copy>
        </xsl:when>
        <xsl:when test="descendant::*/@*[name()='a:value']=$myparam">
            <xsl:copy>
                <xsl:apply-templates select="@*" mode="copy"/>
                <xsl:apply-templates select="*" />
            </xsl:copy>
        </xsl:when>
        <xsl:otherwise>
            <xsl:apply-templates />
        </xsl:otherwise>
    </xsl:choose>
</xsl:template>

</xsl:stylesheet>

e.g称为whith xsltproc和param myparam

  xsltproc  --stringparam myparam BBB in.xsl in.xml

它产生的输出为(有希望的)预期。

<a:level1 xmlns:a="some:a" xmlns:b="some:b" xmlns:c="some:c" xmlns:d="some:d">
  <a:level2>
    <b:level3>
      <b:date a:value="TODAY">
        <c:level4>
          <d:level5>
            <d:level6 a:value="BBB">
              <d:level7 a:value="BBB_BBB">
                <d:level8 a:value="XXX/123">
                  <d:leaf a:value="1505">
                    <b:leaf1>0.42</b:leaf1>
                    <b:leaf2>0.42</b:leaf2>
                  </d:leaf>
                </d:level8>
              </d:level7>
            </d:level6>
          </d:level5>
        </c:level4>
      </b:date>
    </b:level3>
  </a:level2>
</a:level1>