XSLT可以进一步改进吗?

时间:2016-08-17 06:05:06

标签: python xml xslt

我有2个XSL:

获取ID

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.1"
                xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
                xmlns:oval="http://oval.mitre.org/XMLSchema/oval-common-5"
                xmlns:oval-res="http://oval.mitre.org/XMLSchema/oval-results-5"
                xmlns:oval-def="http://oval.mitre.org/XMLSchema/oval-definitions-5"
                xmlns:ind-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#independent" 
                xmlns:unix-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#unix"
                xmlns:linux-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#linux"
                exclude-result-prefixes="oval oval-def oval-res ind-def unix-def linux-def">
<xsl:output method="text" encoding="utf-8" />

<xsl:template match="/">
    <xsl:apply-templates/>
</xsl:template>

<xsl:template match="oval-def:definition">
    <xsl:value-of select='@id'/>
    <xsl:text>&#xa;</xsl:text>
</xsl:template>

<!-- include to stop leakage from builtin templates -->
<xsl:template match='node()' mode='engine-results'/>
<xsl:template match="text()"/>

获取标题和结果

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.1"
                xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
                xmlns:oval="http://oval.mitre.org/XMLSchema/oval-common-5"
                xmlns:oval-res="http://oval.mitre.org/XMLSchema/oval-results-5"
                xmlns:oval-def="http://oval.mitre.org/XMLSchema/oval-definitions-5"
                xmlns:ind-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#independent" 
                xmlns:unix-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#unix"
                xmlns:linux-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#linux"
                exclude-result-prefixes="oval oval-def oval-res ind-def unix-def linux-def">
<xsl:output method="text" encoding="utf-8" />

<xsl:template match="/">
    <xsl:apply-templates/>
</xsl:template>

<xsl:template match="oval-def:definition">
    <xsl:if test="@id=$defid">
        <xsl:value-of select='oval-def:metadata/oval-def:title'/>
        <xsl:text>&#xa;</xsl:text>
    </xsl:if>
</xsl:template>

<xsl:template match="oval-res:system/oval-res:definitions/oval-res:definition">
    <xsl:if test="@definition_id=$defid">
        <xsl:value-of select='@result'/>
    </xsl:if>
</xsl:template>

<!-- include to stop leakage from builtin templates -->
<xsl:template match='node()' mode='engine-results'/>
<xsl:template match="text()"/>

</xsl:stylesheet>

一些统计信息 源XML文件大约为50 MB。 源文件中的ID数为2962。 我在Linux上使用xsltproc。

我正在使用python程序首先从源XML获取所有ID。然后,对于每个ID,从源XML收集标题和状态。在具有8 GB RAM的4 CPU盒上进行此转换大约需要2个小时。

我的问题是,我能做些什么来进一步改进XSLT以减少转换时间?

示例源文件

