XSLT按字母顺序排列XML

时间:2010-04-26 15:58:47

标签: xslt schema

我有大约10个xml模式,我必须通过按字母顺序排列元素/类型来清理。我用谷歌搜索了一段时间,找到了某人的解决方案,

Here

对于我来说无论什么原因都不起作用(它从xsd:schema直接跳到xsd:comlplexType name = Account)。 这是一个简单的例子,因为你可以看到前10个左右的元素是按顺序排列的,但是当开发人员添加了2个新字段时,它们就会出现故障(crossRef和ID)。我想确保CrossRef和ID不仅在定义为Account对象的一部分时按顺序排列,而且,如果它们被单独定义为它们自己的类型(这两个字段不是,但其余的是),他们的定义也将与其他定义按字母顺序排列。

<?xml version="1.0" encoding="utf-8"?><xsd:schema targetNamespace="####" xmlns="####" xmlns:lms.base="####/base" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<xsd:import namespace="###/base" schemaLocation="Base.xsd" />

<xsd:element name="Account" type="Account" />

<xsd:complexType name="Account" >

    <xsd:complexContent >
        <xsd:extension base="lms.base:ExtensionBase">
            <xsd:sequence >
                <xsd:element name="Address" type="lms.base:Address" minOccurs="0" maxOccurs ="unbounded" />       
                <xsd:element name="BusinessSegment" type="lms.base:BusinessSegment" minOccurs ="0" maxOccurs ="1" />
                <xsd:element name="Name" type="AccountName" minOccurs ="0" maxOccurs ="1" />
                <xsd:element name="Number" type="AccountNumber" minOccurs ="0" maxOccurs ="1" />
                <xsd:element name="Office" type="AccountOffice" minOccurs ="0" maxOccurs ="1" />
                <xsd:element name="Status" type="AccountStatus" minOccurs ="0" maxOccurs ="1" />
                <xsd:element name="UWMemo" type="lms.base:UWMemo" minOccurs ="0" maxOccurs ="1" />
      <xsd:element name="CrossRef" type="lms.base:string-minLength" minOccurs="0" maxOccurs="unbounded" />
            </xsd:sequence>
    <xsd:attribute name="ID" type="xsd:long" />
        </xsd:extension>
    </xsd:complexContent>       
</xsd:complexType>

<xsd:simpleType name="AccountID">
    <xsd:restriction base="lms.base:ID" />
</xsd:simpleType>

<xsd:simpleType name="AccountName">
    <xsd:restriction base="lms.base:string-minLength" />
</xsd:simpleType>

<xsd:simpleType name="AccountNumber">
    <xsd:restriction base="lms.base:string-minLength" />
</xsd:simpleType>

<xsd:simpleType name="AccountStatus">
    <xsd:restriction base="lms.base:string-minLength">
        <xsd:enumeration value="Not_Assigned" />
        <xsd:enumeration value="Active" />
        <xsd:enumeration value="Inactive" />
        <xsd:enumeration value="Targeted/Prospect" />
        <xsd:enumeration value="Lost" />
        <xsd:enumeration value="Submission Declined" />
        <xsd:enumeration value="Terminated" />
        <xsd:enumeration value="Claim" />
        <xsd:enumeration value="Watch List" />
        <xsd:enumeration value="H.O. Hold/Suspend" />
        <xsd:enumeration value="Infrequent" />
    </xsd:restriction>
</xsd:simpleType>

<xsd:complexType name="AccountOffice">
    <xsd:complexContent>
        <xsd:extension base="lms.base:Value"/>
    </xsd:complexContent>
</xsd:complexType>

1 个答案:

答案 0 :(得分:3)

您希望按name属性对所有内容进行排序,对吗?在这种情况下,这可能有效:

<xsl:stylesheet version='1.0' xmlns:xsl='http://www.w3.org/1999/XSL/Transform'>

    <!-- Sort child elements by name, if any child has one -->
    <xsl:template match="*[*/@name]">
        <xsl:copy>
            <xsl:copy-of select="@*|text()"/>
            <xsl:apply-templates select="*">
                <xsl:sort select="@name"/>
            </xsl:apply-templates>
        </xsl:copy>
    </xsl:template>

    <!-- Identity template for everything else -->
    <xsl:template match="node()|@*">
        <xsl:copy>
            <xsl:apply-templates select="node()|@*">
        </xsl:copy>
    </xsl:template>

</xsl:stylesheet>