<?xml version="1.0" encoding="UTF-8"?>
<oval_results xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:oval="http://oval.mitre.org/XMLSchema/oval-common-5" xmlns="http://oval.mitre.org/XMLSchema/oval-results-5" xsi:schemaLocation="http://oval.mitre.org/XMLSchema/oval-results-5 oval-results-schema.xsd http://oval.mitre.org/XMLSchema/oval-common-5 oval-common-schema.xsd">
  <generator>
    <oval:product_name>cpe:/a:open-scap:oscap</oval:product_name>
    <oval:product_version>1.2.5</oval:product_version>
    <oval:schema_version>5.10</oval:schema_version>
    <oval:timestamp>2016-08-17T11:43:37</oval:timestamp>
  </generator>
  <directives>
    <definition_true reported="true" content="full"/>
    <definition_false reported="true" content="full"/>
    <definition_unknown reported="true" content="full"/>
    <definition_error reported="true" content="full"/>
    <definition_not_evaluated reported="true" content="full"/>
    <definition_not_applicable reported="true" content="full"/>
  </directives>
  <oval_definitions xmlns:oval="http://oval.mitre.org/XMLSchema/oval-common-5" xmlns:unix-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#unix" xmlns:ind-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#independent" xmlns:lin-def="http://oval.mitre.org/XMLSchema/oval-definitions-5#linux" xmlns="http://oval.mitre.org/XMLSchema/oval-definitions-5" xsi:schemaLocation="http://oval.mitre.org/XMLSchema/oval-definitions-5#unix unix-definitions-schema.xsd http://oval.mitre.org/XMLSchema/oval-definitions-5#independent independent-definitions-schema.xsd http://oval.mitre.org/XMLSchema/oval-definitions-5#linux linux-definitions-schema.xsd http://oval.mitre.org/XMLSchema/oval-definitions-5 oval-definitions-schema.xsd http://oval.mitre.org/XMLSchema/oval-common-5 oval-common-schema.xsd">
    <generator>
      <oval:product_name>Enhanced SCAP Content Editor (eSCAPe)</oval:product_name>
      <oval:product_version>1.2.2</oval:product_version>
      <oval:schema_version>5.10</oval:schema_version>
      <oval:timestamp>2015-09-20T02:13:56</oval:timestamp>
    </generator>
    <definitions>
      <definition id="oval:com.vmware.test.linux:def:3" version="1" class="compliance">
        <metadata>
          <title>Rule 3 - /etc/passwd file is group-owned by root</title>
          <affected family="unix">
            <platform>cpe:/o:sles11:linux</platform>
          </affected>
          <description>This rule verifies that /etc/passwd file is group-owned by root.</description>
        </metadata>
        <criteria comment="None">
          <criterion test_ref="oval:com.vmware.test.linux:tst:3" comment="This rule verifies that /etc/passwd file is group-owned by root."/>
        </criteria>
      </definition>
      <definition id="oval:com.vmware.test.linux:def:2" version="1" class="compliance">
        <metadata>
          <title>Rule 2 - /etc/passwd file is owned by root</title>
          <affected family="unix">
            <platform>cpe:/o:sles11:linux</platform>
          </affected>
          <description>This rule verifies that /etc/passwd file is owned by root.</description>
        </metadata>
        <criteria comment="None">
          <criterion test_ref="oval:com.vmware.test.linux:tst:2" comment="This rule verifies that /etc/passwd file is owned by root."/>
        </criteria>
      </definition>
      <definition id="oval:com.vmware.test.linux:def:1" version="1" class="compliance">
        <metadata>
          <title>Rule 1 - /etc/passwd file has permissions of 644 or more restrictive</title>
          <affected family="unix">
            <platform>cpe:/o:sles11:linux</platform>
          </affected>
          <description>This rule verifies that /etc/passwd file has permissions of 644 or more restrictive.</description>
        </metadata>
        <criteria comment="None">
          <criterion test_ref="oval:com.vmware.test.linux:tst:1" comment="This rule verifies that /etc/passwd file has permissions of 644 or more restrictive."/>
        </criteria>
      </definition>
    </definitions>
    <tests>
      <unix-def:file_test id="oval:com.vmware.test.linux:tst:3" version="1" check="all" comment="Default comment, please change">
        <unix-def:object object_ref="oval:com.vmware.test.linux:obj:1"/>
        <unix-def:state state_ref="oval:com.vmware.test.linux:ste:3"/>
      </unix-def:file_test>
      <unix-def:file_test id="oval:com.vmware.test.linux:tst:2" version="1" check="all" comment="This rule verifies that /etc/passwd file is owned by root.">
        <unix-def:object object_ref="oval:com.vmware.test.linux:obj:1"/>
        <unix-def:state state_ref="oval:com.vmware.test.linux:ste:2"/>
      </unix-def:file_test>
      <unix-def:file_test id="oval:com.vmware.test.linux:tst:1" version="1" check="all" comment="This rule verifies that /etc/passwd file has permissions of 644 or more restrictive.">
        <unix-def:object object_ref="oval:com.vmware.test.linux:obj:1"/>
        <unix-def:state state_ref="oval:com.vmware.test.linux:ste:1"/>
      </unix-def:file_test>
    </tests>
    <objects>
      <unix-def:file_object id="oval:com.vmware.test.linux:obj:1" version="1" comment="/etc/passwd file">
        <unix-def:filepath>/etc/passwd</unix-def:filepath>
      </unix-def:file_object>
    </objects>
    <states>
      <unix-def:file_state id="oval:com.vmware.test.linux:ste:3" version="1" comment="This rule verifies that /etc/passwd file is group-owned by root.">
        <unix-def:group_id datatype="int">0</unix-def:group_id>
      </unix-def:file_state>
      <unix-def:file_state id="oval:com.vmware.test.linux:ste:2" version="1" comment="This rule verifies that /etc/passwd file is owned by root.">
        <unix-def:user_id datatype="int">0</unix-def:user_id>
      </unix-def:file_state>
      <unix-def:file_state id="oval:com.vmware.test.linux:ste:1" version="1" comment="This rule verifies that /etc/passwd file has permissions of 644 or more restrictive.">
        <unix-def:uexec datatype="boolean">false</unix-def:uexec>
        <unix-def:gwrite datatype="boolean">false</unix-def:gwrite>
        <unix-def:gexec datatype="boolean">false</unix-def:gexec>
        <unix-def:owrite datatype="boolean">false</unix-def:owrite>
        <unix-def:oexec datatype="boolean">false</unix-def:oexec>
      </unix-def:file_state>
    </states>
  </oval_definitions>
  <results>
    <system>
      <definitions>
        <definition definition_id="oval:com.vmware.test.linux:def:3" result="true" version="1">
          <criteria operator="AND" result="true">
            <criterion test_ref="oval:com.vmware.test.linux:tst:3" version="1" result="true"/>
          </criteria>
        </definition>
        <definition definition_id="oval:com.vmware.test.linux:def:2" result="true" version="1">
          <criteria operator="AND" result="true">
            <criterion test_ref="oval:com.vmware.test.linux:tst:2" version="1" result="true"/>
          </criteria>
        </definition>
        <definition definition_id="oval:com.vmware.test.linux:def:1" result="true" version="1">
          <criteria operator="AND" result="true">
            <criterion test_ref="oval:com.vmware.test.linux:tst:1" version="1" result="true"/>
          </criteria>
        </definition>
      </definitions>
      <tests>
        <test test_id="oval:com.vmware.test.linux:tst:1" version="1" check="all" result="true">
          <tested_item item_id="1312221" result="true"/>
        </test>
        <test test_id="oval:com.vmware.test.linux:tst:2" version="1" check="all" result="true">
          <tested_item item_id="1312221" result="true"/>
        </test>
        <test test_id="oval:com.vmware.test.linux:tst:3" version="1" check="all" result="true">
          <tested_item item_id="1312221" result="true"/>
        </test>
      </tests>
      <oval_system_characteristics xmlns:oval="http://oval.mitre.org/XMLSchema/oval-common-5" xmlns:unix-sys="http://oval.mitre.org/XMLSchema/oval-system-characteristics-5#unix" xmlns:ind-sys="http://oval.mitre.org/XMLSchema/oval-system-characteristics-5#independent" xmlns:lin-sys="http://oval.mitre.org/XMLSchema/oval-system-characteristics-5#linux" xmlns="http://oval.mitre.org/XMLSchema/oval-system-characteristics-5" xsi:schemaLocation="http://oval.mitre.org/XMLSchema/oval-system-characteristics-5 oval-system-characteristics-schema.xsd http://oval.mitre.org/XMLSchema/oval-system-characteristics-5#independent independent-system-characteristics-schema.xsd http://oval.mitre.org/XMLSchema/oval-system-characteristics-5#unix unix-system-characteristics-schema.xsd http://oval.mitre.org/XMLSchema/oval-system-characteristics-5#linux linux-system-characteristics-schema.xsd http://oval.mitre.org/XMLSchema/oval-common-5 oval-common-schema.xsd">
        <generator>
          <oval:product_name>cpe:/a:open-scap:oscap</oval:product_name>
          <oval:schema_version>5.10</oval:schema_version>
          <oval:timestamp>2016-08-17T11:43:36</oval:timestamp>
        </generator>
        <system_info>
          <os_name>Linux</os_name>
          <os_version>#1 SMP Thu Mar 26 10:55:49 UTC 2015 (0e3c7c8)</os_version>
          <architecture>x86_64</architecture>
          <primary_host_name>vROPS_6-1</primary_host_name>
          <interfaces>
            <interface>
              <interface_name>lo</interface_name>
              <ip_address>127.0.0.1</ip_address>
              <mac_address>00:00:00:00:00:00</mac_address>
            </interface>
            <interface>
              <interface_name>lo</interface_name>
              <ip_address>127.0.0.2</ip_address>
              <mac_address>00:00:00:00:00:00</mac_address>
            </interface>
            <interface>
              <interface_name>eth0</interface_name>
              <ip_address>10.112.56.130</ip_address>
              <mac_address>00:50:56:93:61:59</mac_address>
            </interface>
            <interface>
              <interface_name>lo</interface_name>
              <ip_address>::1</ip_address>
              <mac_address>00:00:00:00:00:00</mac_address>
            </interface>
            <interface>
              <interface_name>eth0</interface_name>
              <ip_address>fe80::250:56ff:fe93:6159</ip_address>
              <mac_address>00:50:56:93:61:59</mac_address>
            </interface>
            <interface>
              <interface_name>sit0</interface_name>
              <ip_address>::10.112.56.130</ip_address>
              <mac_address>00:00:00:00:00:00</mac_address>
            </interface>
            <interface>
              <interface_name>sit0</interface_name>
              <ip_address>::127.0.0.2</ip_address>
              <mac_address>00:00:00:00:00:00</mac_address>
            </interface>
            <interface>
              <interface_name>sit0</interface_name>
              <ip_address>::127.0.0.1</ip_address>
              <mac_address>00:00:00:00:00:00</mac_address>
            </interface>
          </interfaces>
        </system_info>
        <collected_objects>
          <object id="oval:com.vmware.test.linux:obj:1" version="1" flag="complete">
            <reference item_ref="1312221"/>
          </object>
        </collected_objects>
        <system_data>
          <unix-sys:file_item id="1312221" status="exists">
            <unix-sys:filepath>/etc/passwd</unix-sys:filepath>
            <unix-sys:path>/etc</unix-sys:path>
            <unix-sys:filename>passwd</unix-sys:filename>
            <unix-sys:type>regular</unix-sys:type>
            <unix-sys:group_id datatype="int">0</unix-sys:group_id>
            <unix-sys:user_id datatype="int">0</unix-sys:user_id>
            <unix-sys:a_time datatype="int">1471360413</unix-sys:a_time>
            <unix-sys:c_time datatype="int">1471360395</unix-sys:c_time>
            <unix-sys:m_time datatype="int">1463992525</unix-sys:m_time>
            <unix-sys:size datatype="int">1254</unix-sys:size>
            <unix-sys:suid datatype="boolean">false</unix-sys:suid>
            <unix-sys:sgid datatype="boolean">false</unix-sys:sgid>
            <unix-sys:sticky datatype="boolean">false</unix-sys:sticky>
            <unix-sys:uread datatype="boolean">true</unix-sys:uread>
            <unix-sys:uwrite datatype="boolean">true</unix-sys:uwrite>
            <unix-sys:uexec datatype="boolean">false</unix-sys:uexec>
            <unix-sys:gread datatype="boolean">true</unix-sys:gread>
            <unix-sys:gwrite datatype="boolean">false</unix-sys:gwrite>
            <unix-sys:gexec datatype="boolean">false</unix-sys:gexec>
            <unix-sys:oread datatype="boolean">true</unix-sys:oread>
            <unix-sys:owrite datatype="boolean">false</unix-sys:owrite>
            <unix-sys:oexec datatype="boolean">false</unix-sys:oexec>
            <unix-sys:has_extended_acl datatype="boolean">false</unix-sys:has_extended_acl>
          </unix-sys:file_item>
        </system_data>
      </oval_system_characteristics>
    </system>
  </results>
</oval_results>

Python程序的输出

[
    {
        "Status": "true",
        "Title": "Rule 3 - /etc/passwd file is group-owned by root",
        "RuleID": "oval:com.vmware.test.linux:def:3"
    },
    {
        "Status": "true",
        "Title": "Rule 2 - /etc/passwd file is owned by root",
        "RuleID": "oval:com.vmware.test.linux:def:2"
    },
    {
        "Status": "true",
        "Title": "Rule 1 - /etc/passwd file has permissions of 644 or more restrictive",
        "RuleID": "oval:com.vmware.test.linux:def:1"
    }
]

1 个答案:

答案 0 :(得分:1)

这样的事情对你有用吗?

XSLT 1.0

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:oval-res="http://oval.mitre.org/XMLSchema/oval-results-5"
xmlns:oval-def="http://oval.mitre.org/XMLSchema/oval-definitions-5"
exclude-result-prefixes="oval-def oval-res">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>

<xsl:key name="result" match="oval-res:definition" use="@definition_id" />

<xsl:template match="/oval-res:oval_results">
    <output>
        <xsl:for-each select="oval-def:oval_definitions/oval-def:definitions/oval-def:definition">
            <def>
                <RuleID>
                    <xsl:value-of select="@id" />
                </RuleID>       
                <Title>
                    <xsl:value-of select="oval-def:metadata/oval-def:title"/>
                </Title>
                <Status>
                    <xsl:value-of select="key('result', @id)/@result"/>
                </Status>
            </def>
        </xsl:for-each>
    </output>
</xsl:template>

</xsl:stylesheet>

为了便于测试,我将此返回XML结果。应用于您的输入示例,结果将是:

<?xml version="1.0" encoding="UTF-8"?>
<output>
   <def>
      <RuleID>oval:com.vmware.test.linux:def:3</RuleID>
      <Title>Rule 3 - /etc/passwd file is group-owned by root</Title>
      <Status>true</Status>
   </def>
   <def>
      <RuleID>oval:com.vmware.test.linux:def:2</RuleID>
      <Title>Rule 2 - /etc/passwd file is owned by root</Title>
      <Status>true</Status>
   </def>
   <def>
      <RuleID>oval:com.vmware.test.linux:def:1</RuleID>
      <Title>Rule 1 - /etc/passwd file has permissions of 644 or more restrictive</Title>
      <Status>true</Status>
   </def>
</output>